Browse Source

JLHWEB: 1、床垫清单,配置,垫层、辅料中出现的“说明”必填检测取消;
2、修复床网报价,选择列表后默认勾选问题;
3、床垫报价,新增新版报价清单导出excel;
4、床垫报价-报价清单,新增内布套、顶布裥棉明细信息;
5、部门列表新增非报关产品税金补偿信息显示与编辑

JohnnyChan 4 days ago
parent
commit
8dc71544f9

+ 1 - 1
JLHWEB/README.md

@@ -24,7 +24,7 @@ L1-ERP WEB 一款基于 Vue3.3、TypeScript、Vite4、Pinia、Element-Plus 开
 - 使用 Prettier 统一格式化代码,集成 ESLint、Stylelint 代码校验规范
 - 使用 husky、lint-staged、commitlint、czg、cz-git 规范提交信息
 - 使用 [vue-drag-select](https://gitee.com/ovsexia/DragSelect-Doc-Cn#https://ovsexia.gitee.io/dragselect-doc-cn/demo.html) 实现拖转框选
-- 使用 [ExcelJs](https://github.com/exceljs/exceljs/blob/HEAD/README_zh.md) 实现自定义导出 Excel
+- 使用 [ExcelJs](https://github.com/exceljs/exceljs/blob/HEAD/README_zh.md) 实现自定义导出 Excel [API](https://gitcode.com/gh_mirrors/ex/exceljs/blob/5bed18b45e824f409b08456b59b87430ded023ab/README_zh.md?utm_source=csdn_github_accelerator)
 
 ### 安装使用步骤 📔
 

+ 8 - 2
JLHWEB/src/components/LjDetail/components/BaseFormItem.vue

@@ -47,6 +47,7 @@
 <script setup lang="tsx" name="BaseFormItem">
 import { computed, inject, ref } from "vue";
 import { handleProp } from "@/utils";
+import { isArray, isObject } from "@/utils/is";
 // import { ColumnProps } from "../interface";
 import { useI18n } from "vue-i18n";
 import { FieldNamesProps } from "@/components/LjVxeTable/interface/index";
@@ -102,8 +103,12 @@ const columnEnum = computed(() => {
       return { ...item, label: item[props.fieldNames.label], value: item[props.fieldNames.value] };
     });
   }
-  console.log("enumData :>> ", enumData, props.fieldNames, enumMap.value);
-  return enumData;
+  console.log("columnEnum enumData :>> ", enumData, props.field, props.fieldNames, enumMap.value);
+  if (isObject(enumData) && enumData.hasOwnProperty("data")) {
+    return enumData.data;
+  } else {
+    return enumData;
+  }
 });
 
 // 处理透传的 searchProps (el 为 tree-select、cascader 的时候需要给下默认 label && value && children)
