/*---------------------------------------------------------------------------

    NN Shader header for DXG20

    Copyright (C) 2002 - 2004 SEGA Corporation Creative Center Graphics Sect.
    All Rights Reserved.

    Module  : NN Shader header for DXG20
    File    : nnlshaderxe.h
    Create  : 2004/06/22 新規作成
    Modify  : 2004/08/05 NND_PLATFORM_XENON追加
    Modify  : 2005/01/17 NNE_SHADER_LIGHT_MAX
    Modify  : 2005/01/31 Xbox統合
    Modify  : 2009/01/20 シェーダ登録及び標準シェーダビルドを要求するコールバック関数型宣言を追加
						 nnSetBuildCallbackStdShaderDXG20 関数を追加
						 nnGetBuildCallbackStdShaderDXG20 関数を追加
						 シェーダコンパイルオプションを追加
						 nnSetCompileOptionStdShaderDXG20 関数を追加
						 nnGetCompileOptionStdShaderDXG20 関数を追加
    Modify  : 2009/01/21 標準シェーダのコンパイルエラーコールバック関数型宣言を追加
	                     nnSetCompileErrorCallbackStdShaderDXG20 関数を追加
	                     nnGetCompileErrorCallbackStdShaderDXG20 関数を追加
    Modify  : 2009/05/12 ヘッダ整理
    Version : 1.18.22
    Note    :

---------------------------------------------------------------------------*/
#ifndef __NNLSHADERDXG20_H__
#define __NNLSHADERDXG20_H__

