#ifndef _STATIC_DATA_
#define _STATIC_DATA_

#include <HPLE3DLapper.h>

#include "resource.h"

#include "GEnum.h"
#include "EnemyLifeBar.h"

#include "Weapon.h"

#include "EnemyManager.h"
#include "ShotManager.h"
#include "NeutralManager.h"

#include "TitleScene.h"

using namespace HPL;
using namespace E3D;

namespace MotionTest {

/** モーションテストの定数
  *
  */
namespace MotionTestConsts {
	static const float GRAVITY = -3.0f;
	static const float GROUND_SIZE = 60000.0f;
	static const float GROUND_DIVX = 30.f;
	static const float GROUND_DIVZ = 30.f;
	static const float GROUND_HEIGHT = 0.f;

	static const float PLAYER_WALK_SPEED = 20.f;
	static const float PLAYER_RUN_SPEED = 120.f;
	static const float PLAYER_BACKWARD_SPEED = 20.f;
	static const float PLAYER_STRAIF_SPEED = 20.f;
	static const int PLAYER_ROTATE_DIVISION = 3;
	static const float PLAYER_BLOWEN_SPEED_RATE = 2.f;
	//static const float MOUSE_LOOK_ZOOM_STEP = 10.f;		//! カメラ遠近変更ステップ
	static const float MOUSE_LOOK_ZOOM_MAX = 10000.f;		//! カメラ遠近変更最大値
	static const float MOUSE_LOOK_ZOOM_MIN = 800.f;		//! カメラ遠近変更最小値
	static const float MOUSE_LOOK_ZOOM_STEP_RATE = 0.001f;	//! カメラ拡大変更割合(現在の距離*この値=変更量)

	static const int OBJECT_MAX = 10;
	static const int WORM_BIG_MAX = 1;
	static const int WORM_SMALL_MAX = 10;
	static const int ENEMY_LIFE_BAR_STACK_NUM_MAX = 5;
	static const int ENEMY_LIFE_BAR_INTERVAL_Y = 5;
	static const int ENEMY_LIFE_BAR_REMAIN_COUNT = 30;
	static const float ENEMY_WALK_RATE = 1.3f;
	static const float RECOGNIZE_THRESHOLD = 20000.f;
	static const int ZOMBIE_MAX = 10;
	static const float ZOMBIE_HOLD_DISTANCE = 400.f;
	static const int MOSUKO_MAX = 20;
	static const int ZOMBIE_B_MAX = 1;
	static const float ZOMBIE_B_JUMP_SPEED = 20.f;

	static const int SHOT_MAX = 20;
	static const int SHOT_LIFE_COUNT = 120;
	static const float SHOT_SPEED = 500.f;
	static const float SHOT_SIZE = 200.f;
//	static const float SHOT_AT_TARGET_MODE_ERROR = 5.f;	//! 発射方向のズレ(度) TODO 武器ごとに異なる
//	static const float SHOT_SHOT_BEHIND_MODE_ERROR = 2.f;
	static const float SHOT_AT_TARGET_MODE_ERROR_RATE = 2.5f;

	static const int SHELL_LIFE_COUNT = 50;

	static const int MISSILE_MAX = 10;
	static const int SHELL_MAX = 10;
	static const float SHELL_SPEED = 25.f;
	static const float SHELL_ERROR = 5.f;
	static const float HEAD_ERROR = 5.f;
	static const float HEAD_SPEED = 70.f;

	static const float MAP_SIZE = 60000;
	static const int MAP_DIV = 30;
	static const float MAP_HEIGHT = 200000.f;
	static const float MAP_MIN = -100.f;

	//static const int MAP_NUM = 1;
	static const float PLAYER_JUMP_SPEED_Y = 70.f;
	static const float PLAYER_JUMP_ACCEL_Y = 30.f;

	static const int LIFE_FRAME_MERGINE = 10;			//! ライフバーのフレームを画面端からどれだけ離して描画するか
	//static const int LIFE_BAR_LEFT_DELTA = 12;
	//static const int LIFE_BAR_TOP_DELTA = 12;

