diff --git a/README.md b/README.md
index ff6acbe7..4fe917f2 100644
--- a/README.md
+++ b/README.md
@@ -70,6 +70,7 @@ npm run serve
- 边框
- 阴影
- 透明度
+- 翻转
### 线条
- 颜色
- 宽度
diff --git a/src/types/slides.ts b/src/types/slides.ts
index 78209721..0542b16f 100644
--- a/src/types/slides.ts
+++ b/src/types/slides.ts
@@ -41,6 +41,10 @@ export interface PPTTextElement {
shadow?: PPTElementShadow;
}
+export interface ImageOrShapeFlip {
+ x?: number;
+ y?: number;
+}
export interface ImageElementFilters {
'blur'?: string;
'brightness'?: string;
@@ -68,7 +72,7 @@ export interface PPTImageElement {
range: [[number, number], [number, number]];
shape: 'rect' | 'roundRect' | 'ellipse' | 'triangle' | 'pentagon' | 'rhombus' | 'star';
};
- flip?: { x?: number; y?: number };
+ flip?: ImageOrShapeFlip;
shadow?: PPTElementShadow;
}
@@ -94,6 +98,7 @@ export interface PPTShapeElement {
rotate?: number;
outline?: PPTElementOutline;
opacity?: number;
+ flip?: ImageOrShapeFlip;
shadow?: PPTElementShadow;
}
diff --git a/src/views/Editor/Toolbar/ElementStylePanel/ImageStylePanel.vue b/src/views/Editor/Toolbar/ElementStylePanel/ImageStylePanel.vue
index 490fe81b..a174cf9a 100644
--- a/src/views/Editor/Toolbar/ElementStylePanel/ImageStylePanel.vue
+++ b/src/views/Editor/Toolbar/ElementStylePanel/ImageStylePanel.vue
@@ -58,20 +58,8 @@
-
-
- 水平翻转
- 垂直翻转
-
-
+
+
@@ -96,6 +84,7 @@ import useHistorySnapshot from '@/hooks/useHistorySnapshot'
import ElementOutline from '../common/ElementOutline.vue'
import ElementShadow from '../common/ElementShadow.vue'
+import ElementFlip from '../common/ElementFlip.vue'
interface FilterOption {
label: string;
@@ -156,6 +145,7 @@ export default defineComponent({
components: {
ElementOutline,
ElementShadow,
+ ElementFlip,
},
setup() {
const store = useStore()
@@ -164,24 +154,11 @@ export default defineComponent({
const clipPanelVisible = ref(false)
- const flip = ref({
- x: 0,
- y: 0,
- })
-
const filterOptions = ref(JSON.parse(JSON.stringify(defaultFilters)))
watch(handleElement, () => {
if (!handleElement.value || handleElement.value.type !== 'image') return
-
- if (handleElement.value.flip) {
- flip.value = {
- x: handleElement.value.flip.x || 0,
- y: handleElement.value.flip.y || 0,
- }
- }
- else flip.value = { x: 0, y: 0 }
-
+
const filters = handleElement.value.filters
if (filters) {
filterOptions.value = defaultFilters.map(item => {
@@ -194,11 +171,6 @@ export default defineComponent({
const { addHistorySnapshot } = useHistorySnapshot()
- const updateImage = (props: Partial) => {
- store.commit(MutationTypes.UPDATE_ELEMENT, { id: handleElement.value.id, props })
- addHistorySnapshot()
- }
-
const updateFilter = (filter: FilterOption, value: number) => {
const originFilters = handleElement.value.filters || {}
const filters = { ...originFilters, [filter.key]: `${value}${filter.unit}` }
@@ -337,9 +309,7 @@ export default defineComponent({
shapeClipPathOptions,
ratioClipOptions,
filterOptions,
- flip,
handleElement,
- updateImage,
updateFilter,
clipImage,
presetImageClip,
diff --git a/src/views/Editor/Toolbar/ElementStylePanel/ShapeStylePanel.vue b/src/views/Editor/Toolbar/ElementStylePanel/ShapeStylePanel.vue
index 5098a6e7..8c6e2068 100644
--- a/src/views/Editor/Toolbar/ElementStylePanel/ShapeStylePanel.vue
+++ b/src/views/Editor/Toolbar/ElementStylePanel/ShapeStylePanel.vue
@@ -68,6 +68,7 @@
+
@@ -86,6 +87,7 @@ import useHistorySnapshot from '@/hooks/useHistorySnapshot'
import ElementOpacity from '../common/ElementOpacity.vue'
import ElementOutline from '../common/ElementOutline.vue'
import ElementShadow from '../common/ElementShadow.vue'
+import ElementFlip from '../common/ElementFlip.vue'
import ColorButton from '../common/ColorButton.vue'
export default defineComponent({
@@ -94,6 +96,7 @@ export default defineComponent({
ElementOpacity,
ElementOutline,
ElementShadow,
+ ElementFlip,
ColorButton,
},
setup() {
diff --git a/src/views/Editor/Toolbar/common/ElementFlip.vue b/src/views/Editor/Toolbar/common/ElementFlip.vue
new file mode 100644
index 00000000..12c71d31
--- /dev/null
+++ b/src/views/Editor/Toolbar/common/ElementFlip.vue
@@ -0,0 +1,70 @@
+
+
+
+ 水平翻转
+ 垂直翻转
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/src/views/components/element/ImageElement/BaseImageElement.vue b/src/views/components/element/ImageElement/BaseImageElement.vue
index 9392fe69..70b0b108 100644
--- a/src/views/components/element/ImageElement/BaseImageElement.vue
+++ b/src/views/components/element/ImageElement/BaseImageElement.vue
@@ -13,7 +13,7 @@
class="element-content"
:style="{
filter: shadowStyle ? `drop-shadow(${shadowStyle})` : '',
- transform: flip,
+ transform: flipStyle,
}"
>
{
- if (!props.elementInfo.flip) return ''
- const { x, y } = props.elementInfo.flip
- if (x && y) return `rotateX(${x}deg) rotateY(${y}deg)`
- else if (x) return `rotateX(${x}deg)`
- else if (y) return `rotateY(${y}deg)`
- return ''
- })
-
const shadow = computed(() => props.elementInfo.shadow)
const { shadowStyle } = useElementShadow(shadow)
+ const flip = computed(() => props.elementInfo.flip)
+ const { flipStyle } = useElementFlip(flip)
+
return {
imgPosition,
clipShape,
filter,
- flip,
+ flipStyle,
shadowStyle,
}
},
diff --git a/src/views/components/element/ImageElement/index.vue b/src/views/components/element/ImageElement/index.vue
index cd0eb6f3..fb8eb984 100644
--- a/src/views/components/element/ImageElement/index.vue
+++ b/src/views/components/element/ImageElement/index.vue
@@ -28,7 +28,7 @@
v-contextmenu="contextmenus"
:style="{
filter: shadowStyle ? `drop-shadow(${shadowStyle})` : '',
- transform: flip,
+ transform: flipStyle,
}"
>
props.elementInfo.shadow)
const { shadowStyle } = useElementShadow(shadow)
+ const flip = computed(() => props.elementInfo.flip)
+ const { flipStyle } = useElementFlip(flip)
+
const handleSelectElement = (e: MouseEvent) => {
if (props.elementInfo.lock) return
e.stopPropagation()
@@ -159,15 +163,6 @@ export default defineComponent({
return filter
})
- const flip = computed(() => {
- if (!props.elementInfo.flip) return ''
- const { x, y } = props.elementInfo.flip
- if (x && y) return `rotateX(${x}deg) rotateY(${y}deg)`
- else if (x) return `rotateX(${x}deg)`
- else if (y) return `rotateY(${y}deg)`
- return ''
- })
-
const clip = (data: ImageClipedEmitData) => {
store.commit(MutationTypes.SET_CLIPING_IMAGE_ELEMENT_ID, '')
@@ -195,7 +190,7 @@ export default defineComponent({
clipShape,
imgPosition,
filter,
- flip,
+ flipStyle,
}
},
})
diff --git a/src/views/components/element/ShapeElement/BaseShapeElement.vue b/src/views/components/element/ShapeElement/BaseShapeElement.vue
index 0ffcca93..f6fb3c31 100644
--- a/src/views/components/element/ShapeElement/BaseShapeElement.vue
+++ b/src/views/components/element/ShapeElement/BaseShapeElement.vue
@@ -14,6 +14,7 @@
:style="{
opacity: elementInfo.opacity,
filter: shadowStyle ? `drop-shadow(${shadowStyle})` : '',
+ transform: flipStyle,
}"
>
props.elementInfo.shadow)
const { shadowStyle } = useElementShadow(shadow)
+ const flip = computed(() => props.elementInfo.flip)
+ const { flipStyle } = useElementFlip(flip)
+
return {
shadowStyle,
outlineWidth,
outlineStyle,
outlineColor,
+ flipStyle,
}
},
})
diff --git a/src/views/components/element/ShapeElement/index.vue b/src/views/components/element/ShapeElement/index.vue
index 9258bb2d..72c64a8f 100644
--- a/src/views/components/element/ShapeElement/index.vue
+++ b/src/views/components/element/ShapeElement/index.vue
@@ -17,6 +17,7 @@
:style="{
opacity: elementInfo.opacity,
filter: shadowStyle ? `drop-shadow(${shadowStyle})` : '',
+ transform: flipStyle,
}"
>
props.elementInfo.shadow)
const { shadowStyle } = useElementShadow(shadow)
+ const flip = computed(() => props.elementInfo.flip)
+ const { flipStyle } = useElementFlip(flip)
+
return {
handleSelectElement,
shadowStyle,
outlineWidth,
outlineStyle,
outlineColor,
+ flipStyle,
}
},
})
diff --git a/src/views/components/element/hooks/useElementFlip.ts b/src/views/components/element/hooks/useElementFlip.ts
new file mode 100644
index 00000000..0e9826bc
--- /dev/null
+++ b/src/views/components/element/hooks/useElementFlip.ts
@@ -0,0 +1,21 @@
+import { ref, Ref, watchEffect } from 'vue'
+import { ImageOrShapeFlip } from '@/types/slides'
+
+export default (flip: Ref) => {
+ const flipStyle = ref('')
+
+ watchEffect(() => {
+ if (flip.value) {
+ const { x, y } = flip.value
+ if (x && y) flipStyle.value = `rotateX(${x}deg) rotateY(${y}deg)`
+ else if (x) flipStyle.value = `rotateX(${x}deg)`
+ else if (y) flipStyle.value = `rotateY(${y}deg)`
+ else flipStyle.value = ''
+ }
+ else flipStyle.value = ''
+ })
+
+ return {
+ flipStyle,
+ }
+}
\ No newline at end of file