1 /*---------------------------------------------------------------------------* 2 Project: NintendoWare 3 File: gfx_Material.h 4 5 Copyright (C)2009-2011 Nintendo/HAL Laboratory, Inc. All rights reserved. 6 7 These coded instructions, statements, and computer programs contain proprietary 8 information of Nintendo and/or its licensed developers and are protected by 9 national and international copyright laws. They may not be disclosed to third 10 parties or copied or duplicated in any form, in whole or in part, without the 11 prior written consent of Nintendo. 12 13 The content herein is highly confidential and should be handled accordingly. 14 15 $Revision: 31311 $ 16 *---------------------------------------------------------------------------*/ 17 18 #ifndef NW_GFX_MATERIAL_H_ 19 #define NW_GFX_MATERIAL_H_ 20 21 #include <nw/gfx/gfx_SceneObject.h> 22 #include <nw/ut/ut_RuntimeTypeInfo.h> 23 #include <nw/ut/ut_MoveArray.h> 24 #include <nw/gfx/gfx_ShaderProgram.h> 25 26 namespace nw 27 { 28 namespace gfx 29 { 30 31 class Model; 32 class AnimGroup; 33 34 //--------------------------------------------------------------------------- 35 //! @brief マテリアルを表すクラスです。 36 //! 37 //! マテリアルに対して、アニメーション後に生成時の状態に戻したい場合、Bufferを使用する必要があります。 38 //--------------------------------------------------------------------------- 39 class Material : public SceneObject 40 { 41 private: 42 NW_DISALLOW_COPY_AND_ASSIGN(Material); 43 44 public: 45 NW_UT_RUNTIME_TYPEINFO; 46 47 //---------------------------------------- 48 //! @name 作成 49 //@{ 50 51 //! @brief リソースからマテリアルを生成します。 52 //! 53 //! @param[in] resource リソースです。 54 //! @param[in] bufferCount 生成するマテリアルバッファの数です。 55 //! @param[in] parent マテリアルの親となるモデルクラスです。 56 //! @param[in] allocator アロケータです。 57 //! 58 //! @return 生成されたマテリアルです。 59 //! 60 static Material* Create( 61 ResMaterial resource, 62 s32 bufferCount, 63 Model* parent, 64 os::IAllocator* allocator); 65 66 //! @brief 生成時に必要なメモリサイズを取得します。 67 //! 68 //! @param[in] resource リソースです。 69 //! @param[in] bufferCount 生成するマテリアルバッファの数です。 70 //! @param[in] parent マテリアルの親となるモデルクラスです。 71 //! @param[in] alignment 計算に用いるアライメントです。2 のべき乗である必要があります。 72 static size_t GetMemorySize( 73 ResMaterial resource, 74 s32 bufferCount, 75 bit32 bufferOption, 76 size_t alignment = os::IAllocator::DEFAULT_ALIGNMENT) 77 { 78 os::MemorySizeCalculator size(alignment); 79 80 GetMemorySizeInternal(&size, resource, bufferCount, bufferOption); 81 82 return size.GetSizeWithPadding(alignment); 83 } 84 85 86 //! @details :private 87 static void GetMemorySizeInternal( 88 os::MemorySizeCalculator* pSize, 89 ResMaterial resource, 90 s32 bufferCount, 91 bit32 bufferOption); 92 93 //@} 94 95 //---------------------------------------- 96 //! @name 取得/設定 97 //@{ 98 99 //! @brief オリジナルリソースを取得します。 GetOriginal()100 ResMaterial GetOriginal() 101 { 102 return ResStaticCast<ResMaterial>(this->GetResSceneObject()); 103 } 104 105 //! @brief オリジナルリソースを取得します。 GetOriginal()106 const ResMaterial GetOriginal() const 107 { 108 return ResStaticCast<ResMaterial>(this->GetResSceneObject()); 109 } 110 111 //! @brief 所有者となるモデルを取得します。 112 //! 113 //! @return マテリアルの所有者のモデルです。 114 //! GetOwnerModel()115 Model* GetOwnerModel() 116 { 117 return this->m_Owner; 118 } 119 120 //! @brief 所有者となるモデルを取得します。 121 //! 122 //! @return マテリアルの所有者のモデルです。 123 //! GetOwnerModel()124 const Model* GetOwnerModel() const 125 { 126 return this->m_Owner; 127 } 128 129 //! @brief リソースを設定します。 130 //! 131 //! @param[in] description シェーダプログラムの詳細設定です。 132 //! SetDescription(ResShaderProgramDescription description)133 void SetDescription(ResShaderProgramDescription description) { m_ProgramDescription = description; } 134 135 //! @brief リソースを取得します。 136 //! 137 //! @return シェーダプログラムの詳細設定です。 138 //! GetDescription()139 const ResShaderProgramDescription GetDescription() const { return m_ProgramDescription; } 140 141 //@} 142 143 //---------------------------------------- 144 //! @name バッファオプション関連 145 //@{ 146 147 //! @brief バッファの数を取得します。 GetBufferCount()148 int GetBufferCount() const 149 { 150 return this->m_Buffers.size(); 151 } 152 153 //! @brief バッファを取得します。 GetBuffer()154 ResMaterial GetBuffer() 155 { 156 bool hasBuffer = (0 < m_BufferCount); 157 158 if (hasBuffer) 159 { 160 return this->m_Buffers[0]; 161 } 162 else 163 { 164 return ResMaterial(NULL); 165 } 166 } 167 168 //! バッファを取得します。 GetBuffer()169 const ResMaterial GetBuffer() const 170 { 171 bool hasBuffer = (0 < m_BufferCount); 172 173 if (hasBuffer) 174 { 175 return this->m_Buffers[0]; 176 } 177 else 178 { 179 return ResMaterial(NULL); 180 } 181 } 182 183 //! 有効なシェーダーパラメータが取得できるマテリアルを取得します。 GetShaderParameterResMaterial()184 ResMaterial& GetShaderParameterResMaterial() { return m_ShaderParameterResMaterial; } 185 186 //! 有効なシェーダーパラメータが取得できるマテリアルを取得します。 GetShaderParameterResMaterial()187 const ResMaterial& GetShaderParameterResMaterial() const { return m_ShaderParameterResMaterial; } 188 189 //! 有効なシェーディングパラメータが取得できるマテリアルを取得します。 GetShadingParameterResMaterial()190 ResMaterial& GetShadingParameterResMaterial() { return m_ShadingParameterResMaterial; } 191 192 //! 有効なシェーディングパラメータが取得できるマテリアルを取得します。 GetShadingParameterResMaterial()193 const ResMaterial& GetShadingParameterResMaterial() const { return m_ShadingParameterResMaterial; } 194 195 //! 有効なマテリアルカラーが取得できるマテリアルを取得します。 GetMaterialColorResMaterial()196 ResMaterial& GetMaterialColorResMaterial() { return m_MaterialColorResMaterial; } 197 198 //! 有効なマテリアルカラーが取得できるマテリアルを取得します。 GetMaterialColorResMaterial()199 const ResMaterial& GetMaterialColorResMaterial() const { return m_MaterialColorResMaterial; } 200 201 //! 有効なラスタライゼーションが取得できるマテリアルを取得します。 GetRasterizationResMaterial()202 ResMaterial& GetRasterizationResMaterial() { return m_RasterizationResMaterial; } 203 204 //! 有効なラスタライゼーションが取得できるマテリアルを取得します。 GetRasterizationResMaterial()205 const ResMaterial& GetRasterizationResMaterial() const { return m_RasterizationResMaterial; } 206 207 //! 有効なテクスチャコーディネータが取得できるマテリアルを取得します。 GetTextureCoordinatorResMaterial()208 ResMaterial& GetTextureCoordinatorResMaterial() { return m_TextureCoordinatorResMaterial; } 209 210 //! 有効なテクスチャコーディネータが取得できるマテリアルを取得します。 GetTextureCoordinatorResMaterial()211 const ResMaterial& GetTextureCoordinatorResMaterial() const { return m_TextureCoordinatorResMaterial; } 212 213 //! 有効なテクスチャマッパーが取得できるマテリアルを取得します。 GetTextureMapperResMaterial()214 ResMaterial& GetTextureMapperResMaterial() { return m_TextureMapperResMaterial; } 215 216 //! 有効なテクスチャマッパーが取得できるマテリアルを取得します。 GetTextureMapperResMaterial()217 const ResMaterial& GetTextureMapperResMaterial() const { return m_TextureMapperResMaterial; } 218 219 //! 有効なフラグメントライティングが取得できるマテリアルを取得します。 GetFragmentLightingResMaterial()220 ResMaterial& GetFragmentLightingResMaterial() { return m_FragmentLightingResMaterial; } 221 222 //! 有効なフラグメントライティングが取得できるマテリアルを取得します。 GetFragmentLightingResMaterial()223 const ResMaterial& GetFragmentLightingResMaterial() const { return m_FragmentLightingResMaterial; } 224 225 //! 有効なフラグメントライティングテーブルが取得できるマテリアルを取得します。 GetFragmentLightingTableResMaterial()226 ResMaterial& GetFragmentLightingTableResMaterial() { return m_FragmentLightingTableResMaterial; } 227 228 //! 有効なフラグメントライティングテーブルが取得できるマテリアルを取得します。 GetFragmentLightingTableResMaterial()229 const ResMaterial& GetFragmentLightingTableResMaterial() const { return m_FragmentLightingTableResMaterial; } 230 231 //! 有効なテクスチャコンバイナが取得できるマテリアルを取得します。 GetTextureCombinerResMaterial()232 ResMaterial& GetTextureCombinerResMaterial() { return m_TextureCombinerResMaterial; } 233 234 //! 有効なテクスチャコンバイナが取得できるマテリアルを取得します。 GetTextureCombinerResMaterial()235 const ResMaterial& GetTextureCombinerResMaterial() const { return m_TextureCombinerResMaterial; } 236 237 //! 有効なアルファテストが取得できるマテリアルを取得します。 GetAlphaTestResMaterial()238 ResMaterial& GetAlphaTestResMaterial() { return m_AlphaTestResMaterial; } 239 240 //! 有効なアルファテストが取得できるマテリアルを取得します。 GetAlphaTestResMaterial()241 const ResMaterial& GetAlphaTestResMaterial() const { return m_AlphaTestResMaterial; } 242 243 //! 有効なフラグメントオペレーションが取得できるマテリアルを取得します。 GetFragmentOperationResMaterial()244 ResMaterial& GetFragmentOperationResMaterial() { return m_FragmentOperationResMaterial; } 245 246 //! 有効なフラグメントオペレーションが取得できるマテリアルを取得します。 GetFragmentOperationResMaterial()247 const ResMaterial& GetFragmentOperationResMaterial() const { return m_FragmentOperationResMaterial; } 248 249 //! 有効なシェーディングパラメータが取得できるマテリアルを取得します。 GetSceneEnvironmentResMaterial()250 ResMaterial& GetSceneEnvironmentResMaterial() { return m_SceneEnvironmentResMaterial; } 251 252 //! 有効なシーン環境の設定が取得できるマテリアルを取得します。 GetSceneEnvironmentResMaterial()253 const ResMaterial& GetSceneEnvironmentResMaterial() const { return m_SceneEnvironmentResMaterial; } 254 255 //@} 256 257 protected: 258 //---------------------------------------- 259 //! @name コンストラクタ/デストラクタ 260 //@{ 261 262 //! コンストラクタです。 263 Material( 264 os::IAllocator* allocator, 265 ResMaterial resMaterial, 266 s32 bufferCount, 267 Model* parent); 268 269 //! デストラクタです。 270 virtual ~Material(); 271 272 //@} 273 274 struct ResMaterialDestroyer : public std::unary_function<ResMaterial, void> 275 { m_AllocatorResMaterialDestroyer276 ResMaterialDestroyer(os::IAllocator* allocator = 0) : m_Allocator(allocator) 277 {} operatorResMaterialDestroyer278 result_type operator()(argument_type data) 279 { 280 DestroyResMaterial(m_Allocator, data); 281 } 282 283 os::IAllocator* m_Allocator; 284 }; 285 286 private: 287 288 //! @brief メンバのメモリ確保と初期化を行います。 289 Result Initialize(os::IAllocator* allocator); 290 291 //--------------------------------------------------------------------------- 292 //! @brief バッファを作成します。 293 //! 294 //! @param[in] allocator アロケータです。 295 //--------------------------------------------------------------------------- 296 Result CreateBuffers(os::IAllocator* allocator); 297 298 //--------------------------------------------------------------------------- 299 //! @brief ResMaterialをコピーします。 300 //! 301 //! @param[in] allocator アロケータです。 302 //! @param[in] bufferOption 生成オプションです。 303 //! 304 //! @return コピーしたマテリアルとコピー結果を表すフラグを返します。 305 //--------------------------------------------------------------------------- 306 ::std::pair<ResMaterial, Result> CopyResMaterial( 307 os::IAllocator* allocator, 308 bit32 bufferOption); 309 310 //--------------------------------------------------------------------------- 311 //! @brief ResMaterial のリソースを破棄します。 312 //! 313 //! @param[in] allocator リソース用のメモリを解放するアロケータです。 314 //! @param[in] resMaterial 解放するリソースです。 315 //--------------------------------------------------------------------------- 316 static void DestroyResMaterial(os::IAllocator* allocator, ResMaterial resMaterial); 317 318 //--------------------------------------------------------------------------- 319 //! @brief ResFragmentShader のリソースを破棄します。 320 //! 321 //! @param[in] allocator リソース用のメモリを解放するアロケータです。 322 //! @param[in] resFragmentShader 解放するリソースです。 323 //--------------------------------------------------------------------------- 324 static void DestroyResFragmentShader( 325 os::IAllocator* allocator, 326 ResFragmentShader resFragmentShader); 327 328 //--------------------------------------------------------------------------- 329 //! @brief ResShaderParameter のリソースを破棄します。 330 //! 331 //! @param[in] allocator リソース用のメモリを解放するアロケータです。 332 //! @param[in] resShaderParameter 解放するリソースです。 333 //--------------------------------------------------------------------------- 334 static void DestroyResShaderParameter( 335 os::IAllocator* allocator, 336 ResShaderParameter resShaderParameter); 337 338 //--------------------------------------------------------------------------- 339 //! @brief リソースからフラグメントライティングテーブルをコピーします。 340 //! 341 //! @param[in] allocator アロケータです。 342 //! @param[in] resFragmentLightingTable オリジナルのデータです。 343 //--------------------------------------------------------------------------- 344 ::std::pair<ResFragmentLightingTable, Result> CopyResFragmentLightingTable( 345 os::IAllocator* allocator, 346 ResFragmentLightingTable resFragmentLightingTable); 347 348 //--------------------------------------------------------------------------- 349 //! @brief リソースからライティング参照テーブルをコピーします。 350 //! 351 //! @param[in] allocator アロケータです。 352 //! @param[in] resLightingLookupTable オリジナルのデータです。 353 //--------------------------------------------------------------------------- 354 ::std::pair<ResLightingLookupTable, Result> CopyResLightingLookupTable( 355 os::IAllocator* allocator, 356 ResLightingLookupTable resLightingLookupTable); 357 358 //! @brief アニメーション対象のリソースを取得します。 359 //! 360 //! @param objectType 対応するタイプです。 361 //! @return バッファがあればバッファを、無ければオリジナルを返します。 362 //! GetActiveResource(u32 objectType)363 ResMaterial GetActiveResource(u32 objectType) 364 { 365 return (CanUseBuffer(objectType)) ? GetBuffer() : GetOriginal(); 366 } 367 368 //! @brief アニメーションに登録するモデルデータのポインタを取得します。 369 void* GetAnimTargetObject(const anim::ResAnimGroupMember& anim, const ResMaterial resMaterial); 370 371 // アニメーションのオブジェクトタイプに対応するバッファーが存在するかどうかを取得します。 372 bool CanUseBuffer(u32 objectType) const; 373 374 typedef ut::MoveArray<ResMaterial> ResMaterialArray; 375 376 ResMaterialArray m_Buffers; 377 Model* m_Owner; 378 ResShaderProgramDescription m_ProgramDescription; 379 s32 m_BufferCount; 380 381 ResMaterial m_ShaderParameterResMaterial; 382 ResMaterial m_ShadingParameterResMaterial; 383 ResMaterial m_MaterialColorResMaterial; 384 ResMaterial m_RasterizationResMaterial; 385 ResMaterial m_TextureCoordinatorResMaterial; 386 ResMaterial m_TextureMapperResMaterial; 387 ResMaterial m_FragmentLightingResMaterial; 388 ResMaterial m_FragmentLightingTableResMaterial; 389 ResMaterial m_TextureCombinerResMaterial; 390 ResMaterial m_AlphaTestResMaterial; 391 ResMaterial m_FragmentOperationResMaterial; 392 ResMaterial m_SceneEnvironmentResMaterial; 393 394 // TODO: CanUseBufferを非公開にするために暫定で対処しています。 395 friend class Model; 396 }; 397 398 //! @brief マテリアルの Array の定義です。 399 typedef ut::MoveArray<Material*> MaterialArray; 400 401 } // namespace gfx 402 } // namespace nw 403 404 #endif // NW_GFX_MATERIAL_H_ 405