	static const int LIFE_AND_GUNS_MERGINE = 10;	//! 装備表示とライフフレームの間のスキマ
	static const int AMMO_TEXT_MERGINE = 60;
	static const int UI_ALPHA = 180;
	static const int WINDOW_FRAME_DELTA = 10;

	static const int TEXT_DELTA_X = 0;
	static const int TEXT_DELTA_Y = 0;

	static const float ENEMY_DAMAGE = 10;
	static const float PLAYER_DAMAGE_MIN_DISTANCE = 100.f;

	static const float SHOT_POWER = 10;
	static const float SHOT_MISSILE_POWER = 100;

	static const int DEFAULT_GENERATE_COUNTER = 100;
	static const int GENERATE_DECREASE_STEP = 1;

	static const int MEDI_KIT_NUM = 10;
	static const int AMMO_NUM = 10;
	static const int MEAT_NUM = 3;
	static const int CONSOLE_NUM = 10;

	static const int ITEM_REMAIN_COUNTER_MAX = 20000;

	static const float MEDI_KIT_HEAL_RATE = 0.3f;
	static const float MEAT_HEAL_RATE = 1.f;

	static const float SHOT_FROM_DISTANCE = 1200.f;

	static const float CLOTH_ALPHA_STEP = 0.1f;

	static const int OPTION_MERGINE_X = 170;
	static const int OPTION_TEXT_MERGINE_Y = 8;				//! タイトル画面、右のオプション位置

	static const int BLOOD_MAX = 10;						//! 血飛沫MAX
	static const float BLOOD_SIZE = 300.f;
	static const int BLOOD_LIFE_COUNT = 120;
	static const float BLOOD_SPEED = 100.f;
	static const int PLAYER_DAMAGE_BLOOD_NUM = 10;
	static const float BLOOD_ERROR_DEGREE = 60.f;

	static const long TITLE_ROTATE_Y_SPEED = 1;
	namespace Sprite {
		enum {
			CROSS_HAIR,
			LIFE_FRAME,
			LIFE_BAR,
			GUN_01_MINI_GUN,
			ENEMY_LIFE_BAR,
			GUN_02_MACHINE_GUN,
			GUN_03_MISSILE_LAUNCHER,
			TITLE,
			TITLE_SUBJECT,
			GUN_04_HAND_GUN,
			GUN_05_GRANADE_LAUNCHER,
			SELECT_MISSION,
			MISSION_FRAME,
			PREVIOUS_BUTTON,
			NEXT_BUTTON,
			MESSAGE_FRAME,
			CHECK_BOX,
			CHECK_BOX_CHECKED,
			//LOADING_SCREEN,
			TITLE_SCREEN,
			GUN_06_CROWBAR,
		};
	}
	namespace Motion {
		namespace Evigen {
			enum {
				IDLE,
				RUN,
				WALK,
				CROUCH,
				JUMP_UP,
				JUMP_DOWN,
				MINI_GUN_SETTLE,// 構え
				MINI_GUN_FIRE,	// 発射
				MINI_GUN_UP,	// 持ち上げ
				MINI_GUN_CARRY,	// 撃ってない状態
				MINI_GUN_DOWN,	// 構え状態に入る
				DAMAGE_A,		// 小ダメージ
				DAMAGE_B,		// 中ダメージ
				DAMAGE_CRASH_UP,// 吹っ飛び
				DAMAGE_BOUND,	// 着地
				DOWN,			//ダウンand吹っ飛びで死亡
				DEATH,
				RETURN,			// 戻り
				HAND_GUN_IDLE,		//待機
				HAND_GUN_SETTLE,	//構え
				HAND_GUN_FIRE,
				HAND_GUN_UP,
				HAND_GUN_DOWN,
				HAND_GUN_RELOAD,
				SWALLOW,			//丸呑まれ
			};
		}
		namespace Tanya{
			enum {
				IDLE,
				WALK,
				RUN,
				CROUCH,
				JUMP_UP,
				JUMP_DOWN,
				BAR_SET,
				BAR_ATTACK,
			};
		}
		namespace Worm{
			enum {
				IDLE,
				TURN_RIGHT,
				TURN_LEFT,
				MOVE,				//前進
				DIVE,
				APPEAR,
				STAND,
				ATTACK_A,			// 立ち上がり→噛み付き
				DOWN_DIVE,			// 立ち上がり→潜り
				BRITS,				// 口を開けて突進
				ATTACK_B,			// もぐり中に噛み付き
				VOMIT,				// 吐き出し
				DEAD,				// 死ぬ
				DOWN,				// たち状態からMOVEに移行
				SWALLOW,			// 丸呑み
			};
		}

