import {ApiCall} from "tsrpc"
import {YangChengMuBiaofun} from "../api_s2c/event/yangchengmubiao/fun"
import {Christmasfun} from "../api_s2c/event/christmas/fun"
// import { YangChengMuBiaofun } from "../api_s2c/event/yangchengmubiao/fun"
import {Wjjl} from "../module/collection_wjjl"
import {PublicShared} from "../shared/public/public"
import {PayFun} from "./pay"
import {TaskFun} from "./task"
import {CollectionWanted} from "../module/collection_wanted";
import {TanXianFun} from "./tanxian";
import {PataFun} from "./pata";
import {weixiuchangType} from "../shared/protocols/weixiuchang/type";
import {FunWeiXiuChang} from "./weixiuchang";
import {JJCFun} from "./jjc";
import {getGud} from "./gud";
import {Yuandanfun} from "../api_s2c/event/yuandan/fun";

let _classNameFunc = {}
/**
 * stype , isinc 分别是任务类型 是否累加
 * initVal： 获取初值方法， 返回整形, 默认初值为0
 * getVal: 获取设置的值， 默认返回(1, 0)
 * 事件类型： 类名
 */

export module manager {
    // 任务基类
    abstract class BaseClass {
        abstract stype
        abstract isinc

        constructor() {
            if (_classNameFunc[this.name]) {
                return
            }
            // 注册监听事件
            if (this.name) {
                this.addEventOn()
            }
            _classNameFunc[this.name] = this
        }

        // 获取初始任务值
        async getInitVal(call: ApiCall, con) {
            let _val = await this.initVal(call, con)
            return await this.fmtinitval(_val, con)
        }

        // 任务初值，根据任务情况是否重写
        async initVal(call: ApiCall, con) {
            return 0
        }

        // 初值处理
        async fmtinitval(val: number, con) {
            val = val < con["pval"] ? val : con["pval"]
            return val
        }

        // 数据检测，默认没有条件限制
        async chkCall(cond, chkval, arg) {
            if (cond.length == 0 || chkval == cond[0] || !chkval) {
                return 1
            }
            return 0
        }

        // 改变数值
        async alchangeVal(call: ApiCall, con, val: number, arg) {
            return val
        }

        // 设置数据
        async setVal(call: ApiCall, val: number, chkval, arg) {
            TaskFun.setTaskVal(call, this.stype, val, this.chkCall, chkval, this.isinc, this.alchangeVal, arg)
            // 养成目标任务计数
            YangChengMuBiaofun.setTaskVal(call, this.stype, val, this.chkCall, chkval, this.isinc, this.alchangeVal, arg)
            // 圣诞活动任务计数
            Christmasfun.setTaskVal(call, this.stype, val, this.chkCall, chkval, this.isinc, this.alchangeVal, arg)
            // 元旦活动任务计数
            Yuandanfun.setTaskVal(call, this.stype, val, this.chkCall, chkval, this.isinc, this.alchangeVal, arg)
        }

        // 任务数值， 和检测值，看情况需要上层复写
        async getVal(call: ApiCall, ...arg) {
            return arg[0]
        }

        // 事件处理
        async eventdo(eventname, call: ApiCall, ...arg) {
            if (eventname != this.name) {
                return 0
            }
            let [val, chkval] = await this.getVal(call, arg)
            this.setVal(call, val, chkval, arg)

            // 活动任务监听 todo

        }

        // 监听事件
        async addEventOn(this) {
            G.on(this.name.toString(), await this.eventdo.bind(this))
        }

        get name() {
            return this.constructor.name
        }

    }

    // 第一个任务  签到 n 次
    export class Class_task_100 extends BaseClass {
        stype = 100
        isinc = 1
    }

    // 第二个任务 升级 n 次干部
    export class Class_task_101 extends BaseClass {
        stype = 101
        isinc = 1
    }

    // 第3个任务 杂货铺购买 n 次
    export class Class_task_102 extends BaseClass {
        stype = 102
        isinc = 1
    }

    // 第4个任务 日常任务完成 n 次
    export class Class_task_999 extends BaseClass {
        stype = 999
        isinc = 1
    }

