/**
 * Created by Mai on 2017/4/1.
 */

var Ration = {
    createNew: function (project) {
        // 用户定义private方法
        var tools = {
        };

        // 所有通过this访问的属性，都不应在此单元外部进行写入操作
        var ration = function (proj) {
            this.project = proj;
            this.datas = null;

            var sourceType = ModuleNames.ration;
            this.getSourceType = function () {
                return sourceType;
            }
            proj.registerModule(ModuleNames.ration, this);

            var maxRationID = 0;
            this.getNewRationID = function () {
                return maxRationID += 1;
            };
            this.maxRationID = function (maxID) {
                if (arguments.length === 0) {
                    return maxRationID;
                } else {
                    maxRationID = Math.max(maxID, maxRationID);
                }
            };
        };

        // prototype用于定义public方法
        ration.prototype.loadData = function (datas) {
            var that = this;
            this.datas = datas;
            // generate Fees & Flags Index，For View & Calculate
            this.datas.forEach(function (data) {
                data.feesIndex = {};
                data.fees.forEach(function (fee) {
                    data.feesIndex[fee.fieldName] = fee;
                });
                data.flagsIndex = {};
                data.flags.forEach(function (flag) {
                    data.flagsIndex[flag.fieldName] = flag;
                });
                that.maxRationID(data.ID);
            });
        };

        ration.prototype.setMaxID = function (ID) {
            this.maxRationID(ID);
        }

        // refresh after update
        ration.prototype.doAfterUpdate = function(err, data){
            if(data.stateRefresh){
                this.refreshAdjustState(data);
            }
            if(data.quantityRefresh){
                this.refreshQuantity(data);
            }
        };
        ration.prototype.refreshAdjustState = function(data){
            this.refreshDatas(data,'adjustState');
            if(data.hasOwnProperty('name')){
              this.refreshDatas(data,'name')
            }
        };
        ration.prototype.refreshQuantity = function(data){
            this.refreshDatas(data,'quantity');
        };
        ration.prototype.refreshDatas = function(data,fieldName){
            var dataIndex = _.findIndex(this.datas,function(item) {
                return item.ID ==data.rationID;
            });
            this.datas[dataIndex][fieldName] = data[fieldName];
            if(fieldName=='quantity'){
                this.datas[dataIndex]['isFromDetail']=1
            }
            var controller = projectObj.mainController;
            var selected = controller.sheet.getSelections();
            var col =   _.findIndex(BillsGridSetting.cols,function (col) {
                return col.data.field ==fieldName;
            });
            controller.sheet.getCell(selected[0].row,col).value(data[fieldName]);
        };
        ration.prototype.getTempRationData = function (id, billsID, serialNo) {
            var newData = {'ID': id, 'serialNo': serialNo, projectID: this.project.ID()};
            newData[project.masterField.ration] = billsID;
            return newData;
        };

        ration.prototype.getBillsSortRation = function (billsID) {
            var rations = this.datas.filter(function (data) {
                return data[project.masterField.ration] === billsID;
            });
            rations.sort(function (x, y) {
                return x.serialNo - y.serialNo;
            });
            return rations;
        };

        ration.prototype.getInsertRationData = function (billsID, preRation) {
            var br = this.getBillsSortRation(billsID);
            var updateData = [];
            if (preRation) {
                var preIndex = br.indexOf(preRation), i;
                updateData.push({updateType: 'ut_create', updateData: this.getTempRationData(this.maxRationID() + 1, billsID, preIndex < br.length - 1 ? br[preIndex + 1].serialNo : br[preIndex].serialNo + 1)});
                for (i = preIndex + 1; i < br.length; i++) {
                    updateData.push({updateType: 'ut_update', updateData: this.getTempRationData(br[i].ID, billsID, i < br.length - 1 ? br[i+1].serialNo : br[i].serialNo + 1)});
                }
            } else {
                updateData.push({updateType: 'ut_create', updateData: this.getTempRationData(this.maxRationID() + 1, billsID, br.length > 0 ? br[br.length - 1].serialNo + 1 : 1)});
            }
            return updateData;
        };
        ration.prototype.getCounterData = function (count) {
            var updateData = {'projectID': this.project.ID()};
            if (count) {
                updateData[this.getSourceType()] = this.maxRationID() + count;
            } else {
                updateData[this.getSourceType()] = this.maxRationID() + 1;
            }
            return updateData;
        };
        ration.prototype.insertRation = function (billsID, preRation) {
            var br = this.getBillsSortRation(billsID);
            this.project.pushNow('insertRation', [this.getSourceType(), this.project.projCounter()],
                [this.getInsertRationData(billsID, preRation), this.getCounterData()]);

            var newRation = null;
            if (preRation) {
                var preIndex = br.indexOf(preRation), i;
                newRation = this.getTempRationData(this.getNewRationID(), billsID, preIndex < br.length - 1 ? br[preIndex + 1].serialNo : br[preIndex].serialNo + 1);
                this.datas.push(newRation);
                for (i = preIndex + 1; i < br.length; i++) {
                    br[i].serialNo = i < br.length - 1 ? br [i + 1].serialNo : br[i].serialNo + 1;
                }
            } else {
                newRation = this.getTempRationData(this.getNewRationID(), billsID, br.length > 0 ? br[br.length - 1].serialNo + 1 : 1);
                this.datas.push(newRation);
            }
            return newRation;
        };
        ration.prototype.insertStdRation = function (billsID, preRation, std) {
            var br = this.getBillsSortRation(billsID), updateData = this.getInsertRationData(billsID, preRation), newRation = null;
            updateData.forEach(function (data) {
                if (data.updateType === 'ut_create') {
                    data.updateData.code = std.code;
                    data.updateData.name = std.name;
                    data.updateData.caption=std.caption;
                    data.updateData.unit = std.unit;
                    data.updateData.libID = std.rationRepId;
                    data.updateData.rationAssList =  projectObj.project.ration_ass.CreateNewAss(std);
                    newRation = data.updateData;
                }
            });
            this.project.pushNow('insertRation', [this.getSourceType(), this.project.projCounter()], [updateData, this.getCounterData()]);

            newRation.ID = this.getNewRationID();
            if (preRation) {
                var preIndex = br.indexOf(preRation), i;
                this.datas.push(newRation);
                for (i = preIndex + 1; i < br.length; i++) {
                    br[i].serialNo = i < br.length - 1 ? br [i + 1].serialNo : br[i].serialNo + 1;
                }
            } else {
                this.datas.push(newRation);
            }
            return newRation;
        };

        ration.prototype.getDeleteData = function (rationData) {
            var updateData = [];
            updateData.push({'updateType': 'ut_delete', 'updateData': {'ID': rationData.ID, 'projectID': this.project.ID()}});
            return updateData;
        };
        ration.prototype.delete = function (ration) {
            var ration_glj =projectObj.project.ration_glj;
            this.project.pushNow('deleteRation', [this.getSourceType(),ration_glj.getSourceType()], [this.getDeleteData(ration),ration_glj.getDeleteDataByRation(ration)]);

            project.ration_glj.deleteByRation(ration);
            project.ration_coe.deleteByRation(ration);
            project.quantity_detail.deleteByRation(ration);
            this.datas.splice(this.datas.indexOf(ration), 1);
        };
        ration.prototype.getDeleteDataByBill = function (nodes) {
            let updateData = [];
            for (let node of nodes) {
                if (node.children.length > 0) {
                    updateData = updateData.concat(this.getDeleteDataByBills[node.children]);
                } else {
                    let rations = this.getBillsSortRation(node.getID());
                    for (let r of rations) {
                        updateData.push({'updateType': 'ut_delete', 'updateData': {'ID': r.ID, 'projectID': this.project.ID()}});
                    }
                }
            }
            return updateData;
        };
        ration.prototype.deleteByBills = function (nodes) {
            for (let node of nodes) {
                if (node.children.length > 0) {
                    this.deleteByBills([node.children]);
                } else {
                    let rations = this.getBillsSortRation(node.getID());
                    for (let r of rations) {
                        this.datas.splice(this.datas.indexOf(r), 1);
                    }
                }
            }
        }

        ration.prototype.getChangePosUpdateData = function (ration1, ration2) {
            var updateData = [];
            updateData.push({updateType: 'ut_update', updateData: this.getTempRationData(ration1.ID, ration1.billsItemID, ration2.serialNo)});
            updateData.push({updateType: 'ut_update', updateData: this.getTempRationData(ration2.ID, ration2.billsItemID, ration1.serialNo)});
            return updateData;
        };
        ration.prototype.changePos = function (ration1, ration2) {
            var updateData = this.getChangePosUpdateData(ration1, ration2);
            this.project.pushNow('insertRation', [this.getSourceType()], [updateData]);

            var preSerialNo = ration1.serialNo;
            ration1.serialNo = ration2.serialNo;
            ration2.serialNo = preSerialNo;
        };

        ration.prototype.updateField = function (ration, field, newValue) {
            calcFees.setFee(ration, field, newValue);
            let updateData = [];
            let data = {'ID': ration.ID, 'projectID': this.project.ID()};
            if (field === 'quantity') {
                data[field] = newValue;
                data.isFromDetail=0;
                // to do Calculate
                if (ration.fees) {
                    data.fees = ration.fees;
                }
            } else if (field === 'feesIndex.common.unitFee') {
                // to do Calculate
                if (ration.fees) {
                    data.fees = ration.fees;
                }
            } else {
                data[field] = newValue;
            }
            updateData.push({'updateType': 'ut_update', 'updateData': data});
            this.project.pushNow('updateBills', this.getSourceType(), updateData);
        };

        return new ration(project);
    }
};
