<template>
  <div class="editor-panel" id="editorPanel" :class="{ closed: !isOpen }">
    <div class="title">{{ type === 'text' ? $t('editorPanel.textProp') : $t('editorPanel.imageProp') }}</div>

    <!-- 文本编辑 -->
    <div v-show="type === 'text'" class="edit-container">
      <div class="color">
        <div class="color-title">{{ $t('editorPanel.fontColor') }}</div>
        <div class="colors-container">
          <!-- <span class="cell-container">
            <span class="cell-outer" :class="{ active: property.color === '#FFFFFF' }" @click="setActiveToolColor('#FFFFFF')">
              <span class="cell while"></span>
            </span>
          </span> -->
          <span class="cell-container">
            <span class="cell-outer" :class="{ active: property.color === '#FF0000' }" @click="setActiveToolColor('#FF0000')">
              <span class="cell red"></span>
            </span>
          </span>
          <span class="cell-container">
            <span class="cell-outer" :class="{ active: property.color === '#FFEC66' }" @click="setActiveToolColor('#FFEC66')">
              <span class="cell yellow"></span>
            </span>
          </span>
          <span class="cell-container">
            <span class="cell-outer" :class="{ active: property.color === '#2D77FA' }" @click="setActiveToolColor('#2D77FA')">
              <span class="cell blue"></span>
            </span>
          </span>
        </div>
      </div>
      <div class="opacity">
        <div class="opacity-title">{{ $t('opacity') }}</div>
        <div class="tool">
          <n-slider v-model:value="property.opacity" :tooltip="false" :step="1" :max="100" :min="0" class="width-slider">
            <template #thumb>
              <Slider />
            </template>
          </n-slider>
          <n-select v-model:value="opacityLabel" :options="opacityOptions" @update:value="handleBlur" to="#editorPanel"/>
        </div>
      </div>
      <div class="text">
        <div class="text-title">{{ $t('font') }}</div>
        <n-select v-model:value="property.fontFamily" :options="fontFamilyOptions" to="#editorPanel" class="text-family" />
        <div class="content-block">
          <n-select v-model:value="property.fontStyle" :options="fontStyleOptions" to="#editorPanel" class="font-style-select" />
          <n-select v-model:value="property.fontSize" :options="fontSizeOptions" to="#editorPanel" class="font-size-select" />
        </div>
        <div class="text-align">
          <div :class="{ active: property.alignType === 2 }" @click="changeAlign(2)">
            <span :class="{ border: property.alignType === 3 }">
              <TextLeft />
            </span>
          </div>
          <div :class="{ active: property.alignType === 5 }" @click="changeAlign(5)">
            <span :class="{ border: property.alignType === 2 }">
              <TextCenter />
            </span>
          </div>
          <div :class="{ active: property.alignType === 3 }" @click="changeAlign(3)">
            <span>
              <TextRight />
            </span>
          </div>
        </div>
      </div>
    </div>

    <!-- 图片编辑 -->
    <div v-show="type === 'image'" class="edit-container">
      <div class="overview">
        <img v-show="imageUrl" :src="imageUrl">
      </div>
      <div class="rotate">
        <div class="content-title">{{ $t('editorPanel.rotate') }}</div>
        <div class="buttons">
          <div @click="setProperty('rotate', '-90')" :title="$t('editorPanel.rotateLeft')">
            <RotateImageLeft />{{ $t('editorPanel.rotateLeft') }}
          </div>
          <div @click="setProperty('rotate', '90')" :title="$t('editorPanel.rotateRight')">
            <RotateImageRight />{{ $t('editorPanel.rotateRight') }}
          </div>
        </div>
      </div>
      <div class="flips">
        <div class="content-title">{{ $t('editorPanel.flip') }}</div>
        <div class="buttons">
          <div @click="setProperty('flip', 'x')" :title="$t('editorPanel.flipHorizontal')">
            <span>
              <FlipX />
            </span>
          </div>
          <div @click="setProperty('flip', 'y')" :title="$t('editorPanel.flipVertical')">
            <span>
              <FlipY />
            </span>
          </div>
        </div>
      </div>
      <div class="opacity">
        <div class="opacity-title">{{ $t('opacity') }}</div>
        <div class="tool">
          <n-slider v-model:value="property.opacity" :tooltip="false" :step="1" :max="100" :min="0" class="width-slider">
            <template #thumb>
              <Slider />
            </template>
          </n-slider>
          <n-select v-model:value="opacityLabel" :options="opacityOptions" @update:value="handleBlur" to="#editorPanel"/>
        </div>
      </div>
      <div class="tools">
        <div class="content-title">{{ $t('editorPanel.tools') }}</div>
        <div class="buttons">
          <div @click="setProperty('tool', 'replace')" :title="$t('editorPanel.replace')">
            <span>
              <ReplaceImage />
            </span>
          </div>
          <div @click="setProperty('tool', 'export')" :title="$t('editorPanel.export')">
            <span>
              <ExportImage />
            </span>
          </div>
          <div @click="setProperty('tool', 'crop')" :title="$t('editorPanel.crop')">
            <span>
              <CropImage />
            </span>
          </div>
        </div>
      </div>
    </div>
  </div>
