1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168
|
#include "myguitexture.hpp"
#include <stdexcept>
#include <osg/StateSet>
#include <osg/Texture2D>
#include <components/debug/debuglog.hpp>
#include <components/resource/imagemanager.hpp>
namespace MyGUIPlatform
{
OSGTexture::OSGTexture(const std::string& name, Resource::ImageManager* imageManager)
: mName(name)
, mImageManager(imageManager)
, mFormat(MyGUI::PixelFormat::Unknow)
, mUsage(MyGUI::TextureUsage::Default)
, mNumElemBytes(0)
, mWidth(0)
, mHeight(0)
{
}
OSGTexture::OSGTexture(osg::Texture2D* texture, osg::StateSet* injectState)
: mImageManager(nullptr)
, mTexture(texture)
, mInjectState(injectState)
, mFormat(MyGUI::PixelFormat::Unknow)
, mUsage(MyGUI::TextureUsage::Default)
, mNumElemBytes(0)
, mWidth(texture->getTextureWidth())
, mHeight(texture->getTextureHeight())
{
}
OSGTexture::~OSGTexture() {}
void OSGTexture::createManual(int width, int height, MyGUI::TextureUsage usage, MyGUI::PixelFormat format)
{
GLenum glfmt = GL_NONE;
size_t numelems = 0;
switch (format.getValue())
{
case MyGUI::PixelFormat::L8:
glfmt = GL_LUMINANCE;
numelems = 1;
break;
case MyGUI::PixelFormat::L8A8:
glfmt = GL_LUMINANCE_ALPHA;
numelems = 2;
break;
case MyGUI::PixelFormat::R8G8B8:
glfmt = GL_RGB;
numelems = 3;
break;
case MyGUI::PixelFormat::R8G8B8A8:
glfmt = GL_RGBA;
numelems = 4;
break;
}
if (glfmt == GL_NONE)
throw std::runtime_error("Texture format not supported");
mTexture = new osg::Texture2D();
mTexture->setTextureSize(width, height);
mTexture->setSourceFormat(glfmt);
mTexture->setSourceType(GL_UNSIGNED_BYTE);
mWidth = width;
mHeight = height;
mTexture->setFilter(osg::Texture::MIN_FILTER, osg::Texture::LINEAR);
mTexture->setFilter(osg::Texture::MAG_FILTER, osg::Texture::LINEAR);
mTexture->setWrap(osg::Texture::WRAP_S, osg::Texture::CLAMP_TO_EDGE);
mTexture->setWrap(osg::Texture::WRAP_T, osg::Texture::CLAMP_TO_EDGE);
mFormat = format;
mUsage = usage;
mNumElemBytes = numelems;
}
void OSGTexture::destroy()
{
mTexture = nullptr;
mFormat = MyGUI::PixelFormat::Unknow;
mUsage = MyGUI::TextureUsage::Default;
mNumElemBytes = 0;
mWidth = 0;
mHeight = 0;
}
void OSGTexture::loadFromFile(const std::string& fname)
{
if (!mImageManager)
throw std::runtime_error("No imagemanager set");
osg::ref_ptr<osg::Image> image(mImageManager->getImage(VFS::Path::Normalized(fname)));
mTexture = new osg::Texture2D(image);
mTexture->setWrap(osg::Texture::WRAP_S, osg::Texture::CLAMP_TO_EDGE);
mTexture->setWrap(osg::Texture::WRAP_T, osg::Texture::CLAMP_TO_EDGE);
mTexture->setTextureWidth(image->s());
mTexture->setTextureHeight(image->t());
// disable mip-maps
mTexture->setFilter(osg::Texture2D::MIN_FILTER, osg::Texture2D::LINEAR);
mWidth = image->s();
mHeight = image->t();
mUsage = MyGUI::TextureUsage::Static;
}
void OSGTexture::saveToFile(const std::string& fname)
{
Log(Debug::Warning) << "Would save image to file " << fname;
}
void* OSGTexture::lock(MyGUI::TextureUsage /*access*/)
{
if (!mTexture.valid())
throw std::runtime_error("Texture is not created");
if (mLockedImage.valid())
throw std::runtime_error("Texture already locked");
mLockedImage = new osg::Image();
mLockedImage->allocateImage(mTexture->getTextureWidth(), mTexture->getTextureHeight(),
mTexture->getTextureDepth(), mTexture->getSourceFormat(), mTexture->getSourceType());
return mLockedImage->data();
}
void OSGTexture::unlock()
{
if (!mLockedImage.valid())
throw std::runtime_error("Texture not locked");
mLockedImage->flipVertical();
// mTexture might be in use by the draw thread, so create a new texture instead and use that.
osg::ref_ptr<osg::Texture2D> newTexture = new osg::Texture2D;
newTexture->setTextureSize(getWidth(), getHeight());
newTexture->setSourceFormat(mTexture->getSourceFormat());
newTexture->setSourceType(mTexture->getSourceType());
newTexture->setFilter(osg::Texture::MIN_FILTER, mTexture->getFilter(osg::Texture::MIN_FILTER));
newTexture->setFilter(osg::Texture::MAG_FILTER, mTexture->getFilter(osg::Texture::MAG_FILTER));
newTexture->setWrap(osg::Texture::WRAP_S, mTexture->getWrap(osg::Texture::WRAP_S));
newTexture->setWrap(osg::Texture::WRAP_T, mTexture->getWrap(osg::Texture::WRAP_T));
newTexture->setImage(mLockedImage.get());
// Tell the texture it can get rid of the image for static textures (since
// they aren't expected to update much at all).
newTexture->setUnRefImageDataAfterApply(mUsage.isValue(MyGUI::TextureUsage::Static) ? true : false);
mTexture = newTexture;
mLockedImage = nullptr;
}
// Render-to-texture not currently implemented.
MyGUI::IRenderTarget* OSGTexture::getRenderTarget()
{
return nullptr;
}
void OSGTexture::setShader(const std::string& /*shaderName*/)
{
Log(Debug::Warning) << "OSGTexture::setShader is not implemented";
}
}
|