//=========================================================================
//	メイン関数 (main.cpp)
//	作成者：小暮大樹
//	作成日：2017/04/19
//=========================================================================
//=========================================================================
// インクルードファイル
//=========================================================================
#include <windows.h>
#include "main.h"
#include "manager.h"

// メモリリーク検出用
#if _DEBUG
#define _CRTDBG_MAP_ALLOC
#include <stdlib.h>
#include <crtdbg.h>
#define	new	new(_NORMAL_BLOCK, __FILE__, __LINE__)

#endif

//=========================================================================
//	定数定義
//=========================================================================
#define	CLASS_NAME	"サンプル"
#define WINDOW_NAME	"フレームワーク"

#define	SCENE_ALL ( 3 )

//=========================================================================
//	プロトタイプ宣言
//=========================================================================
//ウインドウプロシージャ
LRESULT CALLBACK  WndProc ( HWND hWnd , UINT uMsg , WPARAM wParam , LPARAM lParam );

//=========================================================================
//	グローバル変数
//=========================================================================

#ifdef _DEBUG
	int g_nCountFPS;		// FPSカウンタ
#endif

//=========================================================================
//	メイン関数
//=========================================================================
int	APIENTRY WinMain( HINSTANCE hInstance , HINSTANCE hPrevInstance , LPSTR lpCmdLine , int nCmdShow )
{
	//使用しない変数の宣言
    UNREFERENCED_PARAMETER( hPrevInstance );
    UNREFERENCED_PARAMETER( lpCmdLine );

#ifdef _DEBUG
	//メモリリーク検出用
	_CrtSetDbgFlag(_CRTDBG_ALLOC_MEM_DF | _CRTDBG_LEAK_CHECK_DF);
	//_CrtSetBreakAlloc(66);
#endif

	WNDCLASSEX wcex =  
	{
		//wcex.を順番通りに
		sizeof ( WNDCLASSEX ) ,		//WINCLASSEXPERTSのメモリサイズの指定
		CS_CLASSDC ,				//表示するウインドウのスタイルを設定
		WndProc ,					//★ここ大事　ウインドウプロシージャのアドレス（関数名）
		0 ,							//通常は使用しないので０を指定
		0 ,							//通常は使用しないので０を指定
		hInstance ,					//WinMainののパラメーターのインスタントハンドルを設定
		NULL ,						//使用するアイコンを指定（Windowsが持っているアイコンを使用するなら……）
		LoadCursor ( NULL , IDC_ARROW ) ,	//マウスカーソルを指定
		( HBRUSH ) ( COLOR_WINDOW + 1 ) ,	//ウインドウのクライアント領域の背景色を設定
		NULL ,								//Windowにつけるメニューを設定
		CLASS_NAME ,						//ウインドウクラスの名前
		NULL								//小さいアイコンが設定された場合の情報を記述
	};

	//ウインドウクラスの登録
	RegisterClassEx ( &wcex );

	HWND hWnd;
	MSG  msg;

	// 矩形を取得
	RECT cr = { 0 , 0 , SCREEN_WIDTH , SCREEN_HEIGHT };
	AdjustWindowRect( &cr , WINDOW_STYLE , FALSE );

	//ウインドウの幅と高さを設定
	int	Window_W = cr.right - cr.left;
	int Window_H = cr.bottom - cr.top;

	//Desktopの矩形を取得
	RECT DesktopRect;
	GetWindowRect( GetDesktopWindow() , &DesktopRect );
	
	//Desktopの幅と高さを取得
	int	desctop_w = DesktopRect.right - DesktopRect.left;	//幅
	int	desctop_h = DesktopRect.bottom - DesktopRect.top;	//高さ
	
	//ウインドウの場所が画面外に出ないかどうかのチェック
	int	Window_X = Window_W > desctop_w ? 0 : (desctop_w - Window_W) / 2;
	int	Window_Y = Window_H > desctop_h ? 0 : (desctop_h - Window_H) / 2;

	//ウインドウを作成
	//hWnd	ウインドウハンドル
	hWnd = CreateWindowEx(
		0,					//拡張ウインドウスタイル
		CLASS_NAME,			//ウインドウクラスの名前
		WINDOW_NAME,		//ウインドウの名前
		WINDOW_STYLE,		//ウインドウスタイル WS_POPUPnihenkou
		Window_X,			//ウインドウの左上X座標（フレームも合わせた）
		Window_Y,			//ウインドウの左上Y座標
		Window_W,			//ウインドウの幅
		Window_H,			//ウインドウの高さ
		NULL,				//親ウインドウのハンドル
		NULL,				//メニューのハンドルまたは子ウインドウ
		hInstance,			//インスタンスハンドル
		NULL);				//ウインドウ作成データ

	//ウインドウの表示

	ShowWindow(hWnd , nCmdShow);	//指定されたウインドウの表示
	UpdateWindow(hWnd);				//

	//マネージャーの生成
	CManager::Init( hInstance , hWnd , true );

	//フレームレート用
	DWORD dwCurrentTime;
	DWORD dwFrameCount;
	DWORD dwExecLastTime;
	DWORD dwFPSLastTime;

	// 分解能を設定
	timeBeginPeriod(1);

	// フレームカウント初期化
	dwCurrentTime =	dwFrameCount = 0;
	dwExecLastTime =  dwFPSLastTime = timeGetTime();

	// メッセージループをゲームループに対応させる
	for(;;)	 
	{		
		if( PeekMessage( &msg , NULL , 0 , 0 , PM_REMOVE ) != 0 )
		{
			//Windowsの処理
			if( msg.message == WM_QUIT )
			{
				break;
			}
			else
			{
				TranslateMessage( &msg );
				DispatchMessage( &msg );
			}
		}
		else
		{
			dwCurrentTime = timeGetTime();
			if((dwCurrentTime - dwFPSLastTime) >= 500)	// 0.5秒ごとに実行
			{
#ifdef _DEBUG
				g_nCountFPS = dwFrameCount * 1000 / (dwCurrentTime - dwFPSLastTime);
#endif
				dwFPSLastTime = dwCurrentTime;
				dwFrameCount = 0;
			}

			if((dwCurrentTime - dwExecLastTime) >= (1000 / 60))
			{
				dwExecLastTime = dwCurrentTime;

				// 更新処理
				CManager::Update();

				// 描画処理
				CManager::Draw();

				dwFrameCount++;
			}
		}
		
	}

	CManager::Uninit();

	return (int)msg. wParam;
}

