Browse Source

添加多边形

liwei 1 year ago
parent
commit
b4322c1e18

+ 169 - 0
src/modules/editor/components/CompUI/basicUI/Polygon/component.tsx

@@ -0,0 +1,169 @@
+import { defineComponent, onMounted , ref, effect} from "vue";
+import { string } from "vue-types";
+import { useCompData } from ".";
+import { useEditor } from "../../../..";
+import { View } from "../View";
+import { CompUI } from "../..";
+import { values } from "lodash";
+
+export const Component = defineComponent({
+  props: {
+    compId: string().isRequired,
+  },
+  setup(props) {
+    const { helper, controls , store} = useEditor();
+    const data = useCompData(props.compId);
+    const canvasRef =  ref<HTMLCanvasElement>();
+
+  
+
+    onMounted(()=>{
+        
+        // draw();
+        let isDragingIndex = -1;
+
+        canvasRef.value?.addEventListener("dblclick", function(e:MouseEvent){
+            
+            const x = helper.pxToDesignSize(e.offsetX )
+            const y = helper.pxToDesignSize(e.offsetY)
+            console.log("dbclick=>xxxxx", x, y);
+
+            //判断直线相交求解点到直线的距离
+            
+            //判断是否
+
+        })
+
+        canvasRef.value?.addEventListener("mousedown", function(e:MouseEvent){
+                if (store.currCompId != props.compId) return;
+
+                const el = canvasRef.value as HTMLCanvasElement;
+                const x = helper.pxToDesignSize(e.offsetX )
+                const y = helper.pxToDesignSize(e.offsetY)
+                
+                console.log(x , y);
+
+                const points = data.value.points as number[][];
+                const width = data.layout.size[0];
+                const height = data.layout.size[1];
+
+                let n = points.length;
+                isDragingIndex = -1;
+                let initX = 0;
+                let initY = 0;
+
+                while(n--) {
+                    const p = points[n];
+
+                    const px = width * p[0];
+                    const py = height * p[1];
+                    
+                    if(!(x < (px -10) || x > (px + 10) || y < (py -10) || y > (py+10) ) ) {
+                        isDragingIndex = n;
+                        initX = p[0]
+                        initY = p[1]
+                        break;
+                    }
+
+                }
+                
+                const dragingX = x;
+                const dragingY = y;
+
+                if (isDragingIndex != -1) {
+                    e.preventDefault();
+                    e.stopPropagation();
+
+                    const move =  function (e:MouseEvent){
+                        if ( isDragingIndex == -1) return;
+                         
+                        const offx = (helper.pxToDesignSize(e.offsetX ) - dragingX) / width;
+                        const offy = (helper.pxToDesignSize(e.offsetY ) -  dragingY) / height;
+
+                        points[isDragingIndex][0] = initX + offx;
+                        points[isDragingIndex][1] = initY + offy;
+
+                        draw();
+                    }
+
+                    el.addEventListener("mousemove", move)
+
+                    el.addEventListener("mouseup", function(e:MouseEvent){
+                        el.removeEventListener("mousemove", move);
+                    });
+
+                    el.addEventListener("mouseleave", function(e:MouseEvent){
+                        el.removeEventListener("mousemove", move);
+                    })
+
+
+                }
+        }, )
+
+       
+        effect(draw);
+    })
+
+    
+
+   
+    function draw() {
+        const canvas = canvasRef.value as HTMLCanvasElement;
+        if (!canvas) return;
+
+        const ctx = canvasRef.value?.getContext("2d") as CanvasRenderingContext2D;
+
+        const width = data.layout.size[0];
+        const height = data.layout.size[1];
+        canvas.width = Math.ceil(Math.max(1, width));
+        canvas.height = Math.ceil(Math.max(1, height));
+        ctx.clearRect(0, 0, canvas.width, canvas.height);
+        ctx.lineWidth = data.value.lineWidth;
+        
+    
+        ctx.strokeStyle = data.value.lineColor;
+    
+        const padding = 0.2;
+
+        ctx.lineJoin = "round";
+        ctx.beginPath();
+       
+
+        let points = data.value.points as number[][];
+        if (data.value.points.length == 0) {
+            data.value.points = [[padding, padding], [1 - padding, padding], [1 - padding, 1 - padding] , [padding, 1 - padding]];
+            points = data.value.points;
+        }
+
+        points.forEach((p, index)=>{
+            const x = width * p[0];
+            const y = height * p[1];
+            index == 0 ?  ctx.moveTo(x, y) :  ctx.lineTo(x, y);
+            if (store.isEditMode) {
+                ctx.fillStyle = "red"
+                ctx.fillRect(x-10, y-10, 20, 20);
+            }
+        })
+
+        if (data.value.isClose) {
+            ctx.closePath();
+        }
+        if (data.value.lineWidth !== 0) {
+            ctx.stroke();
+        }
+
+        if (data.value.isFill)    {
+            let bColor = data.value.fillColor;
+            if (!bColor) bColor = data.value.lineColor;
+            ctx.fillStyle = bColor;
+            ctx.fill();
+        }
+    }
+
+    return () => (
+      <View compId={props.compId}>
+         <canvas ref={canvasRef} style={{width:"100%", height: "100%"}}> </canvas>
+      </View>
+    );
+  },
+});