    // 第5个任务 成就任务完成 n 次
    export class Class_task_105 extends BaseClass {
        stype = 105
        isinc = 1
    }

    // 第6个任务 玩家等级升级 n 次
    export class Class_task_104 extends BaseClass {
        stype = 104
        isinc = 0

        async initVal(call: ApiCall, con) {
            return call.conn.gud?.lv || 1
        }
    }

    // 第7个任务 玩家通关主线关卡 n 次
    export class Class_task_1 extends BaseClass {
        stype = 1
        isinc = 0

        async initVal(call: ApiCall, con) {
            let gud = await call.conn.gud
            return gud["mapId"]
        }
    }

    // 第8个任务 干部等级达到 n 级
    export class Class_task_106 extends BaseClass {
        stype = 106
        isinc = 0

        async initVal(call: ApiCall, con) {
            let _chk = parseInt(con.cond[0])
            return await G.mongodb.collection('hero').countDocuments({uid: call.uid, lv: {$gte: _chk}}) || 0
        }

        async alchangeVal(call: ApiCall, con, val: number) {
            let _chk = parseInt(con.cond[0])
            return await G.mongodb.collection('hero').countDocuments({uid: call.uid, lv: {$gte: _chk}}) || 0
        }
    }

    // 第9个任务 同时出站 n 个干部
    export class Class_task_107 extends BaseClass {
        stype = 107
        isinc = 0

        async initVal(call: ApiCall, con) {
            let userchuzhan = await call.conn.getDefaultFightData()
            return Object.keys(userchuzhan.roles).length
        }
    }

    // 第10个任务 n 个干部进阶 配置k阶
    export class Class_task_108 extends BaseClass {
        stype = 108
        isinc = 0

        async initVal(call: ApiCall, con) {
            let _chk = parseInt(con.cond[0])
            let _num = await G.mongodb.collection('hero').countDocuments({uid: call.uid, jieji: {$gte: _chk}}) || 0
            return _num
        }

        async alchangeVal(call: ApiCall, con, val: number) {
            let _chk = parseInt(con.cond[0])
            let _num = await G.mongodb.collection('hero').countDocuments({uid: call.uid, jieji: {$gte: _chk}}) || 0
            return _num
        }
    }

    // 第11个任务 综合频道聊天 n 次
    export class Class_task_109 extends BaseClass {
        stype = 109
        isinc = 1
    }

    // 第12个任务 升级 n 次训练技能
    export class Class_task_110 extends BaseClass {
        stype = 110
        isinc = 0

        async initVal(call: ApiCall, con) {
            let skills = Object.assign({}, call.conn.gud.skills)
            let _num = Object.values(skills).sum()
            return _num
        }

        async alchangeVal(call: ApiCall, con, val: number) {
            let skills = Object.assign({}, call.conn.gud.skills)
            let _num = Object.values(skills).sum()
            return _num
        }
    }

    // 第13个任务 装备强化 n 次
    export class Class_task_111 extends BaseClass {
        stype = 111
        isinc = 1
    }

    // 第14个任务 装备强化到 n 级
    export class Class_task_112 extends BaseClass {
        stype = 112
        isinc = 0

        async initVal(call: ApiCall, con) {
            let usertasklog = await G.mongodb.collection('playerInfo', 'usertasklog').findOne({
                uid: call.uid,
                type: 'usertasklog'
            })
            return usertasklog?.maxequiplv | 0
        }
    }

    // 第15个任务 有 n 件强化 配置 等级装备
    export class Class_task_113 extends BaseClass {
        stype = 113
        isinc = 0

        async initVal(call: ApiCall, con) {
            let _chk = parseInt(con.cond[0])
            let _num = await G.mongodb.collection('equip').countDocuments({uid: call.uid, lv: {$gte: _chk}}) || 0
            return _num
        }

        async alchangeVal(call: ApiCall, con, val: number) {
            let _chk = parseInt(con.cond[0])
            let _num = await G.mongodb.collection('equip').countDocuments({uid: call.uid, lv: {$gte: _chk}}) || 0
            return _num
        }
    }

