Bläddra i källkod

侧边元素编辑调整

zhangjie 2 år sedan
förälder
incheckning
9dbb0faac1

+ 2 - 2
src/modules/card/elements/gutter/model.js

@@ -4,8 +4,8 @@ const MODEL = {
   type: "GUTTER",
   x: 0,
   y: 0,
-  w: 0,
-  h: 0,
+  w: 40,
+  h: 600,
   content: "装订线",
   direction: "left",
 };

+ 16 - 1
src/modules/card/elements/text/ElemText.vue

@@ -1,5 +1,5 @@
 <template>
-  <div class="elem-text">
+  <div class="elem-text" :style="elemStyles">
     <div class="text-body" :style="styles">
       <span
         v-for="(cont, index) in data.content"
@@ -34,6 +34,21 @@ export default {
         color: this.data.color,
       };
     },
+    elemStyles() {
+      if (this.data.mode === "side") {
+        return {
+          position: "absolute",
+          width: this.data.h + "px",
+          height: this.data.w + "px",
+          transform: "rotate(-90deg)",
+          "transform-origin": "0 100%",
+          bottom: 0,
+          left: this.data.w + "px",
+        };
+      } else {
+        return null;
+      }
+    },
   },
   methods: {},
 };

+ 1 - 0
src/modules/card/elements/text/model.js

