Merge branch 'fixes' into main/rendor-staging
[ryzomcore.git] / nel / src / cegui / neltexture.cpp
blobeca8a70f78ec187f6229df40c0111b1d20bda83f
1 /**
2 * \file neltexture.cpp
3 * \date November 2004
4 * \author Matt Raykowski
5 * \author Henri Kuuste
6 */
8 // NeL - MMORPG Framework <http://dev.ryzom.com/projects/nel/>
9 // Copyright (C) 2010 Winch Gate Property Limited
11 // This program is free software: you can redistribute it and/or modify
12 // it under the terms of the GNU Affero General Public License as
13 // published by the Free Software Foundation, either version 3 of the
14 // License, or (at your option) any later version.
16 // This program is distributed in the hope that it will be useful,
17 // but WITHOUT ANY WARRANTY; without even the implied warranty of
18 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 // GNU Affero General Public License for more details.
21 // You should have received a copy of the GNU Affero General Public License
22 // along with this program. If not, see <http://www.gnu.org/licenses/>.
25 /************************************************************************
26 purpose: Implementation for main Nevrax Engine GUI texture class
28 For use with GUI Library:
29 Crazy Eddie's GUI System (http://crayzedsgui.sourceforge.net)
30 Copyright (C)2004 Paul D Turner (crayzed@users.sourceforge.net)
32 This file contains code that is specific to NeL (http://www.nevrax.org)
33 *************************************************************************/
35 // NeL Renderer includes
36 #include <nel/cegui/neltexture.h>
37 #include <nel/cegui/nelrenderer.h>
39 // CEGUI includes
40 #include "CEGUIExceptions.h"
42 // ditch min/max, they mess stuff up.
43 #undef max
44 #undef min
46 //nel includes
47 #include <nel/misc/file.h>
48 #include <nel/misc/bitmap.h>
49 #include <nel/3d/texture_mem.h>
50 #include <nel/3d/material.h>
52 namespace CEGUI
54 NeLTexture::NeLTexture(Renderer *owner) : Texture(owner)
56 m_Owner=dynamic_cast<NeLRenderer *>(owner);
57 m_Material = m_Owner->getNeLDriver().createMaterial();
58 m_TextureFile=NULL;
59 m_TextureMem=NULL;
60 m_UsingFile=false;
61 m_UsingMem=false;
64 NeLTexture::~NeLTexture(void)
66 freeNeLTexture();
67 // can't free material in the same phase as the texture.
68 m_Owner->getNeLDriver().deleteMaterial(m_Material);
69 m_Material=NULL;
73 void NeLTexture::loadFromFile(const String &filename, const String& resourceGroup)
75 String file = NLMISC::CPath::lookup(filename.c_str()).c_str();
77 // this object can only contain one texture at a time, free the old one if it exists.
78 freeNeLTexture();
80 // create the texture from a file...
82 /* TODO: Determine if Kervala was correct in removing setWrapS/T */
83 m_TextureFile=m_Owner->getNeLDriver().createTextureFile(file.c_str());
84 m_TextureFile->setWrapS(NL3D::UTexture::Clamp);
85 m_TextureFile->setWrapT(NL3D::UTexture::Clamp);
87 if(m_TextureFile == 0) { // failed to load the texture.
88 nlinfo("Failed to load texture: %s",filename.c_str());
89 return;
92 // because nel unloads the texture from RAM when it loads it into VRAM
93 // we need to load the texture into a bitmap to get the sizes.
94 NL3D::CBitmap tmpBitmap;
95 NLMISC::CIFile nelfile(file.c_str());
96 tmpBitmap.load(nelfile);
97 d_width=tmpBitmap.getWidth();
98 d_height=tmpBitmap.getHeight();
100 // set the material up.
101 m_UsingFile=true; m_UsingMem=false;
102 m_Material.setTexture(m_TextureFile);
103 m_Material.setBlend(true);
104 m_Material.setBlendFunc(NL3D::UMaterial::srcalpha, NL3D::UMaterial::invsrcalpha);
105 m_Material.setAlphaTest(false);
106 m_Material.setZFunc(NL3D::UMaterial::always);
107 m_Material.setDoubleSided();
110 void NeLTexture::loadFromMemory(const void *buffPtr, uint buffWidth, uint buffHeight, PixelFormat pixelFormat)
112 // this object can only contain one texture at a time, free the old one if it exists.
113 freeNeLTexture();
116 * This debugging is handy when you're not sure if the memory buffer
117 * being sent to you from CEGUI is valid. Uncomment it and it'll create
118 * a file called loadfrommem###.tga in your working directory.
120 * NLMISC::CBitmap btm;
121 * btm.reset();
122 * btm.resize(buffWidth,buffHeight,NLMISC::CBitmap::RGBA);
123 * uint8 *dest=&(btm.getPixels()[0]);
124 * memcpy(dest,buffPtr,buffWidth*buffHeight*4);
125 * std::string filename = NLMISC::CFile::findNewFile("loadfrommem.tga");
126 * NLMISC::COFile fs(filename);
127 * btm.writeTGA(fs);
130 int size=4;
132 switch(pixelFormat)
134 case PF_RGB:
135 size = 3;
136 break;
137 case PF_RGBA:
138 size = 4;
139 break;
142 // copy the memory stream for use in the NeL texture.
143 uint8 *pTmpBuf=new uint8[buffWidth*buffHeight*size];
144 memcpy(pTmpBuf,buffPtr,buffWidth*buffHeight*size);
146 // create the texture
147 m_TextureMem=new NL3D::CTextureMem( pTmpBuf,buffWidth*buffHeight*size,true,false,buffWidth,buffHeight,NLMISC::CBitmap::RGBA);
148 m_TextureMem->setWrapS(NL3D::ITexture::Clamp);
149 m_TextureMem->setWrapT(NL3D::ITexture::Clamp);
150 m_TextureMem->setFilterMode(NL3D::ITexture::Linear, NL3D::ITexture::LinearMipMapOff);
151 m_TextureMem->setReleasable(false);
152 m_TextureMem->generate();
153 if(m_TextureMem == 0) { // failed to load the texture.
154 nlinfo("Failed to load texture from memory");
155 return;
159 * Configure the material. This is a little more complicated than loading a texture from
160 * a file, since CTextureFileUser and CTextureFile take care of prepping all of the
161 * necessary alpha settings.
163 NL3D::CMaterial *mat = m_Material.getObjectPtr();
164 mat->initUnlit();
165 mat->setShader(NL3D::CMaterial::Normal);
166 mat->setTexture(0, m_TextureMem);
169 * We still use alpha testing to cull out pixels to speed up
170 * blending and multitexturing.
172 m_Material.setAlphaTest(true);
173 m_Material.setAlphaTestThreshold(0.1f);
174 m_Material.setBlend(true);
175 m_Material.setBlendFunc(NL3D::UMaterial::srcalpha,NL3D::UMaterial::invsrcalpha);
176 m_Material.texEnvOpRGB(0, NL3D::UMaterial::Modulate);
177 m_Material.texEnvArg0RGB(0, NL3D::UMaterial::Texture, NL3D::UMaterial::SrcColor);
178 m_Material.texEnvArg1RGB(0, NL3D::UMaterial::Diffuse, NL3D::UMaterial::SrcColor);
179 m_Material.texEnvOpAlpha(0, NL3D::UMaterial::Modulate);
180 m_Material.texEnvArg0Alpha(0, NL3D::UMaterial::Texture, NL3D::UMaterial::SrcAlpha);
181 m_Material.texEnvArg1Alpha(0, NL3D::UMaterial::Diffuse, NL3D::UMaterial::SrcAlpha);
182 m_Material.setZFunc(NL3D::UMaterial::always);
183 m_Material.setDoubleSided(true);
185 // make sure to record our changes.
186 d_width=buffWidth;
187 d_height=buffHeight;
188 m_UsingFile=false; m_UsingMem=true;
191 NL3D::UMaterial NeLTexture::getNeLTexture(void) {
192 return m_Material;
195 void NeLTexture::freeNeLTexture(void)
197 // never been populated.
198 if(m_TextureMem==NULL && m_TextureFile==NULL)
199 return;
201 if(m_UsingFile==true) {
202 m_Owner->getNeLDriver().deleteTextureFile(m_TextureFile);
203 m_TextureFile=NULL;
204 m_UsingFile=false;
205 } else if(m_UsingMem==true) {
206 //m_Owner->getNeLDriver().deleteTextureMem(m_TextureMem);
207 m_TextureMem=NULL;
208 m_UsingMem=false;
209 } else {
210 nlwarning("Something has gone horribly wrong, unable to free any type of texture.");
214 } // end namespace CEGUI