    // 第16个任务 获得 n 个 配置颜色 干部
    export class Class_task_114 extends BaseClass {
        stype = 114
        isinc = 1

        async initVal(call: ApiCall, con) {
            let color = con.cond[0].toString()
            let usertasklog = await G.mongodb.collection('playerInfo', 'usertasklog').findOne({
                uid: call.uid,
                type: 'usertasklog'
            })
            // 符合颜色的key取出来
            let array = (Object.keys(usertasklog?.herocolor || {})).filter(v => {
                return v >= color
            })
            let _val = 0
            for (let index = 0; index < array.length; index++) {
                // 累加符合的数量
                const element = array[index];
                _val += usertasklog.herocolor[element] || 0
            }
            return _val
        }

        async chkCall(cond, chkval, arg) {
            if (cond.length == 1 && chkval >= cond[0]) {
                return 1
            }
            return 0
        }
    }

    // 第17个任务 获得 n 个 配置颜色 装备
    export class Class_task_115 extends BaseClass {
        stype = 115
        isinc = 1

        async initVal(call: ApiCall, con) {
            let color = con.cond[0].toString()
            let usertasklog = await G.mongodb.collection('playerInfo', 'usertasklog').findOne({
                uid: call.uid,
                type: 'usertasklog'
            })
            // 符合颜色的key取出来
            let array = (Object.keys(usertasklog?.equipcolor || {})).filter(v => {
                return v >= color
            })
            let _val = 0
            for (let index = 0; index < array.length; index++) {
                // 累加符合的数量
                const element = array[index];
                _val += usertasklog.equipcolor[element] || 0
            }
            return _val
        }

        async chkCall(cond, chkval, arg) {
            if (cond.length == 1 && chkval >= cond[0].toString()) {
                return 1
            }
            return 0
        }
    }

    // 第18个任务 累计充值 n 钻石
    export class Class_task_116 extends BaseClass {
        stype = 116
        isinc = 0

        async initVal(call: ApiCall, con) {
            // let _val = 0
            // 成就任务走计数
            // if (con.type == 3) {
            //     _val = await PayFun.getPayDaysAllPayNum(call.uid, await PublicShared.getToDayZeroTime(G.openTime), G.time) * 10
            // }
            return (await getGud(call.uid)).payExp
        }

        async alchangeVal(call: ApiCall, con, val: number, arg) {
            // val = 0
            // let _where = {taskid: con.id, stype: con.stype}
            // let _task = await TaskFun.getUserTaksList(call.uid, _where)
            // if (_task[0]) {
            //     val = await PayFun.getPayDaysAllPayNum(call.uid, await PublicShared.getToDayZeroTime(_task[0].retime), G.time) * 10
            // }
            return (await getGud(call.uid)).payExp
        }
    }

    // 第19个任务 使用 n 次点金
    export class Class_task_117 extends BaseClass {
        stype = 117
        isinc = 1
    }

    // 第20个任务 酒吧招募 n 次
    export class Class_task_118 extends BaseClass {
        stype = 118
        isinc = 1
    }

    // 第21个任务 商店购买 n 次道具
    export class Class_task_119 extends BaseClass {
        stype = 119
        isinc = 1
    }

    // 第22个任务 探险进行 n 次战斗 不管输赢
    export class Class_task_120 extends BaseClass {
        stype = 120
        isinc = 1
    }

    // 第23个任务 势力捐献进行 n 次捐献
    export class Class_task_121 extends BaseClass {
        stype = 121
        isinc = 1
    }

    // 第24个任务 进行 n 次快速探险
    export class Class_task_122 extends BaseClass {
        stype = 122
        isinc = 1

        async initVal(call: ApiCall, con) {
            const data = await TanXianFun.getData(call);
            if (data?.resetTime > PublicShared.getToDayZeroTime()) {
                return data.useFastGuaJiNum || 0
            }
            return 0
        }
    }

    // 第25个任务 竞技场中挑战 n 次对手
    export class Class_task_123 extends BaseClass {
        stype = 123
        isinc = 1

