/**
 * Created by zhang on 2020/1/17.
 */
let itemBaseOptions = ["人工费","材料费","机械费","人工费+材料费","人工费+机械费","人工费+材料费","材料费+机械费","人工费+材料费+机械费"];
let itemIncreaseFeeObj = {
    settingSpread:null,
    itemSetting:{
        header:[
            {headerName: "名称", headerWidth: 270, dataCode: "name", dataType: "String"},
            {headerName: "范围", headerWidth: 70, dataCode: "displayScope",hAlign: "center",dataType: "String",cellType:'cusButton',callback:'selectScope'},
            {headerName: "取费基数", headerWidth: 150, dataCode: "base",  hAlign: "center", dataType: "String",cellType:'comboBox',options:itemBaseOptions},
            {headerName: "系数(%)", headerWidth: 55, dataCode: "coe", hAlign: "center", dataType: "Number",validator:"number"}
        ],
        view: {
            lockColumns: ["name","displayScope"],
            rowHeaderWidth:25,
            colHeaderHeight:36
        },
        autoFit:true,
        fitRow:['name'],
        callback:{
            selectScope:function (hitinfo) {
                $("#item_increase_scope").modal('show');
            }
        }
    },
    settingDatas:[],
    scopeSpread:null,
    scopeSetting:{
        header:[
            {headerName: "编码", headerWidth: 250, dataCode: "code", dataType: "String"},
            {headerName: "类别", headerWidth: 100, dataCode: "type",hAlign: "center",dataType: "String"},
            {headerName: "名称", headerWidth: 300, dataCode: "name", dataType: "String"},
            {headerName: "计取", headerWidth: 100, dataCode: "selected", hAlign: "center", dataType: "String",cellType:'checkBox'}
        ],
        view: {
            lockColumns: ["name","code","type","selected"],
            rowHeaderWidth:25,
            colHeaderHeight:36
        }
    },
    scopeDatas:[],
    initSpread:function () {
        if(this.settingSpread) return this.settingSpread.refresh();
        this.settingSpread = SheetDataHelper.createNewSpread($("#itemIncreaseFee_sheet")[0]);
        sheetCommonObj.spreadDefaultStyle(this.settingSpread);
        this.settingSheet = this.settingSpread.getSheet(0);
        sheetCommonObj.initSheet(this.settingSheet, this.itemSetting, 4);
        this.settingSheet.bind(GC.Spread.Sheets.Events.SelectionChanged,this.onItemSelectionChange);
        this.settingSheet.bind(GC.Spread.Sheets.Events.ValueChanged, this.onItemValueChange);
        this.settingSheet.name('itemIncreaseFee_sheet');
        if(projectReadOnly){
            sheetCommonObj.disableSpread(this.settingSpread);
        }
    },
    initScopeSpread:function () {
        if(this.scopeSpread) return this.scopeSpread.refresh();
        this.scopeSpread = SheetDataHelper.createNewSpread($("#scopeSheet")[0]);
        sheetCommonObj.spreadDefaultStyle(this.scopeSpread);
        this.scopeSheet = this.scopeSpread.getSheet(0);
        sheetCommonObj.initSheet(this.scopeSheet, this.scopeSetting, 0);
        this.scopeSpread.bind(GC.Spread.Sheets.Events.ButtonClicked, this.onScopeCheckBoxClick);
        this.scopeSheet.name('scopeSheet');
        if(projectReadOnly){
            sheetCommonObj.disableSpread(this.scopeSpread);
        }
    },
    getSelectedItem:function () {
        let selectedItem = null;
        let sel = this.settingSheet.getSelections()[0];
        if(sel.row != -1 && this.settingDatas.length>sel.row){
            selectedItem = this.settingDatas[sel.row];
        }
        return selectedItem;
    },
    showScopeDatas:function () {
        let controller = projectObj.mainController, project = projectObj.project;
        let allNodes=[];
        this.scopeDatas=[];
        let selectedItem = this.getSelectedItem();
        let fbfcNode = project.Bills.getFBFXNode(controller).source;//分部分项节点
        if(fbfcNode){
            allNodes.push(fbfcNode);
            controller.tree.getAllSubNode(project.Bills.getFBFXNode(controller).source,allNodes);
        }
        let meaNode = project.Bills.getMeasureNode(controller).source;//措施项目节点
        if(meaNode){
            allNodes.push(meaNode);
            controller.tree.getAllSubNode(project.Bills.getMeasureNode(controller).source,allNodes);
        }
        for(let row=0;row<allNodes.length;row++){
            let node = allNodes[row];
            let tem = {
                ID:node.data.ID,
                ParentID:node.data.ParentID,
                code:node.data.code,
                name:node.data.name,
                type:billText[node.data.type],
                selected:0,
                collapsed:false,
                row:row
            };
            if(selectedItem && selectedItem.scope&&selectedItem.scope[tem.ID]) tem.selected = 1;
            if(node.data.calcBase&&node.data.calcBase!="") delete tem.selected;//有基数计算的不可选
            this.scopeDatas.push(tem);
        }
        sheetCommonObj.showTreeData(this.scopeSheet, this.scopeSetting,this.scopeDatas);
    },
    onScopeCheckBoxClick:function (sender,args) {
        let me = itemIncreaseFeeObj;
        let checkboxValue = args.sheet.getCell(args.row, args.col).value();
        let newval = 0;
        checkboxValue?newval=0:newval=1;
        let record = me.scopeDatas[args.row];
        let dataMap= _.groupBy(me.scopeDatas,"ParentID");
        args.sheet.suspendPaint();
        args.sheet.suspendEvent();
        cascadeSelected(record,newval);
        args.sheet.resumeEvent();
        args.sheet.resumePaint();
        function cascadeSelected(parent,val) {
            if(gljUtil.isDef(parent.selected)){
                args.sheet.getCell(parent.row, args.col).value(val);
                parent.selected = val;
                if(dataMap[parent.ID]){
                    for(let c of dataMap[parent.ID]){
                        cascadeSelected(c,val);
                    }
                }
            }
        }
    },
    onItemSelectionChange:function (sender,args) {
        args.sheet.repaint();
    },
    showDatas:function(datas){
        let sel = this.settingSheet.getSelections()[0];
        let oldData = sel.row<this.settingDatas.length?this.settingDatas[sel.row]:"";
        this.settingSheet.setRowCount(0);
        this.settingDatas = datas?datas:this.getItemSettingDatas();
        this.setItemForeStyle(this.settingDatas);
        sheetCommonObj.showData(this.settingSheet, this.itemSetting,this.settingDatas);
        this.settingSheet.setRowCount(this.settingDatas.length);
        sel.row =  oldData?_.findIndex(this.settingDatas,{'name':oldData.name}):sel.row ;
        this.settingSheet.setSelection(sel.row==-1?0:sel.row,sel.col,sel.rowCount,sel.colCount);
    },
    setItemForeStyle:function (datas) {
        for(let d of datas){
            if(_.isEmpty(d.scope)){
                d.foreColor = "#ff2a23";
                d.styleCol = 1;
            }else {
                delete  d.foreColor;
                delete  d.styleCol;
            }
        }
    },

    getItemSettingDatas:function () {
        let datas = [];
        if(projectObj.project.property.itemIncreaseSetting){
            for(let i of projectObj.project.property.itemIncreaseSetting.setting){
                let d = {name:i.name,displayScope:"范围",scope:i.scope,base:i.base,coe:i.coe};
                datas.push(d);
            }
        }
        return datas;
    },
    isItemIncrease: function (node) {
        return node
        && node.sourceType === ModuleNames.ration
        && node.data.type === rationType.itemIncrease;
    },
    onItemValueChange:function (sender,args) {
        let me = itemIncreaseFeeObj;
        let dataCode = me.itemSetting.header[args.col].dataCode;
        let value = args.newValue;
        let tem = me.settingDatas[args.row];
        if (value&&!sheetCommonObj.checkData(args.col,me.itemSetting,value)) {
            alert('输入的数据类型不对，请重新输入!');
            return  me.showDatas(me.settingDatas);
        }
        if(dataCode == 'coe') {
            if (value) value = scMathUtil.roundForObj(value, 2);
        }
        tem[dataCode] = value;
        me.showDatas(me.settingDatas);
        me.itemChange = true;
    },
    confirmScope:function(){
        let selectedItem = this.getSelectedItem();
        let scope = {};
        for(let n of this.scopeDatas){
            if(n.selected == 1) scope[n.ID] = true;
        }
        if(JSON.stringify(scope) != JSON.stringify(selectedItem.scope)) this.itemChange = true;//有改变的情况下才更新
        selectedItem.scope=scope;
        this.showDatas(this.settingDatas);
    },
    confirmItemIncreaseSetting:async function () {
        if(this.itemChange == true || projectObj.project.property.itemIncreaseSetting.isCalc == false){
            let datas = [];
            let itemIncreaseSetting = {
                isCalc : true,
                setting :[]
            };
            for(let d of this.settingDatas){
                itemIncreaseSetting.setting.push({name:d.name,scope:d.scope,base:d.base,coe:d.coe});
            }
            let tem ={
                type:'project',
                data:{ID:projectObj.project.ID(),"property.itemIncreaseSetting":itemIncreaseSetting}
            };
            datas.push(tem);
            let changeNodes = this.calcAllItemIncreaseFee(itemIncreaseSetting,datas);
            console.log(datas);
            let selectedNode = projectObj.project.mainTree.selected;
            //刷新缓存和树节点的插入删除
            let nodes = await projectObj.project.syncUpdateNodesAndRefresh(datas);
            //重新计算
            cbTools.refreshFormulaNodes();
            projectObj.project.calcProgram.calcNodesAndSave(changeNodes.concat(nodes));
            projectObj.mainController.setTreeSelection(selectedNode);

        }
    },


    calcItemIncreaseFeeByNodes:async function (nodes) {
        let itemIncreaseSetting = projectObj.project.property.itemIncreaseSetting;
        let datas = [];
        let refreshNodes=[];
        let rationGLJMap ={};
        let uniqMap={};
        if(!itemIncreaseSetting) return;
        if(itemIncreaseSetting.isCalc == false) return;
        for (n of nodes){
            if(n.sourceType == ModuleNames.ration) n = n.parent;
            if(uniqMap[n.data.ID]) continue;//去重复
            let newRefreshNodes = this.calcItemIncreasePerNode(n,itemIncreaseSetting,rationGLJMap,datas);
            if(newRefreshNodes.length > 0) refreshNodes = refreshNodes.concat(newRefreshNodes);
            uniqMap[n.data.ID] = true;
        }
        if(datas.length >0 || refreshNodes.length > 0){
            let nodes = await projectObj.project.syncUpdateNodesAndRefresh(datas);
            //重新计算
            cbTools.refreshFormulaNodes();
            projectObj.project.calcProgram.calcNodesAndSave(refreshNodes.concat(nodes));

        }

    },
    cancelItemIncreaseFee:async function () {
        let itemIncreaseSetting = projectObj.project.property.itemIncreaseSetting;
        let datas = [];
        let refreshNodes = [];
        if(itemIncreaseSetting && itemIncreaseSetting.isCalc == true){
            itemIncreaseSetting.isCalc = false;
            let billNodeMap = {};
            let tem ={
                type:'project',
                data:{ID:projectObj.project.ID(),"property.itemIncreaseSetting":itemIncreaseSetting}
            };
            datas.push(tem);
            for(let s of itemIncreaseSetting.setting){
                if(!_.isEmpty(s.scope)){
                    for (let ID in s.scope){
                        billNodeMap[ID] = true;//为了去重复
                    }
                }
            }
            for(let cancelID in billNodeMap){
                let tnode = projectObj.project.mainTree.getNodeByID(cancelID);
                if(tnode){
                    let cNode = this.cancelBillNode(tnode,datas);
                    if(cNode) refreshNodes.push(cNode);
                }
            }
            let selectedNode = projectObj.project.mainTree.selected;
            //刷新缓存和树节点的插入删除
            await projectObj.project.syncUpdateNodesAndRefresh(datas);
            if(refreshNodes.length > 0){
                //重新计算
                cbTools.refreshFormulaNodes();
                projectObj.project.calcProgram.calcNodesAndSave(refreshNodes);
                projectObj.mainController.setTreeSelection(selectedNode);
            }
        }
    },
    getAllBillsIDMap:function () {
        let map = {};
        let itemIncreaseSetting = projectObj.project.property.itemIncreaseSetting;
        if(itemIncreaseSetting.isCalc == true){
            for(let s of itemIncreaseSetting.setting){
                if(!_.isEmpty(s.scope)){
                    for (let ID in s.scope){
                        map[ID] = true;
                    }
                }
            }
        }
        return map;
    },

    calcAllItemIncreaseFee : function(setting,datas){
        let refreshNodes = [];
        let itemIncreaseSetting = setting?setting:projectObj.project.property.itemIncreaseSetting;
        let billNodeMap = {},rationGLJMap={};
        let cancelBillsIDMap = this.getAllBillsIDMap();
        if(itemIncreaseSetting && itemIncreaseSetting.isCalc == true){
            //为了不用循环所有节点，先挑出所有受影响的节点
            for(let s of itemIncreaseSetting.setting){
                if(!_.isEmpty(s.scope)){
                    for (let ID in s.scope){
                        billNodeMap[ID] = true;//为了去重复
                        delete cancelBillsIDMap[ID];
                    }
                }
            }
            for(let billsID in billNodeMap){
                let node = projectObj.project.mainTree.getNodeByID(billsID);
                let newRefreshNodes = this.calcItemIncreasePerNode(node,itemIncreaseSetting,rationGLJMap,datas);
                if(newRefreshNodes.length > 0) refreshNodes = refreshNodes.concat(newRefreshNodes);
            }
            //删除取消范围的清单下的子目定额
            for(let cancelID in cancelBillsIDMap){
                let tnode = projectObj.project.mainTree.getNodeByID(cancelID);
                let cNode = this.cancelBillNode(tnode,datas);
                if(cNode) refreshNodes.push(cNode);
            }
        }
        return refreshNodes;
    },
    cancelBillNode:function (node,datas) {
        if (node.children.length <= 0) return null;//如果没子项，不用计算
        if (node.source.children.length > 0) return null;//如果不是清单叶子节点，不用计算
        let isDelete = false;
        for(let rationNode of node.children){
            if(rationNode.data.code.indexOf("ZMZJF")!= -1){
                datas.push({type:ModuleNames.ration,data:{ID:rationNode.data.ID},action:"delete"});
                isDelete = true;
            }
        }
        return isDelete == true?node:null;
    },


    calcItemIncreasePerNode:function (node,setting,rationGLJMap,datas) {
        let itemIncreaseSetting = setting ? setting : projectObj.project.property.itemIncreaseSetting;
        let refreshNodes = [],rationCodeMap={},FeeMap={},updateDataIDMap={};
        if (node.children.length <= 0) return [];//如果没子项，不用计算
        if (node.source.children.length > 0) return [];//如果不是清单叶子节点，不用计算
        let labourTotal = 0,materialTotal=0,machineTotal=0;
        let process = getDecimal("process");
        let td = getDecimal("ration.totalPrice");
        let gd = getDecimal('glj.quantity');
        let preID="",serialNo=1;
        let manageFeeRate = null;
        for(let rationNode of node.children){
            rationCodeMap[rationNode.data.code] = rationNode;
            if(rationNode.data.type == rationType.ration || rationNode.data.type == rationType.volumePrice ){//先只汇总定额和量价类型，不考虑自动生成的
                if(manageFeeRate == null) manageFeeRate = rationNode.data.manageFeeRate;
                //计算人工费，材料费，机械费
                if(rationNode.data.feesIndex){
                    let labour = rationNode.data.feesIndex.labour && rationNode.data.feesIndex.labour.totalFee?parseFloat(rationNode.data.feesIndex.labour.totalFee):0;
                    let material = rationNode.data.feesIndex.material && rationNode.data.feesIndex.material.totalFee?parseFloat(rationNode.data.feesIndex.material.totalFee):0;
                    let machine = rationNode.data.feesIndex.machine && rationNode.data.feesIndex.machine.totalFee?parseFloat(rationNode.data.feesIndex.machine.totalFee):0;
                    labourTotal = scMathUtil.roundForObj(labourTotal + labour,getDecimal("process"));
                    materialTotal = scMathUtil.roundForObj(materialTotal + material,getDecimal("process"));
                    machineTotal = scMathUtil.roundForObj(machineTotal + machine,getDecimal("process"));
                }
            }
            if(rationNode.data.type != rationType.itemIncrease ){//计录除了子目增加节点外最后的节点ID，和nexeID
                preID = rationNode.data.ID;
                serialNo = rationNode.data.serialNo;
            }
        }
        FeeMap['人工费'] = labourTotal;
        FeeMap['材料费'] = materialTotal;
        FeeMap['机械费'] = machineTotal;
        //ZMZJF_1
        let s_in = 0;//序列号增长
        for(let i = 0; i < itemIncreaseSetting.setting.length;i++){
            let s = itemIncreaseSetting.setting[i];
            if(s.scope&&s.scope[node.data.ID]){
                let feeIndexArry = s.base.split("+");
                let total = 0;
                for(let index of feeIndexArry){
                    total = scMathUtil.roundForObj(total + FeeMap[index],process);
                }
                total = scMathUtil.roundForObj(total,td);
                if(s.coe){
                    let t = scMathUtil.roundForObj(total * s.coe/100,process);
                    total =  t;//scMathUtil.roundForObj(total + t,gd);
                }
                let seq = i+1;
                let code = "ZMZJF_"+seq;
                let ZMZJFnode = rationCodeMap[code];
                if(total > 0) {
                    if(ZMZJFnode){//存在的话更新其它人工费消耗量
                        this.updateItemNode(ZMZJFnode,total,rationGLJMap,datas);
                        if(s_in>0){
                            datas.push({type:ModuleNames.ration,data:{ID:ZMZJFnode.data.ID,serialNo:ZMZJFnode.data.serialNo +1}});
                        } else {//如果s_in>0时，ZMZJFnode会因为有更新而刷新，不用push到refreshNodes里
                            refreshNodes.push(ZMZJFnode);
                        }
                        preID = ZMZJFnode.data.ID;
                        serialNo = ZMZJFnode.data.serialNo;
                    }else {//不存在的话插入新的节点
                        s_in = s_in +1;
                        serialNo = serialNo+1;
                        let newRationData = this.inserNewItemNodes(node.data.ID,node.data.quantity,preID,serialNo,code,s.name,total,datas);
                        preID = newRationData.ID;
                        if(!_.isEmpty(installationFeeObj.feeRateMap))newRationData.manageFeeRate = manageFeeRate;
                    }
                }else { //如果total小于0，但又存在的话，删除定额（同时后端处理时记得要删除定额工料机）
                    if(ZMZJFnode){
                        datas.push({type:ModuleNames.ration,data:{ID:ZMZJFnode.data.ID},action:"delete"});
                        if(refreshNodes.length == 0) refreshNodes.push(node);//删除时，如果清单下没有定额更新，则刷新清单节点就行
                    }
                }
            }
        }
        return refreshNodes;
    },
    updateItemNode:function (node,total,rationGLJMap,datas) {
        if(_.isEmpty(rationGLJMap)) this.setRationGLJMap(rationGLJMap);
        if(rationGLJMap[node.data.ID] && rationGLJMap[node.data.ID].quantity != total){
            datas.push({type:ModuleNames.ration_glj,data:{ID:rationGLJMap[node.data.ID].ID,quantity:total}})
        }
    },
    setRationGLJMap:function (rationGLJMap) {
        let gljList =  projectObj.project.ration_glj.datas;
        for (let g of gljList){
            if(g.code == 'QTRGF') rationGLJMap[g.rationID] = g;
        }
    },
    inserNewItemNodes:function (billsItemID,billsQuantity,preID,serialNo,code,name,total,datas) {
        let Ration = projectObj.project.Ration;
        let newRationData = Ration.getTempRationData(Ration.getNewRationID(), billsItemID, serialNo, rationType.itemIncrease);
        newRationData.code = code;
        newRationData.name=name;
        newRationData.unit = '元';
        newRationData.quantity = "1";
        if(billsQuantity) newRationData.contain = scMathUtil.roundForObj(1/parseFloat(billsQuantity),getDecimal("process"))+"";
        newRationData.quantityEXP = '1';
        datas.push({type:ModuleNames.ration,data:newRationData,preSiblingID:preID,action:"add",parentID:billsItemID});
        let newRationGLJ = {
            rationID:newRationData.ID,
            billsItemID:billsItemID,
            shortName:projectObj.project.projectGLJ.getShortNameByID(gljType.LABOUR),
            GLJID:-1,
            projectID:newRationData.projectID,
            code:'QTRGF',
            original_code:'QTRGF',
            name:'其它人工费',
            specs:'',
            unit:'元',
            type:gljType.LABOUR,
            basePrice:1,
            marketPrice:1,
            adjCoe:null,
            from:'std',
            repositoryId:-1,
            quantity:total+"",
            rationItemQuantity:total+""
        };
        datas.push({type:ModuleNames.ration_glj,data:newRationGLJ,action:"add"});
        return newRationData;
    }
};






$(function () {


    $('#itemIncreaseFeeDiv').on('shown.bs.modal', function (e) {
        itemIncreaseFeeObj.itemChange = false;
        itemIncreaseFeeObj.initSpread();
        itemIncreaseFeeObj.showDatas();
    });

    $('#item_increase_scope').on('shown.bs.modal', function (e) {
        itemIncreaseFeeObj.initScopeSpread();
        itemIncreaseFeeObj.showScopeDatas();
    });
    
    $("#select_scope_confirm").click(function () {
        itemIncreaseFeeObj.confirmScope();
    })

    $("#itemIncreaseFeeConfirm").click(function () {
        itemIncreaseFeeObj.confirmItemIncreaseSetting();
    })
});