<template xlang="wxml" minapp="mpvue">
  <view class="tki-qrcode">
    <!-- #ifndef MP-ALIPAY -->
    <canvas
      class="tki-qrcode-canvas"
      :canvas-id="cid"
      :style="{ width: cpSize + 'px', height: cpSize + 'px' }"
    />
    <!-- #endif -->
    <!-- #ifdef MP-ALIPAY -->
    <canvas
      :id="cid"
      :width="cpSize"
      :height="cpSize"
      class="tki-qrcode-canvas"
    />
    <!-- #endif -->
    <image
      v-show="show"
      :src="result"
      :style="{ width: cpSize + 'px', height: cpSize + 'px' }"
    />
  </view>
</template>

<script setup>
import { ref, computed, watch, onMounted, getCurrentInstance } from "vue";
import QRCode from "./qrcode.js";

let qrcode;

// 定义props
const props = defineProps({
  cid: {
    type: String,
    default: "tki-qrcode-canvas",
  },
  size: {
    type: Number,
    default: 200,
  },
  unit: {
    type: String,
    default: "upx",
  },
  show: {
    type: Boolean,
    default: true,
  },
  val: {
    type: String,
    default: "",
  },
  background: {
    type: String,
    default: "#ffffff",
  },
  foreground: {
    type: String,
    default: "#000000",
  },
  pdground: {
    type: String,
    default: "#000000",
  },
  icon: {
    type: String,
    default: "",
  },
  iconSize: {
    type: Number,
    default: 40,
  },
  lv: {
    type: Number,
    default: 3,
  },
  onval: {
    type: Boolean,
    default: false,
  },
  loadMake: {
    type: Boolean,
    default: false,
  },
  usingComponents: {
    type: Boolean,
    default: true,
  },
  showLoading: {
    type: Boolean,
    default: true,
  },
  loadingText: {
    type: String,
    default: "二维码生成中",
  },
});

// 定义emits
const emit = defineEmits(["result"]);

// 获取当前实例
const instance = getCurrentInstance()

// 创建一个安全的上下文对象
const getContext = () => {
  return instance?.proxy || instance?.ctx || {}
};

// 响应式数据
const result = ref("");

// 计算属性
const cpSize = computed(() => {
  if (props.unit === "upx") {
    return uni.upx2px(props.size);
  } else {
    return props.size;
  }
});

// 工具函数
const _empty = (v) => {
  let tp = typeof v;
  let rt = false;
  if (tp === "number" && String(v) === "") {
    rt = true;
  } else if (tp === "undefined") {
    rt = true;
  } else if (tp === "object") {
    if (JSON.stringify(v) === "{}" || JSON.stringify(v) === "[]" || v === null)
      rt = true;
  } else if (tp === "string") {
    if (
      v === "" ||
      v === "undefined" ||
      v === "null" ||
      v === "{}" ||
      v === "[]"
    )
      rt = true;
  } else if (tp === "function") {
    rt = false;
  }
  return rt;
};

// 方法定义
const _makeCode = () => {
  console.log('开始生成二维码，内容:', props.val, '大小:', cpSize.value)
  if (!_empty(props.val)) {
    try {
      qrcode = new QRCode({
        context: getContext(), // 上下文环境
        canvasId: props.cid, // canvas-id
        usingComponents: props.usingComponents, // 是否是自定义组件
        showLoading: props.showLoading, // 是否显示loading
        loadingText: props.loadingText, // loading文字
        text: props.val, // 生成内容
        size: cpSize.value, // 二维码大小
        background: props.background, // 背景色
        foreground: props.foreground, // 前景色
        pdground: props.pdground, // 定位角点颜色
        correctLevel: props.lv, // 容错级别
        image: props.icon, // 二维码图标
        imageSize: props.iconSize, // 二维码图标大小
        cbResult: function (res) {
          // 生成二维码的回调
          console.log('二维码生成完成:', res)
          _result(res);
        },
      });
    } catch (error) {
      console.error('二维码生成失败:', error)
    }
  } else {
    console.log('二维码内容为空')
    uni.showToast({
      title: "二维码内容不能为空",
      icon: "none",
      duration: 2000,
    });
  }
};

const _clearCode = () => {
  _result("");
  if (qrcode) {
    qrcode.clear();
  }
};

const _saveCode = () => {
  if (result.value !== "") {
    uni.saveImageToPhotosAlbum({
      filePath: result.value,
      success: function () {
        uni.showToast({
          title: "二维码保存成功",
          icon: "success",
          duration: 2000,
        });
      },
    });
  }
};

const _result = (res) => {
  result.value = res;
  emit("result", res);
};

// 监听器
watch(
  () => props.size,
  (newVal, oldVal) => {
    if (newVal !== oldVal && !_empty(newVal)) {
      if (!_empty(props.val)) {
        setTimeout(() => {
          _makeCode();
        }, 100);
      }
    }
  }
);

watch(
  () => props.val,
  (newVal, oldVal) => {
    if (props.onval) {
      if (newVal !== oldVal && !_empty(newVal)) {
        setTimeout(() => {
          _makeCode();
        }, 0);
      }
    }
  }
);

// 生命周期
onMounted(() => {
  if (props.loadMake) {
    if (!_empty(props.val)) {
      setTimeout(() => {
        _makeCode();
      }, 0);
    }
  }
});

// 暴露方法给父组件
defineExpose({
  _makeCode,
  _clearCode,
  _saveCode,
});
</script>

<style>
.tki-qrcode {
  position: relative;
}

.tki-qrcode-canvas {
  position: fixed;
  top: -99999upx;
  left: -99999upx;
  z-index: -99999;
}
</style>
