Browse Source

1. 优化

MONSTER-ygh 10 months ago
parent
commit
ac87c580b7
21 changed files with 872 additions and 35 deletions
  1. BIN
      src/assets/images/login-prod.jpg
  2. 1 0
      src/myComponents/selectMoreBox.vue
  3. 23 4
      src/views/tourism/financialManagement/ticketRefundOrder.vue
  4. 1 1
      src/views/tourism/marketingActivities/couponAllocationSet.vue
  5. 4 4
      src/views/tourism/marketingActivities/couponManagement.vue
  6. 2 2
      src/views/tourism/marketingActivities/couponVerification.vue
  7. 4 4
      src/views/tourism/marketingActivities/eventManagement.vue
  8. 1 0
      src/views/tourism/marketingActivities/model/selectCouponManagement.vue
  9. 1 0
      src/views/tourism/marketingActivities/model/selectMemberInformation.vue
  10. 1 0
      src/views/tourism/marketingActivities/model/selectMembershipLevel.vue
  11. 1 0
      src/views/tourism/marketingActivities/model/selectMoreBox.vue
  12. 1 0
      src/views/tourism/marketingActivities/model/selectTicketOrders.vue
  13. 3 3
      src/views/tourism/marketingActivities/templateManagement.vue
  14. 2 2
      src/views/tourism/membershipManagement/electronicMembership/memberInformation.vue
  15. 9 1
      src/views/tourism/orderManagement/ticketOrdersAll/detailsBox/ticketOrdersDetails.vue
  16. 1 1
      src/views/tourism/orderManagement/ticketOrdersAll/ticketOrders.vue
  17. 60 5
      src/views/tourism/productManagement/formBox/scenicAreaTicketsSpecsForm.vue
  18. 351 0
      src/views/tourism/scenicAreaManagement/contentManagement/detailsBox/suggestionsDetails.vue
  19. 345 0
      src/views/tourism/scenicAreaManagement/contentManagement/formBox/suggestionsForm.vue
  20. 58 6
      src/views/tourism/scenicAreaManagement/contentManagement/suggestions.vue
  21. 3 2
      src/views/tourism/scenicAreaManagement/navigationManagement/scenicGuide.vue

BIN
src/assets/images/login-prod.jpg


+ 1 - 0
src/myComponents/selectMoreBox.vue

@@ -352,6 +352,7 @@ export default {
         },
         /** 点击页码  */
         handleCurrentChange(val) {
+            this.page.pageNum = val
             this.listLoading = true
             this.listUser()
         },

+ 23 - 4
src/views/tourism/financialManagement/ticketRefundOrder.vue

@@ -63,6 +63,16 @@
         </el-form>
 
         <el-row :gutter="10" class="mb8">
+          <el-col :span="1.5">
+            <el-button
+              type="warning"
+              plain
+              icon="el-icon-download"
+              size="mini"
+              @click="handleExport"
+              v-hasPermi="configPermi.export"
+            >导出</el-button>
+          </el-col>
           <right-toolbar :showSearch.sync="showSearch" @queryTable="getList" :columns="columns"></right-toolbar>
         </el-row>
 
@@ -154,14 +164,14 @@ export default {
         delect: [''], // 删除权限
         edit: [''], // 编辑权限
         upload: [''],// 导入权限
-        export: [''],// 导出权限
+        export: ['financialManagement:ticketRefundOrder:export'],// 导出权限
       },
       configUrl: {
         list: '/order/orderRefund/pageList', // 列表地址
         delect: '', // 删除地址
         upload: '',// 导入地址
         download:'', // 下载模板地址
-        export: '',// 导出地址
+        export: '/order/orderRefund/exportExcel',// 导出地址
         edit: '/merchant/merchantTourRoute/updateStatus', // 编辑地址
       },
       // 遮罩层