//=========================================================================
//	ウインドプロシージャ
//=========================================================================
LRESULT CALLBACK WndProc ( HWND hWnd , UINT uMsg , WPARAM wParam , LPARAM lParam )
{

	//RECT関数X_
	const RECT	rect = { 0 , 0 , SCREEN_WIDTH , SCREEN_HEIGHT };

	switch(uMsg)
	{
	case	WM_DESTROY:		//ウインドウ破棄のメッセージ
		PostQuitMessage(0);	//"WM_QUIT"メッセージを返す
		break;

	case	WM_CREATE:
		break;

	case	WM_COMMAND:
		break;


	case	WM_KEYDOWN:		//キーが押された場合
		switch	(wParam)	//キーの内容の判定SwitchCase
		{
			case	VK_ESCAPE:	//ESCAPEキーを押した場合（終了処理）
				{
					UINT nID = MessageBox( NULL , "終了しますか？" , "終了メッセージ" , MB_YESNO );

					//イエスを押したらDestroyWindowを呼ぶ。
					if( nID == IDYES )
					{
						DestroyWindow(hWnd);	
					}
				}
				break;
		}
		break;

	default :
		break;
	}

	return DefWindowProc (hWnd , uMsg , wParam , lParam);
}

#ifdef _DEBUG
//=============================================================================
// FPS取得
//=============================================================================
int GetFPS(void)
{
	return g_nCountFPS;
}
#endif

//=========================================================================
//					EOF						 //
//=========================================================================