#ifdef __cplusplus
extern "C" {
#endif /* __cplusplus */

/*------ Custom Shader ----------------------------------------------------*/

#define NNE_SAMPLE_MAX			(16)

#define NNE_MTX_PAL_MAX			(16)

typedef struct {
	NNS_MATRIX		WorldMatrix;
	NNS_MATRIX		ViewMatrix;
	NNS_MATRIX		ProjectionMatrix;
	NNS_MATRIX		ViewInverseMatrix;
	NNS_MATRIX		ViewProjectionMatrix;
	NNS_MATRIX		WorldViewMatrix;
#if 1 /* 2008.07.17 */
	NNS_MATRIX		NormalMatrix;	/* WorldViewMatrixの3x3部分の逆転置行列 */
#endif
	NNS_MATRIX		WorldViewProjectionMatrix;
}NNS_SHADERCONST_MATRIX;

typedef struct {
	NNS_MATRIX		BoneMtx[NNE_MTX_PAL_MAX];
	NNS_MATRIX		BoneNmMtx[NNE_MTX_PAL_MAX];	// 標準シェーダのみ対応(2008.06.05)
	Sint32			nBoneMtx;
} NNS_SHADERCONST_BONEMTX;

typedef struct {
	NNS_RGBA		MatDiffuse;
	NNS_RGBA		MatAmbient;
	NNS_RGBA		MatSpecular;
	NNS_RGBA		MatEmissive;
	union {
		Float		Misc[4];
		struct {
			Float	Fog0;
			Float	Fog1;
			Float	Z;
			Float	Power;
		};
	};
} NNS_SHADERCONST_MATERIAL;

typedef struct{
	void*			pTex[NNE_SAMPLE_MAX];
	Float			OffsetUV[NNE_SAMPLE_MAX][2];
	Float			UvIdx[NNE_SAMPLE_MAX];
	Sint32			nTex;
	NNS_MATRIX		CoordMtx[NNE_SAMPLE_MAX];
} NNS_SHADERCONST_TEXTURE;

typedef struct{
	Float		value;
	Float		BoneNum;
	Float		CpuTransform;
	Float		FixtoFloat;
	Float		reserved[4];
} NNS_SHADERCONST_MISC2;

/*------ Standard Shader --------------------------------------------------*/

/* フォグモデル */
typedef enum {
	NNE_FOG_NONE,
	NNE_FOG_LINEAR,
	NNE_FOG_EXP,
	NNE_FOG_EXP2,
} NNE_FOG_MODEL;


/* ライト距離減衰モデル */
typedef enum {
	NNE_ATTEN_CONSTANT,
	NNE_ATTEN_INVLINEAR,
	NNE_ATTEN_INVQUADRATIC,
} NNE_ATTEN_FUNC;


/* 標準シェーダ設定 */
/*
　※１
    nMaxParallelLight, nMaxPointLight, nMaxSpotLight は合計８個までとなっていますので注意してください。
*/
typedef struct {
	NNE_BOOL		bNormalizeVertexNormal;		// 法線正規化(Vertex Shader)
	NNE_BOOL		bRescaleVertexNormal;		// 法線再スケール(Vertex Shader)
	Sint32			nMaxParallelLight;			// 最大パラレルライト数(0〜4) ※１
	Sint32			nMaxPointLight;				// 最大ポイントライト数(0〜4) ※１
	Sint32			nMaxSpotLight;				// 最大スポットライト数(0〜4) ※１
	NNE_BOOL		bLightAmbient;				// ライトアンビエント有効
	NNE_ATTEN_FUNC	PointLightDistAtten;		// ポイントライト距離減衰モデル
	NNE_ATTEN_FUNC	SpotLightDistAtten;			// スポットライト距離減衰モデル
	NNE_FOG_MODEL	FogModel;					// フォグモデル
	NNE_BOOL		bDistanceFog;				// 距離フォグ or Z値フォグ
	NNE_BOOL		bFragmentFog;				// フラグメント単位のフォグ計算

	Uint32			nUserUniform;				// ユーザユニフォーム変数の個数

	NNE_BOOL		bNoScaleEnvelope;			// エンベロープの法線計算にスケールを考慮しない

	// オブジェクト登録により変更される可能性のある設定
	NNE_BOOL		bVertexSpecular;			// 頂点スペキュラカラー使用
	NNE_BOOL		bCalcBinormal;				// 法線と接線から従法線計算
} NNS_STDSHADER_CONFIG;


/* テクスチャ座標 */
typedef Sint32 NNS_TEXCOORDIDX;
enum {
	NNE_TEXCOORD_NONE	= 0,	// テクスチャなしの場合に指定（シェーダプロファイルの種類を減らすため）

	NNE_TEXCOORD_0		= 0,
	NNE_TEXCOORD_1,
	NNE_TEXCOORD_2,
	NNE_TEXCOORD_3,

	NNE_TEXCOORD_NRM	= -1,
	NNE_TEXCOORD_POS	= -2,
	NNE_TEXCOORD_SPHERE_MAP			= -1,
	NNE_TEXCOORD_PROJECTION_MAP		= -2,
	NNE_TEXCOORD_DUALPARABOLOID_MAP	= -3,

	NNE_TEXCOORD_MAX	= NNE_TEXCOORD_3,
	NNE_TEXCOORD_MIN	= NNE_TEXCOORD_DUALPARABOLOID_MAP,
};


#define NND_FRAGPARALIGHT_MAX		(3)
#define NND_FRAGPOINTLIGHT_MAX		(3)


/* シェーダプロファイル */
typedef struct {
	NNE_BOOL			bVtxCol;					// 頂点カラーあるなし 0:無し 1:あり
#if 1 /* 2008.07.01〜2008.07.04(追加) */
	/* 2008.07.04 */
	/*   頂点カラーがあるとき２個目のカラー(スペキュらカラー)があるかどうかの判断に使う */
	NNE_BOOL			bVtxColSpe;					// 頂点カラーにスペキュラーカラーあるなし 0:無し 1:あり
	/* 2008.07.01 */
	NNE_BOOL			bVtxNrm;					// 法線あるなし 0:無し 1:あり
	NNE_BOOL			bVtxObjSpaceNrm;			// オブジェクトスペースの法線
	NNE_BOOL			bVtxReverseTan;				// 接線の反転
#endif
	Sint32				VtxTfmMode;					// 頂点変換方式	0:RIGID 1:PLIABLE(Matrix Palette 4) 2::PLIABLE(Matrix Palette 32)

	NNE_BOOL			bLighting;					// 頂点ライティング
	NNE_BOOL			bSpecular;					// スペキュラ
	NNE_BOOL			bTwoSidedLighting;			// ２面ライティング

	Sint32				nFragParallelLight;			// フラグメント単位パラレルライト数
	Sint32				nFragPointLight;			// フラグメント単位ポイントライト数

	// テクスチャ使用
	Sint32				NormalMapType;				// 0:なし 1:RGB->XYZ 2:AXLY
	NNE_BOOL			bBaseMap;
	Sint32				nDecalMap;					// 0〜3
	NNE_BOOL			bSpecularMap;
	NNE_BOOL			bShininessMap;
	NNE_BOOL			bDualParaboloidMap;
	NNE_BOOL			bEnvMaskMap;
	NNE_BOOL			bModulateMap;
	NNE_BOOL			bAddMap;
	NNE_BOOL			bOpacityMap;
	NNE_BOOL			bUser1Map;
	NNE_BOOL			bUser2Map;
	NNE_BOOL			bUser3Map;
	NNE_BOOL			bUser4Map;
	NNE_BOOL			bUser5Map;
	NNE_BOOL			bUser6Map;
	NNE_BOOL			bUser7Map;
	NNE_BOOL			bUser8Map;
	Sint32				nShadowMap;					// 0〜2
	NNE_BOOL			bUserSampler2D1;
	NNE_BOOL			bUserSampler2D2;
	NNE_BOOL			bUserSampler3D1;
	NNE_BOOL			bUserSampler3D2;
	NNE_BOOL			bUserSamplerCube1;
	NNE_BOOL			bUserSamplerCube2;

	// テクスチャ座標（上記のテクスチャの順（DualParaboloid,Shadow除く）で使用するもののみ）
	NNS_TEXCOORDIDX		TexCoord[8];
#if 1 /* 2008.05.19〜2008.05.20 */
	Uint32				UserProfile;				// マテリアルユーザープロファイル 0〜15
	Uint32				UserProfileDrawobj;			// 描画フラグユーザープロファイル 0〜15
#endif
} NNS_STDSHADER_PROFILE;

#define NND_MAX_USER_PROFILE			(63)		// マテリアルユーザープロファイル最大値
#define NND_MAX_USER_PROFILE_DRAWOBJ	(255)		// 描画フラグユーザープロファイル最大値
#define NND_MAX_NUM_USER_UNIFORM		(256)		// ユーザユニフォーム変数最大個数（実際の制限値はシェーダやドライバによる）

#if 0 /* 2008.05.20 */
typedef Uint64 NNS_STDSHADER_NAME;		// シェーダプロファイルに1対1対応する値。nnGetStdShaderName,nnGetStdShaderProfile参照
#else
// シェーダ名（シェーダプロファイルに1対1対応する値。）
typedef struct {
	Uint64 low;
	Uint64 high;
} NNS_STDSHADER_NAME;
#endif

#include <nnlmaterial.h>

/* 標準シェーダ管理バッファサイズ取得 */
Uint32 nnCalcStdShaderManageBufferSize( Sint32 num );

/* 標準シェーダ基本設定 */
void nnSetUpStdShaderConfigBasic( NNS_STDSHADER_CONFIG *config );

/* 標準シェーダ初期化関数 */
void nnConfigureStdShader( const NNS_STDSHADER_CONFIG *config, void *managebuffer, Sint32 num );
void nnSetConfigStdShader( const NNS_STDSHADER_CONFIG *config);
void nnGetConfigStdShader( NNS_STDSHADER_CONFIG *config );

/* シェーダプロファイル初期化 */
void nnInitStdShaderProfile( NNS_STDSHADER_PROFILE *profile );

/* シェーダネーム取得 */
NNS_STDSHADER_NAME nnGetStdShaderName( const NNS_STDSHADER_PROFILE *profile );
/* シェーダプロファイル取得 */
void nnGetStdShaderProfile( NNS_STDSHADER_PROFILE *profile, NNS_STDSHADER_NAME name );

/* シェーダプロファイル登録 */
Sint32 nnRegistStdShaderProfile( const NNS_STDSHADER_PROFILE *profile );
Sint32 nnRegistStdShaderName( NNS_STDSHADER_NAME Name );

/* オブジェクト使用シェーダプロファイル登録 */
Sint32 nnRegistObjectStdShaderProfiles( const NNS_OBJECT *obj, NNF_DRAWOBJ flag );

/* プライアブルオブジェクト使用シェーダプロファイル登録 */
Sint32 nnRegistPliableObjectStdShaderProfiles(NNS_PLIABLEOBJ *pliableObj, NNF_DRAWOBJ flag );

/* 登録済みシェーダ数取得 */
Sint32 nnGetCurrentStdShaderProfileNumber( void );

/* 登録済みシェーダプロファイル取得 */
void nnGetStdShaderProfileOne( NNS_STDSHADER_PROFILE *profile, Sint32 idx );

/* 登録済みシェーダネームリスト取得 */
const NNS_STDSHADER_NAME *nnGetStdShaderNameList( void );

/* シェーダプロファイル初期化 */
void nnClearStdShaderProfiles( void );

/*** NN外部シェーダビルド用 ***/

	/* シェーダタイプ */
	typedef enum {
		NNE_STDSHADERTYPE_NONE,
		NNE_STDSHADERTYPE_HLSL,
	} NNE_STDSHADERTYPE;

	/* コンパイル済みシェーダプロファイル */
	typedef struct {
		NNE_STDSHADERTYPE		ShaderType;
		IDirect3DVertexShader9* pVertexShader;
		IDirect3DPixelShader9*  pPixelShader;
		LPD3DXCONSTANTTABLE		pVtxConstTbl;
		LPD3DXCONSTANTTABLE		pPixelConstTbl;
	}NNS_COMPILED_STDSHADER_PROFILE;

	/* 未ビルドシェーダプロファイル取得 */
	Sint32 nnGetUnbuildStdShaderProfileOne( NNS_STDSHADER_PROFILE *profile );

	/* コンパイル済みシェーダ登録 */
	void nnRegistCompiledStdShaderProfile(const NNS_COMPILED_STDSHADER_PROFILE *compiledShader, const NNS_STDSHADER_PROFILE *profile);

	/* 標準シェーダのコンパイル */
	typedef enum{
		NNE_STDSHADER_PROFILE_VERTEX,
		NNE_STDSHADER_PROFILE_PIXEL
	}NNE_STDSHADER_PROFILE;
	Sint32 nnCompileStdShaderDXG20(const char *pSrcData, Uint32 SrcDataLen, const NNE_STDSHADER_PROFILE shaderProfile, const NNS_STDSHADER_PROFILE *profile, void *ppShader, void *ppConstantTable);

	/* シェーダ登録及び標準シェーダビルドを要求するコールバック関数型宣言 */
	typedef Sint32 (*NNS_BUILD_STDSHADER_CALLBACK_FUNC)(NNS_STDSHADER_NAME name, const char *vertexshader, Uint32 vtxshadersize, const char *fragmentshader, Uint32 fragshadersize );

	/* シェーダ登録及び標準シェーダビルドを要求するコールバック関数の設定 */
	void nnSetBuildCallbackStdShaderDXG20( NNS_BUILD_STDSHADER_CALLBACK_FUNC func );

	/* シェーダ登録及び標準シェーダビルドを要求するコールバック関数を取得 */
	NNS_BUILD_STDSHADER_CALLBACK_FUNC nnGetBuildCallbackStdShaderDXG20( void );


/* シェーダコンパイルオプション */
typedef	Uint32 NNF_SHADERFLAG;
#define NND_SHADERFLAG_DEBUG							D3DXSHADER_DEBUG
#define NND_SHADERFLAG_SKIPVALIDATION					D3DXSHADER_SKIPVALIDATION
#define NND_SHADERFLAG_SKIPOPTIMIZATION					D3DXSHADER_SKIPOPTIMIZATION
#define NND_SHADERFLAG_PACKMATRIX_ROWMAJOR				D3DXSHADER_PACKMATRIX_ROWMAJOR
#define NND_SHADERFLAG_PACKMATRIX_COLUMNMAJOR			D3DXSHADER_PACKMATRIX_COLUMNMAJOR
#define NND_SHADERFLAG_PARTIALPRECISION					D3DXSHADER_PARTIALPRECISION
#define NND_SHADERFLAG_FORCE_VS_SOFTWARE_NOOPT			D3DXSHADER_FORCE_VS_SOFTWARE_NOOPT
#define NND_SHADERFLAG_FORCE_PS_SOFTWARE_NOOPT			D3DXSHADER_FORCE_PS_SOFTWARE_NOOPT
#define NND_SHADERFLAG_NO_PRESHADER						D3DXSHADER_NO_PRESHADER
#define NND_SHADERFLAG_AVOID_FLOW_CONTROL				D3DXSHADER_AVOID_FLOW_CONTROL
#define NND_SHADERFLAG_PREFER_FLOW_CONTROL				D3DXSHADER_PREFER_FLOW_CONTROL
//#define NND_SHADERFLAG_ENABLE_BACKWARDS_COMPATIBILITY	D3DXSHADER_ENABLE_BACKWARDS_COMPATIBILITY
//#define NND_SHADERFLAG_IEEE_STRICTNESS					D3DXSHADER_IEEE_STRICTNESS
#define NND_SHADERFLAG_USE_LEGACY_D3DX9_31_DLL			D3DXSHADER_USE_LEGACY_D3DX9_31_DLL
//#define NND_SHADERFLAG_OPTIMIZATION_LEVEL0				D3DXSHADER_OPTIMIZATION_LEVEL0
//#define NND_SHADERFLAG_OPTIMIZATION_LEVEL1				D3DXSHADER_OPTIMIZATION_LEVEL1
//#define NND_SHADERFLAG_OPTIMIZATION_LEVEL2				D3DXSHADER_OPTIMIZATION_LEVEL2
//#define NND_SHADERFLAG_OPTIMIZATION_LEVEL3				D3DXSHADER_OPTIMIZATION_LEVEL3

/* 標準シェーダのコンパイルオプションを設定 */
void nnSetCompileOptionStdShaderDXG20(NNF_SHADERFLAG flag);

/* 標準シェーダのコンパイルオプションを取得 */
NNF_SHADERFLAG nnGetCompileOptionStdShaderDXG20(void);

/* 標準シェーダのコンパイルエラーコールバック関数型宣言　*/
typedef void (*NNS_COMPILEERROR_STDSHADER_CALLBACK_FUNC)(Uint32 shaderProfile, const void *buf, Uint32 bufSize);

/* 標準シェーダのコンパイルエラーコールバック関数の設定 */
void nnSetCompileErrorCallbackStdShaderDXG20(NNS_COMPILEERROR_STDSHADER_CALLBACK_FUNC func);

/* 標準シェーダのコンパイルエラーコールバック関数の取得 */
NNS_COMPILEERROR_STDSHADER_CALLBACK_FUNC nnGetCompileErrorCallbackStdShaderDXG20(void);

/* 標準シェーダビルド */
Sint32 nnBuildStdShader( const char *vertexshader,  Uint32 vtxshadersize,
					    const char *fragmentshader, Uint32 fragshadersize );

/* 標準シェーダー設定 */
void nnBindStdShader( const NNS_DRAWCALLBACK_VAL *val, NNE_BOOL bFroceRigid );

/* 組み込みシェーダー 設定*/
void nnBindFixedShader( void );

/* 標準シェーダ解放 */
void nnReleaseStdShader( void );

/* ユーザユニフォーム変数設定(2008.05.20) */
void nnSetUserUniformDXG20(Sint32 idx, Float x, Float y, Float z, Float w);

/* 必要になった時点でそのシェーダーを生成するか否かの設定   */
/*   オンデマンド有効時はシェーダコードのメモリを解放してはいけない */
void nnEnableOndemandShaderCreation( NNE_BOOL bEnable,
									 const char* pVtxSdr,Uint32 VtxSdrSize,
									 const char* pPixSdr,Uint32 PixSdrSize );

/*-------------------------------------------------------------------------*/


#ifdef __cplusplus
}
#endif /* __cplusplus */

#endif /* __NNLSHADERDXG20_H__ */

/* End of file */
