- Improved texture handling in OpenGL ES2.
git-svn-id: svn://svn.code.sf.net/p/irrlicht/code/branches/ogl-es@4993 dfc29bdd-3216-0410-991c-e03cc46cb475master
parent
bba02a5d20
commit
971059c81c
|
@ -130,8 +130,10 @@ COGLES2Driver::COGLES2Driver(const SIrrlichtCreationParameters& params,
|
|||
|
||||
COGLES2Driver::~COGLES2Driver()
|
||||
{
|
||||
if (BridgeCalls)
|
||||
BridgeCalls->reset();
|
||||
|
||||
RequestedLights.clear();
|
||||
CurrentTexture.clear();
|
||||
deleteMaterialRenders();
|
||||
delete MaterialRenderer2D;
|
||||
deleteAllTextures();
|
||||
|
@ -177,13 +179,13 @@ COGLES2Driver::~COGLES2Driver()
|
|||
VendorName = glGetString(GL_VENDOR);
|
||||
os::Printer::log(VendorName.c_str(), ELL_INFORMATION);
|
||||
|
||||
CurrentTexture.clear();
|
||||
|
||||
// load extensions
|
||||
initExtensions(this, stencilBuffer);
|
||||
|
||||
if (!BridgeCalls)
|
||||
BridgeCalls = new COGLES2CallBridge(this);
|
||||
else
|
||||
BridgeCalls->reset();
|
||||
|
||||
StencilBuffer = stencilBuffer;
|
||||
|
||||
|
@ -1062,9 +1064,9 @@ bool COGLES2Driver::endScene()
|
|||
|
||||
const core::rect<s32> poss(targetPos, sourceSize);
|
||||
|
||||
disableTextures(1);
|
||||
if (!setActiveTexture(0, texture))
|
||||
return;
|
||||
chooseMaterial2D();
|
||||
Material.TextureLayer[0].Texture = const_cast<ITexture*>(texture);
|
||||
|
||||
setRenderStates2DMode(color.getAlpha() < 255, true, useAlphaChannelOfTexture);
|
||||
|
||||
f32 left = (f32)poss.UpperLeftCorner.X / (f32)renderTargetSize.Width * 2.f - 1.f;
|
||||
|
@ -1103,9 +1105,6 @@ bool COGLES2Driver::endScene()
|
|||
|
||||
IRR_PROFILE(CProfileScope p1(EPID_ES2_DRAW_2DIMAGE_BATCH);)
|
||||
|
||||
if (!setActiveTexture(0, const_cast<video::ITexture*>(texture)))
|
||||
return;
|
||||
|
||||
const irr::u32 drawCount = core::min_<u32>(positions.size(), sourceRects.size());
|
||||
|
||||
core::array<S3DVertex> vtx(drawCount * 4);
|
||||
|
@ -1204,6 +1203,9 @@ bool COGLES2Driver::endScene()
|
|||
|
||||
const core::rect<s32> poss(targetPos, sourceSize);
|
||||
|
||||
chooseMaterial2D();
|
||||
Material.TextureLayer[0].Texture = const_cast<ITexture*>(texture);
|
||||
|
||||
setRenderStates2DMode(color.getAlpha() < 255, true, useAlphaChannelOfTexture);
|
||||
|
||||
f32 left = (f32)poss.UpperLeftCorner.X / (f32)renderTargetSize.Width * 2.f - 1.f;
|
||||
|
@ -1282,8 +1284,9 @@ bool COGLES2Driver::endScene()
|
|||
|
||||
const video::SColor* const useColor = colors ? colors : temp;
|
||||
|
||||
disableTextures(1);
|
||||
setActiveTexture(0, texture);
|
||||
chooseMaterial2D();
|
||||
Material.TextureLayer[0].Texture = const_cast<ITexture*>(texture);
|
||||
|
||||
setRenderStates2DMode(useColor[0].getAlpha() < 255 || useColor[1].getAlpha() < 255 ||
|
||||
useColor[2].getAlpha() < 255 || useColor[3].getAlpha() < 255,
|
||||
true, useAlphaChannelOfTexture);
|
||||
|
@ -1343,9 +1346,9 @@ bool COGLES2Driver::endScene()
|
|||
|
||||
IRR_PROFILE(CProfileScope p1(EPID_ES2_DRAW_2DIMAGE_BATCH);)
|
||||
|
||||
disableTextures(1);
|
||||
if (!setActiveTexture(0, texture))
|
||||
return;
|
||||
chooseMaterial2D();
|
||||
Material.TextureLayer[0].Texture = const_cast<ITexture*>(texture);
|
||||
|
||||
setRenderStates2DMode(color.getAlpha() < 255, true, useAlphaChannelOfTexture);
|
||||
|
||||
const core::dimension2d<u32>& renderTargetSize = getCurrentRenderTargetSize();
|
||||
|
@ -1434,7 +1437,9 @@ bool COGLES2Driver::endScene()
|
|||
{
|
||||
IRR_PROFILE(CProfileScope p1(EPID_ES2_DRAW_2DRECTANGLE);)
|
||||
|
||||
disableTextures();
|
||||
chooseMaterial2D();
|
||||
Material.TextureLayer[0].Texture = 0;
|
||||
|
||||
setRenderStates2DMode(color.getAlpha() < 255, false, false);
|
||||
|
||||
core::rect<s32> pos = position;
|
||||
|
@ -1485,7 +1490,8 @@ bool COGLES2Driver::endScene()
|
|||
if (!pos.isValid())
|
||||
return;
|
||||
|
||||
disableTextures();
|
||||
chooseMaterial2D();
|
||||
Material.TextureLayer[0].Texture = 0;
|
||||
|
||||
setRenderStates2DMode(colorLeftUp.getAlpha() < 255 ||
|
||||
colorRightUp.getAlpha() < 255 ||
|
||||
|
@ -1526,7 +1532,9 @@ bool COGLES2Driver::endScene()
|
|||
drawPixel(start.X, start.Y, color);
|
||||
else
|
||||
{
|
||||
disableTextures();
|
||||
chooseMaterial2D();
|
||||
Material.TextureLayer[0].Texture = 0;
|
||||
|
||||
setRenderStates2DMode(color.getAlpha() < 255, false, false);
|
||||
|
||||
const core::dimension2d<u32>& renderTargetSize = getCurrentRenderTargetSize();
|
||||
|
@ -1559,7 +1567,9 @@ bool COGLES2Driver::endScene()
|
|||
if (x > (u32)renderTargetSize.Width || y > (u32)renderTargetSize.Height)
|
||||
return;
|
||||
|
||||
disableTextures();
|
||||
chooseMaterial2D();
|
||||
Material.TextureLayer[0].Texture = 0;
|
||||
|
||||
setRenderStates2DMode(color.getAlpha() < 255, false, false);
|
||||
|
||||
f32 X = (f32)x / (f32)renderTargetSize.Width * 2.f - 1.f;
|
||||
|
@ -1578,77 +1588,6 @@ bool COGLES2Driver::endScene()
|
|||
}
|
||||
|
||||
|
||||
bool COGLES2Driver::setActiveTexture(u32 stage, const video::ITexture* texture)
|
||||
{
|
||||
if (stage >= MaxSupportedTextures)
|
||||
return false;
|
||||
|
||||
if (CurrentTexture[stage]==texture)
|
||||
return true;
|
||||
|
||||
CurrentTexture.set(stage,texture);
|
||||
|
||||
if (!texture)
|
||||
return true;
|
||||
else if (texture->getDriverType() != EDT_OGLES2)
|
||||
{
|
||||
CurrentTexture.set(stage, 0);
|
||||
os::Printer::log("Fatal Error: Tried to set a texture not owned by this driver.", ELL_ERROR);
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
bool COGLES2Driver::isActiveTexture(u32 stage)
|
||||
{
|
||||
return (CurrentTexture[stage]) ? true : false;
|
||||
}
|
||||
|
||||
|
||||
//! disables all textures beginning with the optional fromStage parameter.
|
||||
bool COGLES2Driver::disableTextures(u32 fromStage)
|
||||
{
|
||||
bool result = true;
|
||||
for (u32 i = fromStage; i < MaxTextureUnits; ++i)
|
||||
result &= setActiveTexture(i, 0);
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
//! creates a matrix in supplied GLfloat array to pass to OGLES1
|
||||
inline void COGLES2Driver::createGLMatrix(float gl_matrix[16], const core::matrix4& m)
|
||||
{
|
||||
memcpy(gl_matrix, m.pointer(), 16 * sizeof(f32));
|
||||
}
|
||||
|
||||
|
||||
//! creates a opengltexturematrix from a D3D style texture matrix
|
||||
inline void COGLES2Driver::createGLTextureMatrix(float *o, const core::matrix4& m)
|
||||
{
|
||||
o[0] = m[0];
|
||||
o[1] = m[1];
|
||||
o[2] = 0.f;
|
||||
o[3] = 0.f;
|
||||
|
||||
o[4] = m[4];
|
||||
o[5] = m[5];
|
||||
o[6] = 0.f;
|
||||
o[7] = 0.f;
|
||||
|
||||
o[8] = 0.f;
|
||||
o[9] = 0.f;
|
||||
o[10] = 1.f;
|
||||
o[11] = 0.f;
|
||||
|
||||
o[12] = m[8];
|
||||
o[13] = m[9];
|
||||
o[14] = 0.f;
|
||||
o[15] = 1.f;
|
||||
}
|
||||
|
||||
|
||||
//! returns a device dependent texture from a software surface (IImage)
|
||||
ITexture* COGLES2Driver::createDeviceDependentTexture(IImage* surface, const io::path& name, void* mipmapData)
|
||||
{
|
||||
|
@ -1658,7 +1597,7 @@ bool COGLES2Driver::endScene()
|
|||
texture = new COGLES2Texture(surface, name, mipmapData, this);
|
||||
|
||||
return texture;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//! returns a device dependent texture from a software surface (IImage)
|
||||
|
@ -1685,10 +1624,7 @@ bool COGLES2Driver::endScene()
|
|||
OverrideMaterial.apply(Material);
|
||||
|
||||
for (u32 i = 0; i < MaxTextureUnits; ++i)
|
||||
{
|
||||
setActiveTexture(i, material.getTexture(i));
|
||||
setTransform((E_TRANSFORMATION_STATE)(ETS_TEXTURE_0 + i), material.getTextureMatrix(i));
|
||||
}
|
||||
}
|
||||
|
||||
//! prints error if an error happened.
|
||||
|
@ -1967,14 +1903,16 @@ bool COGLES2Driver::endScene()
|
|||
|
||||
for (s32 i = MaxTextureUnits-1; i>= 0; --i)
|
||||
{
|
||||
const COGLES2Texture* tmpTexture = static_cast<const COGLES2Texture*>(CurrentTexture[i]);
|
||||
GLenum tmpTextureType = (tmpTexture) ? tmpTexture->getOpenGLTextureType() : GL_TEXTURE_2D;
|
||||
COGLES2Texture* tmpTexture = static_cast<COGLES2Texture*>(material.TextureLayer[i].Texture);
|
||||
|
||||
BridgeCalls->setTexture(i, tmpTextureType);
|
||||
BridgeCalls->setActiveTexture(i);
|
||||
BridgeCalls->setTexture(tmpTexture);
|
||||
|
||||
if (!CurrentTexture[i])
|
||||
if (!tmpTexture)
|
||||
continue;
|
||||
|
||||
GLenum tmpTextureType = tmpTexture->getOpenGLTextureType();
|
||||
|
||||
if (resetAllRenderstates)
|
||||
tmpTexture->getStatesCache().IsCached = false;
|
||||
|
||||
|
@ -1988,7 +1926,7 @@ bool COGLES2Driver::endScene()
|
|||
tmpTexture->getStatesCache().TrilinearFilter = material.TextureLayer[i].TrilinearFilter;
|
||||
}
|
||||
|
||||
if (material.UseMipMaps && CurrentTexture[i]->hasMipMaps())
|
||||
if (material.UseMipMaps && tmpTexture->hasMipMaps())
|
||||
{
|
||||
if (!tmpTexture->getStatesCache().IsCached || material.TextureLayer[i].BilinearFilter != tmpTexture->getStatesCache().BilinearFilter ||
|
||||
material.TextureLayer[i].TrilinearFilter != tmpTexture->getStatesCache().TrilinearFilter || !tmpTexture->getStatesCache().MipMapStatus)
|
||||
|
@ -2079,24 +2017,6 @@ bool COGLES2Driver::endScene()
|
|||
CurrentRenderMode = ERM_2D;
|
||||
}
|
||||
|
||||
if (!OverrideMaterial2DEnabled)
|
||||
Material = InitMaterial2D;
|
||||
|
||||
if (OverrideMaterial2DEnabled)
|
||||
{
|
||||
OverrideMaterial2D.Lighting=false;
|
||||
OverrideMaterial2D.ZWriteEnable=false;
|
||||
OverrideMaterial2D.ZBuffer=ECFN_NEVER; // it will be ECFN_DISABLED after merge
|
||||
OverrideMaterial2D.Lighting=false;
|
||||
|
||||
Material = OverrideMaterial2D;
|
||||
}
|
||||
|
||||
if (texture)
|
||||
MaterialRenderer2D->setTexture(CurrentTexture[0]);
|
||||
else
|
||||
MaterialRenderer2D->setTexture(0);
|
||||
|
||||
MaterialRenderer2D->OnSetMaterial(Material, LastMaterial, true, 0);
|
||||
LastMaterial = Material;
|
||||
|
||||
|
@ -2115,6 +2035,23 @@ bool COGLES2Driver::endScene()
|
|||
}
|
||||
|
||||
|
||||
void COGLES2Driver::chooseMaterial2D()
|
||||
{
|
||||
if (!OverrideMaterial2DEnabled)
|
||||
Material = InitMaterial2D;
|
||||
|
||||
if (OverrideMaterial2DEnabled)
|
||||
{
|
||||
OverrideMaterial2D.Lighting=false;
|
||||
OverrideMaterial2D.ZWriteEnable=false;
|
||||
OverrideMaterial2D.ZBuffer=ECFN_DISABLED; // it will be ECFN_DISABLED after merge
|
||||
OverrideMaterial2D.Lighting=false;
|
||||
|
||||
Material = OverrideMaterial2D;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//! \return Returns the name of the video driver.
|
||||
const wchar_t* COGLES2Driver::getName() const
|
||||
{
|
||||
|
@ -2264,9 +2201,10 @@ bool COGLES2Driver::endScene()
|
|||
if (!StencilBuffer)
|
||||
return;
|
||||
|
||||
setRenderStates2DMode(true, false, false);
|
||||
chooseMaterial2D();
|
||||
Material.TextureLayer[0].Texture = 0;
|
||||
|
||||
disableTextures();
|
||||
setRenderStates2DMode(true, false, false);
|
||||
|
||||
BridgeCalls->setDepthMask(false);
|
||||
BridgeCalls->setColorMask(true, true, true, true);
|
||||
|
@ -2517,7 +2455,6 @@ bool COGLES2Driver::endScene()
|
|||
|
||||
// check if we should set the previous RT back
|
||||
|
||||
setActiveTexture(0, 0);
|
||||
ResetRenderStates = true;
|
||||
if (RenderTargetTexture != 0)
|
||||
{
|
||||
|
@ -2711,7 +2648,6 @@ bool COGLES2Driver::endScene()
|
|||
return;
|
||||
|
||||
CNullDriver::removeTexture(texture);
|
||||
CurrentTexture.remove(texture);
|
||||
}
|
||||
|
||||
void COGLES2Driver::deleteFramebuffers(s32 n, const u32 *framebuffers)
|
||||
|
@ -2827,7 +2763,7 @@ bool COGLES2Driver::endScene()
|
|||
BlendSourceAlpha(GL_ONE), BlendDestinationAlpha(GL_ZERO), Blend(false),
|
||||
CullFaceMode(GL_BACK), CullFace(false),
|
||||
DepthFunc(GL_LESS), DepthMask(true), DepthTest(false),
|
||||
Program(0), ActiveTexture(GL_TEXTURE0), Viewport(core::rect<s32>(0, 0, 0, 0))
|
||||
Program(0), ActiveTextureID(0), Viewport(core::rect<s32>(0, 0, 0, 0))
|
||||
{
|
||||
// Initial OpenGL values from specification.
|
||||
|
||||
|
@ -2835,10 +2771,7 @@ bool COGLES2Driver::endScene()
|
|||
ColorMask[i] = true;
|
||||
|
||||
for (u32 i = 0; i < MATERIAL_MAX_TEXTURES; ++i)
|
||||
{
|
||||
Texture[i] = 0;
|
||||
TextureType[i] = GL_TEXTURE_2D;
|
||||
}
|
||||
|
||||
glBlendFunc(GL_ONE, GL_ZERO);
|
||||
glDisable(GL_BLEND);
|
||||
|
@ -2851,6 +2784,58 @@ bool COGLES2Driver::endScene()
|
|||
glDepthFunc(GL_LESS);
|
||||
glDepthMask(GL_TRUE);
|
||||
glDisable(GL_DEPTH_TEST);
|
||||
|
||||
glActiveTexture(GL_TEXTURE0);
|
||||
}
|
||||
|
||||
void COGLES2CallBridge::reset()
|
||||
{
|
||||
// Initial OpenGL values from specification.
|
||||
|
||||
BlendEquation = GL_FUNC_ADD;
|
||||
BlendSourceRGB = GL_ONE;
|
||||
BlendDestinationRGB = GL_ZERO;
|
||||
BlendSourceAlpha = GL_ONE;
|
||||
BlendDestinationAlpha = GL_ZERO;
|
||||
Blend = false;
|
||||
|
||||
for (u32 i = 0; i < 4; ++i)
|
||||
ColorMask[i] = true;
|
||||
|
||||
CullFaceMode = GL_BACK;
|
||||
CullFace = false;
|
||||
|
||||
DepthFunc = GL_LESS;
|
||||
DepthMask = true;
|
||||
DepthTest = false;
|
||||
|
||||
Program = 0;
|
||||
|
||||
ActiveTextureID = 0;
|
||||
|
||||
for (u32 i = 0; i < MATERIAL_MAX_TEXTURES; ++i)
|
||||
{
|
||||
if (Texture[i])
|
||||
Texture[i]->drop();
|
||||
|
||||
Texture[i] = 0;
|
||||
}
|
||||
|
||||
Viewport = core::rect<s32>(0, 0, 0, 0);
|
||||
|
||||
glBlendFunc(GL_ONE, GL_ZERO);
|
||||
glDisable(GL_BLEND);
|
||||
|
||||
glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE);
|
||||
|
||||
glCullFace(GL_BACK);
|
||||
glDisable(GL_CULL_FACE);
|
||||
|
||||
glDepthFunc(GL_LESS);
|
||||
glDepthMask(GL_TRUE);
|
||||
glDisable(GL_DEPTH_TEST);
|
||||
|
||||
glActiveTexture(GL_TEXTURE0);
|
||||
}
|
||||
|
||||
void COGLES2CallBridge::setBlendEquation(GLenum mode)
|
||||
|
@ -2992,57 +2977,59 @@ bool COGLES2Driver::endScene()
|
|||
}
|
||||
}
|
||||
|
||||
void COGLES2CallBridge::resetTexture(const ITexture* texture)
|
||||
GLuint COGLES2CallBridge::getActiveTexture() const
|
||||
{
|
||||
for (u32 i = 0; i < MATERIAL_MAX_TEXTURES; ++i)
|
||||
{
|
||||
if (Texture[i] == texture)
|
||||
{
|
||||
setActiveTexture(GL_TEXTURE0 + i);
|
||||
glBindTexture(GL_TEXTURE_2D, 0);
|
||||
return ActiveTextureID;
|
||||
}
|
||||
|
||||
Texture[i] = 0;
|
||||
TextureType[i] = GL_TEXTURE_2D;
|
||||
}
|
||||
void COGLES2CallBridge::setActiveTexture(GLuint id)
|
||||
{
|
||||
if (ActiveTextureID != id && id < MATERIAL_MAX_TEXTURES)
|
||||
{
|
||||
glActiveTexture(GL_TEXTURE0 + id);
|
||||
|
||||
ActiveTextureID = id;
|
||||
}
|
||||
}
|
||||
|
||||
void COGLES2CallBridge::setActiveTexture(GLenum texture)
|
||||
void COGLES2CallBridge::getTexture(GLenum& type, GLuint& name) const
|
||||
{
|
||||
if (ActiveTexture != texture)
|
||||
if (Texture[ActiveTextureID])
|
||||
{
|
||||
glActiveTexture(texture);
|
||||
ActiveTexture = texture;
|
||||
type = Texture[ActiveTextureID]->getOpenGLTextureType();
|
||||
name = Texture[ActiveTextureID]->getOpenGLTextureName();
|
||||
}
|
||||
else
|
||||
{
|
||||
type = GL_TEXTURE_2D;
|
||||
name = 0;
|
||||
}
|
||||
}
|
||||
|
||||
void COGLES2CallBridge::getTexture(u32 stage, GLenum& type)
|
||||
COGLES2Texture* COGLES2CallBridge::getTexture() const
|
||||
{
|
||||
if (stage < MATERIAL_MAX_TEXTURES)
|
||||
type = TextureType[stage];
|
||||
return Texture[ActiveTextureID];
|
||||
}
|
||||
|
||||
void COGLES2CallBridge::setTexture(u32 stage, GLenum type)
|
||||
void COGLES2CallBridge::setTexture(COGLES2Texture* texture)
|
||||
{
|
||||
if (stage < MATERIAL_MAX_TEXTURES)
|
||||
if (Texture[ActiveTextureID] != texture)
|
||||
{
|
||||
setActiveTexture(GL_TEXTURE0 + stage);
|
||||
|
||||
if (Texture[stage] != Driver->CurrentTexture[stage])
|
||||
if (texture)
|
||||
{
|
||||
if (Driver->CurrentTexture[stage])
|
||||
{
|
||||
glBindTexture(type, static_cast<const COGLES2Texture*>(Driver->CurrentTexture[stage])->getOpenGLTextureName());
|
||||
texture->grab();
|
||||
|
||||
TextureType[stage] = type;
|
||||
}
|
||||
else
|
||||
{
|
||||
glBindTexture(TextureType[stage], 0);
|
||||
}
|
||||
|
||||
Texture[stage] = Driver->CurrentTexture[stage];
|
||||
glBindTexture(texture->getOpenGLTextureType(), texture->getOpenGLTextureName());
|
||||
}
|
||||
else
|
||||
{
|
||||
glBindTexture(Texture[ActiveTextureID]->getOpenGLTextureType(), 0);
|
||||
}
|
||||
|
||||
if (Texture[ActiveTextureID])
|
||||
Texture[ActiveTextureID]->drop();
|
||||
|
||||
Texture[ActiveTextureID] = texture;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -244,15 +244,6 @@ namespace video
|
|||
//! Int interface for the above.
|
||||
virtual bool setPixelShaderConstant(s32 index, const s32* ints, int count);
|
||||
|
||||
//! sets the current Texture
|
||||
bool setActiveTexture(u32 stage, const video::ITexture* texture);
|
||||
|
||||
//! check if active texture is not equal null.
|
||||
bool isActiveTexture(u32 stage);
|
||||
|
||||
//! disables all textures beginning with fromStage.
|
||||
bool disableTextures(u32 fromStage = 0);
|
||||
|
||||
//! Adds a new material renderer to the VideoDriver
|
||||
virtual s32 addShaderMaterial(const c8* vertexShaderProgram, const c8* pixelShaderProgram,
|
||||
IShaderConstantSetCallBack* callback, E_MATERIAL_TYPE baseMaterial, s32 userData);
|
||||
|
@ -355,75 +346,6 @@ namespace video
|
|||
COGLES2CallBridge* getBridgeCalls() const;
|
||||
|
||||
private:
|
||||
|
||||
class STextureStageCache
|
||||
{
|
||||
public:
|
||||
STextureStageCache()
|
||||
{
|
||||
for (u32 i = 0; i < MATERIAL_MAX_TEXTURES; ++i)
|
||||
CurrentTexture[i] = 0;
|
||||
}
|
||||
|
||||
~STextureStageCache()
|
||||
{
|
||||
clear();
|
||||
}
|
||||
|
||||
void set(u32 stage, const ITexture* tex)
|
||||
{
|
||||
if (stage < MATERIAL_MAX_TEXTURES)
|
||||
{
|
||||
const ITexture* oldTexture = CurrentTexture[stage];
|
||||
|
||||
if (tex)
|
||||
tex->grab();
|
||||
|
||||
CurrentTexture[stage] = tex;
|
||||
|
||||
if (oldTexture)
|
||||
oldTexture->drop();
|
||||
}
|
||||
}
|
||||
|
||||
const ITexture* operator[](int stage) const
|
||||
{
|
||||
if ((u32)stage < MATERIAL_MAX_TEXTURES)
|
||||
return CurrentTexture[stage];
|
||||
else
|
||||
return 0;
|
||||
}
|
||||
|
||||
void remove(ITexture* tex)
|
||||
{
|
||||
for (s32 i = MATERIAL_MAX_TEXTURES-1; i>= 0; --i)
|
||||
{
|
||||
if (CurrentTexture[i] == tex)
|
||||
{
|
||||
tex->drop();
|
||||
CurrentTexture[i] = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void clear()
|
||||
{
|
||||
for (u32 i = 0; i < MATERIAL_MAX_TEXTURES; ++i)
|
||||
{
|
||||
if (CurrentTexture[i])
|
||||
{
|
||||
CurrentTexture[i]->drop();
|
||||
CurrentTexture[i] = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
const ITexture* CurrentTexture[MATERIAL_MAX_TEXTURES];
|
||||
};
|
||||
|
||||
void uploadClipPlane(u32 index);
|
||||
|
||||
//! inits the opengl-es driver
|
||||
bool genericDriverInit(const core::dimension2d<u32>& screenSize, bool stencilBuffer);
|
||||
|
||||
|
@ -434,11 +356,6 @@ namespace video
|
|||
virtual ITexture* createDeviceDependentTextureCube(const io::path& name, IImage* posXImage, IImage* negXImage,
|
||||
IImage* posYImage, IImage* negYImage, IImage* posZImage, IImage* negZImage);
|
||||
|
||||
//! creates a transposed matrix in supplied GLfloat array to pass to OGLES1
|
||||
inline void createGLMatrix(float gl_matrix[16], const core::matrix4& m);
|
||||
|
||||
inline void createGLTextureMatrix(float gl_matrix[16], const core::matrix4& m);
|
||||
|
||||
//! Map Irrlicht wrap mode to OpenGL enum
|
||||
GLint getTextureWrapMode(u8 clamp) const;
|
||||
|
||||
|
@ -448,6 +365,8 @@ namespace video
|
|||
//! sets the needed renderstates
|
||||
void setRenderStates2DMode(bool alpha, bool texture, bool alphaChannel);
|
||||
|
||||
void chooseMaterial2D();
|
||||
|
||||
void createMaterialRenderers();
|
||||
|
||||
void loadShaderData(const io::path& vertexShaderName, const io::path& fragmentShaderName, c8** vertexShaderData, c8** fragmentShaderData);
|
||||
|
@ -472,7 +391,6 @@ namespace video
|
|||
|
||||
SMaterial Material, LastMaterial;
|
||||
COGLES2Texture* RenderTargetTexture;
|
||||
STextureStageCache CurrentTexture;
|
||||
core::array<ITexture*> DepthTextures;
|
||||
|
||||
struct SUserClipPlane
|
||||
|
@ -527,6 +445,10 @@ namespace video
|
|||
public:
|
||||
COGLES2CallBridge(COGLES2Driver* driver);
|
||||
|
||||
// Reset to default state.
|
||||
|
||||
void reset();
|
||||
|
||||
// Blending calls.
|
||||
|
||||
void setBlendEquation(GLenum mode);
|
||||
|
@ -561,13 +483,15 @@ namespace video
|
|||
|
||||
// Texture calls.
|
||||
|
||||
void resetTexture(const ITexture* texture);
|
||||
GLuint getActiveTexture() const;
|
||||
|
||||
void setActiveTexture(GLenum texture);
|
||||
void setActiveTexture(GLuint id);
|
||||
|
||||
void getTexture(u32 stage, GLenum& type);
|
||||
void getTexture(GLenum& type, GLuint& name) const;
|
||||
|
||||
void setTexture(u32 stage, GLenum type);
|
||||
COGLES2Texture* getTexture() const;
|
||||
|
||||
void setTexture(COGLES2Texture* texture);
|
||||
|
||||
// Viewport calls.
|
||||
|
||||
|
@ -596,10 +520,8 @@ namespace video
|
|||
|
||||
GLuint Program;
|
||||
|
||||
GLenum ActiveTexture;
|
||||
|
||||
const ITexture* Texture[MATERIAL_MAX_TEXTURES];
|
||||
GLenum TextureType[MATERIAL_MAX_TEXTURES];
|
||||
GLuint ActiveTextureID;
|
||||
COGLES2Texture* Texture[MATERIAL_MAX_TEXTURES];
|
||||
|
||||
core::rect<s32> Viewport;
|
||||
};
|
||||
|
|
|
@ -17,7 +17,7 @@ namespace video
|
|||
{
|
||||
|
||||
COGLES2Renderer2D::COGLES2Renderer2D(const c8* vertexShaderProgram, const c8* pixelShaderProgram, COGLES2Driver* driver) :
|
||||
COGLES2MaterialRenderer(driver, 0, EMT_SOLID), Texture(0)
|
||||
COGLES2MaterialRenderer(driver, 0, EMT_SOLID)
|
||||
{
|
||||
#ifdef _DEBUG
|
||||
setDebugName("COGLES2Renderer2D");
|
||||
|
@ -52,25 +52,19 @@ void COGLES2Renderer2D::OnSetMaterial(const video::SMaterial& material,
|
|||
{
|
||||
Driver->getBridgeCalls()->setProgram(Program);
|
||||
Driver->setBasicRenderStates(material, lastMaterial, resetAllRenderstates);
|
||||
|
||||
f32 Thickness = (material.Thickness > 0.f) ? material.Thickness : 1.f;
|
||||
setPixelShaderConstant(ThicknessID, &Thickness, 1);
|
||||
|
||||
s32 TextureUsage = material.TextureLayer[0].Texture ? 1 : 0;
|
||||
setPixelShaderConstant(TextureUsageID, &TextureUsage, 1);
|
||||
}
|
||||
|
||||
bool COGLES2Renderer2D::OnRender(IMaterialRendererServices* service, E_VERTEX_TYPE vtxtype)
|
||||
{
|
||||
Driver->setTextureRenderStates(Driver->getCurrentMaterial(), false);
|
||||
|
||||
s32 TextureUsage = Texture ? 1 : 0;
|
||||
setPixelShaderConstant(TextureUsageID, &TextureUsage, 1);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void COGLES2Renderer2D::setTexture(const ITexture* texture)
|
||||
{
|
||||
Texture = texture;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -27,13 +27,9 @@ public:
|
|||
|
||||
virtual bool OnRender(IMaterialRendererServices* service, E_VERTEX_TYPE vtxtype);
|
||||
|
||||
void setTexture(const ITexture* texture);
|
||||
|
||||
protected:
|
||||
s32 ThicknessID;
|
||||
s32 TextureUsageID;
|
||||
|
||||
const ITexture* Texture;
|
||||
};
|
||||
|
||||
|
||||
|
|
|
@ -185,8 +185,6 @@ COGLES2Texture::~COGLES2Texture()
|
|||
|
||||
if (LockImage)
|
||||
LockImage->drop();
|
||||
|
||||
Driver->getBridgeCalls()->resetTexture(this);
|
||||
}
|
||||
|
||||
|
||||
|
@ -455,8 +453,13 @@ void COGLES2Texture::uploadTexture(bool newTexture, u32 imageNumber, bool regMip
|
|||
if (!newTexture)
|
||||
InternalFormat = oldInternalFormat;
|
||||
|
||||
Driver->setActiveTexture(0, this);
|
||||
Driver->getBridgeCalls()->setTexture(0, TextureType);
|
||||
GLenum origTextureType = GL_TEXTURE_2D;
|
||||
GLuint origTextureName = 0;
|
||||
|
||||
Driver->getBridgeCalls()->setActiveTexture(0);
|
||||
Driver->getBridgeCalls()->getTexture(origTextureType, origTextureName);
|
||||
|
||||
glBindTexture(TextureType, TextureName);
|
||||
|
||||
if (Driver->testGLError())
|
||||
os::Printer::log("Could not bind Texture", ELL_ERROR);
|
||||
|
@ -605,8 +608,7 @@ void COGLES2Texture::uploadTexture(bool newTexture, u32 imageNumber, bool regMip
|
|||
if (Driver->testGLError())
|
||||
os::Printer::log("Could not glTexImage2D", ELL_ERROR);
|
||||
|
||||
Driver->setActiveTexture(0, 0);
|
||||
Driver->getBridgeCalls()->setTexture(0, TextureType);
|
||||
glBindTexture(origTextureType, origTextureName);
|
||||
}
|
||||
|
||||
|
||||
|
@ -656,10 +658,11 @@ void* COGLES2Texture::lock(E_TEXTURE_LOCK_MODE mode, u32 mipmapLevel)
|
|||
|
||||
const core::dimension2d<u32> screenSize = Driver->getScreenSize();
|
||||
|
||||
const COGLES2Texture* origTexture = static_cast<const COGLES2Texture*>(Driver->CurrentTexture[0]);
|
||||
GLuint origTextureType = GL_TEXTURE_2D;
|
||||
GLint origTextureName = (origTexture) ? origTexture->getOpenGLTextureName() : 0;
|
||||
Driver->getBridgeCalls()->getTexture(0, origTextureType);
|
||||
GLenum origTextureType = GL_TEXTURE_2D;
|
||||
GLuint origTextureName = 0;
|
||||
|
||||
Driver->getBridgeCalls()->setActiveTexture(0);
|
||||
Driver->getBridgeCalls()->getTexture(origTextureType, origTextureName);
|
||||
|
||||
COGLES2Texture* origRT = static_cast<COGLES2Texture*>(Driver->getRenderTargetTexture());
|
||||
core::rect<s32> origViewport = Driver->getBridgeCalls()->getViewport();
|
||||
|
@ -811,13 +814,16 @@ void COGLES2Texture::regenerateMipMapLevels(void* mipmapData)
|
|||
// hardware moethods for generate mipmaps.
|
||||
if (!mipmapData && AutomaticMipmapUpdate)
|
||||
{
|
||||
const COGLES2Texture* tmpTexture = static_cast<const COGLES2Texture*>(Driver->CurrentTexture[0]);
|
||||
GLuint tmpTextureType = GL_TEXTURE_2D;
|
||||
GLint tmpTextureName = (tmpTexture) ? tmpTexture->getOpenGLTextureName() : 0;
|
||||
Driver->getBridgeCalls()->getTexture(0, tmpTextureType);
|
||||
GLenum origTextureType = GL_TEXTURE_2D;
|
||||
GLuint origTextureName = 0;
|
||||
|
||||
Driver->getBridgeCalls()->setActiveTexture(0);
|
||||
Driver->getBridgeCalls()->getTexture(origTextureType, origTextureName);
|
||||
|
||||
glBindTexture(TextureType, TextureName);
|
||||
glGenerateMipmap(TextureType);
|
||||
glBindTexture(tmpTextureType, tmpTextureName);
|
||||
|
||||
glBindTexture(origTextureType, origTextureName);
|
||||
|
||||
return;
|
||||
}
|
||||
|
@ -826,10 +832,12 @@ void COGLES2Texture::regenerateMipMapLevels(void* mipmapData)
|
|||
if (Type != ETT_2D)
|
||||
return;
|
||||
|
||||
const COGLES2Texture* tmpTexture = static_cast<const COGLES2Texture*>(Driver->CurrentTexture[0]);
|
||||
GLuint tmpTextureType = GL_TEXTURE_2D;
|
||||
GLint tmpTextureName = (tmpTexture) ? tmpTexture->getOpenGLTextureName() : 0;
|
||||
Driver->getBridgeCalls()->getTexture(0, tmpTextureType);
|
||||
GLenum origTextureType = GL_TEXTURE_2D;
|
||||
GLuint origTextureName = 0;
|
||||
|
||||
Driver->getBridgeCalls()->setActiveTexture(0);
|
||||
Driver->getBridgeCalls()->getTexture(origTextureType, origTextureName);
|
||||
|
||||
glBindTexture(TextureType, TextureName);
|
||||
|
||||
// Manually create mipmaps or use prepared version
|
||||
|
@ -881,7 +889,7 @@ void COGLES2Texture::regenerateMipMapLevels(void* mipmapData)
|
|||
if (!mipmapData)
|
||||
delete [] target;
|
||||
|
||||
glBindTexture(tmpTextureType, tmpTextureName);
|
||||
glBindTexture(origTextureType, origTextureName);
|
||||
}
|
||||
|
||||
|
||||
|
@ -977,8 +985,13 @@ COGLES2FBOTexture::COGLES2FBOTexture(const core::dimension2d<u32>& size,
|
|||
// generate color texture
|
||||
glGenTextures(1, &TextureName);
|
||||
|
||||
Driver->setActiveTexture(0, this);
|
||||
Driver->getBridgeCalls()->setTexture(0, TextureType);
|
||||
GLenum origTextureType = GL_TEXTURE_2D;
|
||||
GLuint origTextureName = 0;
|
||||
|
||||
Driver->getBridgeCalls()->setActiveTexture(0);
|
||||
Driver->getBridgeCalls()->getTexture(origTextureType, origTextureName);
|
||||
|
||||
glBindTexture(TextureType, TextureName);
|
||||
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
|
||||
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
|
||||
|
@ -1000,8 +1013,7 @@ COGLES2FBOTexture::COGLES2FBOTexture(const core::dimension2d<u32>& size,
|
|||
checkOGLES2FBOStatus(Driver);
|
||||
#endif
|
||||
|
||||
Driver->setActiveTexture(0, 0);
|
||||
Driver->getBridgeCalls()->setTexture(0, TextureType);
|
||||
glBindTexture(origTextureType, origTextureName);
|
||||
|
||||
unbindRTT();
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue