//
// Asura_Windows.h
//
// Created by Kevin Lea - 02/07/2001 11:10:55
// 
// Copyright (C) 2001 Rebellion, All Rights Reserved.
//

#ifdef ASURA_USE_PRAGMA_ONCE
    #pragma once
#endif

#ifndef __ASURA_WINDOWS_H__
#define __ASURA_WINDOWS_H__

#include "Asura_PlatformBasics.h"

#ifdef ASURA_MAIN
#include "core/Asura_UserInput.h"
#include "Core/Asura_String.h"

#ifndef ASURA_PC_APPLICATION_NAME
#define ASURA_PC_APPLICATION_NAME TEXT("Asura")
#endif

#ifndef ASURA_PC_APPLICATION_TITLE
#define ASURA_PC_APPLICATION_TITLE TEXT("Asura")
#endif

struct AsuraWindowsCommandLineInfo
{
	bool bPositionSet;
	bool bSizeSet;
	int iWindowXPos;
	int iWindowYPos;
	int iWindowXSize;
	int iWindowYSize;
};

class Asura_Windows
{
	public:
#if NDEBUG
	static void Initialise(HINSTANCE hInstance, HINSTANCE hPrevInstance, const char* szCmdLine, int nCmdShow, const LPVOID guid, bool bFullScreen = true);
#else
	static void Initialise(HINSTANCE hInstance, HINSTANCE hPrevInstance, const char* szCmdLine, int nCmdShow, const LPVOID guid, bool bFullScreen = false);
#endif
		static void LateInitialise();

		static void Shutdown(void);
	
		static void CheckForWindowsMessages(void);

		static inline bool RunningFullScreen()
		{
			return s_bFullScreen;
		}
		static void SetRunningFullScreen(bool bFullscreen);
		static HWND GetWindowHandle(u_int uWindowIndex = 0);
		static inline HINSTANCE GetWindowhInstance()
		{
			return WindowhInstance;
		}
		static inline void GetWindowCoords(RECT *rectPtr)
		{
			rectPtr->left = WinLeftX;
			rectPtr->top = WinTopY;
			rectPtr->right = WinLeftX + WinWidth;
			rectPtr->bottom = WinTopY + WinHeight;
		}
		//Gets the screenspace coordinates of the part of the window used for rendering
		//(ie not including minus frame and title bar)
		static void GetWindowViewportCoords(RECT * pxRect);

		static inline bool IsApplicationActive()
		{
			return ApplicationIsActive;
		}

		static void SetWindowSize(int iWidth,int iHeight);
		static void SetWindowPosition(int iX, int iY);
		static void MaximiseWindow();
		static void RequestMaximiseWindow();
		static bool IsMaximised() { return s_bIsMaximised; }
		
		static inline LONG_PTR FAR PASCAL WindowsMessageHandler(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam);

		//For changing whether the application stops processing while minimised (the default behaviour)
		//To be seen whether not pausing will cause problems... RAR 22/08/02
		static void SetPauseWhileMinimised(bool bPause){s_bPauseWhileMinimised = bPause;}
		static bool GetPauseWhileMinimised(){return s_bPauseWhileMinimised;}

		//Determines whether idle or normal priority should be used while minimised.
		//If pausing while minimised this becomes somewhat irrelevant.
		static void SetIdlePriorityWhileMinimised(bool bIdle);

		static u_int GetUserNameFromPC( Asura_Char* pszRetUserName, u_int uMaxUserNameLength);

		static void SetCommandLineWindowStateFlags(bool bSubWindow, bool bFullscreen) { s_bSubwindowSpecifiedOnCommandLine = bSubWindow; s_bFullscreenSpecifiedOnCommandLine = bFullscreen; }
		static void GetCommandLineWindowStateFlags(bool& bSubWindow, bool& bFullscreen) { bSubWindow = s_bSubwindowSpecifiedOnCommandLine; bFullscreen = s_bFullscreenSpecifiedOnCommandLine; }

#ifdef ASURA_USE_HANDLECOPYMESSAGE
		static bool Project_HandleCopyMessage(char* pszMessage);
#endif
		static int GetWindowedXPos() { return s_iWindowedXPos; }
		static int GetWindowedYPos() { return s_iWindowedYPos; }
		static void SetWindowedXPos(int iX) { s_iWindowedXPos = iX; }
		static void SetWindowedYPos(int iY) { s_iWindowedYPos = iY; }

