<template>
    <div class="cu-tree-node-children">
        <div class="cu-tree-node-view is-leaf" v-for="item in nodes" :key="item['primaryKeyId']">
            <div class="cu-tree-node-label">
                <div class="cu-tree-node-label-text">
                    <div class="cu-tree-node-label-name" :id="`node-tree-${item.key}`" @click="nodeLabelClick(item)" @dblclick="nodeLabelDblClick(item)" @contextmenu.prevent.stop="nodeLabelContextMenu($event,item,item?.data)">
                        <el-button hc-btn color="#0081ff" :loading="item.loading" v-if="item?.colorStatus === 2">{{item.label}}</el-button>
                        <el-button hc-btn color="#f37b1d" :loading="item.loading" v-else-if="item?.colorStatus === 3">{{item.label}}</el-button>
                        <el-button hc-btn color="#1ECC95" text-white :loading="item.loading" v-else-if="item?.colorStatus === 4">{{item.label}}</el-button>
                        <el-button type="info" hc-btn :loading="item.loading" v-else>{{item.label}}</el-button>
                    </div>
                    <span class="cu-tree-node-label-btn" :class="[ifExpanded(item)?'expanded':'']" v-if="isExpanded(item)" @click="expandedClick(item)"/>
                </div>
            </div>
            <TreeNodeChildren :data="item.childNodes" :parentNodes="item" v-if="ifExpanded(item)" @expandClick="ChildrenExpandedClick" @nodeClick="ChildrenNodeLabelClick" @nodeDblClick="ChildrenNodeLabelDblClick" @menuClick="ChildrenCpoverMenuClick"/>
        </div>
    </div>
</template>

<script setup>
import {ref,watch,onMounted} from "vue";
import TreeNodeChildren from "./children.vue"
import {isObject,isBoolean} from "vue-utils-plus"
const props = defineProps({
    data: {
        type: Array,
        default: () => ([])
    },
    parentNodes: {
        type: Object,
        default: () => ({})
    },
    accordion: {
        type: Boolean,
        default: false
    },
})

//初始数据
const datas = ref(props.data)
const parent = ref(props.parentNodes)
const nodes = ref([])

//监听
watch(() => [
    props.data,
    props.parentNodes
], ([val,Nodes]) => {
    datas.value = val
    if (isDataType(Nodes)) {
        parent.value = Nodes
        setDatasToNodes()
    } else {
        parent.value = {}
    }
})

//渲染完成
onMounted(()=> {
    if (isDataType(props.parentNodes)) {
        parent.value = props.parentNodes
        setDatasToNodes()
    } else {
        parent.value = {}
    }
})

//检查数据类型
const isDataType = (data) => {
    if (isObject(data)) {
        return Object.keys(data).length !== 0;
    } else {
        return false
    }
}

//处理为node节点类型的数据
const setDatasToNodes = () => {
    let nodesArr = [];
    const deepData = datas.value
    for (let i = 0; i < deepData.length; i++) {
        let childNodes = deepData[i]['children'] //子级数据
        let ifChildren = !!(childNodes && childNodes.length > 0);
        nodesArr.push({
            childNodes: childNodes, //子节点原始数据
            childrenNodes: [],      //子节点node封装数据
            data: deepData[i],      //节点主要数据
            parentNodes: parent.value,  //父节点数据
            expanded: ifChildren || deepData[i]['expanded'] || false,  //是否展开
            isExpand: ifChildren || deepData[i]['isExpand'] || false,   //是否能展开
            isLeaf: deepData[i]['isLeaf'] || false,     //是否为最后一节
            loading: deepData[i]['loading'] || false,   //加载状态
            colorStatus: deepData[i]['colorStatus'] || 1,   //颜色状态
            key: deepData[i]['primaryKeyId'],      //节点的key
            label: deepData[i]['title']   //节点显示的名称
        })
    }
    nodes.value = nodesArr //渲染使用
    parent.value['childrenNodes'] = nodes.value //把当前节点数据，存入父节点的数据里。
}

const emit = defineEmits(['expandClick','nodeMouseover','nodeMouseout', 'nodeClick', 'nodeDblClick', 'menuClick'])

//下级数据是否存在
const isChildren = (item) => {
    return !!(item.childNodes && item.childNodes.length > 0);
}
//是否显示展开和隐藏按钮
const isExpanded = (item) => {
    let ifChildren = isChildren(item);
    if (isBoolean(item['expanded'])) {
        let res = !!(item['expanded'] && ifChildren);
        item['expanded'] = res;
        return res;
    } else {
        item['expanded'] = false;
        return false;
    }
}
//处理展开和隐藏的样式
const ifExpanded = (item) => {
    let ifChildren = isChildren(item);
    if (isBoolean(item['isExpand'])) {
        let res = !!(item['isExpand'] && ifChildren);
        item['isExpand'] = res;
        return res;
    } else {
        item['isExpand'] = ifChildren;
        return ifChildren;
    }
}
//展开和隐藏按钮被点击
const expandedClick = (item) => {
    emit('expandClick', {
        node: item,
        data: item.data
    })
}
const ChildrenExpandedClick = ({node,data}) => {
    emit('expandClick', {node,data})
}

//鼠标左键单击事件
const nodeLabelClick = (item) => {
    emit('nodeClick', {
        node: item,
        data: item.data
    })
}
const ChildrenNodeLabelClick = ({node,data}) => {
    emit('nodeClick', {node,data})
}

//双击事件
const nodeLabelDblClick = (item) => {
    emit('nodeDblClick', {
        node: item,
        data: item.data
    })
}
const ChildrenNodeLabelDblClick = ({node,data}) => {
    emit('nodeDblClick', {node,data})
}

//鼠标右键事件
const nodeLabelContextMenu = (event, node, data) => {
    emit('menuClick', event, node, data)
}

//菜单被点击
const ChildrenCpoverMenuClick = (event, node, data) => {
    emit('menuClick', event, node, data)
}
</script>

<style lang="scss" scoped>
@import "style";
</style>
