<script setup>
import { ElLoading, ElMessageBox } from 'element-plus'
import { emojis } from '@/constant/im'
import { messageType } from '@/constant/im'
import _ from 'lodash'
import { onClickOutside } from '@vueuse/core'
/* 组件 */
import PreviewSendImg from '../suit/previewSendImg.vue'
import VueAt from 'vue-at/dist/vue-at-textarea' // for textarea
import * as MessageApi from '@/api/im/message'
import { generateUUID } from '@/utils'
const props = defineProps({
  nowPickInfo: {
    type: Object,
    required: true,
    default: () => ({})
  }
})
const { ALL_MESSAGE_TYPE, CHAT_TYPE, MENTION_ALL } = messageType
const { nowPickInfo } = toRefs(props)
const atMembersList = ref([])
//附件类上传加载状态
const loadingBox = ref(null)
const isAtAll = ref(false)
const atMembers = ref([])
//输入框插入@事件
const onInsert = (target) => {
  // if (!) return false
  console.log('onInset', target)
  if (_.map(atMembers.value, 'value').includes(target.value)) return false
  if (target.value === MENTION_ALL.VALUE) {
    return (isAtAll.value = true)
  } else {
    atMembers.value.push({ ...target })
  }
}
//校验消息内容中是否包含要@的成员
const checkAtMembers = (text) => {
  if (!text) {
    return false
  }
  //判断是否文本中是否有@ALL，没有则直接设置为false
  const patternAtAll = new RegExp(`@${MENTION_ALL.TEXT}`)
  console.log('patternAtAll', patternAtAll)
  if (isAtAll.value && !patternAtAll.test(text)) {
    isAtAll.value = false
  }
  if (atMembers.value.length !== 0) {
    //循环AT成员数组通过匹配文本内容判断是否存在已经移除@成员
    _.map(atMembers.value, 'text').forEach((item, index) => {
      console.log('atMembers item', item, index)
      const pattern = new RegExp(`@${item}`)
      const result = pattern.test(text)
      if (!result) {
        console.log('文本中不满足条件')
        //不包含则从@列表中移除该成员
        atMembers.value.splice(index, 1)
        console.log('>>>>>已删除', atMembers.value)
      }
    })
  }
}
//emojis框展开
const isShowEmojisBox = ref(false)
const emojisBox = ref(null)
onClickOutside(emojisBox, (event) => {
  console.log('>>>>>关闭模态框')
  isShowEmojisBox.value = false
  event.stopPropagation()
})
const showEmojisBox = () => {
  console.log('>>>>>展开模态框')
  if (!isShowEmojisBox.value) {
    isShowEmojisBox.value = true
  }
}
//新增一个emoji
const addOneEmoji = (emoji) => {
  console.log('>>>>>>emoji', emoji)
  textContent.value = textContent.value + emoji
}
//消息引用
const messageQuoteRef = ref(null)
const handleQuoteMessage = (msgBody) => {
  messageQuoteRef.value && messageQuoteRef.value.setQuoteContent(msgBody)
}

