// Learn TypeScript:
//  - https://docs.cocos.com/creator/manual/en/scripting/typescript.html
// Learn Attribute:
//  - https://docs.cocos.com/creator/manual/en/scripting/reference/attributes.html
// Learn life-cycle callbacks:
//  - https://docs.cocos.com/creator/manual/en/scripting/life-cycle-callbacks.html

import IInitiator from "./initiators/IInitiator";
import EngineEvent from "./events/EngineEvent";
import LayerManager from "./gui/LayerManager";
import GUIManager from "./gui/GUIManager";


const {ccclass, property} = cc._decorator;

@ccclass
export default class GEngine extends cc.Component {

    /**
     * 启动器列表
     */
    private initiatorList:IInitiator[];
    private data:any;
    private index:number;
    private total:number;
    private currentInitiator:IInitiator;

    /**
     * 启动
     * @param initiatorList 启动器列表
     * @param data
     */
    Startup(initiatorList:IInitiator[],data?:any):void{
        this.initiatorList=initiatorList;
        this.data=data;
        this.index=0;
        this.total=this.initiatorList.length;
        this.Init();
        this.TryNext();
    }

    private Init():void{
        let layerRoot:cc.Node=this.data as cc.Node;
        LayerManager.single.Init(layerRoot,10);
    }

    /**
     * 尝试下一个
     */
    private TryNext(){
        if(this.initiatorList.length){
            this.currentInitiator=this.initiatorList.shift();
            this.currentInitiator.AddEvent(EngineEvent.PROGRESS,this,this.ProgressEventHandler,0);
            this.currentInitiator.AddEvent(EngineEvent.ERROR,this,this.ErrorEventHandler,0);
            this.currentInitiator.AddEvent(EngineEvent.COMPLETE,this,this.CompelteEventHandler,0);
            this.currentInitiator.Startup(this.data);
        }else{
            this.node.emit(EngineEvent.COMPLETE);
        }
    }

    private ProgressEventHandler(data?:any):void{
        let progress:number=this.index+this.currentInitiator.getProgress()/this.total;
        this.node.emit(EngineEvent.PROGRESS,progress);
    }
    
    private ErrorEventHandler(msg:string):void{
        this.node.emit(EngineEvent.ERROR,msg);
    }

    private CompelteEventHandler(data?:any):void{
        this.currentInitiator.Destroy();
        this.index++;
        this.TryNext();
    }

    onLoad(){
        GEngine.instance=this;
    }

    private static instance:GEngine;
    public static get single()
    {
        return this.instance;
    }
}
