保誠-保戶業務員媒合平台
Tomas
2024-01-11 756f8a63347119f511fc964bf1e2ff2417339c56
PAMapp/pages/agentInfo/edit/_agentNo.vue
@@ -1,35 +1,100 @@
<template>
    <div>
    <div class="edit-agent-info-page" v-if="!!agentInfo">
      <el-row
        type="flex"
        justify="center">
        <UiAvatar
          :size="150"
          :agentNo="agentInfo.agentNo">
        </UiAvatar>
        <EditConsultantAvatar
          :agentNo="agentInfo.agentNo"
          :photoBase64.sync="editInfoValue.photoBase64"/>
      </el-row>
      <el-row
      <!-- NOTE: 我認為編輯頁面不需要顯示 avgScore,先隱藏 [Tomas, 2022/2/10 13:55] -->
      <!-- <el-row
        type="flex"
        class="pt-10"
        justify="center"
        align="middle" v-if="!hideReviews">
        <!-- TODO:隱藏滿意度 -->
          <i class="pam-icon icon--primary icon-star"></i>
          <h3 class="mdTxt">{{ agentInfo.avgScore }}</h3>
      </el-row>
      </el-row> -->
      <el-row
      <!-- <el-row
        type="flex"
        class="pt-10"
        class="pam-paragraph"
        justify="center">
        <el-input class="mdTxt" v-model="editInfoValue.name"></el-input>
      </el-row> -->
       <el-row
        type="flex"
        class="pam-paragraph">
        <el-col :span="24" class="pam-field">
          <div class="pam-field__label pam-progress__label">
            <div>
              <div class="pam-field__title mb-10">
                <i class="pam-icon icon-avatar"
                  ></i>顯示名稱
                  <span class="hint text--bold" v-show="!editInfoValue.name">顯示名稱為必填</span>
              </div>
            </div>
            <el-input
              v-model="editInfoValue.name"
              :class="{'is-invalid': !nameValid}"
              maxlength="10"
              minlength="10"></el-input>
          </div>
        </el-col>
      </el-row>
      <el-row
        type="flex"
        class="pam-paragraph">
        <UiField :span="12" icon="agent" label="頭銜">
          <el-input  v-model="editInfoValue.title"></el-input>
        <el-col :span="24" class="pam-field">
          <div class="pam-field__label pam-progress__label">
            <div>
              <div class="pam-field__title mb-10">
                <i class="pam-icon icon-phone"
                  ></i>手機號碼
                  <span class="hint text--bold" v-show="!phoneValid">手機號碼格式有誤</span>
                  <span class="hint text--bold" v-show="editInfoValue.phoneNumber.length === 0">手機號碼為必填</span>
              </div>
            </div>
            <el-input
            v-model="editInfoValue.phoneNumber"
            :class="{'is-invalid': !phoneValid}"
            maxlength="10"
            minlength="10"></el-input>
          </div>
        </el-col>
      </el-row>
      <el-row
        type="flex"
        class="pam-paragraph">
        <el-col :span="24" class="pam-field">
          <div class="pam-field__label pam-progress__label">
            <div>
              <div class="pam-field__title mb-10">
                <i class="pam-icon icon-comment"
                  ></i>信箱
                  <span class="hint text--bold" v-show="!emailValid">信箱格式有誤</span>
                  <span class="hint text--bold" v-show="editInfoValue.email.length === 0">信箱為必填</span>
              </div>
            </div>
            <el-input
            v-model="editInfoValue.email"
            :class="{'is-invalid': !emailValid}"
            ></el-input>
          </div>
        </el-col>
      </el-row>
      <el-row
        type="flex"
        class="pam-paragraph">
        <UiField :span="24" icon="agent" label="頭銜">
          <el-input  v-model="editInfoValue.title" class="mt-10"></el-input>
        </UiField>
      </el-row>
@@ -37,7 +102,12 @@
        type="flex"
        class="pam-paragraph">
        <UiField icon="company" label="服務地區">
          <el-input  v-model="editInfoValue.serveArea"></el-input>
          <MultiSelectBtn class="mt-30"
            :mutiSelect.sync="editInfoValue.serveArea"
            :nameOfSelectAll="'全台'"
            :options="serveAreaOptions"
            >
          </MultiSelectBtn>
        </UiField>
      </el-row>
@@ -45,7 +115,7 @@
        type="flex"
        class="pam-paragraph">
        <UiField icon="address" label="公司地址">
          <el-input  v-model="editInfoValue.companyAddress"></el-input>
          <el-input  v-model="editInfoValue.companyAddress" class="mt-10"></el-input>
        </UiField>
      </el-row>