        async initVal(call: ApiCall, con) {
            let data = await JJCFun.getData(call);
            if (data?.resetTime >= PublicShared.getToDayZeroTime()) {
                return data?.useFightNum || 0
            }
            return 0
        }
    }

    // 第26个任务 斩草除根进行 n 次通关或扫荡
    export class Class_task_124 extends BaseClass {
        stype = 124
        isinc = 1
    }

    // 第27个任务 挑战 n 次物资筹集
    export class Class_task_125 extends BaseClass {
        stype = 125
        isinc = 1

        async initVal(call: ApiCall, con) {
            let myData = await G.mongodb.cPlayerInfo('meirishilian').findOne({uid: call.uid, type: 'meirishilian'});
            if (myData.data.refreshTime > PublicShared.getToDayZeroTime()) {
                return R.compose(R.sum(), R.map(i => i[0].useFightNum), R.values())(myData.data.numInfo) || 0
            }
            return 0
        }
    }

    // 第28个任务 地盘争夺抢夺或战领 n 次
    export class Class_task_126 extends BaseClass {
        stype = 126
        isinc = 1
    }

    // 第29个任务 挑战 n 次清缴真主党
    export class Class_task_127 extends BaseClass {
        stype = 127
        isinc = 1

        async initVal(call: ApiCall, con) {
            let myData = await G.mongodb.cPlayerInfo('qjzzd').findOne({uid: call.uid, type: 'qjzzd'});
            if (myData?.refreFightTime > PublicShared.getToDayZeroTime()) {
                return myData?.useFightNum || 0
            }
            return 0
        }
    }

    // 第30个任务 今日登录
    export class Class_task_128 extends BaseClass {
        stype = 128
        isinc = 1

        async initVal(call: ApiCall, con) {
            // 任务直接完成
            return con.pval
        }
    }

    // 第31个任务 竞技场首次达到x名
    export class Class_task_129 extends BaseClass {
        stype = 129
        isinc = 0

        async initVal(call: ApiCall, con) {
            let _val = await Wjjl.getVal(call.uid, "jjc_rank")
            if (_val && _val <= con.pval) {
                return con.pval
            }
            return 0
        }

        async alchangeVal(call: ApiCall, con, val: number, arg) {
            let _val = await Wjjl.getVal(call.uid, "jjc_rank")
            if (_val && _val <= con.pval) {
                return con.pval
            }
            return 0
        }
    }

    // 第32个任务 在仓库使用 x 次交易10次(交易一次不算)
    export class Class_task_130 extends BaseClass {
        stype = 130
        isinc = 1
    }

    // 第33个任务 在仓库使用 x 次指定高级仓库
    export class Class_task_131 extends BaseClass {
        stype = 131
        isinc = 1
    }

    // 第34个任务 进行 x 次公路狂飙
    export class Class_task_132 extends BaseClass {
        stype = 132
        isinc = 1

        async initVal(call: ApiCall, con) {
            let data: Partial<CollectionWanted> = await G.mongodb.collection('wanted').findOne({uid: call.uid}) || {};
            if (data.refreshTime > PublicShared.getToDayZeroTime()) {
                return data.toDayUseNum || 0
            }
            return 0
        }
    }

    // 第35个任务 进行 x 教会招募
    export class Class_task_133 extends BaseClass {
        stype = 133
        isinc = 1
    }

    // 第36个任务 消耗 x 个 配置道具
    export class Class_task_134 extends BaseClass {
        stype = 134
        isinc = 1

        async alchangeVal(call: ApiCall, con, val: number, arg) {
            // todo 统计藏品修复胶，此处只是临时处理，防止线上任务数据出错，正确做法是，统计修复胶的消耗，走136任务的统计
            if (call.service.name == 'gongyu/mingdao/Repair' && typeof call.eventMsg?.['msg_s2c/PlayerChange']?.rmbmoney == 'number') {
                return val || 1
            }

            let _need = arg[2].filter(l => l.a == 'item')
            let _res = {}
            for (let index = 0; index < _need.length; index++) {
                const element = _need[index];
                if (!Object.keys(_res).includes(element.a)) _res[element.t] = 0
                _res[element.t] += element.n
            }

            let _val = Object.keys(_res).includes(con.cond[0].toString()) ? _res[con.cond[0]] : 0
            return _val
        }