		static int GetWindowedWidth() { return s_iWindowedWidth; }
		static int GetWindowedHeight() { return s_iWindowedHeight; }
		static void SetWindowedWidth(int iWidth) { s_iWindowedWidth = iWidth; }
		static void SetWindowedHeight(int iHeight) { s_iWindowedHeight = iHeight; }

		static int WinLeftX, WinTopY;
		static int s_iWindowedXPos, s_iWindowedYPos;
		static int s_iWindowedWidth, s_iWindowedHeight;
		static bool s_bSubwindowSpecifiedOnCommandLine, s_bFullscreenSpecifiedOnCommandLine;

        static const Asura_UnicodeChar* GetInputBuffer();
        static u_int GetSizeOfInputBuffer();

		static bool IsMainThread(void);

		static void UpdateWindowsCursorVisibility();

		//RAR 29/08/2006 
		//These deal with various bits that need to be done to get the windows dialog boxes to appear
		//correctly , and to restore stuff afterwards.
		static void PreShowDialogBox();
		static void PostShowDialogBox();

		static void SetWindowTitle(const char* szTitle);

		//Store of a default window title to use, so other systems know what to put it back to after
		//fiddling with it.
		static void SetDefaultWindowTitle(const char* szTitle) {s_xDefaultTitle = szTitle;}
		static const char* GetDefaultWindowTitle(){return s_xDefaultTitle.GetString();}
		static void RestoreDefaultWindowTitle() {SetWindowTitle(GetDefaultWindowTitle());}

		static bool GetDesktopSize( u_int* puWidth, u_int* puHeight);

		static bool InitialiseWindow(HINSTANCE hInstance, int nCmdShow);
		static void DestroyWindows();

		static bool CopyToClipboard( const char* const szString );
		static bool CopyFromClipboard( char* const szBuffer, const int iBufferSize );

		static void SetCommandLineWindowPosition(int iXPos, int iYPos);
		static bool GetCommandLineWindowPosition(int& iXPos, int& iYPos);

		static void SetCommandLineWindowSize(int iXSize, int iYSize);
		static bool GetCommandLineWindowSize(int& iXSize, int& iYSize);

	private:
		static void InitialiseToAsciiTable(void);

	
		static bool s_bFullScreen;

		static u_int s_uNumWindowHandles;
		static HWND* s_pxWindowHandles;
		static HINSTANCE WindowhInstance;
		
		static int WinWidth,WinHeight;
		static float WinScaleX,WinScaleY;

		static bool ApplicationIsActive;
		static char *ApplicationName;
		
		static unsigned char ToAsciiTable[256][256];
        static ASURA_KEYID s_aeExtendedKeyPressed[256][2];

		static bool s_bPauseWhileMinimised;
		static bool s_bIdlePriorityWhileMinimised;
		
		static DWORD s_uMainThreadID;
		static bool s_bInitialised;

		static Asura_String s_xTitle;
		static Asura_String s_xDefaultTitle;

		static bool s_bIsMaximised;
		static bool s_bMaximiseWindowRequested;

		static AsuraWindowsCommandLineInfo s_xCommandLineInfo;
};

#else //ASURA_MAIN
class Asura_Windows
{
public :
	//Non-ASURA_MAIN projects will need implenetations of these in order to get the
	//asserts working. RAR 07/10/2005

	static HWND GetWindowHandle();
	static HINSTANCE GetWindowhInstance();
};

#endif //ASURA_MAIN


#endif//__ASURA_WINDOWS_H__
