import { getGoodsDecimalplaceByGoodsCode, getQuoteDayInfoByCode } from '@/services/bus/goods';
import { QueryQuoteDayRsp } from '@/services/go/quote/interface';
import { addSubscribeQuotation, removeSubscribeQuotation } from '@/services/socket/quota';
import TimerUtils from '@/utils/timer/timerUtil';
import { v4 } from 'uuid';
import { nextTick, onBeforeUnmount, onMounted, Ref, ref, watchEffect } from "vue";

/**
 * 订阅商品行情
 * @param goodsCodes 需要订阅的商品 code
 * @param itemTableHeight 表格每一行的高度
 * @param selector 当前的滚动区域的选择器
 */
export function subcriteGoodsQuote(goodsCodes: string[], itemTableHeight = 31, selector = '.ant-table-body') {
    const beforeScrollTop = ref<number>(0)
    const uuid = v4();

    nextTick(() => {
        //listenSrcoll(document.querySelector(selector)!)
    });

    // 第一次自动订阅当前可视区域的数据
    const stop = watchEffect(() => {
        const len = goodsCodes.length
        if (len) {
            const end = len > 16 ? 16 : len;
            subscribeAction(0, end)
        }
    })
    // 停止订阅
    function stopSubcribe() {
        removeSubscribeQuotation(uuid);
        TimerUtils.clearTimeout('subscribeQuote')
        stop()
    }
    function listenSrcoll(ele: Element) {
        ele.addEventListener('scroll', (event: any) => {
            stop && stop()
            debounceSroll(event)
        }, true)
    }
    // 判断滚动方向
    function srollDrection(event: any) {
        const { scrollTop, offsetHeight } = event.target
        const diffSrollTop = scrollTop - beforeScrollTop.value
        if (diffSrollTop === 0) {
            // 横向滚动
            return
        } else if (diffSrollTop > 0) {
            // 向下滚动
            caclcuteSubcribeNum(scrollTop, offsetHeight)
        } else {
            // 向上滚动
            caclcuteSubcribeNum(scrollTop, offsetHeight)
        }
        beforeScrollTop.value = scrollTop
    }
    /**
     *
     * @param scrollTop 当前滚动条所处的位置
     * @param offsetHeight 当前滚动范围的可视区域的高度
     */
    function caclcuteSubcribeNum(scrollTop: number, offsetHeight: number) {
        // 可视区域的列表行数
        const rowNum = Math.ceil(offsetHeight / itemTableHeight) - 1;
        const tableIndex = scrollTop < itemTableHeight ? 0 : Math.ceil(scrollTop / itemTableHeight)
        // 开始订阅
        subscribeAction(tableIndex, tableIndex + rowNum)
    }
    // 防抖
    function debounceSroll(event: any) {
        TimerUtils.clearTimeout('subscribeQuote')
        TimerUtils.setTimeout(() => {
            srollDrection(event)
        }, 200, 'subscribeQuote')
    }
    // 开始订阅
    function subscribeAction(start: number, end: number) {
        removeSubscribeQuotation(uuid);
        const result: Array<{ exchangeCode: 250, goodsCode: string, subState: 0 }> = []
        for (let i = 0; i < goodsCodes.length; i++) {
            const code = goodsCodes[i]
            result.push({
                exchangeCode: 250,
                goodsCode: code,
                subState: 0
            })
        }
        console.log('开始订阅', result)
        addSubscribeQuotation(uuid, result);
    }
    return stopSubcribe
}

/**
 * 处理行情按需订阅 ------------------------------------------------------------------------ 待废弃
 * @param tableList 全部表格数据
 * @param codeKey 需要订阅商品code对应的key
 * @param itemTableHeight 表格每一行的高度
 * @param selector 当前的滚动区域的选择器
 */
export function handleSubcriteOnDemandQuote<T extends object>(tableList: Ref<T[]>, codeKey = 'goodscode', itemTableHeight = 31, selector = '.ant-table-body') {
    const beforeScrollTop = ref<number>(0)
    const uuid = v4();
    onMounted(() => {
        listenSrcoll(document.querySelector(selector)!)
    });
    onBeforeUnmount(() => {
        stopSubcribe()
    })

    // 第一次自动订阅当前可视区域的数据
    const stop = watchEffect(() => {
        const len = tableList.value.length
        if (len) {
            const end = len > 16 ? 16 : len;
            subscribeAction(0, end)
        }
    })
    // 停止订阅
    function stopSubcribe() {
        removeSubscribeQuotation(uuid);
        TimerUtils.clearTimeout('subscribeQuote')
        stop()
    }
    function listenSrcoll(ele: Element) {
        ele.addEventListener('scroll', (event: any) => {
            stop && stop()
            debounceSroll(event)
        }, true)
    }
    // 判断滚动方向
    function srollDrection(event: any) {
        const { scrollTop, offsetHeight } = event.target
        const diffSrollTop = scrollTop - beforeScrollTop.value
        if (diffSrollTop === 0) {
            // 横向滚动
            return
        } else if (diffSrollTop > 0) {
            // 向下滚动
            caclcuteSubcribeNum(scrollTop, offsetHeight)
        } else {
            // 向上滚动
            caclcuteSubcribeNum(scrollTop, offsetHeight)
        }
        beforeScrollTop.value = scrollTop
    }
    /**
     *
     * @param scrollTop 当前滚动条所处的位置
     * @param offsetHeight 当前滚动范围的可视区域的高度
     */
    function caclcuteSubcribeNum(scrollTop: number, offsetHeight: number) {
        // 可视区域的列表行数
        const rowNum = Math.ceil(offsetHeight / itemTableHeight) - 1;
        const tableIndex = scrollTop < itemTableHeight ? 0 : Math.ceil(scrollTop / itemTableHeight)
        // 开始订阅
        subscribeAction(tableIndex, tableIndex + rowNum)
    }
    // 防抖
    function debounceSroll(event: any) {
        TimerUtils.clearTimeout('subscribeQuote')
        TimerUtils.setTimeout(() => {
            srollDrection(event)
        }, 200, 'subscribeQuote')
    }
    // 开始订阅
    function subscribeAction(start: number, end: number) {
        removeSubscribeQuotation(uuid);
        const result: Array<{ exchangeCode: 250, goodsCode: string, subState: 0 }> = []
        for (let i = start; i < end; i++) {
            const obj = tableList.value[i] as unknown as any
            if (obj && Reflect.has(obj, codeKey)) {
                result.push({ exchangeCode: 250, goodsCode: obj[codeKey], subState: 0 })
            } else {
                console.warn(`订阅商品的code对应的key${codeKey}不存在，请手动传入！`)
            }
        }
        console.log('开始订阅', result)
        addSubscribeQuotation(uuid, result);
    }
    return stopSubcribe
}