@@ -55,20 +125,18 @@
        <UiField :span="12" icon="time" label="最後上線時間">
          {{ agentInfo.latestLoginTime | formatDate }}
        </UiField>
        <UiField :span="12" icon="calender" label="服務資歷" style="display:flex">
          <el-input  v-model="editInfoValue.seniorityYear" class="seniority-input"></el-input>年
          <el-select  style="width:60px" v-model="editInfoValue.seniorityMonth" class="seniority-input">
            <el-option
              v-for="(month) in [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12]"
              :value="month"
              :key="month">
              {{ month }}
            </el-option>
          </el-select>月
        <UiField :span="12" icon="calender" label="到職日期" class="pam-editInfo-date-picker">
          <UiDatePicker
              :isFutureDateDisabled = true
              id="el-date-picker"
              class="mt-10"
              :defaultValue ="agentInfo.entryDate"
              @changeDate="onChangeDate($event)"
          ></UiDatePicker>
        </UiField>
      </el-row>
      <el-row
      <!-- <el-row
        type="flex"
        class="pam-paragraph">
        <el-col :span="24" class="pam-field">
@@ -87,38 +155,54 @@
            <el-progress :show-text="false" :stroke-width="15" :percentage="agentInfo.evaluation * 2"></el-progress>
          </div>
        </el-col>
      </el-row> -->
      <el-row
        type="flex"
        class="pam-paragraph">
        <el-col :span="24" class="pam-field">
          <div class="pam-field__label pam-progress__label">
            <div>
              <div class="pam-field__title">
                <i class="pam-icon icon-flag"
                  ></i>溝通風格  <span class="hint text--bold">(可複選,最多2項)</span>
              </div>
            </div>
            <MultiSelectBtn class="mt-30"
              :mutiSelect.sync="editInfoValue.communicationStyle"
              :options="agentCommunicationStyleList"
              :maxLength="2"
            >
            </MultiSelectBtn>
          </div>
        </el-col>
      </el-row>
      <el-row
        type="flex"
        class="pam-paragraph">
        <UiField icon="flag" label="溝通風格">
        <el-checkbox
            v-model="editInfoValue.communicationStyle"
            :label="communicateStyle"
            :key="index"
            v-for="(communicateStyle, index) in communicationStyleList">
          </el-checkbox>
        </UiField>
      </el-row>
      <el-row
        type="flex"
        class="pam-paragraph">
        <UiField icon="flag" label="專長領域">
          <el-checkbox
            v-model="editInfoValue.expertise"
            :label="expert"
            :key="index"
            v-for="(expert, index) in expertList">
          </el-checkbox>
        </UiField>
        <el-col :span="24" class="pam-field">
          <div class="pam-field__label pam-progress__label">
            <div>
              <div class="pam-field__title">
                <i class="pam-icon icon-flag"
                  ></i>專長領域  <span class="hint text--bold">(可複選)</span>
              </div>
            </div>
            <MultiSelectBtn class="mt-30"
              :mutiSelect.sync="editInfoValue.expertise"
              :options="agentExpertList"
            >
            </MultiSelectBtn>
          </div>
        </el-col>
      </el-row>
      <el-row
        type="flex"
        class="pam-paragraph">
        <UiField icon="comment" label="個人理念">
          <el-input type="textarea" autosize v-model="editInfoValue.concept"></el-input>
          <el-input type="textarea" autosize v-model="editInfoValue.concept" class="mt-10"></el-input>
        </UiField>
      </el-row>
@@ -126,7 +210,12 @@
        type="flex"
        class="pam-paragraph">
        <UiField icon="school" label="個人背景">
            <el-input type="textarea" autosize v-model="editInfoValue.experiences"></el-input>
            <el-input
              autosize
              type="textarea"
              class="mt-10"
              v-model="editInfoValue.experiences">
            </el-input>
        </UiField>
      </el-row>
@@ -134,7 +223,7 @@
        type="flex"
        class="pam-paragraph">
        <UiField icon="trophy" label="得獎經歷">
          <el-input type="textarea" autosize style="height:70%" v-model="editInfoValue.awards"></el-input>
          <el-input type="textarea" autosize style="height:70%" v-model="editInfoValue.awards" class="mt-10"></el-input>
        </UiField>
      </el-row>