		namespace Zombie {
			enum {
				IDLE,
				WALK,
				ATTACK_A,			// 攻撃１
				ATTACK_B,			// 攻撃２
				ATTACK_C,			// ホールド。-> HOLDへ。
				HOLD,				// 噛み付き
				RELEASE,			// プレイヤー解放
				DEAD,				// 死亡
			};
		}
		namespace Zombie_B {
			enum {
				IDLE,
				RUN,
				JUMP_ON,			// ジャンプ開始
				JUMP_ATTACK,
				ATTACK_A,			// 地上攻撃。やや前進
				AIR_DAMAGE,
				DEAD,

			};
		}

		namespace Head {
			enum {
				IDLE,
				I_CAN_FLY,
				SLEEP,
			};
		}

		namespace Mosuko {
			enum {
				IDLE,
				RUN,
				SIDEWALK,
				GUN,
				ATTACK_A,
				ATTACK_B,
				ATTACK_C,
			
			};
		}
		namespace Trol {
			enum {
				IDLE,
				WALK,
				JUMP_UP,
				JUMP_DOWN,
				ATTACK,
			};
		}
	}

	namespace Parts {
		// 上から着ているものから順にする。
		enum {
			CLOTH,
			APRON,
			BRA,
			PANTS,
			GARTER,

			MAX_NUM
		};
	}

	namespace TanyaParts {
		enum {
			CLOTH,
			WEAR,
			PANTS,

			MAX_NUM,
		};
	}

	namespace SceneType {
		enum {
			TITLE,
			SELECT_MISSION,
			BRIEFING,
			GAME,
			ENEMY_MODE,
			GAME_OVER,
		};
	}

	namespace Material {
		enum {
			NORMAL,
			SHOOT,
			DAMAGE,
			DAMAGE_CRASH,
			DOWN,

			CLOTH_NORMAL,
			CLOTH_BREAK,

			KARADA_NORMAL,
			KARADA_DAMAGE,
			KARADA_BLACK,
			KARADA_DAMAGE_BLACK,

			UNDER,
			UNDER_BLACK,

			// MOSUKO
			MOSUKO_HAIR,	//blue
			MOSUKO_HAIR_GOLD,
			MOSUKO_KAO_1,	//normal
			MOSUKO_KAO_2,	//attack
			MOSUKO_KAO_3,	//raped
			MOSUKO_KAO_4,	//damage/death
			MOSUKO_KAO_5,	//higii
			
			//
			MOSUKO_KARADA_1,	//naked
			MOSUKO_KARADA_2,	// ?
			MOSUKO_KARADA_3,	//cloth(スカートはこれ固定)
			MOSUKO_KARADA_4,	//SUKUMIZU


			MAX_NUM
		};
	}
	namespace GroundType {
		enum {
			TEST,
			DANIMOTH_ROOM,
			EVIL_STAR,
			PRACTICE_ROOM,
			ZOMBIE,
			WORM,
			MAX_NUM
		};
	}

	namespace WallType {
		enum {
			PRACTICE_ROOM,
			ZOMBIE,
			WORM,
			MAX_NUM,
		};
	}
	namespace Sound {
		enum {
			TITLE,
			GAME,
			PANIC,
			EVIL_STAR,
			TROL,

			BGM_NUM,

			GUN = BGM_NUM,
			ENEMY_HIT_1,
			ENEMY_HIT_2,
			VOICE_HIT_1,
			VOICE_HIT_2,
			VOICE_CRASH,
			MAX_NUM,
		};
	}

	namespace PlayerType{
		enum {
			EVIGEN,
			TANYA,