        async chkCall(cond, chkval, arg) {
            let _val = 1
            if (_val == 0) {
                return 0   // 不知道怎么回事，这里强制返回1就报错
            }
            return 1
        }
    }

    // 第37个任务 累计登录天数
    export class Class_task_135 extends BaseClass {
        stype = 135
        isinc = 1

        // 第一天不会正常计数，直接设置1
        async initVal(call: ApiCall, con) {
            return 1
        }
    }

    // 第38个任务 修复 x 次名刀
    export class Class_task_136 extends BaseClass {
        stype = 136
        isinc = 1
    }

    // 第39个任务 获得 x 个 配置颜色 配件
    export class Class_task_137 extends BaseClass {
        stype = 137
        isinc = 1

        async alchangeVal(call: ApiCall, con, val: number, arg) {
            let _need = arg[2].filter(l => l.a == 'peijian')
            let _val = 0
            let _con = G.gc.peijian
            for (let index = 0; index < _need.length; index++) {
                const element = _need[index];
                let _peijian = _con[element.t]
                if (_peijian.colour >= con.cond[0]) {
                    _val += element.n
                }
            }
            return _val
        }

        async chkCall(cond, chkval, arg) {
            if (chkval == undefined) {
                return 0
            }
            return 1
        }
    }

    // 第40个任务 配件升级 xx 次
    export class Class_task_138 extends BaseClass {
        stype = 138
        isinc = 1
    }

    // 第41个任务 配件升级到 xx 级(无条件要求)
    export class Class_task_139 extends BaseClass {
        stype = 139
        isinc = 0

        async initVal(call: ApiCall, con) {
            let _chk = parseInt(con.cond[0])
            return await G.mongodb.collection('peijian').countDocuments({uid: call.uid, lv: {$gte: _chk}}) || 0
        }

        async alchangeVal(call: ApiCall, con, val: number) {
            let _chk = parseInt(con.cond[0])
            return await G.mongodb.collection('peijian').countDocuments({uid: call.uid, lv: {$gte: _chk}}) || 0
        }
    }

    // 第42个任务 配置 配件升级到 xx 级（颜色限制）
    export class Class_task_140 extends BaseClass {
        stype = 140
        isinc = 0

        async initVal(call: ApiCall, con) {
            let color = con.cond[0].toString()
            let usertasklog = await G.mongodb.collection('playerInfo', 'usertasklog').findOne({
                uid: call.uid,
                type: 'usertasklog'
            })
            // 符合颜色的key取出来
            let array = (Object.keys(usertasklog?.peijiancolor || {})).filter(v => {
                return v >= color
            })
            let _val = 0
            for (let index = 0; index < array.length; index++) {
                // 取出符合条件的最高等级
                const element = array[index];
                let _tmp = usertasklog.peijiancolor[element] || 0
                if (_tmp > _val) _val = _tmp
            }
            return _val
        }

        async chkCall(cond, chkval, arg) {
            if (cond.length == 1 && chkval >= parseInt(cond[0])) {
                return 1
            }
            return 0
        }
    }

    // 第43个任务 在仓库交易x次
    export class Class_task_141 extends BaseClass {
        stype = 141
        isinc = 1
    }

    // 第44个任务 势力 配置xx 捐献进行 n 次捐献
    export class Class_task_142 extends BaseClass {
        stype = 142
        isinc = 1

        async chkCall(cond, chkval, arg) {
            if (cond.length == 1 && chkval == parseInt(cond[0])) {
                return 1
            }
            return 0
        }
    }

    // 第45个任务 穿戴X件以上装备
    export class Class_task_143 extends BaseClass {
        stype = 143
        isinc = 0

        async initVal(call: ApiCall, con) {
            return await G.mongodb.collection('equip').countDocuments({uid: call.uid, wearaId: {$ne: ""}}) || 0
        }