+ 61 - 0
src/modules/editor/components/CompUI/basicUI/Polygon/index.ts

@@ -0,0 +1,61 @@
+import { Dict_Imgs } from "@/dict";
+import { createAttrsForm } from "../../defines/createAttrsForm";
+import { createCompHooks } from "../../defines/createCompHooks";
+import { InputNumber, Switch } from "ant-design-vue";
+import { createColorOpts } from "../../defines/formOpts/createColorOpts";
+
+export { Component } from "./component";
+
+export const options = {
+  name: "多边形",
+  thumbnail: require("@/modules/editor/assets/icons/image.svg"),
+};
+
+export const { createComp, useCompData } = createCompHooks({
+  value: {
+    lineColor: "black",
+    lineWidth: 1,
+    isFill: false,
+    fillColor: "black",
+    points: [],
+    isClose: true,
+    isCurve: false,
+  },
+  layout: {
+    size: [750, 750],
+  },
+});
+
+export const Form = createAttrsForm([
+  {
+    label: "线宽",
+    dataIndex: "value.lineWidth",
+    component: InputNumber,
+  },
+  {
+    label:"颜色",
+    dataIndex: "value.lineColor",
+    ...createColorOpts(),
+  },
+  {
+    label: "是否填充",
+    dataIndex: "value.isFill",
+    component: "Switch",
+  },
+  {
+    label:"填充颜色",
+    dataIndex: "value.fillColor",
+    ...createColorOpts(),
+    isVisible: (value, data) => data?.value?.isFill == true,
+  },
+  {
+    label: "是否封闭",
+    dataIndex: "value.isClose",
+    component: "Switch",
+  },
+  {
+    label: "是否支持曲线",
+    dataIndex: "value.isCurve",
+    component: "Switch",
+  }
+]);

+ 2 - 1
src/modules/editor/components/CompUI/basicUI/index.ts

@@ -10,4 +10,5 @@ export * as Line from "./Line";
 export * as Arc from "./Arc";
 export * as Ellipse from "./Ellipse";
 export * as Triangle from "./Triangle";
-export * as QuadraticCurve from "./QuadraticCurve";
+export * as QuadraticCurve from "./QuadraticCurve";
+export * as Polygon from "./Polygon";

+ 1 - 1
src/modules/editor/components/Viewport/Slider/SliderLeft/BaseComp.tsx

@@ -13,7 +13,7 @@ export default defineComponent({
 
     const state = useReactive(() => ({
       basicComps() {
-        return ["Text", "Image", "Video", "Web3D", "Rectage", "Line", "Arc", "Ellipse", "Triangle", "QuadraticCurve"].map(
+        return ["Text", "Image", "Video", "Web3D", "Rectage", "Line", "Arc", "Ellipse", "Triangle", "QuadraticCurve", "Polygon"].map(
           (key) => compUICtrl.state.components.get(key) as any
         );
       },

+ 3 - 2
src/modules/editor/module/actions/edit.ts

@@ -51,8 +51,9 @@ export const editActions = EditorModule.action({
       compKey != "Arc" && 
       compKey != "Triangle" &&
       compKey != "Ellipse" && 
-      compKey != "QuadraticCurve" 
-      
+      compKey != "QuadraticCurve" &&
+      compKey != "Polygon"
+
     let yOffset = 0;
     if (
       this.store.currCompId != this.store.currStreamCardId &&