			MAX_NUM,
		};
	}
	// 首チョンパ表現
	static const TCHAR OPTION_ELEMENT_LIST[][100] = {
		_T("Kubi"),
		_T("Transparent"),
		_T("Black"),
		_T("NoCloth"),
		_T("Mugen"),
	};

	static const TCHAR* OPTION_INI_FILE_PATH = _T("Media\\Option\\Option.ini");

	namespace MosukoWeaponType {
		enum {
			NONE,	// 手ぶら
			KATANA,	// 刀
			GUN,	// 銃
			BOTH,	// 両方

			NUM_MAX
		};
	}
}

class StaticData : public BasicStaticData{
public:
	//! プレイヤー番号とSigIDの対応
	//int m_aryPlayerSigIDList[MotionTestConsts::PlayerType::MAX_NUM ];

	//! BGMのインデックス
	int m_nBGMIndex;

	/** BGM番号をセットする（前のBGM停止と、次の曲開始）
	  *
	  */
	void set_BGMIndex( int nBGMIndex );

	/** SE番号とsound idの対応
	  *
	  */
	int m_arySoundList[MotionTestConsts::Sound::MAX_NUM];

	int m_nPlayerMaterialIndex;
	int m_aryMaterials[MotionTestConsts::Material::MAX_NUM];

	//! 敵マネージャ
	EnemyManager m_EnemyManager;
	ShotManager m_ShotManager;
	NeutralManager m_NeutralManager;

	//! プレイヤー
private:
	//E3DObject* player;
public:
	int m_nPlayerType;

	E3DObject m_aryPlayerList[MotionTestConsts::PlayerType::MAX_NUM];


	//! 選択している武器インデックス
	int m_nWeaponIndex;

	//! 武器リスト
	Weapon m_aryWeaponList[WeaponType::MAX_NUM ];

	//! 次の武器を選択
	void set_NextWeapon();

	//! 前の武器を選択
	void set_PreviousWeapon();

	//! 武器情報取得
	Weapon* get_Weapon();

	// パーツ
	BOOL m_aryPartsValidList[ MotionTestConsts::Parts::MAX_NUM ];
	int m_aryPartsIndexList[ MotionTestConsts::Parts::MAX_NUM ];

	// タニャパーツ
	BOOL m_aryTanyaPartsValidList[ MotionTestConsts::TanyaParts::MAX_NUM ];
	int m_aryTanyaPartsIndexList[ MotionTestConsts::TanyaParts::MAX_NUM ];

	//! デフォルト（えびげん）のSIGID
//	int m_nDefaultPlayerSigID;

	//! カメラ対象
	int m_nCameraTargetSigID;

	//! 透け具合
	float m_fClothAlpha;

	//
	float m_fUnderAlpha;

	float m_fApronAlpha;

	// 下半身
	float m_fClothUnderAlpha;
	float m_fApronUnderAlpha;

	float m_fKatyuAlpha;

	// RGB
	//float m_nUnderR;
	//float m_nUnderG;
	//float m_nUnderB;

	//! 破れ具合
	//! 0:普通
	//! 1:破れ
	int m_nClothBreak;

	//! 下着の色
	//! 0:白！
	//! 1:黒！
	int m_nUnderColor;

	//! 現在のシナリオインデックス
	int m_nScenarioIndex;

	//! 首チョンパ表現有り？
	BOOL m_aryOptionList[ TitleSceneConsts::CheckType::NUM_MAX ];
///	BOOL m_bIsKubi;

	//! 丸呑み時中を見せる
//	BOOL m_bIsTransparent;

	//! コンソールのそばにくっついた([F]キーを押すガイドを表示するためのフラグ)
	BOOL m_bNearByConsole;

	//! 触れているコンソールの情報
	//E3DObject* m_Console;
	// シナリオ
	HPL::E3D::ScenarioManager m_ScenarioManager;
	//! 現在の表示アイテム
	HPL::E3D::ScenarioItem* m_ScenarioItem;
	int m_nScenarioListID;
private:
	//int get_WeaponIndex();

	//! ライトの方向
	D3DXVECTOR3 m_vLightDirection;

	//! 敵の体力表示段数
	//int m_nEnemyLifeBarStackNum;