</template>

<script setup>
  import { ref, computed, watch, reactive, onMounted, getCurrentInstance } from 'vue'
  import { useViewerStore } from '@/stores/modules/viewer'
  import { useDocumentStore } from '@/stores/modules/document'
  import { NSlider, NSelect } from 'naive-ui'
  import core from '@/core'

  const useViewer = useViewerStore()
  const useDocument = useDocumentStore()

  const instance = getCurrentInstance().appContext.app.config.globalProperties
  const $t = instance.$t

  let property = reactive({
    color: '#000000',
    opacity: 100,
    fontFamily: 'Helvetica',
    fontStyle: 0,
    alignType: 2,
    fontSize: 14
  })

  let opacityLabel = ref('100%')
  const opacityArr = [25, 50, 75, 100]
  const opacityOptions = opacityArr.map(opacity => {
    return {
      label: `${opacity}%`,
      value: `${opacity}%`,
      class: 'edit-select'
    }
  })
  const loadFont = (data) => {
    const fontFamily = data.fontFamily
    if (!fontFamilyArr.includes(fontFamily)) {
      fontFamilyArr.push(fontFamily)
      fontFamilyOptions.value.push({
        label: fontFamily,
        value: fontFamily,
        class: 'edit-select'
      })
    }
  }
  core.addEvent('LoadFont', loadFont)
  const fontFamilyArr = ['Helvetica', 'Courier', 'Times-Roman']
  const fontFamilyOptions = ref([])
  fontFamilyOptions.value = fontFamilyArr.map(fontFamily => {
    return {
      label: fontFamily,
      value: fontFamily,
      class: 'edit-select'
    }
  })
  const fontStyleOptions = computed(() => {
    return [{
      label: $t('regular'),
      value: 0,
      class: 'edit-select'
    }, {
      label: $t('bold'),
      value: 1,
      class: 'edit-select'
    }, {
      label: $t('boldOblique'),
      value: 3,
      class: 'edit-select'
    }, {
      label: $t('oblique'),
      value: 2,
      class: 'edit-select'
    }]
  })
  const fontSizeArr = [12, 14, 16, 20, 24, 28]
  const fontSizeOptions = fontSizeArr.map(fontSize => {
    return {
      label: `${fontSize} pt`,
      value: fontSize,
      class: 'edit-select'
    }
  })

  const isOpen = computed(() => useViewer.isElementOpen('contentEditorPanel'))
  const type = computed(() => useViewer.getContentEditorType)

  const imageUrl = ref('')

  // 打开右侧属性面板时，关闭视图面板
  watch(() => isOpen.value, (newValue, oldValue) => {
    if (newValue) {
      useViewer.closeElement('pageModePanel')
    }
  })

  watch(() => property.fontFamily, (newValue, oldValue) => {
    core.setContentEditorProperty(type.value, { fontFamily: newValue })
  })

  watch(() => property.fontStyle, (newValue, oldValue) => {
    core.setContentEditorProperty(type.value, { fontStyle: newValue })
  })

  watch(() => property.opacity, (newValue, oldValue) => {
    opacityLabel.value = newValue + '%'
    core.setContentEditorProperty(type.value, { opacity: property.opacity })
  })

  watch(() => property.fontSize, (newValue, oldValue) => {
    if (typeof newValue === 'number') {
      core.setContentEditorProperty(type.value, { fontSize: property.fontSize })
    }
  })

  const setActiveToolColor = (color) => {
    property.color = color
    core.setContentEditorProperty(type.value, { color })
  }

  const handleBlur = () => {
    property.opacity = Number.isNaN(Number.parseInt(opacityLabel.value)) ? 100 : Number.parseInt(opacityLabel.value)
  }

  const changeAlign = (value) => {
    property.alignType = value

    core.setContentEditorProperty(type.value, { alignType: property.alignType })
  }

  const updateProperty = (props) => {
    for (const item in props) {
      if (item === 'type') {
        useViewer.setContentEditorType(props[item])
      }
      if (item === 'isOpen') {
        props.isOpen ? useViewer.openElement('contentEditorPanel') : useViewer.closeElement('contentEditorPanel')
      }
      if (item === 'imageUrl') {
        imageUrl.value = props[item]
      }

      for (const key in property) {
        if (item === key) {
          property[key] = props[item]

          if (item === 'fontSize' && !fontSizeArr.includes(props.fontSize)) {
            property.fontSize = props.fontSize + ' pt'
          }
        }
      }
    }
  }
  core.addEvent('contentPropertyChange', updateProperty)

  const setProperty = (key, value) => {
    core.setContentEditorProperty(type.value, { [key]: value })
  }
