#ifndef __CLINETWAKERCLASS_H__
#define __CLINETWAKERCLASS_H__
/*
#include "ObjNet\ObjNet.h"
#include "ObjNet\lsockutil.h"
#include "ObjNet\lDebug.h"
*/
/*
#include <boost/function.hpp>
#include <boost/bind.hpp>
#include <functional>
*/
#include "netbridge/NetBridge.h"
#include "NetWakerPackage.h"
#include "NetWakerDefine.h"
#include "functionschedular\functionschedular.h"

#pragma unmanaged


class CliNetWakerClass;
using namespace std;
using namespace NetWakerPackage;
//---------------------------------------------------------------------------------
typedef void  (CliNetWakerClass::*NetPGCallBack) ( int	NetID , PGSysNULL* PG , int Size );
//#define NetPGCallBack         boost::function<void ( int , PGSysNULL*, int ) >
//---------------------------------------------------------------------------------
//處理與Switch & Proxy 間通訊傳輸的Class
/*
class LSwitch: public INewConnectionListener, public INetEventListener 
{ 
public:
    CliNetWakerClass	*Parent;
    INetEventListener* LSAPI OnNewConnection( LNETID ){return this;}
    void LSAPI OnConnected      ( LNETID NetID );
    void LSAPI OnDisconnected   ( LNETID NetID );
    void LSAPI OnPeerShutdown   ( LNETID NetID );
    bool LSAPI OnPacket         ( LNETID NetID, HBUFFER hIncomingData );
    void LSAPI OnConnectFailed  ( int NetID );
};
*/
class LBSwitch: public CEventObj
{
    CliNetWakerClass	*_Parent;
public:
    LBSwitch( CliNetWakerClass* value ) { _Parent = value; };
    virtual bool		OnRecv			( DWORD dwNetID, DWORD dwPackSize, PVOID pPacketData );
    virtual void		OnConnectFailed	( DWORD dwFailedCode );
    virtual void		OnConnect		( DWORD dwNetID );
    virtual	void		OnDisconnect	( DWORD dwNetID );
    virtual CEventObj*	OnAccept		( DWORD dwNetID );
};
//---------------------------------------------------------------------------------
//處理與Switch & Proxy 間通訊傳輸的Class
/*
class LProxy: public INewConnectionListener, public INetEventListener 
{ 
public:
    CliNetWakerClass	*Parent;
    INetEventListener* LSAPI OnNewConnection( LNETID ){return this;}
    void LSAPI OnConnected      ( LNETID NetID );
    void LSAPI OnDisconnected   ( LNETID NetID );
    void LSAPI OnPeerShutdown   ( LNETID NetID );
    bool LSAPI OnPacket         ( LNETID NetID, HBUFFER hIncomingData );
    void LSAPI OnConnectFailed  ( int NetID );
};
*/
class LBProxy: public CEventObj
{
    CliNetWakerClass	*_Parent;
public:
    LBProxy( CliNetWakerClass* value ) { _Parent = value; };
    virtual bool		OnRecv			( DWORD dwNetID, DWORD dwPackSize, PVOID pPacketData );
    virtual void		OnConnectFailed	( DWORD dwFailedCode );
    virtual void		OnConnect		( DWORD dwNetID );
    virtual	void		OnDisconnect	( DWORD dwNetID );
    virtual CEventObj*	OnAccept		( DWORD dwNetID );
};
//---------------------------------------------------------------------------------

class CliNetWakerClass
{
    friend	LBSwitch;	
    friend	LBProxy;	

    NewWakerEventListener*   _Listener;

    FunctionSchedularClass  _Schedular;

    CNetBridge*			    _NetBSwitch;			//主要是用連接Switch
    CNetBridge*			    _NetBProxy;  		//主要是用連接Proxy
    LBSwitch*		        _LBSwitch;           //資料列舉Class
    LBProxy* 		        _LBProxy;            //資料列舉Class
    int                     _ProxyNetID;
    int                     _SwitchNetID;

    int                     _ProxyID;           //所連到的Proxy 的 ID
    int                     _CliID;

    bool                    _ExitFlag;          //結束旗標
    bool                    _IsReady;           //登入ok


    set<int>			    _SrvConnect;	    //Cli 與 哪些 GSrv 連結

    char                    _Account[ _Max_CliAccount_Name_Size_ ];
    char                    _Password[ _Max_CliPassword_Name_Size_ ];

    void	_OnSwitchConnected        ( DWORD NetID );
    void	_OnSwitchDisconnected     ( DWORD NetID );
    bool	_OnSwitchPacket           ( DWORD NetID, DWORD Size , void* Data );
    void    _OnSwitchConnectFailed    ( DWORD NetID );


    void	_OnProxyConnected        ( DWORD NetID );
    void	_OnProxyDisconnected     ( DWORD NetID );
    bool	_OnProxyPacket           ( DWORD NetID, DWORD Size , void* Data );
    void    _OnProxyConnectFailed    ( DWORD NetID );

    NetPGCallBack		    _PGCallBack[ _Sys_Max_CallbackCount_ ];
    vector<PGBaseInfo>	    _PGInfo;			//封包管理的資訊
    //-----------------------------------------------------------------------------------
    // 封包Call Back 處理
    //-----------------------------------------------------------------------------------
    void _PGxUnKnoew( int NetID , PGSysNULL* PG , int Size );
    //-----------------------------------------------------------------------------------
    //(Switch)
    //登入資料要求
    void _PG_LoginInfoRequest(  int NetID , PGSysNULL* PG , int Size );
    
    //登入 Proxy 要求
    void _PG_LoginInProxyNotify( int NetID , PGSysNULL* PG , int Size );
    
    //-----------------------------------------------------------------------------------
    //(Proxy)
    //登入資料要求
    void _PG_LoginProxyRequest( int NetID , PGSysNULL* PG , int Size );

    //與 GSrv成立連線
    void _PGxGSrvOnConnect( int NetID , PGSysNULL* PG , int Size );
    //與 GSrv斷線
    void _PGxGSrvOnDisonnect( int NetID , PGSysNULL* PG , int Size );
    //收到 GSrv 轉送給 Client 的封包
    void _PGxDataGSrvToCli( int NetID , PGSysNULL* PG , int Size );

    //有其他的玩家用此帳號重新登入
    void _PGxCliRelogin( int NetID , PGSysNULL* PG , int Size );

    //-----------------------------------------------------------------------------------
    //重新連結 Switch Server
//    int  _ReConnectSwitch( SchedularInfo* Obj , void* InputClass );

    //-----------------------------------------------------------------------------------
    void	_ConnectProxy( UInt32 IPnum , int Port  );
public:

    CliNetWakerClass( );
    virtual ~CliNetWakerClass( );

    void	ConnectSwitch( char* IP,int Port , char* Account , char* Password );

    //定時處理
    bool	Process( );

    //登出
    bool    Logout( );

    //設定事件回呼函式
    void    SetListener(  NewWakerEventListener* );

    //
    bool    SendToSwitch( int Size , void* Data );
    bool    SendToProxy( int Size , void* Data );

    bool    SendToGSrv( int GSrvID , int Size , void* Data );
    //-----------------------------------------------------------------------------------
    // 初始化 Client 與 Server 的 CallBack函式
    //-----------------------------------------------------------------------------------
    void	InitPGCallBack( );

};

#pragma managed
#endif //__CLINETWAKERCLASS_H__