	// sig idからオブジェクトを参照。
	// オブジェクト消去時にこのマップからも削除。
	//std::map<int, E3DObject*> m_mapSigIDToObjectMap;
public:
	//! 武器設定
	void set_WeaponIndex(int nNewWeaponIndex);
	// プレイヤーのSigデータ保存用バッファ
	char* m_lpPlayerSigBuffer;
	int m_nPlayerSigBufferSize;

	//! 弾の管理
	//! 他のビルボードはまた新たにビルボードマネージャを作成すること
	//! ビルボードの合計が2000を超えることはできない
	//HPL::E3D::E3DBillBoardManager m_ShotBillBoardManager;

	//! ちのりビルボード
	HPL::E3D::E3DBillBoardManager m_BloodBillBoardManager;

	//! 連射のインターバルカウンタ
	General::HPLCounter* m_cntShotAutomaticCounter;

	/////////////////////////////////// 影マネージャ必要？
	//! 影のスワップチェインID
	int m_nShadowSwapChainID;
	//! 影のテクスチャID
	int m_nShadowTextureID;
	//! 影のテクスチャのID
	SIZE m_szShadowTextureSize;
	//! 影のスプライトID
	int m_nShadowSpriteID;

	//! スプライト番号管理
	E3DSpriteIndexManager m_SpriteIndexManager;

	//EnemyLifeBar m_aryEnemyLifeBarStack[MotionTestConsts::ENEMY_LIFE_BAR_STACK_NUM_MAX];
	std::list<EnemyLifeBar*> m_lstEnemyLifeBarList;

	//! 仮：ビルのオブジェクト
//	E3DObject* m_Building;

	StaticData(HINSTANCE hInstance);
	virtual ~StaticData();

	//! 表示している敵の数
	//int m_nRenderNum;

public: //オーバーライド
	/** 一回だけ実施するシーン初期化
	  * @retval 成功時は0
	  */
	int oneTimeSceneInit();

	HPL::General::HPLCounter m_cntEnemyGenerateCounter;

	// 倒した数
	int m_nScore;

	std::map<int, int> m_mapWallSigMap;
	int m_nSelectedWallType;
private:
	std::map<int, int> m_mapGroundMap;
	std::map<int, int> m_mapWallMap;
	int m_nSelectedGroundType;
	//! 地形sigid
/*	int m_nGroundSigID;

	//! ダニモスルーム
	int m_nDanimothRoomSigID;

	// 現在使用している地形データSIG
	int m_nSelectedGroundSigID;*/

	// TODO 地形/オブジェクト配置データマネージャを作成

	//! 地形との当り判定
	//int m_nResultGroundChk[4];


protected:
	///////////////////////////////////////////////////////////
	// 敵リストの操作

	/** ビルボードと敵の接触判定
	  *
	  */
	int checkEnemyHitToBillBoard( E3DObject* obj );

public:
	/** プレイヤーと地面の接触判定
	  *
	  */
	int checkPlayerOnGround( );
	/** オブジェクトと地面の接触判定
	  *
	  */
	int checkObjectOnGround( E3DObject* obj, BOOL bIsPlayer);

	

	/** 1024x1024のテクスチャ作成試行
	  * @param[in]	nFormat			DirectXが設定しているフォーマット
	  * @param[out]	lpszSize		作成できたサイズ。作成に失敗した場合中身は変更されない
	  * @retval		0				成功
	  * @retval		1				失敗
	  */
	int tryToCreateTexture( int nFormat, SIZE* lpszSize );

	//E3DObject* searchMissile();

	/** 発射方向を設定
	  * @param[out]	vDirection		発射方向（オイラー座標ベクトル）
	  */
	void get_ShotDirection( D3DXVECTOR3* vDirection, D3DXVECTOR3& vShotFrom );

	/**
	  *
	  */
	BOOL is_Runnable();

	/** 影付き描画
	  *
	  */
	int renderWithShadow( BOOL bIsGround, BOOL bIsPlayer, BOOL bIsMissile, BOOL bIsEnemy );

	/**
	  *
	  */
	int movePlayer();

	/**
	  *
	  */
	int shotPlayer();