</script>

<style lang="scss" scoped>
  .editor-panel {
    position: fixed;
    right: 0;
    z-index: 3;
    display: flex;
    flex-direction: column;
    height: calc(100% - 88px);
    overflow: hidden;
    transition: transform .3s ease-in-out;
    background-color: var(--c-side-bg);
    border-left: 1px solid var(--c-side-header-border);
    &.closed {
      transform: translateX(100%);
    }
    .title {
      font-size: 14px;
      font-weight: 700;
      line-height: 36px;
      text-align: center;
      color: var(--c-side-title);
      background: var(--c-header-bg);
    }
    .edit-container {
      padding: 16px;
      .color {
        .color-title {
          font-family: Helvetica;
          font-size: 14px;
          font-weight: 700;
          line-height: 40px;
          color: var(--c-side-title);
        }
        .colors-container {
          padding: 0;
          border: none;
          .cell-container {
            padding: 2px;
            .cell-outer {
              width: 28px;
              height: 28px;
              border: 1px solid transparent;
              display: flex;
              align-items: center;
              justify-content: center;
              .cell {
                width: 22px;
                height: 22px;
              }
              .while {
                border: 0.93px solid #DADBDE;
                overflow: hidden;
                position: relative;
                background-color: #ffffff;
                &::before {
                  content: '';
                  width: 125%;
                  height: 2.3px;
                  position: absolute;
                  top: 50%;
                  background: #FA1E5D;
                  transform: rotate(-45deg);
                }
              }
            }
            .cell-outer.active {
              border: 1px solid var(--c-header-circle-bg)
            }
          }
          .cell-container + .cell-container {
            margin-left: 8px;
          }
        }
      }
      
      .opacity {
        .opacity-title {
          margin-top: 12px;
          font-size: 14px;
          font-weight: 700;
          line-height: 32px;
          color: var(--c-side-title);
        }
        .tool {
          display: flex;
          align-items: center;
          height: 32px;
          ::v-deep(.n-slider.width-slider) {
            margin-left: 0px;
            width: 60%;
            .n-slider-rail {
              height: 2px;
              border-radius: 0;
              .n-slider-rail__fill {
                background-color: #0078D7;
                border-radius: 0;
              }
            }
            .n-slider-handles {
              left: 0;
              right: 0;
            }
          }
          ::v-deep(.n-select) {
            max-width: 35%;
            margin-left: 5%;
          }
          select {
            max-width: 35%;
            margin-left: 5%;
          }
        }
      }

      .text {
        margin-top: 12px;
        .text-title {
          font-size: 14px;
          font-weight: 700;
          line-height: 32px;
          color: var(--c-side-title);
        }
        .text-family {
          margin-top: 4px;
          width: 100%;
        }
        .content-block {
          margin-top: 8px;
          height: 28px;
          width: 100%;
          .font-style-select {
            width: 60%;
          }
          .font-size-select {
            width: 35%;
            margin-left: 5%;
          }
        }
        .text-align {
          margin-top: 8px;
          display: inline-flex;
          border: 1px solid #0000001F;
          background: var(--c-right-side-content-fillbox-bg);
          div {
            padding: 8px 0px;
            width: 48px;
            height: 32px;
            text-align: center;
            cursor: pointer;
            span {
              display: inline-block;
              font-size: 0;
              width: 100%;
              svg {
                color: var(--c-text);
              }
            }
            .border {
              border-right: var(--c-edit-right-page) 1px solid;
            }
          }
          .active {
            background: #DDE9FF;
            svg {
              color: #43474D;
            }
          }
        }
      }

      select {
        height: 28px;
        padding: 6px 8px;
        font-size: 14px;
        line-height: 16px;
        border-radius: 1px;
        background: var(--c-right-side-content-fillbox-bg);
        border: 1px solid var(--c-right-side-content-fillbox-border);
        color: var(--c-text);
      }

      ::v-deep(.n-select) {
        display: inline-block;
        .n-base-selection {
          min-height: 28px;
          --n-border-active: none !important;
          --n-border-focus: none !important;
          --n-border-hover: none !important;
          --n-box-shadow-active: none !important;
          --n-box-shadow-focus: none !important;
          .n-base-selection-label {
            height: 28px;
            background: var(--c-right-side-content-fillbox-bg);

            .n-base-selection-input, .n-base-selection-input__content {
              color: var(--c-text);
            }
          }
          .n-base-selection__border {
            border: 1px solid var(--c-right-side-content-fillbox-border);
          }
        }
        input {
          font-size: 14px;
          line-height: 16px;
          padding: 0 8px;
          background: var(--c-right-side-content-fillbox-bg);
          caret-color: transparent;
        }
        .n-base-selection-overlay__wrapper {
          color: var(--c-text);
        }
        .n-base-selection .n-base-suffix .n-base-suffix__arrow {
          color: var(--c-text);
        }
      }

      .overview {
        display: flex;
        align-items: center;
        justify-content: center;
        width: 100%;
        height: 80px;
        border: 1px solid #E2E3E6;
        background: var(--c-right-side-content-fillbox-bg);

        img {
          max-width: 90%;
          max-height: 90%;
        }
      }

      .tools,
      .flips {
        margin-top: 12px;
        .content-title {
          font-size: 14px;
          font-weight: 700;
          line-height: 32px;
          color: var(--c-side-title);
        }

        .buttons {
          margin-top: 8px;
          display: inline-flex;
          border: 1px solid #0000001F;
          background: var(--c-right-side-content-fillbox-bg);

          :hover {
            background: #DDE9FF;
            svg {
              color: #43474D;
            }
          }

          div {
            padding: 8px 0px;
            width: 48px;
            height: 32px;
            text-align: center;
            cursor: pointer;
            span {
              display: inline-block;
              font-size: 0;
              width: 100%;
              svg {
                color: var(--c-text);
              }
            }
            & + div span {
              border-left: var(--c-edit-right-page) 1px solid;
            }
          }
        }
      }

      .rotate {
        margin-top: 12px;

        .content-title {
          font-size: 14px;
          font-weight: 700;
          line-height: 32px;
          color: var(--c-side-title);
        }

        .buttons {
          margin-top: 8px;
          display: inline-flex;
          width: 100%;
          gap: 5px;

          div {
            display: flex;
            align-items: center;
            justify-content: center;
            flex: 1;
            padding: 8px 0px;
            height: 32px;
            text-align: center;
            cursor: pointer;
            border: 1px solid #0000001F;
            border-radius: 1px;
            background: var(--c-right-side-content-fillbox-bg);

            &:hover {
              background: #DDE9FF;
              svg {
                color: #43474D;
              }
            }

            svg {
              margin-right: 8px;
            }
          }
        }
      }
    }
  }
  @media screen and (max-width: 640px) {
    .editor-panel {
      width: 100vw;

      .title {
        border-bottom: 1px solid rgba($color: #000000, $alpha: 0.12);
      }
    }
  }
  @media screen and (min-width: 641px) {
    .editor-panel {
      width: 260px;
    }
  }
</style>
<style lang="scss">
  .n-base-select-menu {
    .n-base-select-option {
      &.n-base-select-option--selected {
      color: var(--c-text);
      }
      .n-base-select-option__check {
        color: var(--c-header-text-theme-active) !important;
        &.fade-in-scale-up-transition-leave-active {
          display: none;
        }
      }
      &:active {
        color: var(--c-text);
      }
      &.n-base-select-option--show-checkmark {
        padding-right: calc(var(--n-option-padding-right) + 10px);
      }
    }
    .edit-select {
      background: var(--c-right-side-content-fillbox-bg);
      color: var(--c-text);
    }
  }
</style>