@@ -11,6 +11,7 @@ const MODEL = {
   fontFamily: "宋体",
   fontSize: "14px",
   color: "#000",
+  mode: "normal", // side:侧边模式,normal:正常模式
   content: [
     {
       type: "text",

+ 5 - 9
src/modules/paper-export/assets/styles/paper-temp-preview.scss

@@ -63,15 +63,11 @@
       position: absolute;
     }
 
-    .elem-text {
-      writing-mode: vertical-rl;
-      transform: rotate(180deg);
-      text-orientation: sideways;
-      height: 100%;
-    }
-
-    // .element-item-gutter {
-    //   height: 100% !important;
+    // .elem-text {
+    //   writing-mode: vertical-rl;
+    //   transform: rotate(180deg);
+    //   text-orientation: sideways;
+    //   height: 100%;
     // }
   }
 

+ 1 - 1
src/modules/paper-export/components/BoxElementEdit.vue

@@ -34,7 +34,7 @@ import EditLines from "../../card/elements/lines/ElemLines";
 import EditGrids from "../../card/elements/grids/ElemGrids";
 import EditPane from "../../card/elements/pane/ElemPane";
 import EditGutter from "../../card/elements/gutter/ElemGutter";
-import EditFillField from "../../card/elements/fill-field/ElemFillField";
+import EditFillField from "../elements/fill-field/ElemFillField";
 import EditFillTable from "../../card/elements/fill-table/ElemFillTable";
 import EditFillPane from "../../card/elements/fill-pane/ElemFillPane";
 

+ 1 - 1
src/modules/paper-export/components/BoxElementPreview.vue

@@ -19,7 +19,7 @@ import PreviewLines from "../../card/elements/lines/ElemLines";
 import PreviewGrids from "../../card/elements/grids/ElemGrids";
 import PreviewPane from "../../card/elements/pane/ElemPane";
 import PreviewGutter from "../../card/elements/gutter/ElemGutter";
-import PreviewFillField from "../../card/elements/fill-field/ElemFillField";
+import PreviewFillField from "../elements/fill-field/ElemFillField";
 import PreviewFillTable from "../../card/elements/fill-table/ElemFillTable";
 import PreviewFillPane from "../../card/elements/fill-pane/ElemFillPane";
 

+ 1 - 1
src/modules/paper-export/components/ElementPropEdit.vue

@@ -35,7 +35,7 @@ import EditLines from "../../card/elements/lines/EditLines";
 import EditGrids from "../../card/elements/grids/EditGrids";
 import EditPane from "../../card/elements/pane/EditPane";
 import EditGutter from "../../card/elements/gutter/EditGutter";
-import EditFillField from "../../card/elements/fill-field/EditFillField";
+import EditFillField from "../elements/fill-field/EditFillField";
 import EditFillTable from "../../card/elements/fill-table/EditFillTable";
 import EditFillPane from "../../card/elements/fill-pane/EditFillPane";
 import EditPaneBox from "../elements/pane-box/EditPaneBox.vue";

+ 17 - 2
src/modules/paper-export/components/PaperSideEdit.vue

@@ -20,6 +20,18 @@
 import { mapState, mapActions, mapMutations } from "vuex";
 import BoxElementEdit from "./BoxElementEdit";
 
+const defaultProp = {
+  FILL_FIELD: {
+    mode: "side",
+    w: 40,
+    h: 400,
+  },
+  TEXT: {
+    mode: "side",
+    h: 100,
+  },
+};
+
 export default {
   name: "PaperSideEdit",
   components: { BoxElementEdit },
@@ -45,13 +57,16 @@ export default {
       const { offsetTop } = this.getOffsetInfo(e.target || e.srcElement);
       const maxWidth = this.$el.offsetWidth;
 
-      const curElement = {
+      let curElement = {
         ...this.curDragElement,
         x: 0,
         y: y + offsetTop,
         w: Math.min(this.curDragElement.w, maxWidth),
       };
-      // 装订线:特殊
+      curElement = Object.assign(
+        curElement,
+        defaultProp[this.curDragElement.type] || {}
+      );
 
       this.setCurDragElement({});
       this.addSideElement(curElement);

+ 1 - 1
src/modules/paper-export/elementModel.js

@@ -6,7 +6,7 @@ import { getModel as createImage } from "../card/elements/image/model";
 import { getModel as createGrids } from "../card/elements/grids/model";
 import { getModel as createPane } from "../card/elements/pane/model";
 import { getModel as createGutter } from "../card/elements/gutter/model";
-import { getModel as createFillField } from "../card/elements/fill-field/model";
+import { getModel as createFillField } from "./elements/fill-field/model";
 import { getModel as createFillTable } from "../card/elements/fill-table/model";
 import { getModel as createFillPane } from "../card/elements/fill-pane/model";
 import { getModel as createPaneBox } from "./elements/pane-box/model";

+ 123 - 0
src/modules/paper-export/elements/fill-field/EditFillField.vue

@@ -0,0 +1,123 @@
+<template>
+  <div class="edit-fill-field">
+    <el-form
+      ref="modalFormComp"
+      :key="modalForm.id"
+      :model="modalForm"
+      :rules="rules"
+      label-width="120px"
+    >
+      <el-form-item prop="fieldCountPerLine" label="每行名词数:">
+        <el-input-number
+          v-model="modalForm.fieldCountPerLine"
+          style="width: 125px"
+          :min="1"
+          :max="10"
+          :step="1"
+          step-strictly
+          :controls="false"
+        ></el-input-number>
+        <span class="el-input-tips">*指一行显示名词数量</span>
+      </el-form-item>
+      <el-form-item prop="lineSpacing" label="空位上下间距:">
+        <el-input-number
+          v-model.number="modalForm.lineSpacing"
+          style="width: 125px"
+          :min="20"
+          :max="100"
+          :step="1"
+          step-strictly
+          :controls="false"
+        ></el-input-number>
+      </el-form-item>
+      <el-form-item prop="fields" label="名词:">
+        <el-input
+          v-model="modalForm.fields"
+          placeholder="请输入名词项"
+          type="textarea"
+          style="width: 100%"
+          @change="fieldsChange"
+        ></el-input>
+        <span class="el-input-tips">*多个名词用逗号隔开,支持中英文逗号</span>
+      </el-form-item>
+      <el-form-item>
+        <el-checkbox v-model="modalForm.nameIsJustify"
+          >名词名是否两端对齐</el-checkbox
+        >
+      </el-form-item>
+    </el-form>
+  </div>
+</template>
+
+<script>
+import { objAssign } from "../../../card/plugins/utils";
+
+const initModalForm = {
+  id: "",
+  fieldCountPerLine: 1,
+  lineSpacing: 30,
+  nameIsJustify: false,
+  fields: "",
+};
+
+export default {
+  name: "EditFillField",
+  props: {
+    instance: {
+      type: Object,
+      default() {
+        return {};
+      },
+    },
+  },
+  data() {
+    return {
+      modalForm: { ...initModalForm },
+      fieldList: [],
+      rules: {
+        fields: [
+          {
+            required: true,
+            message: "请输入名词",
+            trigger: "change",
+          },
+        ],
+        lineSpacing: [
+          {
+            required: true,
+            type: "number",
+            message: "请输入空位上下间距",
+            trigger: "change",
+          },
+        ],
+        fieldCountPerLine: [
+          {
+            required: true,
+            type: "number",
+            message: "请输入每行名词数",
+            trigger: "change",
+          },
+        ],
+      },
+    };
+  },
+  mounted() {
+    this.initData(this.instance);
+  },
+  methods: {
+    initData(val) {
+      this.modalForm = { ...val };
+    },
+    fieldsChange() {
+      this.modalForm.fields = this.modalForm.fields.replace(/\\n/g, "");
+    },
+    async submit() {
+      const valid = await this.$refs.modalFormComp.validate().catch(() => {});
+      if (!valid) return;
+
+      const model = objAssign(this.instance, this.modalForm);
+      this.$emit("modified", model);
+    },
+  },
+};
+</script>

+ 106 - 0
src/modules/paper-export/elements/fill-field/ElemFillField.vue

@@ -0,0 +1,106 @@
+<template>
+  <div class="elem-fill-field" :style="elemStyles">
+    <div
+      v-for="(info, index) in fieldList"
+      :key="index"
+      class="fill-field-item"
+      :style="itemStyles"
+    >
+      <div class="fill-field-content" :style="lineStyles">
+        <span :style="paramStyle">{{ info }}</span>
+        <span>:</span>
+        <span></span>
+      </div>
+    </div>
+    <div v-if="!fieldList.length" class="fill-field-item" :style="itemStyles">
+      <div class="fill-field-content" :style="lineStyles">
+        <span :style="paramStyle">名称名</span>
+        <span>:</span>
+        <span></span>
+      </div>
+    </div>
+  </div>
+</template>
+
+<script>
+export default {
+  name: "ElemFillField",
+  props: {
+    data: {
+      type: Object,
+      default() {
+        return {};
+      },
+    },
+  },
+  data() {
+    return {
+      questions: [],
+      paramStyle: {},
+      lenWidths: {
+        3: 44,
+        4: 62,
+        5: 72,
+        6: 86,
+        7: 100,
+        8: 114,
+      },
+      fieldList: [],
+    };
+  },
+  computed: {
+    itemStyles() {
+      return {
+        width: 100 / this.data.fieldCountPerLine + "%",
+      };
+    },
+    lineStyles() {
+      return {
+        height: this.data.lineSpacing + "px",
+        paddingTop: this.data.lineSpacing - 26 + "px",
+      };
+    },
+    elemStyles() {
+      if (this.data.mode === "side") {
+        return {
+          position: "absolute",
+          width: this.data.h + "px",
+          height: this.data.w + "px",
+          transform: "rotate(-90deg)",
+          "transform-origin": "0 100%",
+          bottom: 0,
+          left: this.data.w + "px",
+        };
+      } else {
+        return null;
+      }
+    },
+  },
+  watch: {
+    data: {
+      immediate: true,
+      handler() {
+        this.init();
+      },
+    },
+  },
+  methods: {
+    init() {
+      this.fieldList = this.data.fields
+        .split(/[,,]/)
+        .filter((item) => item.trim());
+
+      if (this.data.nameIsJustify) {
+        const nameNums = this.fieldList.map((item) => item.length);
+        const maxNameLen = Math.max.apply(null, nameNums);
+        const num = maxNameLen < 3 ? 3 : maxNameLen > 8 ? 8 : maxNameLen;
+        this.paramStyle = {
+          width: this.lenWidths[num] + "px",
+        };
+      } else {
+        this.paramStyle = {};
+      }
+    },
+  },
+};
+</script>

+ 29 - 0
src/modules/paper-export/elements/fill-field/model.js

@@ -0,0 +1,29 @@
+import {
+  getElementId,
+  randomCode,
+  objAssign,
+} from "../../../card/plugins/utils";
+
+const MODEL = {
+  type: "FILL_FIELD",
+  x: 0,
+  y: 0,
+  w: 200,
+  h: 100,
+  sign: "",
+  fieldCountPerLine: 1,
+  lineSpacing: 30,
+  nameIsJustify: false,
+  fields: "",
+  mode: "normal", // side:侧边模式,normal:正常模式
+};
+
+const getModel = (presetData) => {
+  const model = objAssign(MODEL, presetData);
+  model.id = getElementId();
+  model.key = randomCode();
+
+  return model;
+};
+
+export { MODEL, getModel };

+ 3 - 0
src/modules/paper-export/store/index.js

@@ -3,6 +3,7 @@ import {
   calcSum,
   getElementId,
   objAssign,
+  randomCode,
 } from "../../card/plugins/utils";
 
 const state = {
@@ -142,6 +143,7 @@ const actions = {
   },
   // 修改元素
   modifySideElement({ state }, element) {
+    element.key = randomCode();
     const pos = fetchElementPositionInfos(
       element,
       state.pages[state.curPageNo].sides
@@ -168,6 +170,7 @@ const actions = {
   },
   // 修改元素
   modifyElement({ state }, element) {
+    element.key = randomCode();
     const pos = fetchElementPositionInfos(element, state.topics);
     if (pos === -1) return;
     state.topics.splice(pos, 1, element);