	/**
	  *
	  */
	int updatePlayerMotion();

	/** 地面のチェックイン
	  *
	  */
	int checkInGround();

	/** 現在のステージのSIGIDを取得
	  *
	  */
	int get_GroundSigID();
	int set_GroundType( int nGroundType );
	int get_WallSigID();
	int set_WallType( int nWallType );

	//! カメラ移動
	int moveCamera();

	/**
	  * カメラモードをAT_TARGETにする。
	  * カメラ位置をプレイヤーの目の前にする
	  * @param[in]	nSigID			目の前に移動する対象のSIGID
	  * @param[in]	fHeightDelta	Y軸Delta
      */
	int set_CameraInFrontOfObject( int nSigID, float fHeightDelta );

	/** 武器の表示/非表示を切り替える
	  * @param[in]	bEnable	TRUE	表示
	  * @param[in]	bEnable	FALSE	非表示
	  *
	  */
	int set_WeaponEnable( BOOL bEnable );

	/** テクスチャ変更
	  * @param[in]	nSigID			SIG id
	  * @param[in]	lpszMaterialName	貼り付ける材質名（パーツ名ではない）
	  * 
	  */
	int set_Texture( int nSigID, const char* lpszMaterialName, int nMaterial , BOOL bIsPlayerMaterial );
	// 復帰処理
	int restorePlayer();

	BOOL is_MultiLayerMotion();

	/** ボタンクリックなど、UI的な動作を行うシーンでの共通初期化処理
	  * 対象：タイトル/シナリオ選択/ゲームオーバー
	  *
	  */
	int initUISceneCommon();

	BOOL set_MouseOverSpriteColor(int nSpriteID, int nPointX, int nPointY, int nRectX, int nRectY, int nRectWidth, int nRectHeight,
		int nOverColR, int nOverColG, int nOverColB, int nOverColA,
		int nNormalColR, int nNormalColG, int nNormalColB, int nNormalColA );

	/** 最初に行う武器リセット。
	  * Loadedを最大にし、Chargedを0にする。
	  * TODO セーブ可能にする
	  */
	void reset_Weapons();

	HPL::E3D::E3DBillBoard* create_Blood( D3DXVECTOR3& vPosition,
		D3DXVECTOR3& vDirection);

	// 材質の透明度変更
	void set_MaterialAlpha( int nSigID, const char* lpczPartName, float* fTargetAlpha, float fStepAlpha );

	/** MOAファイル読み込み
	  *
	  */
	int loadMOAFile( const char* lpszFilePath, HPL::E3D::E3DObject* obj, float fZoom = 1.f );

	/** ビルボードの移動処理
	  *
	  */
	void move_BillBoard();

	/** プレイヤーへの干渉やターゲッティングをするかどうか判断
	  * @param[in]	obj		干渉してくる敵等
	  * @retval		TRUE	プレイヤーへの干渉はしない。近くにいても無視する
	  *				FALSE	プレイヤーへの干渉を行う。
	  *
	  */
	BOOL is_SkipPlayer( HPL::E3D::E3DObject* obj);

	int draw_Scenario(HPL::E3D::ScenarioItem* item);

	void create_PlayerBlood();

	void remove_Head();

	void set_DirectionToVelocity( HPL::E3D::E3DObject* obj, float fSpeedRate );

	// 下着の色とか変更
	void setup_Under(int nColor);

	void blow_Out( E3DObject* oBlower, E3DObject* oTarget , float fRate);

	void afterRenderCommon();

	/** FromからToへ方向を設定する
	  *
	  */
	void faceToTarget( HPL::E3D::E3DObject* objFrom, int nToSigID, int nDivision );

	/** プレイヤー初期化
	  *
	  */
	void reset_Player( BOOL bIsHPMax );

	/** プレイヤー交代
	  *
	  */
	void change_PlayerType( int nType );

	/** 現在のプレイヤーを取得
	  *
	  */
	E3DObject* get_Player();

	/** プレイヤーのパーツやマテリアルを初期化
	  *
	  */
	void reset_EvigenMaterial();
};


extern StaticData* staticData;
}

#endif
