1 /*---------------------------------------------------------------------------*
2   Project:  NintendoWare
3   File:     gfx_DirectMaterialActivator.cpp
4 
5   Copyright (C)2009-2010 Nintendo Co., Ltd./HAL Laboratory, Inc.  All rights reserved.
6 
7   These coded instructions, statements, and computer programs contain
8   proprietary information of Nintendo of America Inc. and/or Nintendo
9   Company Ltd., and are protected by Federal copyright law.  They may
10   not be disclosed to third parties or copied or duplicated in any form,
11   in whole or in part, without the prior written consent of Nintendo.
12 
13   $Revision: 28423 $
14  *---------------------------------------------------------------------------*/
15 
16 #include "precompiled.h"
17 
18 #include <nw/gfx/gfx_MaterialActivator.h>
19 #include <nw/gfx/gfx_MaterialState.h>
20 #include <nw/gfx/gfx_Model.h>
21 #include <nn/gx.h>
22 
23 namespace nw
24 {
25 namespace gfx
26 {
27 
28 NW_UT_RUNTIME_TYPEINFO_DEFINITION(DirectMaterialActivator, IMaterialActivator);
29 
30 //----------------------------------------
31 DirectMaterialActivator*
Create(os::IAllocator * allocator)32 DirectMaterialActivator::Create(os::IAllocator* allocator)
33 {
34     void* memory = allocator->Alloc(sizeof(DirectMaterialActivator));
35 
36     if (memory == NULL)
37     {
38         return NULL;
39     }
40     else
41     {
42         return new(memory) DirectMaterialActivator(allocator);
43     }
44 }
45 
46 //----------------------------------------
47 void
Activate(RenderContext * renderContext,const Material * material)48 DirectMaterialActivator::Activate(RenderContext* renderContext, const Material* material)
49 {
50     NW_NULL_ASSERT(renderContext);
51     const ShaderProgram* shaderProgram = renderContext->GetShaderProgram();
52     NW_NULL_ASSERT(shaderProgram);
53 
54     const Model* owner = material->GetOwnerModel();
55     NW_NULL_ASSERT(owner);
56 
57     const SceneEnvironment& sceneEnvironment = renderContext->GetSceneEnvironment();
58 
59     RenderContext::MaterialHash materialHash = renderContext->GetMaterialHash();
60 
61     if (ut::CheckFlag(m_ActivateFlags, Model::FLAG_BUFFER_SHADER_PARAMETER))
62     {
63         internal::MaterialState::ActivateShaderParameter(shaderProgram, material->GetShaderParameterResMaterial());
64         materialHash.shaderParameter = 0x0;
65     }
66 
67     const ResMaterial resShadingParameterResMaterial = material->GetShadingParameterResMaterial();
68 
69     // FragmentLightEnabled は必ず設定します。
70     internal::MaterialState::ActivateFragmentLightParameters(sceneEnvironment, shaderProgram, resShadingParameterResMaterial);
71 
72     if (ut::CheckFlag(m_ActivateFlags, Model::FLAG_BUFFER_SHADING_PARAMETER))
73     {
74         internal::MaterialState::ActivateShadingParameters(sceneEnvironment, shaderProgram, resShadingParameterResMaterial);
75         materialHash.shadingParameter = 0x0;
76     }
77 
78     const ResMaterial resRasterizationMaterial = material->GetRasterizationResMaterial();
79     if (ut::CheckFlag(m_ActivateFlags, Model::FLAG_BUFFER_RASTERIZATION))
80     {
81         internal::MaterialState::ActivateRasterization(resRasterizationMaterial.GetRasterization());
82         materialHash.rasterization = 0x0;
83     }
84 
85     if (ut::CheckFlag(m_ActivateFlags, Model::FLAG_BUFFER_TEXTURE_COORDINATOR))
86     {
87         internal::MaterialState::ActivateTextureCoordinators(renderContext, shaderProgram, material->GetTextureCoordinatorResMaterial());
88         materialHash.textureCoordinator = 0x0;
89     }
90 
91     if (ut::CheckFlag(m_ActivateFlags, Model::FLAG_BUFFER_TEXTURE_MAPPER))
92     {
93         internal::MaterialState::ActivateTextureMappers(material->GetTextureMapperResMaterial());
94         materialHash.textureMapper = 0x0;
95     }
96 
97     const ResMaterial resFragmentLightingResMaterial = material->GetFragmentLightingResMaterial();
98     const ResFragmentLighting resFragmentLighting = resFragmentLightingResMaterial.GetFragmentShader().GetFragmentLighting();
99     if (ut::CheckFlag(m_ActivateFlags, Model::FLAG_BUFFER_FRAGMENT_LIGHTING))
100     {
101         internal::MaterialState::ActivateFragmentLighting(sceneEnvironment, resFragmentLighting);
102         materialHash.fragmentLighting = 0x0;
103     }
104 
105     const ResMaterial resFramgnetLightingTableResMaterial = material->GetFragmentLightingTableResMaterial();
106     if (ut::CheckFlag(m_ActivateFlags, Model::FLAG_BUFFER_FRAGMENT_LIGHTING_TABLE))
107     {
108         const ResFragmentLightingTable resFragmentLightingTable = resFramgnetLightingTableResMaterial.GetFragmentShader().GetFragmentLightingTable();
109         internal::MaterialState::ActivateFragmentLightingTable(resFragmentLighting, resFragmentLightingTable);
110         materialHash.fragmentLightingTable = 0x0;
111     }
112 
113     const ResMaterial resMaterialColorResMaterial = material->GetMaterialColorResMaterial();
114     const ResMaterialColor resMaterialColor = resMaterialColorResMaterial.GetMaterialColor();
115 
116     Material* cacheMaterial = renderContext->GetMaterialCache();
117     if (ut::CheckFlag(m_ActivateFlags, Model::FLAG_BUFFER_MATERIAL_COLOR))
118     {
119         bool reflectionEnabled = ut::CheckFlag(resFragmentLighting.GetFlags(), ResFragmentLightingData::FLAG_REFLECTION_ENABLED);
120         internal::MaterialState::ActivateMaterialColor(sceneEnvironment, shaderProgram, resMaterialColor, reflectionEnabled);
121         materialHash.materialColor = 0x0;
122     }
123 
124     const ResMaterial resTextureCombinerResMaterial = material->GetTextureCombinerResMaterial();
125     if (ut::CheckFlag(m_ActivateFlags, Model::FLAG_BUFFER_TEXTURE_COMBINER))
126     {
127         const ResFragmentShader resTextureCombinerFragmentShader = resTextureCombinerResMaterial.GetFragmentShader();
128         internal::MaterialState::ActivateTextureCombiners(resTextureCombinerFragmentShader, resMaterialColor);
129         materialHash.textureCombiner = 0x0;
130     }
131 
132     const ResMaterial resAlphaTestResMaterial = material->GetAlphaTestResMaterial();
133     if (ut::CheckFlag(m_ActivateFlags, Model::FLAG_BUFFER_ALPHA_TEST))
134     {
135         const ResAlphaTest resAlphaTest = resAlphaTestResMaterial.GetFragmentShader().GetAlphaTest();
136         internal::MaterialState::ActivateAlphaTest(resAlphaTest);
137         materialHash.alphaTest = 0x0;
138     }
139 
140     const ResMaterial resFragmentOperationResMaterial = material->GetFragmentOperationResMaterial();
141     if (ut::CheckFlag(m_ActivateFlags, Model::FLAG_BUFFER_FRAGMENT_OPERATION))
142     {
143         const ResFragmentOperation resFragmentOperation = resFragmentOperationResMaterial.GetFragmentOperation();
144         internal::MaterialState::ActivateFragmentOperation(resFragmentOperation);
145         materialHash.fragmentOperation = 0x0;
146     }
147 
148     renderContext->SetMaterialHash(materialHash);
149 }
150 
151 //----------------------------------------
DirectMaterialActivator(os::IAllocator * allocator)152 DirectMaterialActivator::DirectMaterialActivator(os::IAllocator* allocator)
153     : IMaterialActivator(allocator),
154       m_ActivateFlags(Model::MULTI_FLAG_BUFFER_MATERIAL)
155 {
156 }
157 
158 //----------------------------------------
~DirectMaterialActivator()159 DirectMaterialActivator::~DirectMaterialActivator()
160 {
161 }
162 
163 } // namespace gfx
164 } // namespace nw
165