// 处理行情订阅，注意这里不是按需订阅
export function handleSubcriteQuote() {
    const uuid = v4();
    function subscribeAction(goodscode: string[]) {
        removeSubscribeQuotation(uuid);
        const goodsList = goodscode.map(el => {
            return { exchangeCode: 250, goodsCode: el, subState: 0 };
        })
        //  行情订阅
        addSubscribeQuotation(uuid, goodsList);
    }
    onBeforeUnmount(() => {
        removeSubscribeQuotation(uuid);
    });
    return { subscribeAction }
}

function isPrice(price1: number | string, price2: number | string) {
    if (price2 && price2 !== '--' && price1 && price1 !== '--') {
        return true
    } else {
        return false
    }
}

/**
 * 处理行情价格颜色
 * @param value
 * @param presettle 昨结价
 * @returns
 */
export function handleQuotePriceColor(value: number, presettle: number) {
    let result = ''
    if (isPrice(value, presettle)) {
        if (value === presettle) {
            result = ''
        } else if (value > presettle) {
            result = 'up-quote-color'
        } else {
            result = 'down-quote-color'
        }
    }
    return result
}
// 外部行情 获取某个值
export function getQuoteValue_out(goodscode: string, val: keyof QueryQuoteDayRsp) {
    const obj = getQuoteDayInfoByCode(goodscode)
    return obj ? obj[val] : '--'
}

// 外部行情  处理行情价格颜色
export function handleQuotePriceColor_out(goodscode: string, val: keyof QueryQuoteDayRsp) {
    const obj = getQuoteDayInfoByCode(goodscode)
    let result = ''
    if (obj) {
        result = handleQuotePriceColor(obj[val] as number, obj.presettle)
    }
    return result
}
// 涨跌额/涨跌 最新价 - 昨结价
export function quoteChange<T>(record: T, decimalplace = 2) {
    type Key = keyof T;
    const presettle = record['presettle' as Key];
    const last = record['last' as Key];

    if (typeof presettle === 'number' && typeof last === 'number') {
        const calc = last - presettle;
        if (last > 0) {
            return calc.toFixed(decimalplace);
        }
    }
    return '--';
}

// 涨跌幅/幅度（（最新价 - 昨结价） / 昨结价） *  100 %
export function quoteAmplitude<T>(record: T, decimalplace = 2) {
    type Key = keyof T;
    const presettle = record['presettle' as Key];
    const result = quoteChange(record, decimalplace);

    if (typeof presettle === 'number' && result !== '--') {
        const calc = Number(result) / presettle * 100;
        if (!isNaN(calc)) {
            return calc.toFixed(decimalplace) + '%';
        }
    }
    return '--';
}
// 外部行情 幅度（最新价 - 昨结价） / 昨结价） *  100 %
export function quoteAmplitude_out(goodscode: string) {
    const obj = getQuoteDayInfoByCode(goodscode)
    let result = '--'
    // const decimalplace = getGoodsDecimalplaceByGoodsCode(goodscode)
    if (obj) {
        result = quoteAmplitude(obj, 2)
    }
    return result
}
// 外部行情 涨跌 最新价 - 昨结价
export function quoteChange_out(goodscode: string) {
    const obj = getQuoteDayInfoByCode(goodscode)
    let result = '--'
    const decimalplace = getGoodsDecimalplaceByGoodsCode(goodscode)
    if (obj) {
        result = quoteChange(obj, decimalplace)
    }
    return result
}
// 振幅 (最高价 - 最低价 ) / 最新价  * 100 %
export function quoteAmplituOfVibration(record: QueryQuoteDayRsp, decimalplace = 2) {
    const { highest, lowest, last } = record
    let result = '--'
    if (isPrice(highest, lowest)) {
        if (last && (last as unknown as any) !== '--') {
            result = ((highest - lowest) / last * 100).toFixed(decimalplace) + '%'
        }
    }
    return result
}

// 处理 空值  或者 0的时候，显示 --  的情况，
export function handleNoneValue(value: number | string, suffix = '') {
    return value ? value.toString() + suffix : '--'
}