@@ -294,8 +304,17 @@ export default {
     },
     /** 导出按钮操作 */
     handleExport() {
-      this.download(this.configUrl.export, {
-        ...this.queryParams
+      
+      let params = JSON.parse(JSON.stringify({
+          ...this.queryParams,
+          refundTimeStart: this.queryParams.time&&this.queryParams.time[0]?this.queryParams.time[0]:null,
+          refundTimeEnd: this.queryParams.time&&this.queryParams.time[1]?this.queryParams.time[1]:null,
+      }))
+      delete params.time;
+      delete params.pageSize;
+      delete params.pageNum;
+      this.downloadGet(this.configUrl.export, {
+        ...params
       }, `${this.title }_${new Date().getTime()}.xlsx`)
     },
     /** 导入按钮操作 */

+ 1 - 1
src/views/tourism/marketingActivities/couponAllocationSet.vue

@@ -142,7 +142,7 @@ import {
             upload: [''],// 导入权限
             export: [''],// 导出权限http://localhost/scenicAreaManagement/contentManagement/scenicAreaManagement/contentManagement/suggestions
             release: [''],
-            seva: ['pointsManagement:IntegralRecord:seva'] // 保存
+            seva: ['tourism:marketingActivities:couponAllocationSet:edit'] // 保存
         },
         configUrl: {
             details: '/merchant/merchantCouponConfig/getInfo', // 详情地址

+ 4 - 4
src/views/tourism/marketingActivities/couponManagement.vue

@@ -151,10 +151,10 @@
       return {
         title: "优惠券管理",// 通用标题
         configPermi: {
-          add: [''], // 新增权限
-          details: ['electronicMembership:memberInformation:details'], // 详情权限
-          delect: ['electronicMembership:memberInformation:delect'], // 删除权限
-          edit: [''], // 编辑权限
+          add: ['tourism:marketingActivities:couponManagement:add'], // 新增权限
+          details: ['tourism:marketingActivities:couponManagement:details'], // 详情权限
+          delect: ['tourism:marketingActivities:couponManagement:delect'], // 删除权限
+          edit: ['tourism:marketingActivities:couponManagement:edit'], // 编辑权限
           upload: [''],// 导入权限
           export: [''],// 导出权限
         },

+ 2 - 2
src/views/tourism/marketingActivities/couponVerification.vue

@@ -122,8 +122,8 @@
         title: "优惠券核销",// 通用标题
         configPermi: {
           add: [''], // 新增权限
-          details: ['electronicMembership:memberInformation:details'], // 详情权限
-          delect: ['electronicMembership:memberInformation:delect'], // 删除权限
+          details: ['tourism:marketingActivities:couponVerification:details'], // 详情权限
+          delect: [''], // 删除权限
           edit: [''], // 编辑权限
           upload: [''],// 导入权限
           export: [''],// 导出权限

+ 4 - 4
src/views/tourism/marketingActivities/eventManagement.vue

@@ -111,10 +111,10 @@
       return {
         title: "活动管理",// 通用标题
         configPermi: {
-          add: [''], // 新增权限
-          details: ['electronicMembership:memberInformation:details'], // 详情权限
-          delect: ['electronicMembership:memberInformation:delect'], // 删除权限
-          edit: [''], // 编辑权限
+          add: ['tourism:marketingActivities:eventManagement:add'], // 新增权限
+          details: ['tourism:marketingActivities:eventManagement:details'], // 详情权限
+          delect: ['tourism:marketingActivities:eventManagement:delect'], // 删除权限
+          edit: ['tourism:marketingActivities:eventManagement:edit'], // 编辑权限
           upload: [''],// 导入权限
           export: [''],// 导出权限
         },

+ 1 - 0
src/views/tourism/marketingActivities/model/selectCouponManagement.vue

@@ -324,6 +324,7 @@ export default {
         },
         /** 点击页码  */
         handleCurrentChange(val) {
+            this.page.pageNum = val
             this.listLoading = true
             this.listUser()
         },

+ 1 - 0
src/views/tourism/marketingActivities/model/selectMemberInformation.vue

@@ -320,6 +320,7 @@ export default {
         },
         /** 点击页码  */
         handleCurrentChange(val) {
+            this.page.pageNum = val
             this.listLoading = true
             this.listUser()
         },

+ 1 - 0
src/views/tourism/marketingActivities/model/selectMembershipLevel.vue

@@ -320,6 +320,7 @@ export default {
         },
         /** 点击页码  */
         handleCurrentChange(val) {
+            this.page.pageNum = val
             this.listLoading = true
             this.listUser()
         },

+ 1 - 0
src/views/tourism/marketingActivities/model/selectMoreBox.vue

@@ -352,6 +352,7 @@ export default {
         },
         /** 点击页码  */
         handleCurrentChange(val) {
+            this.page.pageNum = val
             this.listLoading = true
             this.listUser()
         },

+ 1 - 0
src/views/tourism/marketingActivities/model/selectTicketOrders.vue

@@ -320,6 +320,7 @@ export default {
         },
         /** 点击页码  */
         handleCurrentChange(val) {
+            this.page.pageNum = val
             this.listLoading = true
             this.listUser()
         },

+ 3 - 3
src/views/tourism/marketingActivities/templateManagement.vue

@@ -94,9 +94,9 @@
       return {
         title: "模板管理",// 通用标题
         configPermi: {
-          add: [''], // 新增权限
-          details: ['electronicMembership:memberInformation:details'], // 详情权限
-          delect: ['electronicMembership:memberInformation:delect'], // 删除权限
+          add: ['tourism:marketingActivities:templateManagement:add'], // 新增权限
+          details: ['tourism:marketingActivities:templateManagement:details'], // 详情权限
+          delect: ['tourism:marketingActivities:templateManagement:delect'], // 删除权限
           edit: [''], // 编辑权限
           upload: [''],// 导入权限
           export: [''],// 导出权限

+ 2 - 2
src/views/tourism/membershipManagement/electronicMembership/memberInformation.vue

@@ -92,7 +92,7 @@
   
           <el-table v-loading="loading" :data="tableList" @selection-change="handleSelectionChange">
             <el-table-column type="index" label="序号" align="center"  />
-            <el-table-column label="用户名" align="center" key="realName" prop="realName" v-if="columns[0].visible" :show-overflow-tooltip="true" />
+            <el-table-column label="用户名" align="center" key="name" prop="name" v-if="columns[0].visible" :show-overflow-tooltip="true" />
             <el-table-column label="会员号" align="center" key="memberCode" prop="memberCode" v-if="columns[1].visible" :show-overflow-tooltip="true" />
             <el-table-column label="会员类型" align="center" key="type" prop="type" v-if="columns[2].visible" :show-overflow-tooltip="true">
               <template slot-scope="scope">
@@ -187,7 +187,7 @@
           delect: ['electronicMembership:memberInformation:delect'], // 删除权限
           edit: [''], // 编辑权限
           upload: [''],// 导入权限
-          export: [''],// 导出权限
+          export: ['electronicMembership:memberInformation:export'],// 导出权限
           resetPwd: ['electronicMembership:memberInformation:resetPwd'], // 设置积分
           AuthRole: ['electronicMembership:memberInformation:AuthRole'], // 设置储值
         },

+ 9 - 1
src/views/tourism/orderManagement/ticketOrdersAll/detailsBox/ticketOrdersDetails.vue

@@ -33,7 +33,7 @@
           </div>
 
           <div style="display: flex;">
-            <el-form-item label="手机号:">
+            <el-form-item label="购票人手机号:">
               <span style="display: block; min-width: 250px;">{{ form.memberMobile }}</span>
             </el-form-item>
             <el-form-item label="身份证号:">
@@ -43,6 +43,14 @@
               <span style="display: block; min-width: 250px;">{{ form.scenicName }}</span>
             </el-form-item>
           </div>
+          <div style="display: flex;">
+            <el-form-item label="联系人:">
+              <span style="display: block; min-width: 250px;">{{  form.purchaser && form.purchaser.name }}</span>
+            </el-form-item>
+            <el-form-item label="联系人手机号:">
+              <span style="display: block; min-width: 250px;">{{ form.purchaser && form.purchaser.mobile }}</span>
+            </el-form-item>
+          </div>
 
           <div style="display: flex;">
             <el-form-item label="游玩日期:">

+ 1 - 1
src/views/tourism/orderManagement/ticketOrdersAll/ticketOrders.vue

@@ -214,7 +214,7 @@
           delect: [''], // 删除权限
           edit: [''], // 编辑权限
           upload: [''],// 导入权限
-          export: [''],// 导出权限
+          export: ['ticketOrdersAll:ticketOrders:export'],// 导出权限
         },
         configUrl: {
           list: '/order/orderInfo/list', // 列表地址

+ 60 - 5
src/views/tourism/productManagement/formBox/scenicAreaTicketsSpecsForm.vue

@@ -49,8 +49,8 @@
                 align="center"
               >
                 <template slot-scope="scope">
-                  <el-button type="primary" @click="getTableDeatilsFun(scope.row)" icon="el-icon-edit" circle></el-button>
-                  <el-button type="danger" @click="handleDelete(scope.row)" icon="el-icon-delete" circle></el-button>
+                  <el-button type="primary" size="mini" @click="getTableDeatilsFun(scope.row)" icon="el-icon-edit" circle></el-button>
+                  <el-button type="danger" size="mini" @click="handleDelete(scope.row)" icon="el-icon-delete" circle></el-button>
                 </template>
               </el-table-column>
             </el-table>
@@ -65,6 +65,31 @@
               <el-form-item label="规格描述:" prop="goodsSnapshot">
                 <el-input style="width: 100%;" v-model="form.goodsSnapshot" placeholder="请输入规格描述" maxlength="50" show-word-limit />
               </el-form-item>
+              <el-form-item label="门票限购:" prop="daySaleRadio">
+                <el-radio-group v-model="form.daySaleRadio" @input="value => radioInput('daySaleDay',value)">
+                  <div style="display: flex;flex-direction: column;padding-top: 10px;">
+                    <div>
+                      <el-radio label="-1">不限</el-radio>
+                    </div>
+                    <div style="display: flex;align-items: center;margin-top: 25px;">
+                      <el-radio style="display: flex;align-items: center;" label="-2">
+                        <div style="display: flex;align-items: center;"> 
+                          <el-form-item label="" label-width="0" :prop="'daySaleDay'">
+                            <span>同一天最多只能购买</span>
+                            <el-input-number 
+                              :disabled="form.daySaleRadio!=-2"
+                              v-model="form.daySaleDay" 
+                              placeholder="请输入限购张数"
+                              controls-position="right">
+                            </el-input-number>
+                            <span>张</span>
+                          </el-form-item>
+                        </div>
+                      </el-radio>
+                    </div>
+                  </div>
+                </el-radio-group>
+              </el-form-item>
               <el-form-item label="日期类型:" :prop="'dayTypeRadio'">
                 <div style="display: flex;align-items: center;">
                   <el-radio-group v-model="form.dayTypeRadio" @input="value => radioInput('dayType',value)">
@@ -347,11 +372,14 @@ export default {
       rules: {
         goodsName: [{ required: true, message: "请输入票种规格名称", trigger: ["change","blur"] }],
         goodsSnapshot: [{ required: true, message: "请输入规格描述", trigger: ["change","blur"] }],
-       
+        
+        daySaleRadio: [{ required: true, message: "请选择门票限购", trigger: ["change","blur"] }],
+        daySaleDay: [{ required: false, message: "请输入限购张数", trigger: ["change","blur"] }],
+
         dayTypeRadio: [{ required: true, message: "请选择日期类型", trigger: ["change","blur"] }],
         dayType: [{ required: false, message: "请选择时间范围", trigger: ["change","blur"] }],
         
-        useExpireDateRadio: [{ required: true, message: "请选择日期", trigger: ["change","blur"] }],
+        useExpireDateRadio: [{ required: true, message: "请选择游玩日期", trigger: ["change","blur"] }],
         useExpireDateDay: [{ required: false, message: "请输入天数", trigger: ["change","blur"] }],
         useExpireDateTime: [{ required: false, message: "请选择时间", trigger: ["change","blur"] }],
 
@@ -436,6 +464,18 @@ export default {
             // useExpireDate: res.data.useExpireDate?res.data.useExpireDate.type:'1',
             // backStatusRadio: res.data.goodsPerformRefundRule?'-2':'-1',
           }
+
+          if(res.data.daySale && res.data.daySale != 0 && res.data.daySale != -1){
+            obj['daySaleRadio'] = '-2'
+            obj['daySaleDay'] = res.data.daySale
+          }else if(!res.data.daySale && res.data.daySale != 0){
+            obj['daySaleRadio'] = null
+            obj['daySaleDay'] = undefined
+          }else {
+            obj['daySaleRadio'] = '-1'
+            obj['daySaleDay'] = undefined
+          }
+
           if(res.data.goodsPerformRefundRule && res.data.goodsPerformRefundRule != 0) {
             obj['backStatusRadio'] = '-2'
             obj['backStatusDay'] = res.data.goodsPerformRefundRule.days
@@ -487,6 +527,7 @@ export default {
           }else {
             obj['areaRadio'] = "-1"
           }
+          this.radioInput('daySaleDay',obj.daySaleRadio)
           this.radioInput('dayType',obj.dayTypeRadio)
           this.radioInputs(obj.useExpireDateRadio)
           this.radioInputss(obj.backStatusRadio)
@@ -515,7 +556,7 @@ export default {
      */
     submitForm(type) {
       console.log("dsfsfds=======",type,this.form)
-      this.$refs["form"].validate(valid => {
+      this.$refs["form"].validate((valid,object) => {
         if (valid) {
           this.loadingText = "提交数据中..."
           this.loading = true
@@ -535,6 +576,13 @@ export default {
             this.$message.error(`${ this.form.goodsId ? '编辑':'新增' }失败!!!`);
             this.loading = false
           })
+        }else {
+          console.log("object===",object)
+          let srt = ''
+          Object.keys(object).forEach((item,index)=>{
+            srt = srt  +','+object[item][0].message
+          })
+          this.$message.error(`[${srt}]`);
         }
       });
     },
@@ -558,6 +606,11 @@ export default {
     },
     resetFormData(type){
       let params = JSON.parse(JSON.stringify(this.form))
+      if(params.daySaleRadio == -1) { // 日期类型
+        params['daySale'] = -1
+      }else {
+        params['daySale'] = params.daySaleDay
+      }
 
       if(params.dayTypeRadio == -1) { // 日期类型
         params.dayType = 0
@@ -608,6 +661,8 @@ export default {
         params['goodsId'] = params.goodsId
       }
       params['performId'] = this.performId
+      delete params.daySaleRadio
+      delete params.daySaleDay
       delete params.dayTypeRadio
       delete params.useExpireDateRadio
       delete params.backStatusRadio

+ 351 - 0
src/views/tourism/scenicAreaManagement/contentManagement/detailsBox/suggestionsDetails.vue

@@ -0,0 +1,351 @@
+<template>
+  <el-dialog
+    :title="title"
+    :visible.sync="open"
+    width="60%"
+    append-to-body
+    :close-on-click-modal="false"
+    @close="cancel"
+  >
+    <div class="form-dialog-box"
+    v-loading="loading"
+    :element-loading-text="loadingText"
+    element-loading-spinner="el-icon-loading"
+    element-loading-background="rgba(0, 0, 0, 0)">
+      <div
+        v-loading="loading"
+        :element-loading-text="''"
+        element-loading-spinner="''"
+        element-loading-background="rgba(0, 0, 0, 0.8)"
+        >
+        <el-form :model="form" ref="form" :rules="rules" label-width="100px">
+          <div style="display: flex;">
+            <el-form-item label="姓名:" prop="contactsName">
+              <span style="min-width: 350px;display: inline-block;">{{ form.contactsName }}</span>
+            </el-form-item>
+            <el-form-item label="联系电话:" prop="contactsMobile">
+              <span style="min-width: 350px;display: inline-block;">{{ form.contactsMobile }}</span>
+            </el-form-item>
+          </div>
+          <el-form-item label="留言内容:" prop="content">
+            <span>{{ form.content }}</span>
+          </el-form-item>
+          <div style="display: flex;">
+            <el-form-item label="类型:" prop="type">
+              <span style="min-width: 350px;display: inline-block;"><dict-tag :options="dict.type.tourism_suggestions_type" :value="form.type"/></span>
+            </el-form-item>
+            <el-form-item label="留言时间:" prop="createTime">
+              <span style="min-width: 350px;display: inline-block;">{{ form.createTime }}</span>
+            </el-form-item>
+          </div>
+          <div style="display: flex;">
+            <el-form-item label="状态:" prop="status">
+              <span style="min-width: 350px;display: inline-block;"><dict-tag :options="dict.type.tourism_suggestions_status" :value="form.status"/></span>
+            </el-form-item>
+            <el-form-item label="处理时间:" v-if="form.status == 1" prop="answerTime">
+              <span style="min-width: 350px;display: inline-block;">{{ form.answerTime }}</span>
+            </el-form-item>
+          </div>
+          <el-form-item label="回复内容:" v-if="form.status == 1" prop="answerContent">
+            <span>{{ form.answerContent }}</span>
+          </el-form-item>
+        </el-form>
+      </div>
+    </div>
+    <span slot="footer" class="dialog-footer" v-if="formStatus==1">
+      <el-button @click="cancel">关闭</el-button>
+    </span>
+    <!-- 添加或修改对话框 End -->
+  </el-dialog>
+</template>
+
+<script>
+import { 
+  getTableDeatilsByIdApi,
+  addTableApi
+ } from '@/api/CURD'
+export default {
+  name: "addAndEdit",
+  dicts: ['tourism_suggestions_type','tourism_suggestions_status'],
+  data() {
+    return {
+      title: "",
+      model: "", // EDIT: 编辑模式 ADD : 新增模式  EDITInit : 编辑模式(需要请求详情)
+      open: false,
+      loading: false,
+      loadingText: "拼命加载数据中...",
+      formStatus: null, // 0/null : 加载中 1 : 获取详情成功 2  : 获取详情失败 
+      configUrl: {
+        add: '', // 新增地址
+        details: '/member/memberSuggestion/selectById', // 详情地址
+        edit: '', // 编辑地址
+      },
+      form: {
+        id: undefined,
+      },
+      rules: {
+        contactsName: [{ required: false, message: "请输入姓名", trigger: ["change","blur"] }],
+        contactsMobile: [{ required: false, message: "请输入联系电话", trigger: ["change","blur"] }],
+        content: [{ required: false, message: "请输入留言内容", trigger: ["change","blur"] }],
+        type: [{ required: false, message: "请选择类型", trigger: ["change","blur"] }],
+        createTime: [{ required: false, message: "请选择留言时间", trigger: ["change","blur"] }],
+        status: [{ required: false, message: "请选择状态", trigger: ["change","blur"] }],
+        answerTime: [{ required: false, message: "请选择处理时间", trigger: ["change","blur"] }],
+        answerContent: [{ required: false, message: "请输入回复内容", trigger: ["change","blur"] }],
+      },
+    };
+  },
+  methods: {
+    async initData(title , model,row){
+      this.title = title
+      this.open = true
+      this.loadingText = "拼命加载数据中..."
+      this.loading = true
+      this.model = model
+      this.formStatus = 0
+      if(model=='ADD') { // 新增
+        this.$set(this,'form',row)
+        this.formStatus = 1
+      }else if(model=='EDIT') { // 新增
+        let obj = {
+          ...row
+        }
+        this.$set(this,'form',obj)
+        this.formStatus = 1
+      }else if(model=='EDITInit' || model=='DEATILSInit') { // 新增 或 详情
+        await this.getTableDeatilsFun(row)
+      }
+      this.loading = false
+      this.$nextTick(()=>{
+        if(this.$refs["form"]) {
+          this.$refs["form"].clearValidate();
+        }
+      })
+    },
+    /** 获取详情 */
+    async getTableDeatilsFun(row) {
+      const id = row.id
+      this.loading = true
+      try {
+        let res = await getTableDeatilsByIdApi(this.configUrl.details,{id})
+        if(res.code == 200) {
+          let obj = {
+            ...res.data
+          }
+          this.$set(this,'form',JSON.parse(JSON.stringify(obj)))
+          this.formStatus = 1
+        }else {
+          this.$message.error('获取详情失败!!!');
+          this.formStatus = 2
+          this.loading = false
+          this.open = false;
+        }
+        this.loading = false
+      } catch (error) {
+        console.error('获取详情失败!!!!',error)
+        this.formStatus = 2
+        this.loading = false
+        this.open = false;
+      }
+    },
+    /**
+     * 保存
+     * @date 2023-11-22
+     * @returns {any}
+     */
+    submitForm() {
+      this.$refs["form"].validate(valid => {
+        if (valid) {
+          this.loadingText = "提交数据中..."
+          this.loading = true
+          if (this.model != 'ADD') {
+            addTableApi(
+              this.configUrl.edit,{
+                ...this.form
+              }).then(response => {
+              this.$modal.msgSuccess("修改成功");
+              this.loading = false
+              this.open = false;
+              this.$emit('refresh')
+            }).catch(()=>{
+              this.$message.error("修改失败!!!");
+              this.loading = false
+            })
+          } else {
+            addTableApi(this.configUrl.edit,{
+                ...this.form
+              }).then(response => {
+              this.$modal.msgSuccess("新增成功");
+              this.loading = false
+              this.open = false;
+              this.$emit('refresh')
+            }).catch(()=>{
+              this.$message.error("新增失败!!!");
+              this.loading = false
+            })
+          }
+        }
+      });
+    },
+    /**
+     * 重置
+     * @date 2023-11-22
+     * @returns {any}
+     */
+    reset() {
+      if(this.$refs["form"]) {
+        this.$refs["form"].clearValidate();
+      }
+    },
+    /**
+     * 关闭弹框
+     * @date 2023-11-22
+     * @returns {any}
+     */
+    cancel() {
+      this.reset();
+      this.open = false;
+    },
+  },
+};
+</script>
+
+<style lang="scss" scoped>
+.form-dialog-box {
+  padding: 0 30px;
+  padding: 0 30px;
+  min-height: 50vh;
+  max-height: 65vh;
+  overflow-y: auto;
+  >div {
+    width: 100%;
+    min-height: 50vh;
+  }
+  .form-title {
+    padding: 0 0 10px 0;
+    span {
+      display: flex;
+      color: rgba(65,80,88,1);
+      font-size: 16px;
+      font-family: SourceHanSansSC;
+      font-weight: 700;
+      line-height: 23px;
+      border-left: 4px solid rgb(22, 132, 252);
+      padding-left: 10px;
+    }
+    
+  }
+  ::v-deep .ql-editor {
+    height: 400px;
+  }
+  .upload-btn {
+    width: 100px;
+    height: 100px;
+    background-color: #fbfdff;
+    border: dashed 1px #c0ccda;
+    border-radius: 5px;
+    i {
+      font-size: 30px;
+      margin-top: 20px;
+    }
+    &-text {
+      margin-top: -10px;
+    }
+  }
+  .avatar {
+    cursor: pointer;
+  }
+}
+.el-table{
+  .upload-btn {
+    width: 100px;
+    height: 100px;
+    background-color: #fbfdff;
+    border: dashed 1px #c0ccda;
+    border-radius: 5px;
+    i {
+      font-size: 30px;
+      margin-top: 20px;
+    }
+    &-text {
+      margin-top: -10px;
+    }
+  }
+  .avatar {
+    cursor: pointer;
+  }
+}
+
+.area-container {
+  min-height: 400px;
+}
+
+::v-deep .area-wrap-city.el-cascader {
+  line-height: normal;
+  .el-input {
+    cursor: pointer;
+    width: 100% !important;
+    height: 28px !important;
+    .el-input__inner {
+      display: none !important;
+    }
+    span.el-input__suffix {
+      position: inherit !important;
+      i.el-input__icon {
+        line-height: inherit;
+        margin-left: 5px;
+      }
+    }
+
+    .el-input__wrapper {
+      box-shadow: none;
+      input {
+        display: none;
+      }
+    }
+  }
+
+  .el-cascader__tags {
+    display: none;
+  }
+}
+
+.area-city-popper {
+  .el-cascader-panel {
+    .el-scrollbar.el-cascader-menu {
+      .el-cascader-menu__wrap.el-scrollbar__wrap {
+        height: 315px;
+      }
+    }
+  }
+}
+
+::v-deep .avatar-uploader .el-upload {
+    border: 1px dashed #d9d9d9;
+    border-radius: 6px;
+    cursor: pointer;
+    position: relative;
+    overflow: hidden;
+  }
+  ::v-deep .avatar-uploader .el-upload:hover {
+    border-color: #409EFF;
+  }
+  ::v-deep .avatar-uploader-icon {
+    font-size: 28px;
+    color: #8c939d;
+    width: 100px;
+    height: 100px;
+    line-height: 100px;
+    text-align: center;
+  }
+  ::v-deep .avatar {
+    width: 100px;
+    height: 100px;
+    display: block;
+  }
+</style>
+<style>
+.custom-class-box {
+  z-index: 999999 !important;
+}
+</style>

+ 345 - 0
src/views/tourism/scenicAreaManagement/contentManagement/formBox/suggestionsForm.vue

@@ -0,0 +1,345 @@
+<template>
+  <el-dialog
+    :title="title"
+    :visible.sync="open"
+    width="60%"
+    append-to-body
+    :close-on-click-modal="false"
+    @close="cancel"
+  >
+    <div class="form-dialog-box"
+    v-loading="loading"
+    :element-loading-text="loadingText"
+    element-loading-spinner="el-icon-loading"
+    element-loading-background="rgba(0, 0, 0, 0)">
+      <div
+        v-loading="loading"
+        :element-loading-text="''"
+        element-loading-spinner="''"
+        element-loading-background="rgba(0, 0, 0, 0.8)"
+        >
+        <el-form :model="form" ref="form" :rules="rules" label-width="100px">
+          <div style="display: flex;">
+            <el-form-item label="姓名:" prop="contactsName">
+              <span style="min-width: 350px;display: inline-block;">{{ form.contactsName }}</span>
+            </el-form-item>
+            <el-form-item label="联系电话:" prop="contactsMobile">
+              <span style="min-width: 350px;display: inline-block;">{{ form.contactsMobile }}</span>
+            </el-form-item>
+          </div>
+          <el-form-item label="留言内容:" prop="content">
+            <span>{{ form.content }}</span>
+          </el-form-item>
+          <div style="display: flex;">
+            <el-form-item label="类型:" prop="type">
+              <span style="min-width: 350px;display: inline-block;"><dict-tag :options="dict.type.tourism_suggestions_type" :value="form.type"/></span>
+            </el-form-item>
+            <el-form-item label="留言时间:" prop="createTime">
+              <span style="min-width: 350px;display: inline-block;">{{ form.createTime }}</span>
+            </el-form-item>
+          </div>
+          <el-form-item label="回复内容:" prop="answerContent">
+            <el-input
+              type="textarea"
+              :rows="4"
+              placeholder="请输入回复内容"
+              v-model="form.answerContent">
+            </el-input>
+          </el-form-item>
+        </el-form>
+      </div>
+    </div>
+    <span slot="footer" class="dialog-footer" v-if="formStatus==1">
+      <el-button @click="cancel">取消</el-button>
+      <el-button
+        type="primary"
+        @click="submitForm"
+        :loading="loading"
+        element-loading-text="提交中..."
+        element-loading-spinner="el-icon-loading"
+        element-loading-background="rgba(0, 0, 0, 0.8)"
+      > 
+        {{ loading ? '提交中...' : '确认' }}
+      </el-button>
+    </span>
+    <!-- 添加或修改对话框 End -->
+  </el-dialog>
+</template>
+
+<script>
+import { 
+  getTableDeatilsByIdApi,
+  addTableApi
+ } from '@/api/CURD'
+export default {
+  name: "addAndEdit",
+  dicts: ['tourism_suggestions_type','tourism_suggestions_status'],
+  data() {
+    return {
+      title: "",
+      model: "", // EDIT: 编辑模式 ADD : 新增模式  EDITInit : 编辑模式(需要请求详情)
+      open: false,
+      loading: false,
+      loadingText: "拼命加载数据中...",
+      formStatus: null, // 0/null : 加载中 1 : 获取详情成功 2  : 获取详情失败 
+      configUrl: {
+        add: '/member/memberSuggestion/answer', // 新增地址
+        details: '/member/memberSuggestion/selectById', // 详情地址
+        edit: '/member/memberSuggestion/answer', // 编辑地址
+      },
+      form: {
+        id: undefined,
+      },
+      rules: {
+        contactsName: [{ required: false, message: "请输入姓名", trigger: ["change","blur"] }],
+        contactsMobile: [{ required: false, message: "请输入联系电话", trigger: ["change","blur"] }],
+        content: [{ required: false, message: "请输入留言内容", trigger: ["change","blur"] }],
+        type: [{ required: false, message: "请选择类型", trigger: ["change","blur"] }],
+        createTime: [{ required: false, message: "请选择留言时间", trigger: ["change","blur"] }],
+        status: [{ required: false, message: "请选择状态", trigger: ["change","blur"] }],
+        answerTime: [{ required: false, message: "请选择处理时间", trigger: ["change","blur"] }],
+        answerContent: [{ required: true, message: "请输入回复内容", trigger: ["change","blur"] }],
+      },
+    };
+  },
+  methods: {
+    async initData(title , model,row){
+      this.title = title
+      this.open = true
+      this.loadingText = "拼命加载数据中..."
+      this.loading = true
+      this.model = model
+      this.formStatus = 0
+      if(model=='ADD') { // 新增
+        this.$set(this,'form',row)
+        this.formStatus = 1
+      }else if(model=='EDIT') { // 新增
+        let obj = {
+          ...row
+        }
+        this.$set(this,'form',obj)
+        this.formStatus = 1
+      }else if(model=='EDITInit' || model=='DEATILSInit') { // 新增 或 详情
+        await this.getTableDeatilsFun(row)
+      }
+      this.loading = false
+      this.$nextTick(()=>{
+        if(this.$refs["form"]) {
+          this.$refs["form"].clearValidate();
+        }
+      })
+    },
+    /** 获取详情 */
+    async getTableDeatilsFun(row) {
+      const id = row.id
+      this.loading = true
+      try {
+        let res = await getTableDeatilsByIdApi(this.configUrl.details,{id})
+        if(res.code == 200) {
+          let obj = {
+            ...res.data
+          }
+          this.$set(this,'form',JSON.parse(JSON.stringify(obj)))
+          this.formStatus = 1
+        }else {
+          this.$message.error('获取详情失败!!!');
+          this.formStatus = 2
+          this.loading = false
+          this.open = false;
+        }
+        this.loading = false
+      } catch (error) {
+        console.error('获取详情失败!!!!',error)
+        this.formStatus = 2
+        this.loading = false
+        this.open = false;
+      }
+    },
+    /**
+     * 保存
+     * @date 2023-11-22
+     * @returns {any}
+     */
+    submitForm() {
+      this.$refs["form"].validate(valid => {
+        if (valid) {
+          this.loadingText = "提交数据中..."
+          this.loading = true
+          addTableApi(
+            this.configUrl.edit,{
+              id: this.form.id,
+              answerContent: this.form.answerContent,
+            }).then(response => {
+            this.$modal.msgSuccess("提交成功");
+            this.loading = false
+            this.open = false;
+            this.$emit('refresh')
+          }).catch(()=>{
+            this.$message.error("提交失败!!!");
+            this.loading = false
+          }) 
+        }
+      });
+    },
+    /**
+     * 重置
+     * @date 2023-11-22
+     * @returns {any}
+     */
+    reset() {
+      if(this.$refs["form"]) {
+        this.$refs["form"].clearValidate();
+      }
+    },
+    /**
+     * 关闭弹框
+     * @date 2023-11-22
+     * @returns {any}
+     */
+    cancel() {
+      this.reset();
+      this.open = false;
+    },
+  },
+};
+</script>
+
+<style lang="scss" scoped>
+.form-dialog-box {
+  padding: 0 30px;
+  padding: 0 30px;
+  min-height: 50vh;
+  max-height: 65vh;
+  overflow-y: auto;
+  >div {
+    width: 100%;
+    min-height: 50vh;
+  }
+  .form-title {
+    padding: 0 0 10px 0;
+    span {
+      display: flex;
+      color: rgba(65,80,88,1);
+      font-size: 16px;
+      font-family: SourceHanSansSC;
+      font-weight: 700;
+      line-height: 23px;
+      border-left: 4px solid rgb(22, 132, 252);
+      padding-left: 10px;
+    }
+    
+  }
+  ::v-deep .ql-editor {
+    height: 400px;
+  }
+  .upload-btn {
+    width: 100px;
+    height: 100px;
+    background-color: #fbfdff;
+    border: dashed 1px #c0ccda;
+    border-radius: 5px;
+    i {
+      font-size: 30px;
+      margin-top: 20px;
+    }
+    &-text {
+      margin-top: -10px;
+    }
+  }
+  .avatar {
+    cursor: pointer;
+  }
+}
+.el-table{
+  .upload-btn {
+    width: 100px;
+    height: 100px;
+    background-color: #fbfdff;
+    border: dashed 1px #c0ccda;
+    border-radius: 5px;
+    i {
+      font-size: 30px;
+      margin-top: 20px;
+    }
+    &-text {
+      margin-top: -10px;
+    }
+  }
+  .avatar {
+    cursor: pointer;
+  }
+}
+
+.area-container {
+  min-height: 400px;
+}
+
+::v-deep .area-wrap-city.el-cascader {
+  line-height: normal;
+  .el-input {
+    cursor: pointer;
+    width: 100% !important;
+    height: 28px !important;
+    .el-input__inner {
+      display: none !important;
+    }
+    span.el-input__suffix {
+      position: inherit !important;
+      i.el-input__icon {
+        line-height: inherit;
+        margin-left: 5px;
+      }
+    }
+
+    .el-input__wrapper {
+      box-shadow: none;
+      input {
+        display: none;
+      }
+    }
+  }
+
+  .el-cascader__tags {
+    display: none;
+  }
+}
+
+.area-city-popper {
+  .el-cascader-panel {
+    .el-scrollbar.el-cascader-menu {
+      .el-cascader-menu__wrap.el-scrollbar__wrap {
+        height: 315px;
+      }
+    }
+  }
+}
+
+::v-deep .avatar-uploader .el-upload {
+    border: 1px dashed #d9d9d9;
+    border-radius: 6px;
+    cursor: pointer;
+    position: relative;
+    overflow: hidden;
+  }
+  ::v-deep .avatar-uploader .el-upload:hover {
+    border-color: #409EFF;
+  }
+  ::v-deep .avatar-uploader-icon {
+    font-size: 28px;
+    color: #8c939d;
+    width: 100px;
+    height: 100px;
+    line-height: 100px;
+    text-align: center;
+  }
+  ::v-deep .avatar {
+    width: 100px;
+    height: 100px;
+    display: block;
+  }
+</style>
+<style>
+.custom-class-box {
+  z-index: 999999 !important;
+}
+</style>

+ 58 - 6
src/views/tourism/scenicAreaManagement/contentManagement/suggestions.vue

@@ -23,6 +23,16 @@
               </el-option>
             </el-select>
           </el-form-item>
+          <el-form-item label="状态" prop="status">
+            <el-select v-model="queryParams.status" clearable placeholder="请选择状态">
+              <el-option
+                v-for="dict in dict.type.tourism_suggestions_status"
+                :key="dict.value"
+                :label="dict.label"
+                :value="dict.value">
+              </el-option>
+            </el-select>
+          </el-form-item>
           <el-form-item>
             <el-button type="primary" icon="el-icon-search" size="mini" @click="handleQuery">搜索</el-button>
             <el-button icon="el-icon-refresh" size="mini" @click="resetQuery">重置</el-button>
@@ -40,7 +50,37 @@
             </template>
           </el-table-column>
           <el-table-column label="留言内容" align="center" key="content" prop="content" v-if="columns[2].visible" :show-overflow-tooltip="true" />
-          <el-table-column label="留言时间" align="center" key="createTime" prop="createTime" v-if="columns[3].visible" :show-overflow-tooltip="true" />
+          <el-table-column label="联系电话" align="center" key="contactsMobile" prop="contactsMobile" v-if="columns[3].visible" :show-overflow-tooltip="true" />
+          <el-table-column label="留言时间" align="center" key="createTime" prop="createTime" v-if="columns[4].visible" :show-overflow-tooltip="true" />
+          <el-table-column label="状态" align="center" key="status" prop="status" v-if="columns[5].visible" :show-overflow-tooltip="true">
+            <template slot-scope="scope">
+              <dict-tag :options="dict.type.tourism_suggestions_status" :value="scope.row.status"/>
+            </template>
+          </el-table-column>
+          <el-table-column
+            label="操作"
+            align="center"
+            width="160"
+            class-name="small-padding fixed-width"
+          >
+            <template slot-scope="scope" >
+              <el-button
+                size="mini"
+                type="text"
+                icon="el-icon-document"
+                @click="handleDetails(scope.row)"
+                v-hasPermi="configPermi.details"
+              >详情</el-button>
+              <el-button
+                size="mini"
+                type="text"
+                icon="el-icon-edit"
+                @click="handleUpdate(scope.row)"
+                v-if="scope.row.status != 1"
+                v-hasPermi="configPermi.edit"
+              >处理</el-button>
+            </template>
+          </el-table-column>
         </el-table>
 
         <pagination
@@ -52,6 +92,11 @@
         />
       </el-col>
     </el-row>
+
+    <!-- 详情 -->
+    <detailsBox ref="detailsBox" />
+    <!--  新增或修改  -->
+    <addAndEdit ref="addAndEdit" @refresh="getList" />
   </div>
 </template>
 
@@ -60,18 +105,23 @@ import {
   listTableApi, 
   delTableParamsApi, 
   } from "@/api/CURD";
+import detailsBox from './detailsBox/suggestionsDetails.vue'
+import addAndEdit from "./formBox/suggestionsForm.vue"
 export default {
   name: "User",
-  dicts: ['tourism_suggestions_type'],
-  components: {},
+  dicts: ['tourism_suggestions_type','tourism_suggestions_status'],
+  components: {
+    detailsBox,
+    addAndEdit
+  },
   data() {
     return {
       title: "投诉建议",// 通用标题
       configPermi: {
         add: [''], // 新增权限
-        details: [''], // 详情权限
+        details: ['scenicAreaManagement:contentManagement:suggestions:details'], // 详情权限
         delect: [''], // 删除权限
-        edit: [''], // 编辑权限
+        edit: ['scenicAreaManagement:contentManagement:suggestions:edit'], // 编辑权限
         upload: [''],// 导入权限
         export: [''],// 导出权限
       },
@@ -107,7 +157,9 @@ export default {
         { key: 0, label: `用户名称`, visible: true },
         { key: 2, label: `类型`, visible: true },
         { key: 3, label: `留言内容`, visible: true },
+        { key: 3.5, label: `联系电话`, visible: true },
         { key: 4, label: `留言时间`, visible: true },
+        { key: 5, label: `状态`, visible: true },
       ],
     };
   },
@@ -163,7 +215,7 @@ export default {
     /** 修改按钮操作 */
     handleUpdate(row) {
       if(this.$refs.addAndEdit) {
-        this.$refs.addAndEdit.initData(this.title + '编辑', "EDITInit",{...row})
+        this.$refs.addAndEdit.initData(this.title + '处理', "EDITInit",{...row})
       }
     },
     handleDetails(row){

+ 3 - 2
src/views/tourism/scenicAreaManagement/navigationManagement/scenicGuide.vue

@@ -33,7 +33,7 @@
               plain
               size="mini"
               @click="handleAddImage"
-              v-hasPermi="configPermi.add"
+              v-hasPermi="configPermi.addImage"
             >手绘图设置</el-button>
           </el-col>
           <right-toolbar :showSearch.sync="showSearch" @queryTable="getList" :columns="columns"></right-toolbar>
@@ -137,7 +137,8 @@ export default {
         edit: ['navigationManagement:scenicGuide:edit'], // 编辑权限
         upload: [''],// 导入权限
         export: [''],// 导出权限
-        distance: ['navigationManagement:scenicGuide:distance'] // 设置打卡距离
+        distance: ['navigationManagement:scenicGuide:distance'], // 设置打卡距离
+        addImage: ['navigationManagement:scenicGuide:addImage'] //手绘图
       },
       configUrl: {
         list: '/merchant/merchantMapMark/pageList', // 列表地址