Merge revision 5277:5282 from trunk to ogl-es.

git-svn-id: svn://svn.code.sf.net/p/irrlicht/code/branches/ogl-es@5288 dfc29bdd-3216-0410-991c-e03cc46cb475
master
cutealien 2016-03-18 17:24:46 +00:00
parent 5c1deb8550
commit 0fc5d21a40
13 changed files with 221 additions and 234 deletions

View File

@ -141,6 +141,8 @@ Changes in 1.9 (not yet released)
--------------------------
Changes in 1.8.4
- Update libpng to 1.6.21
- Update zlib to 1.2.8
- Fix some compile warnings in aes which got handled as errors by some c++11 compilers.
- Get rid of some misleading-indentation warnings in gcc6
- Fix serialization of the InputReceiverEnabled flag in CCameraSceneNode

View File

@ -139,12 +139,11 @@ public:
only mode or read from in write only mode.
Support for this feature depends on the driver, so don't rely on the
texture being write-protected when locking with read-only, etc.
\param mipmapLevel Number of the mipmapLevel to lock. 0 is main texture.
Non-existing levels will silently fail and return 0.
\param layer It determines which cubemap face or texture array layer should be locked.
\return Returns a pointer to the pixel data. The format of the pixel can
be determined by using getColorFormat(). 0 is returned, if
the texture cannot be locked. */
virtual void* lock(E_TEXTURE_LOCK_MODE mode=ETLM_READ_WRITE, u32 mipmapLevel=0) = 0;
virtual void* lock(E_TEXTURE_LOCK_MODE mode = ETLM_READ_WRITE, u32 layer = 0) = 0;
//! Unlock function. Must be called after a lock() to the texture.
/** One should avoid to call unlock more than once before another lock.

View File

@ -651,7 +651,7 @@ bool CD3D9Driver::queryFeature(E_VIDEO_DRIVER_FEATURE feature) const
case EVDF_TEXTURE_COMPRESSED_DXT:
return true;
case EVDF_TEXTURE_CUBEMAP:
return false;
return true;
default:
return false;
};

View File

@ -16,8 +16,8 @@ namespace video
{
CD3D9Texture::CD3D9Texture(const io::path& name, const core::array<IImage*>& image, E_TEXTURE_TYPE type, CD3D9Driver* driver)
: ITexture(name, type), Driver(driver), InternalFormat(D3DFMT_UNKNOWN), LockData(0), LockLevel(0), AutoGenerateMipMaps(false),
Device(0), Texture(0), CubeTexture(0), RTTSurface(0)
: ITexture(name, type), Driver(driver), InternalFormat(D3DFMT_UNKNOWN), LockReadOnly(false), LockData(0), LockLayer(0),
AutoGenerateMipMaps(false), Device(0), Texture(0), CubeTexture(0), RTTSurface(0)
{
#ifdef _DEBUG
setDebugName("CD3D9Texture");
@ -115,8 +115,8 @@ CD3D9Texture::CD3D9Texture(const io::path& name, const core::array<IImage*>& ima
}
CD3D9Texture::CD3D9Texture(CD3D9Driver* driver, const core::dimension2d<u32>& size, const io::path& name, const ECOLOR_FORMAT format)
: ITexture(name, ETT_2D), Driver(driver), InternalFormat(D3DFMT_UNKNOWN), LockData(0), LockLevel(0), AutoGenerateMipMaps(false),
Device(0), Texture(0), CubeTexture(0), RTTSurface(0)
: ITexture(name, ETT_2D), Driver(driver), InternalFormat(D3DFMT_UNKNOWN), LockReadOnly(false), LockData(0), LockLayer(0),
AutoGenerateMipMaps(false), Device(0), Texture(0), CubeTexture(0), RTTSurface(0)
{
#ifdef _DEBUG
setDebugName("CD3D9Texture");
@ -164,16 +164,16 @@ CD3D9Texture::~CD3D9Texture()
Device->Release();
}
void* CD3D9Texture::lock(E_TEXTURE_LOCK_MODE mode, u32 mipmapLevel)
void* CD3D9Texture::lock(E_TEXTURE_LOCK_MODE mode, u32 layer)
{
if (LockData)
return LockData;
if (IImage::isCompressedFormat(ColorFormat) || mipmapLevel > 0) // TO-DO
if (IImage::isCompressedFormat(ColorFormat))
return 0;
bool lockReadOnly = (mode == ETLM_READ_ONLY);
LockLevel = mipmapLevel;
LockReadOnly = (mode == ETLM_READ_ONLY);
LockLayer = layer;
HRESULT hr;
D3DLOCKED_RECT rect;
@ -182,12 +182,13 @@ void* CD3D9Texture::lock(E_TEXTURE_LOCK_MODE mode, u32 mipmapLevel)
{
if (Texture)
{
hr = Texture->LockRect(mipmapLevel, &rect, 0, lockReadOnly ? D3DLOCK_READONLY : 0);
hr = Texture->LockRect(0, &rect, 0, LockReadOnly ? D3DLOCK_READONLY : 0);
}
else if (CubeTexture)
{
// TO-DO -> hardcoded D3DCUBEMAP_FACE_POSITIVE_X.
hr = CubeTexture->LockRect(D3DCUBEMAP_FACE_POSITIVE_X, mipmapLevel, &rect, 0, lockReadOnly ? D3DLOCK_READONLY : 0);
_IRR_DEBUG_BREAK_IF(layer > 5)
hr = CubeTexture->LockRect(static_cast<_D3DCUBEMAP_FACES>(layer), 0, &rect, 0, LockReadOnly ? D3DLOCK_READONLY : 0);
}
if (FAILED(hr))
@ -212,7 +213,7 @@ void* CD3D9Texture::lock(E_TEXTURE_LOCK_MODE mode, u32 mipmapLevel)
}
IDirect3DSurface9 *surface = 0;
hr = Texture->GetSurfaceLevel(mipmapLevel, &surface);
hr = Texture->GetSurfaceLevel(0, &surface);
if (FAILED(hr))
{
os::Printer::log("Could not lock DIRECT3D9 Texture", "Could not get surface.", ELL_ERROR);
@ -225,7 +226,7 @@ void* CD3D9Texture::lock(E_TEXTURE_LOCK_MODE mode, u32 mipmapLevel)
os::Printer::log("Could not lock DIRECT3D9 Texture", "Data copy failed.", ELL_ERROR);
return 0;
}
hr = RTTSurface->LockRect(&rect, 0, lockReadOnly ? D3DLOCK_READONLY : 0);
hr = RTTSurface->LockRect(&rect, 0, LockReadOnly ? D3DLOCK_READONLY : 0);
if(FAILED(hr))
{
os::Printer::log("Could not lock DIRECT3D9 Texture", "LockRect failed.", ELL_ERROR);
@ -247,12 +248,11 @@ void CD3D9Texture::unlock()
{
if (Texture)
{
Texture->UnlockRect(LockLevel);
Texture->UnlockRect(0);
}
else if (CubeTexture)
{
// TO-DO -> hardcoded D3DCUBEMAP_FACE_POSITIVE_X.
CubeTexture->UnlockRect(D3DCUBEMAP_FACE_POSITIVE_X, LockLevel);
CubeTexture->UnlockRect(static_cast<_D3DCUBEMAP_FACES>(LockLayer), 0);
}
}
else if (RTTSurface)
@ -260,11 +260,12 @@ void CD3D9Texture::unlock()
RTTSurface->UnlockRect();
}
if (LockLevel == 0)
regenerateMipMapLevels(0);
if (!LockReadOnly)
regenerateMipMapLevels(0, LockLayer);
LockReadOnly = false;
LockData = 0;
LockLevel = 0;
LockLayer = 0;
}
void CD3D9Texture::regenerateMipMapLevels(void* data, u32 layer)
@ -456,13 +457,6 @@ void CD3D9Texture::uploadTexture(u32 layer, u32 level, void* data)
u32 width = Size.Width >> level;
u32 height = Size.Height >> level;
const D3DCUBEMAP_FACES cubeTextureType[6] =
{
D3DCUBEMAP_FACE_POSITIVE_X, D3DCUBEMAP_FACE_NEGATIVE_X,
D3DCUBEMAP_FACE_POSITIVE_Y, D3DCUBEMAP_FACE_NEGATIVE_Y,
D3DCUBEMAP_FACE_POSITIVE_Z, D3DCUBEMAP_FACE_NEGATIVE_Z
};
u32 dataSize = IImage::getDataSizeFromFormat(ColorFormat, width, height);
HRESULT hr = 0;
@ -475,8 +469,9 @@ void CD3D9Texture::uploadTexture(u32 layer, u32 level, void* data)
}
else if (CubeTexture)
{
const D3DCUBEMAP_FACES tmpCubeTextureType = cubeTextureType[(layer < 6) ? layer : 0];
hr = CubeTexture->LockRect(tmpCubeTextureType, level, &lockRectangle, 0, 0);
_IRR_DEBUG_BREAK_IF(layer > 5)
hr = CubeTexture->LockRect(static_cast<_D3DCUBEMAP_FACES>(layer), level, &lockRectangle, 0, 0);
}
if (FAILED(hr))
@ -493,8 +488,7 @@ void CD3D9Texture::uploadTexture(u32 layer, u32 level, void* data)
}
else if (CubeTexture)
{
const D3DCUBEMAP_FACES tmpCubeTextureType = cubeTextureType[(layer < 6) ? layer : 0];
hr = CubeTexture->UnlockRect(tmpCubeTextureType, level);
hr = CubeTexture->UnlockRect(static_cast<_D3DCUBEMAP_FACES>(layer), level);
}
if (FAILED(hr))

View File

@ -32,7 +32,7 @@ public:
virtual ~CD3D9Texture();
virtual void* lock(E_TEXTURE_LOCK_MODE mode = ETLM_READ_WRITE, u32 mipmapLevel = 0) _IRR_OVERRIDE_;
virtual void* lock(E_TEXTURE_LOCK_MODE mode = ETLM_READ_WRITE, u32 layer = 0) _IRR_OVERRIDE_;
virtual void unlock() _IRR_OVERRIDE_;
@ -59,8 +59,9 @@ private:
D3DFORMAT InternalFormat;
bool LockReadOnly;
void* LockData;
u32 LockLevel;
u32 LockLayer;
bool AutoGenerateMipMaps;

View File

@ -771,7 +771,7 @@ namespace video
{
SDummyTexture(const io::path& name, E_TEXTURE_TYPE type) : ITexture(name, type) {};
virtual void* lock(E_TEXTURE_LOCK_MODE mode=ETLM_READ_WRITE, u32 mipmapLevel=0) _IRR_OVERRIDE_ { return 0; }
virtual void* lock(E_TEXTURE_LOCK_MODE mode = ETLM_READ_WRITE, u32 layer = 0) _IRR_OVERRIDE_ { return 0; }
virtual void unlock()_IRR_OVERRIDE_ {}
virtual void regenerateMipMapLevels(void* data = 0, u32 layer = 0) _IRR_OVERRIDE_ {}
};

View File

@ -46,7 +46,7 @@ public:
};
COpenGLCoreTexture(const io::path& name, const core::array<IImage*>& image, E_TEXTURE_TYPE type, TOpenGLDriver* driver) : ITexture(name, type), Driver(driver), TextureType(GL_TEXTURE_2D),
TextureName(0), InternalFormat(GL_RGBA), PixelFormat(GL_RGBA), PixelType(GL_UNSIGNED_BYTE), Converter(0), LockReadOnly(false), LockImage(0), LockLevel(0),
TextureName(0), InternalFormat(GL_RGBA), PixelFormat(GL_RGBA), PixelType(GL_UNSIGNED_BYTE), Converter(0), LockReadOnly(false), LockImage(0), LockLayer(0),
KeepImage(false), AutoGenerateMipMaps(false)
{
_IRR_DEBUG_BREAK_IF(image.size() == 0)
@ -134,7 +134,7 @@ public:
}
COpenGLCoreTexture(const io::path& name, const core::dimension2d<u32>& size, ECOLOR_FORMAT format, TOpenGLDriver* driver) : ITexture(name, ETT_2D), Driver(driver), TextureType(GL_TEXTURE_2D),
TextureName(0), InternalFormat(GL_RGBA), PixelFormat(GL_RGBA), PixelType(GL_UNSIGNED_BYTE), Converter(0), LockReadOnly(false), LockImage(0), LockLevel(0), KeepImage(false),
TextureName(0), InternalFormat(GL_RGBA), PixelFormat(GL_RGBA), PixelType(GL_UNSIGNED_BYTE), Converter(0), LockReadOnly(false), LockImage(0), LockLayer(0), KeepImage(false),
AutoGenerateMipMaps(false)
{
DriverType = Driver->getDriverType();
@ -192,7 +192,7 @@ public:
Image[i]->drop();
}
virtual void* lock(E_TEXTURE_LOCK_MODE mode = ETLM_READ_WRITE, u32 mipmapLevel = 0) _IRR_OVERRIDE_
virtual void* lock(E_TEXTURE_LOCK_MODE mode = ETLM_READ_WRITE, u32 layer = 0) _IRR_OVERRIDE_
{
if (LockImage)
return LockImage->getData();
@ -201,24 +201,34 @@ public:
return 0;
LockReadOnly |= (mode == ETLM_READ_ONLY);
LockLevel = mipmapLevel;
LockLayer = layer;
if (KeepImage && mipmapLevel == 0)
if (KeepImage)
{
LockImage = Image[0];
_IRR_DEBUG_BREAK_IF(LockLayer > Image.size())
LockImage = Image[LockLayer];
LockImage->grab();
}
else
{
const core::dimension2d<u32> lockImageSize(Size.Width >> mipmapLevel, Size.Height >> mipmapLevel);
LockImage = Driver->createImage(ColorFormat, lockImageSize);
LockImage = Driver->createImage(ColorFormat, Size);
if (LockImage && mode != ETLM_WRITE_ONLY)
{
IImage* tmpImage = Driver->createImage(ECF_A8R8G8B8, lockImageSize);
IImage* tmpImage = Driver->createImage(ECF_A8R8G8B8, Size);
#if 0 // This method doesn't work properly in some cases
glGetTexImage(GL_TEXTURE_2D, mipmapLevel, GL_RGBA, GL_UNSIGNED_BYTE, tmpImage->getData());
GLenum tmpTextureType = TextureType;
if (tmpTextureType == GL_TEXTURE_CUBE_MAP)
{
_IRR_DEBUG_BREAK_IF(layer > 5)
tmpTextureType = GL_TEXTURE_CUBE_MAP_POSITIVE_X + layer;
}
glGetTexImage(tmpTextureType, 0, GL_RGBA, GL_UNSIGNED_BYTE, tmpImage->getData());
if (IsRenderTarget)
{
@ -241,7 +251,7 @@ public:
delete[] tmpBuffer;
}
#else
COpenGLCoreTexture* tmpTexture = new COpenGLCoreTexture("OGL_CORE_LOCK_TEXTURE", lockImageSize, ColorFormat, Driver);
COpenGLCoreTexture* tmpTexture = new COpenGLCoreTexture("OGL_CORE_LOCK_TEXTURE", Size, ColorFormat, Driver);
GLuint tmpFBO = 0;
Driver->irrGlGenFramebuffers(1, &tmpFBO);
@ -251,7 +261,7 @@ public:
GLsizei prevViewportWidth = 0;
GLsizei prevViewportHeight = 0;
Driver->getCacheHandler()->getViewport(prevViewportX, prevViewportY, prevViewportWidth, prevViewportHeight);
Driver->getCacheHandler()->setViewport(0, 0, lockImageSize.Width, lockImageSize.Height);
Driver->getCacheHandler()->setViewport(0, 0, Size.Width, Size.Height);
GLuint prevFBO = 0;
Driver->getCacheHandler()->getFBO(prevFBO);
@ -259,9 +269,11 @@ public:
Driver->irrGlFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, tmpTexture->getOpenGLTextureName(), 0);
Driver->draw2DImage(this, true);
glClear(GL_COLOR_BUFFER_BIT);
glReadPixels(0, 0, lockImageSize.Width, lockImageSize.Height, GL_RGBA, GL_UNSIGNED_BYTE, tmpImage->getData());
Driver->draw2DImage(this, layer, true);
glReadPixels(0, 0, Size.Width, Size.Height, GL_RGBA, GL_UNSIGNED_BYTE, tmpImage->getData());
Driver->getCacheHandler()->setFBO(prevFBO);
Driver->getCacheHandler()->setViewport(prevViewportX, prevViewportY, prevViewportWidth, prevViewportHeight);
@ -316,19 +328,18 @@ public:
const COpenGLCoreTexture* prevTexture = Driver->getCacheHandler()->getTextureCache().get(0);
Driver->getCacheHandler()->getTextureCache().set(0, this);
uploadTexture(false, 0, LockLevel, LockImage->getData());
uploadTexture(false, LockLayer, 0, LockImage->getData());
Driver->getCacheHandler()->getTextureCache().set(0, prevTexture);
if (LockLevel == 0)
regenerateMipMapLevels(0);
regenerateMipMapLevels(0, LockLayer);
}
LockImage->drop();
LockReadOnly = false;
LockImage = 0;
LockLevel = 0;
LockLayer = 0;
}
virtual void regenerateMipMapLevels(void* data = 0, u32 layer = 0) _IRR_OVERRIDE_
@ -484,14 +495,14 @@ protected:
u32 width = Size.Width >> level;
u32 height = Size.Height >> level;
const GLenum cubeTextureType[6] =
{
GL_TEXTURE_CUBE_MAP_POSITIVE_X, GL_TEXTURE_CUBE_MAP_NEGATIVE_X,
GL_TEXTURE_CUBE_MAP_POSITIVE_Y, GL_TEXTURE_CUBE_MAP_NEGATIVE_Y,
GL_TEXTURE_CUBE_MAP_POSITIVE_Z, GL_TEXTURE_CUBE_MAP_NEGATIVE_Z
};
GLenum tmpTextureType = TextureType;
GLenum tmpTextureType = (TextureType == GL_TEXTURE_CUBE_MAP) ? cubeTextureType[(layer < 6) ? layer : 0] : TextureType;
if (tmpTextureType == GL_TEXTURE_CUBE_MAP)
{
_IRR_DEBUG_BREAK_IF(layer > 5)
tmpTextureType = GL_TEXTURE_CUBE_MAP_POSITIVE_X + layer;
}
if (!IImage::isCompressedFormat(ColorFormat))
{
@ -555,7 +566,7 @@ protected:
bool LockReadOnly;
IImage* LockImage;
u32 LockLevel;
u32 LockLayer;
bool KeepImage;
core::array<IImage*> Image;

View File

@ -1511,7 +1511,7 @@ void COpenGLDriver::draw2DImage(const video::ITexture* texture, const core::rect
}
void COpenGLDriver::draw2DImage(const video::ITexture* texture, bool flip)
void COpenGLDriver::draw2DImage(const video::ITexture* texture, u32 layer, bool flip)
{
if (!texture || !CacheHandler->getTextureCache().set(0, texture))
return;
@ -1527,22 +1527,92 @@ void COpenGLDriver::draw2DImage(const video::ITexture* texture, bool flip)
Transformation3DChanged = true;
Quad2DVertices[0].Pos = core::vector3df(-1.f, 1.f, 0.f);
Quad2DVertices[1].Pos = core::vector3df(1.f, 1.f, 0.f);
Quad2DVertices[2].Pos = core::vector3df(1.f, -1.f, 0.f);
Quad2DVertices[3].Pos = core::vector3df(-1.f, -1.f, 0.f);
f32 modificator = (flip) ? 1.f : 0.f;
Quad2DVertices[0].TCoords = core::vector2df(0.f, 0.f + modificator);
Quad2DVertices[1].TCoords = core::vector2df(1.f, 0.f + modificator);
Quad2DVertices[2].TCoords = core::vector2df(1.f, 1.f - modificator);
Quad2DVertices[3].TCoords = core::vector2df(0.f, 1.f - modificator);
CacheHandler->setClientState(true, false, false, true);
glTexCoordPointer(2, GL_FLOAT, sizeof(S3DVertex), &(static_cast<const S3DVertex*>(Quad2DVertices))[0].TCoords);
glVertexPointer(2, GL_FLOAT, sizeof(S3DVertex), &(static_cast<const S3DVertex*>(Quad2DVertices))[0].Pos);
const core::vector3df positionData[4] = {
core::vector3df(-1.f, 1.f, 0.f),
core::vector3df(1.f, 1.f, 0.f),
core::vector3df(1.f, -1.f, 0.f),
core::vector3df(-1.f, -1.f, 0.f)
};
glVertexPointer(2, GL_FLOAT, sizeof(core::vector3df), positionData);
if (texture && texture->getType() == ETT_CUBEMAP)
{
const core::vector3df texcoordCubeData[6][4] = {
// GL_TEXTURE_CUBE_MAP_POSITIVE_X
{
core::vector3df(1.f, 1.f, 1.f),
core::vector3df(1.f, 1.f, -1.f),
core::vector3df(1.f, -1.f, -1.f),
core::vector3df(1.f, -1.f, 1.f)
},
// GL_TEXTURE_CUBE_MAP_NEGATIVE_X
{
core::vector3df(-1.f, 1.f, -1.f),
core::vector3df(-1.f, 1.f, 1.f),
core::vector3df(-1.f, -1.f, 1.f),
core::vector3df(-1.f, -1.f, -1.f)
},
// GL_TEXTURE_CUBE_MAP_POSITIVE_Y
{
core::vector3df(-1.f, 1.f, -1.f),
core::vector3df(1.f, 1.f, -1.f),
core::vector3df(1.f, 1.f, 1.f),
core::vector3df(-1.f, 1.f, 1.f)
},
// GL_TEXTURE_CUBE_MAP_NEGATIVE_Y
{
core::vector3df(-1.f, -1.f, 1.f),
core::vector3df(-1.f, -1.f, -1.f),
core::vector3df(1.f, -1.f, -1.f),
core::vector3df(1.f, -1.f, 1.f)
},
// GL_TEXTURE_CUBE_MAP_POSITIVE_Z
{
core::vector3df(-1.f, 1.f, 1.f),
core::vector3df(-1.f, -1.f, 1.f),
core::vector3df(1.f, -1.f, 1.f),
core::vector3df(1.f, 1.f, 1.f)
},
// GL_TEXTURE_CUBE_MAP_NEGATIVE_Z
{
core::vector3df(1.f, 1.f, -1.f),
core::vector3df(-1.f, 1.f, -1.f),
core::vector3df(-1.f, -1.f, -1.f),
core::vector3df(1.f, -1.f, -1.f)
}
};
const core::vector3df texcoordData[4] = {
texcoordCubeData[layer][(flip) ? 3 : 0],
texcoordCubeData[layer][(flip) ? 2 : 1],
texcoordCubeData[layer][(flip) ? 1 : 2],
texcoordCubeData[layer][(flip) ? 0 : 3]
};
glTexCoordPointer(3, GL_FLOAT, sizeof(core::vector3df), texcoordData);
}
else
{
f32 modificator = (flip) ? 1.f : 0.f;
core::vector2df texcoordData[4] = {
core::vector2df(0.f, 0.f + modificator),
core::vector2df(1.f, 0.f + modificator),
core::vector2df(1.f, 1.f - modificator),
core::vector2df(0.f, 1.f - modificator)
};
glTexCoordPointer(2, GL_FLOAT, sizeof(core::vector2df), texcoordData);
}
glDrawElements(GL_TRIANGLE_FAN, 4, GL_UNSIGNED_SHORT, Quad2DIndices);
}
@ -2871,6 +2941,8 @@ void COpenGLDriver::setRenderStates2DMode(bool alpha, bool texture, bool alphaCh
CacheHandler->setMatrixMode(GL_MODELVIEW);
glLoadIdentity();
glTranslatef(0.375f, 0.375f, 0.0f);
// Make sure we set first texture matrix
CacheHandler->setActiveTexture(GL_TEXTURE0);

View File

@ -145,7 +145,7 @@ namespace video
const core::rect<s32>& sourceRect, const core::rect<s32>* clipRect = 0,
const video::SColor* const colors = 0, bool useAlphaChannelOfTexture = false) _IRR_OVERRIDE_;
virtual void draw2DImage(const video::ITexture* texture, bool flip);
virtual void draw2DImage(const video::ITexture* texture, u32 layer, bool flip);
//! draws a set of 2d images, using a color and the alpha channel of the
//! texture if desired.

View File

@ -76,7 +76,7 @@ CSoftwareTexture::~CSoftwareTexture()
//! lock function
void* CSoftwareTexture::lock(E_TEXTURE_LOCK_MODE mode, u32 mipmapLevel)
void* CSoftwareTexture::lock(E_TEXTURE_LOCK_MODE mode, u32 layer)
{
return Image->getData();
}

View File

@ -30,7 +30,7 @@ public:
virtual ~CSoftwareTexture();
//! lock function
virtual void* lock(E_TEXTURE_LOCK_MODE mode=ETLM_READ_WRITE, u32 mipmapLevel=0) _IRR_OVERRIDE_;
virtual void* lock(E_TEXTURE_LOCK_MODE mode = ETLM_READ_WRITE, u32 layer = 0) _IRR_OVERRIDE_;
//! unlock function
virtual void unlock() _IRR_OVERRIDE_;

View File

@ -38,11 +38,11 @@ public:
virtual ~CSoftwareTexture2();
//! lock function
virtual void* lock(E_TEXTURE_LOCK_MODE mode=ETLM_READ_WRITE, u32 mipmapLevel=0) _IRR_OVERRIDE_
virtual void* lock(E_TEXTURE_LOCK_MODE mode = ETLM_READ_WRITE, u32 layer = 0) _IRR_OVERRIDE_
{
if (Flags & GEN_MIPMAP)
{
MipMapLOD = mipmapLevel;
MipMapLOD = 0;
Size = MipMap[MipMapLOD]->getDimension();
Pitch = MipMap[MipMapLOD]->getPitch();
}

View File

@ -8,6 +8,7 @@ using namespace core;
namespace
{
//! check miplevels by visual test
bool renderMipLevels(video::E_DRIVER_TYPE driverType)
{
@ -30,7 +31,7 @@ bool renderMipLevels(video::E_DRIVER_TYPE driverType)
logTestString("Testing driver %ls\n", driver->getName());
scene::ISceneNode* n = smgr->addCubeSceneNode();
scene::ISceneNode* n2 = smgr->addCubeSceneNode(10, 0, -1, core::vector3df(20,0,30), core::vector3df(0,45,0));
scene::ISceneNode* n2 = smgr->addCubeSceneNode(10, 0, -1, vector3df(20,0,30), vector3df(0,45,0));
// we use a main texture with blue on top and red below
// and mipmap with pink on top and cyan below
@ -40,7 +41,7 @@ bool renderMipLevels(video::E_DRIVER_TYPE driverType)
u32 texData[16*16];
for (u32 i=0; i<16*16; ++i)
texData[i]=(i<8*16?0xff0000ff:0xffff0000);
video::IImage* image = driver->createImageFromData(video::ECF_A8R8G8B8, core::dimension2du(16,16), texData, false);
video::IImage* image = driver->createImageFromData(video::ECF_A8R8G8B8, dimension2du(16,16), texData, false);
u32 mipdata[8*16];
u32 index=0;
for (u32 j=8; j>0; j/=2)
@ -68,7 +69,7 @@ bool renderMipLevels(video::E_DRIVER_TYPE driverType)
image->drop();
}
(void)smgr->addCameraSceneNode(0, core::vector3df(10,0,-30));
(void)smgr->addCameraSceneNode(0, vector3df(10,0,-30));
driver->beginScene(video::ECBF_COLOR | video::ECBF_DEPTH, video::SColor(255,100,101,140));
smgr->drawAll();
@ -88,9 +89,8 @@ bool renderMipLevels(video::E_DRIVER_TYPE driverType)
return result;
}
//! Tests locking miplevels
bool lockAllMipLevels(video::E_DRIVER_TYPE driverType)
//! Tests locking
bool lockTexture(video::E_DRIVER_TYPE driverType)
{
IrrlichtDevice *device = createDevice( driverType, dimension2d<u32>(160, 120), 32);
if (!device)
@ -107,188 +107,97 @@ bool lockAllMipLevels(video::E_DRIVER_TYPE driverType)
return true;
}
bool testCubemap = driver->queryFeature(video::EVDF_TEXTURE_CUBEMAP);
stabilizeScreenBackground(driver);
logTestString("Testing driver %ls\n", driver->getName());
scene::ISceneNode* n = smgr->addCubeSceneNode();
scene::ISceneNode* n2 = smgr->addCubeSceneNode(10, 0, -1, vector3df(20, 0, 30), vector3df(0, 45, 0));
if (n)
if (n && n2)
{
// create the texture and miplevels with distinct colors
u32 texData[16*16];
for (u32 i=0; i<16*16; ++i)
texData[i]=0xff0000ff-i;
video::IImage* image = driver->createImageFromData(video::ECF_A8R8G8B8, core::dimension2du(16,16), texData, false);
u32 mipdata[8*16];
u32 index=0;
for (u32 j=8; j>0; j/=2)
// texture 2d
video::IImage* image = driver->createImageFromData(video::ECF_A8R8G8B8, dimension2du(16,16), texData, false);
video::ITexture* tex = driver->addTexture("tex2d", image);
if (!tex)
return false;
else
n->setMaterialTexture(0, tex);
// cubemap
if (testCubemap)
{
u32 val=(j==8?0x00ff00ff:(j==4?0x0000ffff:(j==2?0xc2c200ff:0x001212ff)));
for (u32 i=0; i<j; ++i)
{
for (u32 k=0; k<j; ++k)
mipdata[index++]=val-i;
}
video::ITexture* texCube = driver->addTextureCubemap("texcube", image, image, image, image, image, image);
if (!texCube)
testCubemap = false;
else
n2->setMaterialTexture(0, texCube);
}
image->setMipMapsData(mipdata, false, true);
video::ITexture* tex = driver->addTexture("miptest", image);
if (!tex)
// is probably an error in the mipdata handling
return false;
else
n->setMaterialTexture(0, tex);
image->drop();
}
(void)smgr->addCameraSceneNode();
smgr->addCameraSceneNode(0, vector3df(10, 0, -30));
driver->beginScene(video::ECBF_COLOR | video::ECBF_DEPTH, video::SColor(255,100,101,140));
smgr->drawAll();
driver->endScene();
video::ITexture* tex = driver->findTexture("miptest");
video::SColor* bits = (video::SColor*)tex->lock(video::ETLM_READ_ONLY, 0);
bool result = (bits[0].color==0xff0000ff);
tex->unlock();
bits = (video::SColor*)tex->lock(video::ETLM_READ_ONLY, 1);
result &= (bits[0].color==0x00ff00ff);
tex->unlock();
bits = (video::SColor*)tex->lock(video::ETLM_READ_ONLY, 2);
result &= (bits[0].color==0x0000ffff);
tex->unlock();
bits = (video::SColor*)tex->lock(video::ETLM_READ_ONLY, 3);
result &= (bits[0].color==0xc2c200ff);
tex->unlock();
bits = (video::SColor*)tex->lock(video::ETLM_READ_ONLY, 4);
result &= (bits[0].color==0x001212ff);
tex->unlock();
video::ITexture* tex = driver->findTexture("tex2d");
if (!result)
logTestString("mipmap lock after init with driver %ls failed.\n", driver->getName());
// test with updating a lower level, and reading upper and lower
bits = (video::SColor*)tex->lock(video::ETLM_READ_WRITE, 3);
video::SColor* bits = (video::SColor*)tex->lock(video::ETLM_READ_WRITE);
bits[0]=0xff00ff00;
bits[1]=0xff00ff00;
tex->unlock();
bits = (video::SColor*)tex->lock(video::ETLM_READ_WRITE, 4);
result &= (bits[0].color==0x001212ff);
tex->unlock();
bits = (video::SColor*)tex->lock(video::ETLM_READ_ONLY, 3);
result &= ((bits[0].color==0xff00ff00)&&(bits[2].color==0xc2c200fe));
tex->unlock();
if (!result)
logTestString("mipmap lock after mipmap write with driver %ls failed.\n", driver->getName());
// now test locking level 0
bits = (video::SColor*)tex->lock(video::ETLM_READ_WRITE, 0);
bits[0]=0xff00ff00;
bits[1]=0xff00ff00;
tex->unlock();
bits = (video::SColor*)tex->lock(video::ETLM_READ_WRITE, 4);
result &= (bits[0].color==0x001212ff);
tex->unlock();
bits = (video::SColor*)tex->lock(video::ETLM_READ_ONLY, 0);
result &= ((bits[0].color==0xff00ff00)&&(bits[2].color==0xff0000fd));
bool result = ((bits[0].color==0xff00ff00)&&(bits[2].color==0xff0000fd));
tex->unlock();
if (!result)
logTestString("mipmap lock at level 0 after mipmap write with driver %ls failed.\n", driver->getName());
logTestString("texture 2d lock with driver %ls failed.\n", driver->getName());
else
logTestString("Passed\n");
device->closeDevice();
device->run();
device->drop();
return result;
}
//! Tests locking miplevels after texture was created with auto mipmap update
bool lockWithAutoMipmap(video::E_DRIVER_TYPE driverType)
{
IrrlichtDevice *device = createDevice( driverType, dimension2d<u32>(160, 120), 32);
if (!device)
return true; // Treat a failure to create a driver as benign; this saves a lot of #ifdefs
video::IVideoDriver* driver = device->getVideoDriver();
scene::ISceneManager * smgr = device->getSceneManager();
if (!driver->queryFeature(video::EVDF_MIP_MAP))
if (testCubemap)
{
device->closeDevice();
device->run();
device->drop();
return true;
}
tex = driver->findTexture("texcube");
stabilizeScreenBackground(driver);
for (u32 i = 0; i < 6; ++i)
{
bits = (video::SColor*)tex->lock(video::ETLM_READ_WRITE, i);
bits[0] = 0xff00ff00;
bits[1] = 0xff00ff00;
tex->unlock();
}
logTestString("Testing driver %ls\n", driver->getName());
for (u32 i = 0; i < 6; ++i)
{
bits = (video::SColor*)tex->lock(video::ETLM_READ_ONLY, i);
u32 b0 = bits[0].color;
u32 b2 = bits[2].color;
scene::ISceneNode* n = smgr->addCubeSceneNode();
result &= ((bits[0].color == 0xff00ff00) && (bits[2].color == 0xff0000fd));
tex->unlock();
}
if (n)
{
// create the texture
u32 texData[16*16];
for (u32 i=0; i<16*16; ++i)
texData[i]=0xff0000ff-i;
video::IImage* image = driver->createImageFromData(video::ECF_A8R8G8B8, core::dimension2du(16,16), texData, false);
video::ITexture* tex = driver->addTexture("miptest", image);
if (!tex)
return false;
if (!result)
logTestString("texture cubemap lock with driver %ls failed.\n", driver->getName());
else
n->setMaterialTexture(0, tex);
image->drop();
logTestString("Passed\n");
}
(void)smgr->addCameraSceneNode();
driver->beginScene(video::ECBF_COLOR | video::ECBF_DEPTH, video::SColor(255,100,101,140));
smgr->drawAll();
driver->endScene();
video::ITexture* tex = driver->findTexture("miptest");
video::SColor* bits = (video::SColor*)tex->lock(video::ETLM_READ_ONLY, 0);
bool result = (bits[0].color==0xff0000ff);
tex->unlock();
if (!result)
logTestString("mipmap lock after init with driver %ls failed.\n", driver->getName());
// test with updating a lower level, and reading upper and lower
bits = (video::SColor*)tex->lock(video::ETLM_READ_WRITE, 3);
bits[0]=0xff00ff00;
bits[1]=0xff00ff00;
tex->unlock();
// lock another texture just to invalidate caches in the driver
bits = (video::SColor*)tex->lock(video::ETLM_READ_WRITE, 4);
tex->unlock();
bits = (video::SColor*)tex->lock(video::ETLM_READ_ONLY, 3);
result &= ((bits[0].color==0xff00ff00)&&(bits[2].color!=0xff00ff00));
tex->unlock();
if (!result)
logTestString("mipmap lock after mipmap write with driver %ls failed.\n", driver->getName());
// now test locking level 0
bits = (video::SColor*)tex->lock(video::ETLM_READ_WRITE, 0);
bits[0]=0x00ff00ff;
bits[1]=0x00ff00ff;
tex->unlock();
bits = (video::SColor*)tex->lock(video::ETLM_READ_ONLY, 3);
result &= ((bits[0].color==0xff00ff00)&&(bits[2].color!=0xff00ff00));
tex->unlock();
if (!result)
logTestString("mipmap lock at level 0 after mipmap write with driver %ls failed.\n", driver->getName());
else
logTestString("Passed\n");
device->closeDevice();
device->run();
@ -296,16 +205,15 @@ bool lockWithAutoMipmap(video::E_DRIVER_TYPE driverType)
return result;
}
}
}
bool textureFeatures(void)
{
bool result = true;
TestWithAllDrivers(renderMipLevels);
TestWithAllDrivers(lockAllMipLevels);
TestWithAllDrivers(lockWithAutoMipmap);
TestWithAllDrivers(lockTexture);
return result;
}