@@ -174,8 +263,7 @@
<script lang="ts">
import { Context } from '@nuxt/types';
import { namespace } from 'nuxt-property-decorator';
import { Vue, Component } from 'vue-property-decorator';
import * as _ from "lodash";
import { Vue, Component, Prop } from 'vue-property-decorator';
import myConsultantService from '~/shared/services/my-consultant.service';
import accountSettingService from '~/shared/services/account-setting.service';
@@ -184,44 +272,94 @@
import { hideReviews } from '~/shared/const/hide-reviews';
import { AgentInfoSetting } from '~/shared/models/account.model';
import { Role } from '~/shared/models/enum/Role';
import { agentExpertList } from '~/shared/const/agent-expert-list';
import { agentCommunicationStyleList } from '~/shared/const/agent-communication-style-list';
import { taiwanCities } from '~/shared/const/taiwan-cities';
const localStorage = namespace('localStorage');
const localStorageTest = namespace('localStorage');
const loginStore = namespace('login.store');
@Component
export default class AgentInfoComponent extends Vue {
export default class AgentInfoEditComponent extends Vue {
  @localStorage.State('current_role')
  currentRole!:string | null;
  @localStorageTest.State
  current_role: any;
  _agentInfoSetting!: AgentInfoSetting;
  @loginStore.Action
  updateConsultantDetail!: (agentNo: string) => Promise<AgentInfo>;
  defaultAgentInfoSetting!: AgentInfoSetting;
  agentInfo!      : AgentInfo
  fieldInfoDesc   : string = '';
  fieldInfoTitle  : string = '';
  hideReviews     : boolean = hideReviews ;
  isAlertFieldInfo: boolean = false;
  isInfoUpdate    : boolean = false;
  serveAreaOptions: any[] = taiwanCities.map((city) => ({ title: city, label: city }));
  editInfoValue = {
    agentNo           : '',
    name              : '',
    expertise         : [] as string[],
    title             : '',
    serveArea         : '',
    serveArea         : [] as string[],
    companyAddress    : '',
    seniorityYear     : 1,
    seniorityMonth    : 0,
    concept           : '',
    experiences       : '',
    awards            : '',
    communicationStyle: [] as string[],
    photoBase64       : '',
    phoneNumber       : '',
    email             : '',
    entryDate         : '',
  };
  communicationStyleList: string[] = agentCommunicationStyleList;
  expertList: string[] = agentExpertList;
  role           = Role;
  agentExpertList = [
    {
        title:'健康與保障',
        label:'健康與保障'
    },
    {
        title:'子女教育',
        label:'子女教育'
    },
    {
        title:'資產規劃',
        label:'資產規劃'
    },
    {
        title:'樂活退休',
        label:'樂活退休'
    },
    {
        title:'保單健檢/規劃',
        label:'保單健檢/規劃'
    },
    {
        title:'分紅保單',
        label:'分紅保單'
    }];
  agentCommunicationStyleList = [
    {
        title:'謹慎務實',
        label:'謹慎務實'
    },
    {
        title:'明快主動',
        label:'明快主動'
    },
    {
        title:'耐心傾聽',
        label:'耐心傾聽'
    },
    {
        title:'健談風趣',
        label:'健談風趣'
    }];
  //////////////////////////////////////////////////////////////////////
@@ -234,54 +372,80 @@
  mounted(){
    this.setAgentInfo(this.agentInfo);
    const bodyEl = document.querySelector('body');
    bodyEl?.addEventListener('scroll', function() {
      const elDatePickerEl = document.querySelector('#el-date-picker');
      const elDatePickerPanelEl = document.querySelector('.el-picker-panel');
      if (elDatePickerPanelEl) {
        elDatePickerPanelEl['style']['z-index'] = 5;
        const elDatePickerOffsetTop = elDatePickerEl!.getBoundingClientRect().top;
        elDatePickerPanelEl!['style'].top = elDatePickerOffsetTop + 30 + 'px';
      }
    });
  }
  /////////////////////////////////////////////////////////////////////////////
  private setAgentInfo(agentInfo: AgentInfo): void {
    const [agentYear, _yearUnit , agentMonth, _monthUnit] =  agentInfo.seniority.split(" ");
    this._agentInfoSetting = {
      agentNo           : agentInfo.agentNo||'',
      name              : agentInfo.name || '',
      expertise         : agentInfo.expertise || [],
      title             : agentInfo.title || '',
      role              : agentInfo.role||'',
      serveArea         : agentInfo.serveArea || '',
      gender            : agentInfo.gender||'',
      phoneNumber       : agentInfo.phoneNumber||'',
      companyAddress    : agentInfo.companyAddress || '',
      seniorityYear     : agentYear? +agentYear : 0,
      seniorityMonth    : agentMonth ? +agentMonth : 0,
      concept           : agentInfo.concept || '',
      experiences       : agentInfo.experiences  || '',
      awards            : agentInfo.awards || '',
      communicationStyle: agentInfo.communicationStyle || '',
      photoBase64       : ''
    this.defaultAgentInfoSetting = {
      agentNo: agentInfo?.agentNo || '',
      name: agentInfo?.name || '',
      expertise: agentInfo?.expertise || [],
      title: agentInfo?.title || '',
      role: agentInfo?.role || '',
      serveArea: agentInfo?.serveArea?.split('、') || [],
      gender: agentInfo?.gender || '',
      phoneNumber: agentInfo?.phoneNumber || '',
      companyAddress: agentInfo?.companyAddress || '',
      concept: agentInfo?.concept || '',
      experiences: agentInfo?.experiences || '',
      awards: agentInfo?.awards || '',
      communicationStyle: agentInfo?.communicationStyle || '',
      photoBase64: '',
      email: agentInfo?.email || '',
      entryDate: agentInfo?.entryDate || '',
    };
    this.editInfoValue = {
      ...this._agentInfoSetting,
      expertise          : _.cloneDeep(this._agentInfoSetting.expertise),
      // TODO: 確認後端此欄位後端應改為以" , "隔開 [Tomas, 2021/12/28]
      communicationStyle : this._agentInfoSetting.communicationStyle.split('、'),
    }
      ...this.defaultAgentInfoSetting,
      expertise: JSON.parse(JSON.stringify(this.defaultAgentInfoSetting.expertise)),
      communicationStyle: this.defaultAgentInfoSetting.communicationStyle?.split('、') || [],
    };
  }
  //////////////////////////////////////////////////////////////////////
  editAgentInfoSetting(): void {
    const editSettingInfo: any = {
      ...this.editInfoValue,
      communicationStyle: this.editInfoValue.communicationStyle.join('、'),
    }
      serveArea: this.editInfoValue.serveArea.join('、'),
    };
    accountSettingService.editAgentInfoSetting(editSettingInfo).then((res: AgentInfoSetting) => {
      console.log(editSettingInfo)
      this.isInfoUpdate = true;
      this.updateConsultantDetail(editSettingInfo.agentNo);
    });
    this.isInfoUpdate = true;
  }
  onChangeDate(date: any): void {
    this.editInfoValue.entryDate = date;
  }
  backToInfo() {
    this.isInfoUpdate = false
    this.$router.push(`/agentInfo/${this.agentInfo.agentNo}`);
    }
  }
  selectCommunicationStyles(): void {
    if (this.editInfoValue.communicationStyle.length > 2) {
            this.editInfoValue.communicationStyle.shift();
        }
  }
  alertFieldInfo(field: string): void {
    this.isAlertFieldInfo = true;
    switch(field) {
@@ -289,13 +453,30 @@
        this.fieldInfoTitle = '匹配度';
        this.fieldInfoDesc = '匹配度是透過嚴選配對或快速篩選後,將每一位保險顧問資料進行比對後排序推薦給您的媒合數值,您可以作為選擇適合顧問的參考值。';
        break;
      case 'evaluation':
        this.fieldInfoTitle = '諮詢度表現';
        this.fieldInfoDesc = '諮詢度表現是將每一位保險顧問近一個月回覆諮詢數量進行比對後排序推薦給您的媒合數值。';
        break;
      // case 'evaluation':
      //   this.fieldInfoTitle = '諮詢度表現';
      //   this.fieldInfoDesc = '諮詢度表現是將每一位保險顧問近一個月回覆諮詢數量進行比對後排序推薦給您的媒合數值。';
      //   break;
    }
  }
  ////////////////////////////////////////////////////////////
  get nameValid(): boolean {
    return !!this.defaultAgentInfoSetting?.name;
  }
  get phoneValid(): boolean {
    const rule = /^09[0-9]{8}$/;
    return this.editInfoValue.phoneNumber
      ? rule.test(this.editInfoValue.phoneNumber) && this.editInfoValue.phoneNumber.length === 10
      : true;
  }
  get emailValid() {
      const rule = /^[a-zA-Z0-9._-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,4}$/;
      return this.editInfoValue.email ? rule.test(this.editInfoValue.email) : true;
    }
  get isSubmitBtnDisabled(): boolean {
      const isFormValid =  this.editInfoValue.name
                        && this.editInfoValue.title
@@ -303,11 +484,11 @@
                        && this.editInfoValue.serveArea
                        && this.editInfoValue.concept
                        && this.editInfoValue.experiences
                        && this.editInfoValue.awards
                        && this.editInfoValue.seniorityYear
                        && this.editInfoValue.seniorityMonth
                        && this.editInfoValue.expertise
                        && this.editInfoValue.communicationStyle;
                        && this.editInfoValue.phoneNumber.length
                        && this.editInfoValue.entryDate
                        && this.editInfoValue.expertise.length
                        && this.editInfoValue.communicationStyle.length
                        && this.editInfoValue.email.length;
      return !isFormValid
  }
}
@@ -315,6 +496,7 @@
</script>
<style lang="scss">
.pam-icon {
  font-size    : 15px;
  padding-right: 8px;
@@ -369,7 +551,17 @@
}
.seniority-input{
  width       : 50px;
  width       : 60px;
  margin-right: 5px;
}
.el-input--suffix .el-input__inner {
  padding-right: 20px;
}
.pam-editInfo-date-picker{
  .pam-date.el-input {
      width: 100%;
  }
}
</style>