        async alchangeVal(call: ApiCall, con, val: number) {
            return await G.mongodb.collection('equip').countDocuments({uid: call.uid, wearaId: {$ne: ""}}) || 0
        }

    }

    // 第46个任务 进行x次好友申请或送礼
    export class Class_task_144 extends BaseClass {
        stype = 144
        isinc = 1

        async initVal(call: ApiCall, con) {
            let usertasklog = await G.mongodb.collection('playerInfo', 'usertasklog').findOne({
                uid: call.uid,
                type: 'usertasklog'
            });
            return (usertasklog.friendAsk || 0) + (usertasklog.sendGift || 0)
        }

        async alchangeVal(call: ApiCall, con) {
            if (call.service.name == 'friend/Gift') {
                return call.return.res.change.sendGift.length || 0
            }
            return 1
        }
    }

    // 第47个任务 领取x次挂机收益
    export class Class_task_145 extends BaseClass {
        stype = 145
        isinc = 1
    }

    // 第48个任务 合成X次英雄
    export class Class_task_146 extends BaseClass {
        stype = 146
        isinc = 0
    }

    // 第49个任务 合成X次装备
    export class Class_task_147 extends BaseClass {
        stype = 147
        isinc = 0
    }

    // 第50个任务 主角的家布置计划上阵{1}个技能
    export class Class_task_148 extends BaseClass {
        stype = 148
        isinc = 0

        async initVal(call: ApiCall, con) {
            let _val = R.compose(R.filter(i => !!i), R.values())(call.conn.gud.fightSkills).length;
            return _val || 0
        }
    }

    // 第51个任务 黑暗塔通关至{1}层
    export class Class_task_149 extends BaseClass {
        stype = 149
        isinc = 0

        async initVal(call: ApiCall, con) {
            let changeInfo = await PataFun.getInfo(call.uid);
            return changeInfo.lv - 1 || 0
        }
    }

    // 第52个任务 维修厂进行{1}次安装或一键安装
    export class Class_task_150 extends BaseClass {
        stype = 150
        isinc = 1

        async initVal(call: ApiCall, con) {
            let data: weixiuchangType = await FunWeiXiuChang.getFindOne(call);
            if (data.star > 0 || data.schedule.find(i => i != 0)) {
                return 1
            }
            return 0
        }
    }

    // 第53个任务 出战阵型启用任意阵型
    export class Class_task_151 extends BaseClass {
        stype = 151
        isinc = 0

        async initVal(call: ApiCall, con) {
            return call.conn.gud.selectMatrix ? 1 : 0;
        }
    }

    // 第54个任务 升级{1}次阵型
    export class Class_task_152 extends BaseClass {
        stype = 152
        isinc = 1
    }

    // 第55个任务 干部助战上阵{1}个干部
    export class Class_task_153 extends BaseClass {
        stype = 153
        isinc = 1

        async initVal(call: ApiCall, con) {
            return call.conn.gud?.helpHeros?.length || 0;
        }
    }

    // 第56个任务 完成圣诞活动小游戏
    export class Class_task_154 extends BaseClass {
        stype = 154
        isinc = 1

        async initVal(call: ApiCall, con) {
            return 0;
        }
    }

    // 第57个任务 领取每日任务最终宝箱
    export class Class_task_155 extends BaseClass {
        stype = 155
        isinc = 0

        async initVal(call: ApiCall, con) {
            return 0;
        }
    }
    // 第58个任务 每日钻石消耗
    export class Class_task_156 extends BaseClass {
        stype = 156
        isinc = 1

        async initVal(call: ApiCall, con) {
            return 1;
        }
    }
    // 第59个任务 获得vip经验
    export class Class_task_157 extends BaseClass {
        stype = 157
        isinc = 1

        async initVal(call: ApiCall, con) {
            return 0;
        }
    }

    // 第60个任务 今日参与{1}次抓娃娃小游戏
    export class Class_task_158 extends BaseClass {
        stype = 158
        isinc = 1

        async initVal(call: ApiCall, con) {
            return 0;
        }
    }

}