//换行操作
const insertNewLine = () => (textContent.value += '\n')
//发送文本内容
const textContent = ref('')
const sendTextMessage = _.debounce(async () => {
  //如果输入框全部为空格同样拒绝发送
  if (textContent.value.match(/^\s*$/)) return
  console.log('atMembers.value', atMembers.value)
  checkAtMembers(textContent.value)
  const msgOptions = {
    id: nowPickInfo.value.id,
    chatType: nowPickInfo.value.chatType,
    msg: textContent.value,
    ext: {
      em_at_list: isAtAll.value ? MENTION_ALL.VALUE : _.map(atMembers.value, 'value')
    }
  }
  const imMessageSendReqVO = {
    clientMessageId: generateUUID(),
    receiverId: nowPickInfo.value.id,
    conversationType: nowPickInfo.value.chatType,
    contentType: ALL_MESSAGE_TYPE.TEXT,
    content: textContent.value
  }
  //关闭引用框
  if (messageQuoteRef.value?.isShowQuoteMsgBox) {
  }
  textContent.value = ''
  messageQuoteRef.value?.clearQuoteContent()
  try {
    console.log('imMessageSendReqVO', imMessageSendReqVO)
    const imMessageSendRespVO = await MessageApi.sendMessage(imMessageSendReqVO)
    console.log('>>>>>发送成功', imMessageSendRespVO)
  } catch (error) {
    console.log('>>>>>>>发送失败+++++++', error)
  } finally {
    isAtAll.value = false
    atMembers.value = []
  }
}, 50)
//监听键盘按下事件，如果为enter键则发送文本内容,shift+enter则换行。
const onTextInputKeyDown = (event) => {
  if (event.keyCode === 13 && !event.shiftKey) {
    event.preventDefault()
    // 执行发送操作
    sendTextMessage()
  } else if (event.keyCode === 13 && event.shiftKey) {
    // 换行操作
    insertNewLine()
  }
}
/* 图片消息相关 */
//选择图片
const uploadImgs = ref(null)
const chooseImages = () => {
  uploadImgs.value.click()
  console.log('uploadImgs')
}
//发送图片
const sendImagesMessage = async (type) => {
  const file = {
    data: null, // file 对象。
    filename: '', //文件名称。
    filetype: '' //文件类型。
  }
  const url = window.URL || window.webkitURL
  const img = new Image() //手动创建一个Image对象
  const msgOptions = {
    id: nowPickInfo.value.id,
    chatType: nowPickInfo.value.chatType,
    file: file,
    width: 0,
    height: 0
  }
  if (type === 'common') {
    //读取图片的宽高
    const imgFile = uploadImgs.value.files[0]
    file.data = imgFile
    file.filename = imgFile.name
    file.filetype = imgFile.type
    console.log('imgFile', file)
    img.src = url.createObjectURL(imgFile) //创建Image的对象的url
    img.onload = async () => {
      const loadingInstance = ElLoading.service({
        target: loadingBox.value,
        background: '#f7f7f7'
      })
      msgOptions.width = img.width
      msgOptions.height = img.height
      console.log('height:' + img.height + '----' + img.width)
      try {
        // await store.dispatch('sendShowTypeMessage', {
        //   msgType: ALL_MESSAGE_TYPE.IMAGE,
        //   msgOptions: _.cloneDeep(msgOptions)
        // })
        loadingInstance.close()
        uploadImgs.value.value = null
      } catch (error) {
        console.log('>>>>>发送失败', error)
        if (error.type && error?.data) {
          handleSDKErrorNotifi(error.type, error.data.error || 'none')
        } else {
          handleSDKErrorNotifi(0, 'none')
        }
        loadingInstance.close()
        uploadImgs.value.value = null
      }
    }
  } else if (type === 'other') {
    console.log('fileObjfileObjfileObj', fileObj)
    const imgFile = fileObj
    file.data = imgFile
    file.filename = imgFile.name
    file.filetype = imgFile.type
    console.log('imgFile', file)
    img.src = url.createObjectURL(imgFile) //创建Image的对象的url
    img.onload = async () => {
      const loadingInstance = ElLoading.service({
        target: loadingBox.value,
        background: '#f7f7f7'
      })
      msgOptions.width = img.width
      msgOptions.height = img.height
      console.log('height:' + img.height + '----' + img.width)
      try {
        await store.dispatch('sendShowTypeMessage', {
          msgType: ALL_MESSAGE_TYPE.IMAGE,
          msgOptions: _.cloneDeep(msgOptions)
        })
        loadingInstance.close()
        uploadImgs.value.value = null
      } catch (error) {
        console.log('>>>>>发送失败', error)
        if (error.type && error?.data) {
          handleSDKErrorNotifi(error.type, error.data.error || 'none')
        } else {
          handleSDKErrorNotifi(0, 'none')
        }
        loadingInstance.close()
        uploadImgs.value.value = null
      }
    }
  }
}
//贴图发送
const previewSendImg = ref(null)
const onPasteImage = (event) => {
  console.log('>>>>>>监听粘贴事件', event)
  const data = event.clipboardData || window.clipboardData
  //获取图片内容
  const imgContent = data.items[0].getAsFile()
  //判断是不是图片，最好通过文件类型判断
  const isImg = (imgContent && 1) || -1
  const reader = new FileReader()
  if (isImg >= 0) {
    //将文件读取为 DataURL
    reader.readAsDataURL(imgContent)
  }
  //文件读取完成时触发
  reader.onload = (event) => {
    //获取base64流
    const base64_str = event.target.result
    const imgInfo = {
      imgFile: imgContent,
      tempFilePath: base64_str
    }
    previewSendImg.value.showPreviewImgModal({ ...imgInfo })
    console.log('>>>>>获取到粘贴到的文本', imgInfo)
  }
}
/* 文件消息相关 */
//选择文件
const uploadFiles = ref(null)
const chooseFiles = () => {
  uploadFiles.value.click()
}
//发送文件
const sendFilesMessages = async () => {
  const commonFile = uploadFiles.value.files[0]
  const file = {
    data: commonFile, // file 对象。
    filename: commonFile.name, //文件名称。
    filetype: commonFile.type, //文件类型。
    size: commonFile.size
  }
  console.log('>>>>>调用发送文件', file)
  const msgOptions = {
    id: nowPickInfo.value.id,
    chatType: nowPickInfo.value.chatType,
    file: file
  }
  const loadingInstance = ElLoading.service({
    target: loadingBox.value,
    background: '#f7f7f7'
  })
  try {
    // await store.dispatch('sendShowTypeMessage', {
    //   msgType: ALL_MESSAGE_TYPE.FILE,
    //   msgOptions: _.cloneDeep(msgOptions)
    // })
    loadingInstance.close()
    uploadFiles.value.value = null
  } catch (error) {
    console.log('>>>>file error', error)
    if (error.type && error?.data) {
      handleSDKErrorNotifi(error.type, error.data.error || 'none')
    } else {
      handleSDKErrorNotifi(0, 'none')
    }

    uploadFiles.value.value = null
    loadingInstance.close()
  }
}
/* 语音消息相关 */
//展示录音对话框
const isHttps = window.location.protocol === 'https:' || window.location.hostname === 'localhost'
const isShowRecordBox = ref(false)
const recordBox = ref(null)
onClickOutside(recordBox, () => {
  isShowRecordBox.value = false
})
const showRecordBox = () => {
  isShowRecordBox.value = true
}
const sendAudioMessages = async (audioData) => {
  const file = {
    // url: EaseChatSDK.utils.parseDownloadResponse(audioData.src),
    filename: '录音',
    filetype: '.amr',
    data: audioData.src
  }
  console.log('>>>>>audioData', audioData, file)
  const msgOptions = {
    id: nowPickInfo.value.id,
    chatType: nowPickInfo.value.chatType,
    file: file,
    length: audioData.length
  }
  try {
    // await store.dispatch('sendShowTypeMessage', {
    //   msgType: ALL_MESSAGE_TYPE.AUDIO,
    //   msgOptions: _.cloneDeep(msgOptions)
    // })
    isShowRecordBox.value = false
  } catch (error) {
    // if (error.type && error?.data) {
    //   handleSDKErrorNotifi(error.type, error.data.error || 'none')
    // } else {
    //   handleSDKErrorNotifi(0, 'none')
    // }
    isShowRecordBox.value = false
  }
}
/*清除屏幕*/
const clearScreen = () => {
  ElMessageBox.confirm('确认清空当前消息内容？', '消息清屏', {
    confirmButtonText: '确认',
    cancelButtonText: '取消',
    type: 'warning'
  })
    .then(() => {
      const key = nowPickInfo.value.id
      // store.commit('CLEAR_SOMEONE_MESSAGE', key)
    })
    .catch(() => {
      return false
    })
}
//func 对应事件 icon class样式等
const all_func = [
  {
    className: 'icon-emoji',
    style: 'font-size:20px;margin-left: 20px;',
    title: '选择表情',
    methodName: showEmojisBox
  },
  {
    className: 'icon-tuku',
    style: 'font-size: 26px;',
    title: '发送图片',
    methodName: chooseImages
  },
  {
    className: 'icon-wenjian',
    style: 'font-size: 20px;',
    title: '发送文件',
    methodName: chooseFiles
  },
  {
    className: 'icon-01',
    style: 'font-size: 20px;',
    title: '发送语音',
    methodName: showRecordBox
  },
  {
    className: 'icon-lajitong',
    style: 'font-size: 23px;',
    title: '清屏',
    methodName: clearScreen
  }
]
defineExpose({
  textContent,
  handleQuoteMessage
})
</script>
<template>
  <div class="chat_func_box">
    <span
      v-for="iconItem in all_func"
      :class="['iconfont', iconItem.className]"
      :key="iconItem.className"
      :style="iconItem.style"
      :title="iconItem.title"
      @click.stop="iconItem.methodName"
    ></span>
    <!-- 表情框 -->
    <el-scrollbar ref="emojisBox" v-if="isShowEmojisBox" class="emojis_box" tag="div">
      <span
        class="emoji"
        v-for="(emoji, index) in emojis"
        :key="index"
        @click="addOneEmoji(emoji)"
        >{{ emoji }}</span
      >
    </el-scrollbar>
    <!-- 图片附件choose -->
    <input
      ref="uploadImgs"
      type="file"
      style="display: none"
      @change="sendImagesMessage('common')"
      accept="image/*"
    />
    <!-- 文件附件choose -->
    <input ref="uploadFiles" type="file" style="display: none" @change="sendFilesMessages" />
    <!-- 录音采集框 -->
    <el-card ref="recordBox" v-if="isShowRecordBox" class="record_box" shadow="always">
      <p v-if="!isHttps"> 由于浏览器限制,录音功能必须为https环境或者为localhost环境下使用！ </p>
      <!--      <CollectAudio v-else @sendAudioMessages="sendAudioMessages" />-->
    </el-card>
    <!-- 附件上传加载容器 -->
    <div ref="loadingBox" class="loading_box"></div>
  </div>
  <template v-if="nowPickInfo.chatType === CHAT_TYPE.SINGLE">
    <textarea
      ref="editable"
      v-model="textContent"
      class="chat_content_editable"
      spellcheck="false"
      contenteditable="true"
      placeholder="请输入消息内容..."
      @keydown="onTextInputKeyDown"
      @paste="onPasteImage"
    >
    </textarea>
  </template>
  <template v-else-if="nowPickInfo.chatType === CHAT_TYPE.GROUP">
    <vue-at :members="atMembersList" name-key="text" @insert="onInsert">
      <textarea
        ref="editable"
        v-model="textContent"
        class="chat_content_editable"
        spellcheck="false"
        contenteditable="true"
        placeholder="请输入消息内容..."
        @keydown="onTextInputKeyDown"
        @paste="onPasteImage"
      >
      </textarea>
    </vue-at>
  </template>

  <el-button
    :class="[textContent === '' ? 'no_content_send_btn' : 'chat_send_btn']"
    type="primary"
    @click="sendTextMessage"
    >发送</el-button
  >
  <PreviewSendImg ref="previewSendImg" @send-images-message="sendImagesMessage" />
</template>

<style lang="scss" scoped>
@import './index.scss';
@import '@/styles/iconfont/iconfont.css';
</style>
