]> git.lizzy.rs Git - irrlicht.git/blob - source/Irrlicht/OpenGL/FixedPipelineRenderer.cpp
421788acd2628d1be5e66e5acd6e344231464634
[irrlicht.git] / source / Irrlicht / OpenGL / FixedPipelineRenderer.cpp
1 // Copyright (C) 2023 Vitaliy Lobachevskiy
2 // Copyright (C) 2014 Patryk Nadrowski
3 // This file is part of the "Irrlicht Engine".
4 // For conditions of distribution and use, see copyright notice in Irrlicht.h
5
6 #include "FixedPipelineRenderer.h"
7
8 #include "IVideoDriver.h"
9
10 namespace irr
11 {
12 namespace video
13 {
14
15 // Base callback
16
17 COpenGL3MaterialBaseCB::COpenGL3MaterialBaseCB() :
18         FirstUpdateBase(true), WVPMatrixID(-1), WVMatrixID(-1), NMatrixID(-1), GlobalAmbientID(-1), MaterialAmbientID(-1), MaterialDiffuseID(-1), MaterialEmissiveID(-1), MaterialSpecularID(-1), MaterialShininessID(-1),
19         FogEnableID(-1), FogTypeID(-1), FogColorID(-1), FogStartID(-1),
20         FogEndID(-1), FogDensityID(-1), ThicknessID(-1), LightEnable(false), MaterialAmbient(SColorf(0.f, 0.f, 0.f)), MaterialDiffuse(SColorf(0.f, 0.f, 0.f)), MaterialEmissive(SColorf(0.f, 0.f, 0.f)), MaterialSpecular(SColorf(0.f, 0.f, 0.f)),
21         MaterialShininess(0.f), FogEnable(0), FogType(1), FogColor(SColorf(0.f, 0.f, 0.f, 1.f)), FogStart(0.f), FogEnd(0.f), FogDensity(0.f), Thickness(1.f)
22 {
23 }
24
25 void COpenGL3MaterialBaseCB::OnSetMaterial(const SMaterial& material)
26 {
27         LightEnable = material.Lighting;
28         MaterialAmbient = SColorf(material.AmbientColor);
29         MaterialDiffuse = SColorf(material.DiffuseColor);
30         MaterialEmissive = SColorf(material.EmissiveColor);
31         MaterialSpecular = SColorf(material.SpecularColor);
32         MaterialShininess = material.Shininess;
33
34         FogEnable = material.FogEnable ? 1 : 0;
35
36         Thickness = (material.Thickness > 0.f) ? material.Thickness : 1.f;
37 }
38
39 void COpenGL3MaterialBaseCB::OnSetConstants(IMaterialRendererServices* services, s32 userData)
40 {
41         IVideoDriver* driver = services->getVideoDriver();
42
43         if (FirstUpdateBase)
44         {
45                 WVPMatrixID = services->getVertexShaderConstantID("uWVPMatrix");
46                 WVMatrixID = services->getVertexShaderConstantID("uWVMatrix");
47                 NMatrixID = services->getVertexShaderConstantID("uNMatrix");
48                 GlobalAmbientID = services->getVertexShaderConstantID("uGlobalAmbient");
49                 MaterialAmbientID = services->getVertexShaderConstantID("uMaterialAmbient");
50                 MaterialDiffuseID = services->getVertexShaderConstantID("uMaterialDiffuse");
51                 MaterialEmissiveID = services->getVertexShaderConstantID("uMaterialEmissive");
52                 MaterialSpecularID = services->getVertexShaderConstantID("uMaterialSpecular");
53                 MaterialShininessID = services->getVertexShaderConstantID("uMaterialShininess");
54                 FogEnableID = services->getVertexShaderConstantID("uFogEnable");
55                 FogTypeID = services->getVertexShaderConstantID("uFogType");
56                 FogColorID = services->getVertexShaderConstantID("uFogColor");
57                 FogStartID = services->getVertexShaderConstantID("uFogStart");
58                 FogEndID = services->getVertexShaderConstantID("uFogEnd");
59                 FogDensityID = services->getVertexShaderConstantID("uFogDensity");
60                 ThicknessID = services->getVertexShaderConstantID("uThickness");
61
62                 FirstUpdateBase = false;
63         }
64
65         const core::matrix4 W = driver->getTransform(ETS_WORLD);
66         const core::matrix4 V = driver->getTransform(ETS_VIEW);
67         const core::matrix4 P = driver->getTransform(ETS_PROJECTION);
68
69         core::matrix4 Matrix = P * V * W;
70         services->setPixelShaderConstant(WVPMatrixID, Matrix.pointer(), 16);
71
72         Matrix = V * W;
73         services->setPixelShaderConstant(WVMatrixID, Matrix.pointer(), 16);
74
75         Matrix.makeInverse();
76         services->setPixelShaderConstant(NMatrixID, Matrix.getTransposed().pointer(), 16);
77
78         services->setPixelShaderConstant(FogEnableID, &FogEnable, 1);
79
80         if (FogEnable)
81         {
82                 SColor TempColor(0);
83                 E_FOG_TYPE TempType = EFT_FOG_LINEAR;
84                 bool TempPerFragment = false;
85                 bool TempRange = false;
86
87                 driver->getFog(TempColor, TempType, FogStart, FogEnd, FogDensity, TempPerFragment, TempRange);
88
89                 FogType = (s32)TempType;
90                 FogColor = SColorf(TempColor);
91
92                 services->setPixelShaderConstant(FogTypeID, &FogType, 1);
93                 services->setPixelShaderConstant(FogColorID, reinterpret_cast<f32*>(&FogColor), 4);
94                 services->setPixelShaderConstant(FogStartID, &FogStart, 1);
95                 services->setPixelShaderConstant(FogEndID, &FogEnd, 1);
96                 services->setPixelShaderConstant(FogDensityID, &FogDensity, 1);
97         }
98
99         services->setPixelShaderConstant(ThicknessID, &Thickness, 1);
100 }
101
102 // EMT_SOLID + EMT_TRANSPARENT_ADD_COLOR + EMT_TRANSPARENT_ALPHA_CHANNEL + EMT_TRANSPARENT_VERTEX_ALPHA
103
104 COpenGL3MaterialSolidCB::COpenGL3MaterialSolidCB() :
105         FirstUpdate(true), TMatrix0ID(-1), AlphaRefID(-1), TextureUsage0ID(-1), TextureUnit0ID(-1), AlphaRef(0.5f), TextureUsage0(0), TextureUnit0(0)
106 {
107 }
108
109 void COpenGL3MaterialSolidCB::OnSetMaterial(const SMaterial& material)
110 {
111         COpenGL3MaterialBaseCB::OnSetMaterial(material);
112
113         AlphaRef = material.MaterialTypeParam;
114         TextureUsage0 = (material.TextureLayer[0].Texture) ? 1 : 0;
115 }
116
117 void COpenGL3MaterialSolidCB::OnSetConstants(IMaterialRendererServices* services, s32 userData)
118 {
119         COpenGL3MaterialBaseCB::OnSetConstants(services, userData);
120
121         IVideoDriver* driver = services->getVideoDriver();
122
123         if (FirstUpdate)
124         {
125                 TMatrix0ID = services->getVertexShaderConstantID("uTMatrix0");
126                 AlphaRefID = services->getVertexShaderConstantID("uAlphaRef");
127                 TextureUsage0ID = services->getVertexShaderConstantID("uTextureUsage0");
128                 TextureUnit0ID = services->getVertexShaderConstantID("uTextureUnit0");
129
130                 FirstUpdate = false;
131         }
132
133         core::matrix4 Matrix = driver->getTransform(ETS_TEXTURE_0);
134         services->setPixelShaderConstant(TMatrix0ID, Matrix.pointer(), 16);
135
136         services->setPixelShaderConstant(AlphaRefID, &AlphaRef, 1);
137         services->setPixelShaderConstant(TextureUsage0ID, &TextureUsage0, 1);
138         services->setPixelShaderConstant(TextureUnit0ID, &TextureUnit0, 1);
139 }
140
141 // EMT_ONETEXTURE_BLEND
142
143 COpenGL3MaterialOneTextureBlendCB::COpenGL3MaterialOneTextureBlendCB() :
144         FirstUpdate(true), TMatrix0ID(-1), BlendTypeID(-1), TextureUsage0ID(-1), TextureUnit0ID(-1), BlendType(0), TextureUsage0(0), TextureUnit0(0)
145 {
146 }
147
148 void COpenGL3MaterialOneTextureBlendCB::OnSetMaterial(const SMaterial& material)
149 {
150         COpenGL3MaterialBaseCB::OnSetMaterial(material);
151
152         BlendType = 0;
153
154         E_BLEND_FACTOR srcRGBFact,dstRGBFact,srcAlphaFact,dstAlphaFact;
155         E_MODULATE_FUNC modulate;
156         u32 alphaSource;
157         unpack_textureBlendFuncSeparate(srcRGBFact, dstRGBFact, srcAlphaFact, dstAlphaFact, modulate, alphaSource, material.MaterialTypeParam);
158
159         if (textureBlendFunc_hasAlpha(srcRGBFact) || textureBlendFunc_hasAlpha(dstRGBFact) || textureBlendFunc_hasAlpha(srcAlphaFact) || textureBlendFunc_hasAlpha(dstAlphaFact))
160         {
161                 if (alphaSource == EAS_VERTEX_COLOR)
162                 {
163                         BlendType = 1;
164                 }
165                 else if (alphaSource == EAS_TEXTURE)
166                 {
167                         BlendType = 2;
168                 }
169         }
170
171         TextureUsage0 = (material.TextureLayer[0].Texture) ? 1 : 0;
172 }
173
174 void COpenGL3MaterialOneTextureBlendCB::OnSetConstants(IMaterialRendererServices* services, s32 userData)
175 {
176         COpenGL3MaterialBaseCB::OnSetConstants(services, userData);
177
178         IVideoDriver* driver = services->getVideoDriver();
179
180         if (FirstUpdate)
181         {
182                 TMatrix0ID = services->getVertexShaderConstantID("uTMatrix0");
183                 BlendTypeID = services->getVertexShaderConstantID("uBlendType");
184                 TextureUsage0ID = services->getVertexShaderConstantID("uTextureUsage0");
185                 TextureUnit0ID = services->getVertexShaderConstantID("uTextureUnit0");
186
187                 FirstUpdate = false;
188         }
189
190         core::matrix4 Matrix = driver->getTransform(ETS_TEXTURE_0);
191         services->setPixelShaderConstant(TMatrix0ID, Matrix.pointer(), 16);
192
193         services->setPixelShaderConstant(BlendTypeID, &BlendType, 1);
194         services->setPixelShaderConstant(TextureUsage0ID, &TextureUsage0, 1);
195         services->setPixelShaderConstant(TextureUnit0ID, &TextureUnit0, 1);
196 }
197
198 }
199 }