@@ -168,6 +173,7 @@ const findParentNodes = (tree, targetId, key = "id", path = []) => {
  * @param key 目标字段
  */
 const getSimpleParentNodes = targetId => {
+  console.log("getSimpleParentNodes :>> ", columnEnum.value, targetId, props.fieldNames.value);
   let parentNodes = findParentNodes(columnEnum.value, targetId, props.fieldNames.value);
   if (!parentNodes) {
     return null;

+ 1 - 1
JLHWEB/src/views/baseinfo/mattressformula/index.vue

@@ -98,7 +98,7 @@ const orderEditAction = [
     label: t("common.saveText"),
     icon: "iconsave-01",
     clickFunc: item => {
-      const save_data = orderStatus.value == "new" ? LjDetailRef.value?.infoParam : LjDetailRef.value?._mainData;
+      const save_data = LjDetailRef.value?._mainData;
 
       fSave({ mattress: save_data }).then(() => {
         LjDrawerRef.value.hide();

+ 25 - 0
JLHWEB/src/views/baseinfo/mtrldef/hooks/index.tsx

@@ -119,6 +119,31 @@ export const useHooks = (t?: any) => {
         visible: false
       }
     },
+    {
+      field: "mtrltype",
+      title: "类别",
+      basicinfo: {
+        el: "tree-select",
+        span: 2,
+        editable: ALLOW_EDIT_STATE
+      },
+      isFilterEnum: true,
+      enum: async () => {
+        const data = await getMtrlType();
+        console.log("transformTreeData(data.reList) :>> ", transformTreeData(data.reList));
+        return { data: transformTreeData(data.reList) };
+      },
+      // enum: async () => {
+      //   const data = await getMtrlType();
+      //   console.log("transformTreeData(data.reList) :>> ", transformTreeData(data.reList));
+      //   return data.reList;
+      // }
+      fieldNames: {
+        label: "mtrltype",
+        value: "mtrltypeid",
+        children: "children"
+      }
+    },
     {
       field: "name",
       title: "物料名称",

+ 2 - 2
JLHWEB/src/views/baseinfo/mtrldef/index.vue

@@ -207,9 +207,9 @@ const orderEditAction = [
     label: t("common.saveText"),
     icon: "iconsave-01",
     clickFunc: item => {
-      const save_data = orderStatus.value == "new" ? LjDetailRef.value?.infoParam : LjDetailRef.value?._mainData;
+      const save_data = LjDetailRef.value?._mainData;
 
-      if (orderStatus.value == "copy") save_data.mtrlid = 0;
+      if (orderStatus.value == "new" || orderStatus.value == "copy") save_data.mtrlid = 0;
       let { fullData } = VxeTableMxRef.value?.element.getTableData();
       save_data.mxlist = fullData;
       fSave({ mtrl: save_data }).then(() => {

+ 6 - 1
JLHWEB/src/views/baseinfo/mtrltype/index.vue

@@ -82,7 +82,12 @@ const orderEditAction = [
     label: t("common.saveText"),
     icon: "iconsave-01",
     clickFunc: item => {
-      const save_data = orderStatus.value == "new" ? LjDetailRef.value?.infoParam : LjDetailRef.value?._mainData;
+      const save_data = LjDetailRef.value?._mainData;
+
+      if (orderStatus.value == "new") {
+        save_data.mtrltypeid = -1;
+      }
+
       fSave({ mtrltype: save_data }).then(() => {
         LjDrawerRef.value.hide();
         refresh();

+ 29 - 17
JLHWEB/src/views/erpapi/mattressInterface/detail.vue

@@ -112,6 +112,7 @@
   </LjDialog>
   <MattressDialog ref="MattressDialogRef" v-bind="MattressDialogProps" />
   <MtrldefErpDialog ref="MtrldefErpDialogRef" v-bind="MtrldefErpDialogProps" />
+  <!-- <SetSubspecsDialog ref=SetSubspecsDialogRef" /> -->
 </template>
 
 <script setup lang="tsx" name="mattressInterfaceDetail">
@@ -135,6 +136,8 @@ import LjFoldLayout from "@/components/LjFoldLayout/index.vue";
 import { detailAction } from "@/components/LjDetail/interface";
 import { transformTreeData, autoMergeCells, isFilterPrice } from "@/utils/index";
 import LjDialog from "@/components/LjDialog/index.vue";
+// import dialog from "@/utils/dialog";
+// import SetSubspecsDialog from "./components/setSubspecs.vue";
 
 interface detailProp {
   /**
@@ -204,6 +207,8 @@ const initParams = ref({ mattressid: 0 as Number });
 
 const layoutSetting = reactive({});
 
+const SetSubspecsDialogRef = ref();
+
 const detailProps = reactive<DetailProp>({
   dwname: DwnameEnum.mattressInterfaceDetail,
   columns: columns_detail,
@@ -243,7 +248,7 @@ const cellClassNameFn = (data: any, editable) => {
   if (editable) {
     if (column.field == "bj_pzname") {
       if (
-        ["垫层", "辅料"].includes(row.itemname) ||
+        (["垫层", "辅料"].includes(row.itemname) && row.bj_pzname.indexOf("说明") == -1) ||
         [
           "边带",
           "面层裥棉图案",
@@ -442,7 +447,7 @@ const orderDefaultAction = [
         visibleData.map(o => {
           console.log("tableYW visibleData o :>> ", o);
           if (
-            ["垫层", "辅料"].includes(o.itemname) ||
+            (["垫层", "辅料"].includes(o.itemname) && o.bj_pzname.indexOf("说明") == -1) ||
             [
               "边带",
               "面层裥棉图案",
@@ -643,21 +648,6 @@ const orderDefaultAction = [
       clickFunc: () => funcCmpCC()
     })
   ],
-  buttonDefault({
-    label: "覆盖配置到副规格产品",
-    limited: () => {
-      return !orderStatus.value || LjDetailRef.value?._mainData.child_count == 0;
-    },
-    disabledTextCallBack: (data: any) => {
-      if (data.child_count == 0) {
-        return "没有副规格产品,无法操作";
-      }
-      return "";
-    },
-    clickFunc: item => {
-      alert("功能维护中!");
-    }
-  }),
   buttonDefault({
     label: "重置半成品归属列数据",
     limited: () => {
@@ -823,6 +813,28 @@ const orderDefaultAction = [
       }
     })
   ],
+  buttonDefault({
+    label: "覆盖配置到副规格产品",
+    limited: () => {
+      return !!orderStatus.value || LjDetailRef.value?._mainData.child_count == 0;
+    },
+    disabledTextCallBack: (data: any) => {
+      if (data.child_count == 0) {
+        return "没有副规格产品,无法操作";
+      }
+      return "";
+    },
+    clickFunc: item => {
+      // dialog(SetSubspecsDialog, {
+      //   mattressid: initParams.value.mattressid
+      // }).then((data: any) => {
+      //   console.log(data);
+      // });
+      alert("功能维护中!");
+
+      // SetSubspecsDialogRef.value.show();
+    }
+  }),
   buttonDefault({
     label: "生成/更新物料",
     power: 88,

+ 2 - 2
JLHWEB/src/views/quote/bednetQuote/hooks/index.tsx

@@ -556,7 +556,7 @@ export const useHooks = (t?: any, props?: any) => {
     _mainData.cnail_mtrl_formula = rBednetType.cnail_mtrl_formula;
     _mainData.cnail_hr_formula = rBednetType.cnail_hr_formula;
 
-    _mainData.if_sponge_drilling = rBednetType.if_sponge_drilling;
+    _mainData.if_sponge_drilling = 0; // rBednetType.if_sponge_drilling;
     _mainData.sponge_mtrl_formula = rBednetType.sponge_mtrl_formula;
     _mainData.sponge_hr_formula = rBednetType.sponge_hr_formula;
 
@@ -566,7 +566,7 @@ export const useHooks = (t?: any, props?: any) => {
     _mainData.fork_mtrl_formula = rBednetType.fork_mtrl_formula;
     _mainData.fork_hr_formula = rBednetType.fork_hr_formula;
 
-    _mainData.if_rsorwa = rBednetType.if_rsorwa;
+    _mainData.if_rsorwa = 0; // rBednetType.if_rsorwa;
     _mainData.rsorwa_mtrl_formula = rBednetType.rsorwa_mtrl_formula;
     _mainData.rsorwa_hr_formula = rBednetType.rsorwa_hr_formula;
     _mainData.sponge_drilling_hr_formula = rBednetType.sponge_drilling_hr_formula;

+ 26 - 2
JLHWEB/src/views/quote/mattressQuote/components/QuoteListNew.vue

@@ -16,6 +16,9 @@
           @change="toggleRowExpansionAll()"
         ></el-checkbox>
       </div>
+      <div class="flx-shrink">
+        <el-button v-if="iforigin" size="small" @click="handleExportExcel"> 导出Excel </el-button>
+      </div>
     </template>
 
     <el-descriptions :column="3">
@@ -187,6 +190,8 @@ const { prefixCls } = useDesign("ljdrawer-quotelist");
 // const { userInfo } = useUserStore();
 const { enumMap, tableData, oriTableData, wf_retrieve_qingdan } = useHooksCpQuote();
 
+const emits = defineEmits(["export"]);
+
 const LjDrawerRef = ref();
 const elTableRef = ref();
 const tableRef = ref();
@@ -393,7 +398,8 @@ const isFilterTime = time => {
 
 const fields = computed(() => {
   if (!ifShowOrigin.value) {
-    const { data } = mainData.value;
+    const { data, replace } = mainData.value;
+    console.log("fieldsfields data :>> ", mainData.value);
 
     let _enum = enumMap.value.get("mattresstypeid");
     let result = "";
@@ -417,6 +423,17 @@ const fields = computed(() => {
     if (Number(data.if_w_butao) == 1) {
       arr.push("外布套");
     }
+
+    let _managerate = 0;
+    let isFormulaValue = replace.find(o => o.label.indexOf("管理费用点") > -1);
+    if (isFormulaValue) {
+      _managerate = isFilterPrice(isFormulaValue.value);
+    }
+    let _com_profitrate = 0;
+    isFormulaValue = replace.find(o => o.label.indexOf("公司利润点(部门)") > -1);
+    if (isFormulaValue) {
+      _com_profitrate = isFilterPrice(isFormulaValue.value);
+    }
     return [
       { label: "核价编码", value: data.mattresscode },
       { label: "核价名称", value: data?.mattressname == "" ? "未命名" : data?.mattressname },
@@ -424,7 +441,10 @@ const fields = computed(() => {
       { label: "床垫规格", value: `${data.mattress_width} * ${data.mattress_length} * ${data.mattress_height}` },
       { label: "拆装、布套", value: arr.join(" ") },
       { label: "地区", value: data.area ?? "" },
-      { label: "柜型", value: data.cabinet_type ?? "" }
+      { label: "柜型", value: data.cabinet_type ?? "" },
+      { label: "管理费用点", value: _managerate ?? "", type: "variable", field: "managerate" },
+      { label: "公司利润点(部门)", value: _com_profitrate ?? "", type: "variable", field: "com_profitrate" },
+      { label: "部门利润率", value: data.dept_profitrate ?? "", type: "variable", field: "dept_profitrate" }
     ];
   } else {
     return [
@@ -582,6 +602,10 @@ const objectSpanMethod = (data: any) => {
   }
 };
 
+const handleExportExcel = () => {
+  emits("export", ifExpandAll.value, ifShowOrigin.value, fields.value);
+};
+
 defineExpose({
   show
 });

+ 64 - 2
JLHWEB/src/views/quote/mattressQuote/detail.vue

@@ -744,7 +744,7 @@
 
   <MtrldefDialog ref="MtrldefDialogRef" v-bind="MtrldefDialogProps" />
   <BednetDialog ref="BednetDialogRef" v-bind="BednetDialogProps" />
-  <LjDrawerQuoteList ref="QuoteListDrawerRef" :iforigin="isShowOriginFormulaMattress" />
+  <LjDrawerQuoteList ref="QuoteListDrawerRef" :iforigin="isShowOriginFormulaMattress" @export="handleExportQuote" />
   <AllFormula
     ref="AllFormulaRef"
     :iforigin="isShowOriginFormulaMattress"
@@ -937,7 +937,7 @@ const {
   gotoErpapi,
   updateSubspecsTable
 } = useHooks(t);
-const { toExcelQuote } = useHooksCpQuote();
+const { toExcelQuote, toExcelQuoteNew } = useHooksCpQuote();
 const { CheckPower, CheckOption, buttonNew, buttonDefault } = useAuthButtons(t);
 const { userInfo } = useUserStore();
 // const toast = useToast();
@@ -1202,6 +1202,14 @@ const isFilterSucessBadge = data => {
 };
 
 const isQuoteListMxData = computed(() => {
+  let innerData = [];
+  if (innerClothLayerMxRef.value) {
+    innerData = innerClothLayerMxRef.value?.element.getTableData()?.visibleData;
+  }
+  let topCottonData = [];
+  if (topCottonMxRef.value) {
+    topCottonData = topCottonMxRef.value?.element.getTableData()?.visibleData;
+  }
   return [
     {
       label: "面裥绵",
@@ -1256,6 +1264,16 @@ const isQuoteListMxData = computed(() => {
       label: "包装",
       field: "packag",
       data: packagMxData.value
+    },
+    {
+      label: "内布套",
+      field: "innerClothLayerMx",
+      data: innerData
+    },
+    {
+      label: "顶布裥棉",
+      field: "topCottonMx",
+      data: topCottonData
     }
   ];
 });
@@ -3047,6 +3065,50 @@ const cmpIfMoneyrate = computed(() => {
   return LjDetailRef.value?._mainData.if_moneyrate ?? 0;
 });
 
+const handleExportQuote = async (ifExpandAll: any, ifShowOrigin: any, fields: any) => {
+  console.log("handleExportQuote ifExpandAll :>> ", ifExpandAll, ifShowOrigin);
+  if (ifShowOrigin) {
+    loadingStatus.download = true;
+    let _data = {
+      data: LjDetailRef.value._mainData,
+      mxdata: isQuoteListMxData.value,
+      enumMap: LjDetailRef.value.enumMap,
+      fabricMx: fabricMxTabList.value,
+      formulakindenum: formulaKindEnum.value,
+      differ: cmpDiffer.value
+    };
+    await toExcelQuote(_data, "床垫报价单_" + LjDetailRef.value._mainData.mattresscode);
+    loadingStatus.download = false;
+  } else {
+    loadingStatus.download = true;
+    // let _data = {
+    //   data: LjDetailRef.value._mainData,
+    //   mxdata: isQuoteListMxData.value,
+    //   enumMap: LjDetailRef.value.enumMap,
+    //   fabricMx: fabricMxTabList.value,
+    //   formulakindenum: formulaKindEnum.value,
+    //   differ: cmpDiffer.value,
+    //   fields: fields
+    // };
+    let _data = {
+      data: LjDetailRef.value._mainData,
+      mxdata: isQuoteListMxData.value,
+      enumMap: LjDetailRef.value.enumMap,
+      fabricMx: fabricMxTabList.value,
+      formulakindenum: formulaKindEnum.value,
+      dannum_type: LjDetailRef.value._mainData.dannum_type,
+      formula: cmpFormulas.value,
+      replace: cmpFormulaReplace.value,
+      formula_ori: cmpFormulasOri.value,
+      formula_bednet: cmpFormulasBednet.value,
+      differ: cmpDiffer.value,
+      fields: fields
+    };
+    await toExcelQuoteNew(_data, "床垫报价单_" + LjDetailRef.value._mainData.mattresscode, ifExpandAll);
+    loadingStatus.download = false;
+  }
+};
+
 // const autoTabsClicks = (data: any) => {
 //   console.log("autoTabsClicks data :>> ", data);
 

+ 368 - 35
JLHWEB/src/views/quote/mattressQuote/hooks/cpQuote.ts

@@ -26,6 +26,9 @@ interface defaultState {
   enumMap: any;
   // tabldId: number;
   bednet_qingdan: any;
+  default_font: any;
+  default_alignment: any;
+  variables: variablesProps[];
 }
 
 interface wfQingdanProps {
@@ -45,6 +48,21 @@ interface wfQingdanProps {
   // replace?: any;
   // formula_ori?: any;
   differ?: any;
+  /**
+   * @description 表头字段
+   */
+  fields?: any;
+}
+
+interface variablesProps {
+  /**
+   * @description 单元格变量
+   */
+  cell: string;
+  /**
+   * @description 变量名称
+   */
+  field: string;
 }
 
 export const useHooksCpQuote = (t?: any) => {
@@ -124,7 +142,14 @@ export const useHooksCpQuote = (t?: any) => {
       }
     ],
     newTableData: [],
-    enumMap: null
+    enumMap: null,
+    default_font: { size: 12, name: "宋体" },
+    default_alignment: {
+      vertical: "middle", // 垂直居中
+      horizontal: "left", // 水平居左
+      wrapText: true // 自动换行
+    },
+    variables: []
   });
 
   const isFilterPrice = data => {
@@ -1002,6 +1027,7 @@ export const useHooksCpQuote = (t?: any) => {
       let reg = /\【(.*?)\】/g;
       let formulaItemArr = formulaItem.value.match(reg);
 
+      console.log("init_new_formula_item formulaItemArr :>> ", formulaItemArr);
       if (formulaItemArr.length) {
         formulaItemArr.map(fName => {
           let _item = {
@@ -1042,6 +1068,7 @@ export const useHooksCpQuote = (t?: any) => {
                         _itemMattress.costamt = isFilterPrice(_valueReplace?.value ?? 0);
                       }
                     });
+                    console.log("init_new_formula_item _itemMattress item :>> ", _itemMattress, differ);
                     arr.push(_itemMattress);
                   });
                 }
@@ -1092,6 +1119,7 @@ export const useHooksCpQuote = (t?: any) => {
             }
           });
 
+          console.log("init_new_formula_item 小计 item :>> ", item);
           arr.push(_item);
         });
       }
@@ -1397,6 +1425,42 @@ export const useHooksCpQuote = (t?: any) => {
             }
           });
           break;
+        case "innerClothLayerMx":
+        case "topCottonMx":
+          console.log("innerClothLayer item.data :>> ", item.data, formulakindenum);
+
+          item.data.map(itm => {
+            if (Number(itm.mtrlid ?? 0) > 0 || Number(itm.costamt ?? 0) != 0) {
+              let result: any = cloneDeep(result_default);
+              result.label = itm.chastr != "" ? itm.chastr : item.label;
+              let _formulaName = "";
+              if (formulakindenum) {
+                _formulaName = formulakindenum.find(t => t.value == itm.formulakind)?.label ?? "";
+              }
+
+              _formulaName = _formulaName.replace(item.replace, "");
+
+              // console.log("_formulaName  rp:>> ", _formulaName, item.replace);
+              result.dscrp = `${_formulaName}:${itm.mtrlname}`;
+
+              if (Number(itm.thickness) > 0) {
+                result.dscrp += ` 厚度:${isFilterPrice(itm.thickness)}`;
+              }
+              result.qty = Number(itm.qty);
+              if (userInfo.usermode == 0) {
+                result.costamt = isFilterPrice(itm.costamt ?? 0);
+                result.costamt_1 = isFilterPrice(formatCutNumber({ val: floatMul(itm.costamt ?? 0, 1 + itm.dannum1_rate) }));
+                result.costamt_2 = isFilterPrice(formatCutNumber({ val: floatMul(itm.costamt ?? 0, 1 + itm.dannum2_rate) }));
+                result.costamt_3 = isFilterPrice(formatCutNumber({ val: floatMul(itm.costamt ?? 0, 1 + itm.dannum3_rate) }));
+                result.costamt_4 = isFilterPrice(formatCutNumber({ val: floatMul(itm.costamt ?? 0, 1 + itm.dannum4_rate) }));
+                result.useqty = Number(itm.useqty ?? 0);
+                result.price = isFilterPrice(itm.price ?? 0);
+              }
+              result.index = index;
+              mattressArr.push(result);
+            }
+          });
+          break;
       }
     }
 
@@ -1494,16 +1558,14 @@ export const useHooksCpQuote = (t?: any) => {
     return sums;
   };
 
+  /**
+   * @description 旧核价格式
+   * @param params
+   * @param fileName
+   */
   const toExcelQuote = async (params: wfQingdanProps, fileName: string) => {
     const { data, mxdata } = params;
-    console.log("mainData :>> ", data);
-
-    let default_font = { size: 12, name: "宋体" };
-    let default_alignment: any = {
-      vertical: "middle", // 垂直居中
-      horizontal: "left", // 水平居左
-      wrapText: true // 自动换行
-    };
+    console.log("mainData :>> ", params);
 
     const workbook = new Exceljs.Workbook(); // 创建工作簿
     const worksheet = workbook.addWorksheet("sheet1"); // 创建工作表(sheet1)
@@ -1535,43 +1597,43 @@ export const useHooksCpQuote = (t?: any) => {
     BCol.width = 13.55;
     BCol.key = "label";
     BCol.style = {
-      font: default_font,
-      alignment: { ...default_alignment, vertical: "top" }
+      font: state.default_font,
+      alignment: { ...state.default_alignment, vertical: "top" }
     };
     const CCol = worksheet.getColumn("C");
     CCol.width = 49.33;
     CCol.key = "dscrp";
     CCol.style = {
-      font: default_font,
-      alignment: default_alignment
+      font: state.default_font,
+      alignment: state.default_alignment
     };
     const DCol = worksheet.getColumn("D");
     DCol.width = 5.69;
     DCol.key = "qty";
     DCol.style = {
-      font: default_font,
-      alignment: { ...default_alignment, horizontal: "center" }
+      font: state.default_font,
+      alignment: { ...state.default_alignment, horizontal: "center" }
     };
     const ECol = worksheet.getColumn("E");
     ECol.width = 10;
     ECol.key = "costamt";
     ECol.style = {
-      font: default_font,
-      alignment: { ...default_alignment, horizontal: "right" }
+      font: state.default_font,
+      alignment: { ...state.default_alignment, horizontal: "right" }
     };
     const FCol = worksheet.getColumn("F");
     FCol.width = 13;
     FCol.key = "useqty";
     FCol.style = {
-      font: default_font,
-      alignment: { ...default_alignment, horizontal: "right" }
+      font: state.default_font,
+      alignment: { ...state.default_alignment, horizontal: "right" }
     };
     const GCol = worksheet.getColumn("G");
     GCol.width = 12.48;
     GCol.key = "price";
     GCol.style = {
-      font: default_font,
-      alignment: { ...default_alignment, horizontal: "right" }
+      font: state.default_font,
+      alignment: { ...state.default_alignment, horizontal: "right" }
     };
 
     //======================================= 第一行 =================================
@@ -1584,7 +1646,7 @@ export const useHooksCpQuote = (t?: any) => {
     cellB1.value = `报价日期:${formatTime(data.createtime, "{y}-{m}-{d}", false)}  报价金额:${foreign_cost}${currency}报价清单`;
     // 设置第一行的单元格样式
     cellB1.font = { size: 15, bold: true, name: "宋体" };
-    cellB1.alignment = default_alignment;
+    cellB1.alignment = state.default_alignment;
     worksheet.getRow(1).height = 26; // 设置行高
 
     //======================================= 第二行 =================================
@@ -1593,8 +1655,8 @@ export const useHooksCpQuote = (t?: any) => {
     cellB2.value = `财务底价:${formatAmount(data.nottax_dept_cost)}     佣金点数:${formatAmount(
       data.commission
     )}     税率:${formatAmount(data.taxrate)}      `;
-    cellB2.font = default_font;
-    cellB2.alignment = default_alignment;
+    cellB2.font = state.default_font;
+    cellB2.alignment = state.default_alignment;
     worksheet.getRow(2).height = 39;
 
     //======================================= 第三行 =================================
@@ -1603,8 +1665,8 @@ export const useHooksCpQuote = (t?: any) => {
     cellB3.value = `额外点数:${formatAmount(data.other_rate)}       额外费用:${formatAmount(
       data.extras_cost
     )}     汇率:${formatAmount(data.moneyrate)}      				`;
-    cellB3.font = default_font;
-    cellB3.alignment = default_alignment;
+    cellB3.font = state.default_font;
+    cellB3.alignment = state.default_alignment;
     worksheet.getRow(3).height = 18;
 
     //======================================= 第四行 =================================
@@ -1613,8 +1675,8 @@ export const useHooksCpQuote = (t?: any) => {
     cellB4.value = `款式费用:${formatAmount(data.hrcost)}     边带费用:${formatAmount(
       data.biandaicost
     )}     总成本:${formatAmount(data.total_cost)}     				`;
-    cellB4.font = default_font;
-    cellB4.alignment = default_alignment;
+    cellB4.font = state.default_font;
+    cellB4.alignment = state.default_alignment;
     worksheet.getRow(4).height = 18;
 
     //======================================= 第五行 =================================
@@ -1623,8 +1685,8 @@ export const useHooksCpQuote = (t?: any) => {
     cellB5.value = `工厂利润率${formatAmount(data.profitrate)}   工艺点数:${formatAmount(
       data.profitrate_point
     )}     不含税出厂价:${formatAmount(data.nottax_factory_cost)}    				`;
-    cellB5.font = default_font;
-    cellB5.alignment = default_alignment;
+    cellB5.font = state.default_font;
+    cellB5.alignment = state.default_alignment;
     worksheet.getRow(5).height = 18;
 
     //======================================= 第六行 =================================
@@ -1633,16 +1695,16 @@ export const useHooksCpQuote = (t?: any) => {
     cellB6.value = `部门利润率:${formatAmount(data.dept_profitrate)}    FOB费用:${formatAmount(
       data.fob
     )}    部门售价:${formatAmount(data.nottax_dept_cost)}     				`;
-    cellB6.font = default_font;
-    cellB6.alignment = default_alignment;
+    cellB6.font = state.default_font;
+    cellB6.alignment = state.default_alignment;
     worksheet.getRow(6).height = 18;
 
     //======================================= 第七行 =================================
     worksheet.mergeCells("B7:F7");
     const cellB7 = worksheet.getCell("B7");
     cellB7.value = `让利点数:${formatAmount(data.dept_profitrate_rangli)}     海绵款扣点:${formatAmount(data.haimian_point)}    				`;
-    cellB7.font = default_font;
-    cellB7.alignment = default_alignment;
+    cellB7.font = state.default_font;
+    cellB7.alignment = state.default_alignment;
     worksheet.getRow(7).height = 18;
 
     //======================================= 第八行 =================================
@@ -1755,9 +1817,280 @@ export const useHooksCpQuote = (t?: any) => {
       saveAs(new Blob([buffer], { type: "application/octet-stream" }), fileName + ".xlsx");
     });
   };
+
+  /**
+   * @description 新核价格式
+   * @param params
+   * @param fileName 文件名
+   * @param ifShowDetail 是否显示明细
+   */
+  const toExcelQuoteNew = async (params: wfQingdanProps, fileName: string, ifShowDetail = true) => {
+    const { data, fields } = params;
+    console.log("toExcelQuoteNew mainData :>> ", params);
+
+    const workbook = new Exceljs.Workbook(); // 创建工作簿
+    const worksheet = workbook.addWorksheet("sheet1"); // 创建工作表(sheet1)
+
+    // 宽度设置
+    const ACol = worksheet.getColumn("A");
+    ACol.width = 0.78;
+    ACol.key = "";
+    getColumnStyle(worksheet, "B", "level", 13.55, { vertical: "top" });
+    getColumnStyle(worksheet, "C", "level1", 13.55, { vertical: "top" });
+    getColumnStyle(worksheet, "D", "level2", 13.55);
+
+    // let mergeCellName = "K";
+    let _val = "";
+    if (ifShowDetail) {
+      // 展开明细
+      getColumnStyle(worksheet, "E", "label", 13.55, { horizontal: "center" });
+      getColumnStyle(worksheet, "F", "dscrp", 26, { horizontal: "right" });
+      getColumnStyle(worksheet, "G", "qty", 13, { horizontal: "right" });
+      getColumnStyle(worksheet, "H", "useqty", 12.48, { horizontal: "right" });
+      getColumnStyle(worksheet, "I", "price", 12.48, { horizontal: "right" });
+      getColumnStyle(worksheet, "J", "costamt_2", 12.48, { horizontal: "right" });
+      getColumnStyle(worksheet, "K", "costamt_1", 12.48, { horizontal: "right" });
+      getColumnStyle(worksheet, "L", "costamt_4", 12.48, { horizontal: "right" });
+      getColumnStyle(worksheet, "M", "costamt_3", 12.48, { horizontal: "right" });
+      // mergeCellName = "K";
+    } else {
+      getColumnStyle(worksheet, "E", "costamt_2", 12.48, { horizontal: "right" });
+      getColumnStyle(worksheet, "F", "costamt_1", 12.48, { horizontal: "right" });
+      getColumnStyle(worksheet, "G", "costamt_4", 12.48, { horizontal: "right" });
+      getColumnStyle(worksheet, "H", "costamt_3", 12.48, { horizontal: "right" });
+      // mergeCellName = "G";
+    }
+
+    //======================================= 第一行 =================================
+    // 合并A1到L1的单元格 (大标题)
+    // worksheet.mergeCells(`B1:${mergeCellName}1`);
+    // const cellB1 = worksheet.getCell("B1");
+
+    let foreign_cost = formatAmount(data?.foreign_cost);
+    let currency = Number(data?.moneyrate) != 1 ? "美金" : "人民币";
+    let _val1 = `报价日期:${formatTime(data.createtime, "{y}-{m}-{d}", false)}`;
+    let _val2 = `报价金额:${foreign_cost}${currency}`;
+    setHeaderStyle(worksheet, 1, `B1:E1`, _val1, 26, { size: 15, bold: true, name: "宋体" });
+    // setHeaderStyle(worksheet, 1, `E1:G1`, "报价清单", 26, { size: 15, bold: true, name: "宋体" }, { horizontal: "center" });
+    setHeaderStyle(worksheet, 1, `F1:M1`, _val2, 26, { size: 15, bold: true, name: "宋体" }, { horizontal: "right" });
+
+    //======================================= 第二行 =================================
+    let rowIndex = 2;
+    if (fields.length > 0) {
+      _val = "";
+      let rowArr = [
+        {
+          sCell: "B",
+          eCell: "E"
+        },
+        {
+          sCell: "F",
+          eCell: "I"
+        },
+        {
+          sCell: "J",
+          eCell: "M"
+        }
+      ];
+      fields
+        .filter(t => t.type != "variable")
+        .forEach((t, i) => {
+          let rowItem = rowArr[i % 3];
+          let _cell = `${rowItem.sCell + rowIndex}:${rowItem.eCell + rowIndex}`;
+
+          _val = `${t.label}: ${t.value}`;
+          setHeaderStyle(worksheet, rowIndex, _cell, _val.trim(), 18);
+          // 每三个一行
+          if ((i + 1) % 3 == 0) {
+            rowIndex = (i + 1) / 3 + 2;
+          }
+        });
+      fields
+        .filter(t => t.type == "variable")
+        .forEach((t, i) => {
+          // 每三个一行
+          if (i % 3 == 0) {
+            rowIndex++;
+          }
+          let rowItem = rowArr[i % 3];
+          let _cell = `${rowItem.sCell + rowIndex}:${getPreLetter(rowItem.eCell) + rowIndex}`;
+          let _cellname_var = rowItem.eCell + rowIndex;
+
+          state.variables.push({
+            cell: _cellname_var,
+            field: t.field
+          });
+
+          _val = `${t.label}:`;
+          setHeaderStyle(worksheet, rowIndex, _cell, _val, 18);
+
+          const _cellVar = worksheet.getCell(_cellname_var);
+          _cellVar.value = t.value;
+          _cellVar.font = state.default_font;
+          _cellVar.alignment = state.default_alignment;
+          _cellVar.fill = {
+            type: "pattern",
+            pattern: "darkTrellis",
+            fgColor: { argb: "FF90c5ff" },
+            bgColor: { argb: "FF90c5ff" }
+          };
+        });
+    }
+
+    // 冻结前7行
+    console.log("冻结行数rowIndex :>> ", rowIndex);
+    worksheet.views = [{ state: "frozen", xSplit: 0, ySplit: rowIndex }];
+    console.log("冻结行数rowIndex end:>> ", rowIndex);
+    //======================================= 表格内容 =================================
+
+    console.log("百分 state.tableData :>> ", state.tableData);
+    await wf_retrieve_qingdan(params, true, ifShowDetail);
+    console.log("af state.tableData :>> ", JSON.stringify(state.tableData));
+
+    console.log("表格内容 bf rowIndex :>> ", rowIndex);
+    rowIndex++;
+
+    const headerRows = worksheet.insertRow(
+      rowIndex,
+      {
+        level: "类目",
+        level1: "一级项目",
+        level2: "二级项目",
+        label: "项目",
+        dscrp: "内容",
+        qty: "数量",
+        useqty: "用量",
+        price: "单价",
+        costamt_2: "标准金额",
+        costamt_1: "散单金额",
+        costamt_4: "小单金额",
+        costamt_3: "大单金额"
+      },
+      "n"
+    );
+    console.log("表格内容 ed rowIndex :>> ", rowIndex);
+    rowIndex++;
+    const insertedRows = worksheet.insertRows(rowIndex, state.tableData, "n");
+    // const cellBSum = worksheet.getCell(`B${9 + state.tableData.length}`);
+    // cellBSum.value = "材料合计:";
+    // const cellESum = worksheet.getCell(`E${9 + state.tableData.length}`);
+    // cellESum.value = getSummaries(state.tableData, "costamt");
+    // const footerRows = worksheet.insertRow(
+    //   9 + state.tableData.length,
+    //   {
+    //     label: "材料合计:",
+    //     dscrp: "",
+    //     qty: "",
+    //     costamt: getSummaries(state.tableData, "costamt"),
+    //     costamt_1: getSummaries(state.tableData, "costamt_1"),
+    //     costamt_2: getSummaries(state.tableData, "costamt_2"),
+    //     costamt_3: getSummaries(state.tableData, "costamt_3"),
+    //     costamt_4: getSummaries(state.tableData, "costamt_4"),
+    //     useqty: "",
+    //     price: ""
+    //   },
+    //   "n"
+    // );
+
+    // 设置单元格边框
+    let default_border: any = {
+      top: { style: "thin", color: { argb: "FF000000" } },
+      left: { style: "thin", color: { argb: "FF000000" } },
+      bottom: { style: "thin", color: { argb: "FF000000" } },
+      right: { style: "thin", color: { argb: "FF000000" } }
+    };
+    headerRows.eachCell(cell => {
+      cell.border = default_border;
+    });
+    // footerRows.eachCell(cell => {
+    //   cell.border = default_border;
+    // });
+    insertedRows.map(row => {
+      row.eachCell(cell => {
+        cell.border = default_border;
+      });
+    });
+
+    toMergeCells(worksheet, "level", "B", rowIndex);
+    toMergeCells(worksheet, "level1", "C", rowIndex);
+    toMergeCells(worksheet, "level2", "D", rowIndex);
+    ifShowDetail && toMergeCells(worksheet, "label", "E", rowIndex);
+
+    console.log("wf_retrieve_qingdan tableData :>> ", state.tableData);
+
+    //======================================= 下载工作簿 =================================
+    workbook.xlsx.writeBuffer().then(buffer => {
+      saveAs(new Blob([buffer], { type: "application/octet-stream" }), fileName + ".xlsx");
+    });
+  };
+
+  const getColumnStyle = (worksheet: any, colNuame: string, key: string, width: number, style: any = {}) => {
+    const col = worksheet.getColumn(colNuame);
+    col.width = width;
+    col.key = key;
+    col.style = {
+      font: state.default_font,
+      alignment: { ...style, ...state.default_alignment }
+    };
+  };
+
+  const setHeaderStyle = (
+    worksheet: any,
+    rowIndex: Number,
+    mergeCellName: string,
+    value: string,
+    height: number,
+    fontStyle: any = state.default_font,
+    alignment: any = {}
+  ) => {
+    worksheet.mergeCells(mergeCellName);
+    let colName = mergeCellName.split(":")[0];
+    const cellB1 = worksheet.getCell(colName);
+
+    cellB1.value = value;
+    // 设置第一行的单元格样式
+    cellB1.font = fontStyle;
+    cellB1.alignment = { ...state.default_alignment, ...alignment };
+    worksheet.getRow(rowIndex).height = height; // 设置行高
+  };
+
+  /**
+   * @description 取上一个字母(从A到Z)
+   * @param letter 当前字母
+   * @returns, z -> y, a -> z, b -> a
+   */
+  const getPreLetter = letter => {
+    let code = letter.charCodeAt(0);
+    if (code === 65) {
+      return String.fromCharCode(code + 25);
+    } else {
+      return String.fromCharCode(code - 1);
+    }
+  };
+
+  /**
+   * @description 合并单元格
+   */
+  const toMergeCells = (worksheet: any, field: string, cellname: string, startRowIndex: number) => {
+    // label列内容相同时合并单元格
+    let same = 0;
+    state.tableData.map((t, i) => {
+      // label列内容相同的时候,多行合并单元格
+      if (i > 0 && t[field] && t[field] === state.tableData[i - 1][field]) {
+        same++;
+      } else {
+        if (same > 0) {
+          worksheet.mergeCells(`${cellname}${startRowIndex + i - 1}:${cellname}${startRowIndex + i - 1 - same}`);
+        }
+        same = 0;
+      }
+    });
+  };
+
   return {
     ...toRefs(state),
     wf_retrieve_qingdan,
-    toExcelQuote
+    toExcelQuote,
+    toExcelQuoteNew
   };
 };

+ 44 - 0
JLHWEB/src/views/quote/mattressQuote/hooks/index.tsx

@@ -4696,6 +4696,50 @@ export const useHooks = (t?: any) => {
       editRender: {
         name: "input"
       }
+    },
+    {
+      title: "标准\r\n成本金额",
+      field: "dannum2_rate",
+      datatype: "number",
+      limited: () => {
+        return userInfo.usermode != 0;
+      },
+      render: (scope: any) => {
+        return formatCutNumber({ val: floatMul(scope.row.costamt, 1 + scope.row.dannum2_rate) });
+      }
+    },
+    {
+      title: "散单\r\n成本金额",
+      field: "dannum1_rate",
+      datatype: "number",
+      limited: () => {
+        return userInfo.usermode != 0;
+      },
+      render: (scope: any) => {
+        return formatCutNumber({ val: floatMul(scope.row.costamt, 1 + scope.row.dannum1_rate) });
+      }
+    },
+    {
+      title: "大单\r\n成本金额",
+      field: "dannum3_rate",
+      datatype: "number",
+      limited: () => {
+        return userInfo.usermode != 0;
+      },
+      render: (scope: any) => {
+        return formatCutNumber({ val: floatMul(scope.row.costamt, 1 + scope.row.dannum3_rate) });
+      }
+    },
+    {
+      title: "小单\r\n成本金额",
+      field: "dannum4_rate",
+      datatype: "number",
+      limited: () => {
+        return userInfo.usermode != 0;
+      },
+      render: (scope: any) => {
+        return formatCutNumber({ val: floatMul(scope.row.costamt, 1 + scope.row.dannum4_rate) });
+      }
     }
   ];
 

+ 12 - 0
JLHWEB/src/views/saleprice/dept/hooks/index.tsx

@@ -240,6 +240,18 @@ export const useHooks = (t?: any) => {
         span: 2,
         editable: ALLOW_EDIT_STATE
       }
+    },
+    {
+      field: "taxes_rate",
+      title: "非报关产品税金补偿",
+      basicinfo: {
+        el: "input",
+        props: {
+          type: "number"
+        },
+        span: 2,
+        editable: ALLOW_EDIT_STATE
+      }
     }
   ];