00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00026
00027
00028 #include "glc_texture.h"
00029 #include "../glc_exception.h"
00030 #include "../glc_global.h"
00031
00032
00033 #include "../quazip/quazip.h"
00034 #include "../quazip/quazipfile.h"
00035
00036 #include <QtDebug>
00037
00038
00039 QSize GLC_Texture::m_MaxTextureSize(676, 676);
00040
00041
00042 const QSize GLC_Texture::m_MinTextureSize(10, 10);
00043
00044 QHash<GLuint, int> GLC_Texture::m_TextureIdUsage;
00045
00047
00049
00051 GLC_Texture::GLC_Texture(const QGLContext *pContext)
00052 : m_pQGLContext(const_cast<QGLContext*>(pContext))
00053 , m_FileName()
00054 , m_GlTextureID(0)
00055 , m_textureImage()
00056 , m_TextureSize()
00057 , m_HasAlphaChannel(false)
00058 {
00059
00060 }
00061
00062
00063 GLC_Texture::GLC_Texture(const QGLContext *pContext, const QString &Filename)
00064 : m_pQGLContext(const_cast<QGLContext*>(pContext))
00065 , m_FileName(Filename)
00066 , m_GlTextureID(0)
00067 , m_textureImage(loadFromFile(m_FileName))
00068 , m_TextureSize()
00069 , m_HasAlphaChannel(m_textureImage.hasAlphaChannel())
00070 {
00071 if (m_textureImage.isNull())
00072 {
00073 QString ErrorMess("GLC_Texture::GLC_Texture open image : ");
00074 ErrorMess.append(m_FileName).append(" Failed");
00075 qDebug() << ErrorMess;
00076 GLC_Exception e(ErrorMess);
00077 throw(e);
00078 }
00079 }
00080
00081 GLC_Texture::GLC_Texture(const QGLContext *pContext, const QFile &file)
00082 : m_pQGLContext(const_cast<QGLContext*>(pContext))
00083 , m_FileName(file.fileName())
00084 , m_GlTextureID(0)
00085 , m_textureImage()
00086 , m_TextureSize()
00087 , m_HasAlphaChannel(m_textureImage.hasAlphaChannel())
00088 {
00089 m_textureImage.load(const_cast<QFile*>(&file), QFileInfo(m_FileName).suffix().toLocal8Bit());
00090 if (m_textureImage.isNull())
00091 {
00092 QString ErrorMess("GLC_Texture::GLC_Texture open image : ");
00093 ErrorMess.append(m_FileName).append(" Failed");
00094 qDebug() << ErrorMess;
00095 GLC_Exception e(ErrorMess);
00096 throw(e);
00097 }
00098 }
00099
00100
00101 GLC_Texture::GLC_Texture(const QGLContext* pContext, const QImage& image, const QString& fileName)
00102 : m_pQGLContext(const_cast<QGLContext*>(pContext))
00103 , m_FileName(fileName)
00104 , m_GlTextureID(0)
00105 , m_textureImage(image)
00106 , m_TextureSize()
00107 , m_HasAlphaChannel(m_textureImage.hasAlphaChannel())
00108 {
00109 Q_ASSERT(!m_textureImage.isNull());
00110 }
00111
00112 GLC_Texture::GLC_Texture(const GLC_Texture &TextureToCopy)
00113 : m_pQGLContext(TextureToCopy.m_pQGLContext)
00114 , m_FileName(TextureToCopy.m_FileName)
00115 , m_GlTextureID(TextureToCopy.m_GlTextureID)
00116 , m_textureImage(TextureToCopy.m_textureImage)
00117 , m_TextureSize(TextureToCopy.m_TextureSize)
00118 , m_HasAlphaChannel(m_textureImage.hasAlphaChannel())
00119 {
00120 if (m_textureImage.isNull())
00121 {
00122 QString ErrorMess("GLC_Texture::GLC_Texture open image : ");
00123 ErrorMess.append(m_FileName).append(" Failed");
00124 qDebug() << ErrorMess;
00125 GLC_Exception e(ErrorMess);
00126 throw(e);
00127 }
00128 addThisOpenGLTextureId();
00129
00130 }
00131
00132
00133 GLC_Texture& GLC_Texture::operator=(const GLC_Texture& texture)
00134 {
00135 if (!(*this == texture))
00136 {
00137 removeThisOpenGLTextureId();
00138 m_pQGLContext= texture.m_pQGLContext;
00139 m_FileName= texture.m_FileName;
00140 m_GlTextureID= texture.m_GlTextureID;
00141 addThisOpenGLTextureId();
00142 m_textureImage= texture.m_textureImage;
00143 m_TextureSize= texture.m_TextureSize;
00144 m_HasAlphaChannel= m_textureImage.hasAlphaChannel();
00145 }
00146
00147 return *this;
00148 }
00149
00150 GLC_Texture::~GLC_Texture()
00151 {
00152
00153 removeThisOpenGLTextureId();
00154 }
00156
00158
00159
00160 bool GLC_Texture::operator==(const GLC_Texture& texture) const
00161 {
00162 bool result;
00163 if (this == &texture)
00164 {
00165 result= true;
00166 }
00167 else
00168 {
00169 result= (m_FileName == texture.m_FileName) && (m_textureImage == texture.m_textureImage);
00170 }
00171 return result;
00172 }
00173
00175
00177
00178
00179 void GLC_Texture::setMaxTextureSize(const QSize& size)
00180 {
00181 if ((size.height() > m_MinTextureSize.height()) && (size.width() > m_MinTextureSize.width()))
00182 {
00183 m_MaxTextureSize= size;
00184 }
00185 else
00186 {
00187 qDebug() << "GLC_Texture::setMaxTextureSize m_MaxTextureSize set to m_MinTextureSize";
00188 m_MaxTextureSize= m_MinTextureSize;
00189 }
00190 }
00191
00193
00195
00196 void GLC_Texture::glLoadTexture(void)
00197 {
00198 if (m_GlTextureID == 0)
00199 {
00200 if (NULL == m_pQGLContext)
00201 {
00202 m_pQGLContext= const_cast<QGLContext*>(QGLContext::currentContext());
00203 }
00204
00205 if ((m_textureImage.height() > m_MaxTextureSize.height())
00206 || (m_textureImage.width() > m_MaxTextureSize.width()))
00207 {
00208 QImage rescaledImage;
00209 if(m_textureImage.height() > m_textureImage.width())
00210 {
00211 rescaledImage= m_textureImage.scaledToHeight(m_MaxTextureSize.height(), Qt::SmoothTransformation);
00212 }
00213 else
00214 {
00215 rescaledImage= m_textureImage.scaledToWidth(m_MaxTextureSize.width(), Qt::SmoothTransformation);
00216 }
00217 m_textureImage= rescaledImage;
00218 m_TextureSize= m_textureImage.size();
00219 }
00220 else
00221 {
00222 m_TextureSize= m_textureImage.size();
00223 }
00224 m_GlTextureID= m_pQGLContext->bindTexture(m_textureImage);
00225 addThisOpenGLTextureId();
00226
00227
00228 }
00229 }
00230
00231
00232 void GLC_Texture::glcBindTexture(void)
00233 {
00234 if (m_GlTextureID == 0)
00235 {
00236 glLoadTexture();
00237 }
00238 glBindTexture(GL_TEXTURE_2D, m_GlTextureID);
00239 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
00240 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
00241 }
00242
00243 QImage GLC_Texture::loadFromFile(const QString& fileName)
00244 {
00245 QImage resultImage;
00246 if (glc::isArchiveString(fileName))
00247 {
00248
00249
00250 QuaZip* p3dxmlArchive= new QuaZip(glc::archiveFileName(fileName));
00251
00252 if(!p3dxmlArchive->open(QuaZip::mdUnzip))
00253 {
00254 delete p3dxmlArchive;
00255 return QImage();
00256 }
00257 else
00258 {
00259
00260 p3dxmlArchive->setFileNameCodec("IBM866");
00261 }
00262 QString imageFileName= glc::archiveEntryFileName(fileName);
00263
00264
00265 QuaZipFile* p3dxmlFile= new QuaZipFile(p3dxmlArchive);
00266
00267
00268 if (!p3dxmlArchive->setCurrentFile(imageFileName, QuaZip::csInsensitive))
00269 {
00270 delete p3dxmlFile;
00271 delete p3dxmlArchive;
00272 return QImage();
00273 }
00274
00275
00276 if(!p3dxmlFile->open(QIODevice::ReadOnly))
00277 {
00278 delete p3dxmlFile;
00279 delete p3dxmlArchive;
00280 return QImage();
00281 }
00282 resultImage.load(p3dxmlFile, QFileInfo(imageFileName).suffix().toLocal8Bit());
00283 p3dxmlFile->close();
00284 delete p3dxmlFile;
00285 delete p3dxmlArchive;
00286 }
00287 else
00288 {
00289 resultImage.load(fileName);
00290 }
00291
00292 return resultImage;
00293 }
00294
00295 void GLC_Texture::removeThisOpenGLTextureId()
00296 {
00297 if ( 0 != m_GlTextureID)
00298 {
00299 Q_ASSERT(m_TextureIdUsage.contains(m_GlTextureID));
00300 --m_TextureIdUsage[m_GlTextureID];
00301 if (m_TextureIdUsage.value(m_GlTextureID) == 0)
00302 {
00303 m_pQGLContext->deleteTexture(m_GlTextureID);
00304 m_TextureIdUsage.remove(m_GlTextureID);
00305 m_GlTextureID= 0;
00306 }
00307 }
00308 }
00309
00310 void GLC_Texture::addThisOpenGLTextureId()
00311 {
00312 if (0 != m_GlTextureID)
00313 {
00314 if (m_TextureIdUsage.contains(m_GlTextureID))
00315 {
00316 ++m_TextureIdUsage[m_GlTextureID];
00317 }
00318 else
00319 {
00320 m_TextureIdUsage.insert(m_GlTextureID, 1);
00321 }
00322 }
00323 }
00324
00325
00326 QDataStream &operator<<(QDataStream &stream, const GLC_Texture &texture)
00327 {
00328 stream << texture.fileName();
00329
00330 return stream;
00331 }
00332 QDataStream &operator>>(QDataStream &stream, GLC_Texture &texture)
00333 {
00334 QString fileName;
00335 stream >> fileName;
00336 texture= GLC_Texture(texture.context(), fileName);
00337
00338 return stream;
00339 }
00340