diff --git a/Salmon Engine/Salmon Engine.vcxproj b/Salmon Engine/Salmon Engine.vcxproj index 456a260..f2ac4de 100644 --- a/Salmon Engine/Salmon Engine.vcxproj +++ b/Salmon Engine/Salmon Engine.vcxproj @@ -52,10 +52,12 @@ + + @@ -94,10 +96,12 @@ + + @@ -152,7 +156,7 @@ Level3 Disabled TARGET_WIN32;WIN32_LEAN_AND_MEAN;_WIN32_WINNT=0x0501;DEBUG - $(SalmonEnginePath);$(LibsPath)\boost_1_52_0;$(LibsPath)\openal\OpenAL11_windows_sdk;$(LibsPath)\libogg-1.3.0\include;$(LibsPath)\libvorbis-1.3.2\include;$(LibsPath)\sqplus\sqplus;$(LibsPath)\sqplus\include;$(LibsPath)\DirectXsdk\Include;$(LibsPath)\lpng1510 + $(SalmonEnginePath);$(LibsPath)\boost_1_52_0;$(LibsPath)\openal\OpenAL11_windows_sdk;$(LibsPath)\libogg-1.3.0\include;$(LibsPath)\libvorbis-1.3.2\include;$(LibsPath)\sqplus\sqplus;$(LibsPath)\sqplus\include;$(LibsPath)\DirectXsdk\Include;$(LibsPath)\lpng1510;$(LibsPath)\jpeg-9;$(LibsPath)\jpeg-9\vc10 4503 diff --git a/include/Render/SalmonRender/Cameras.h b/include/Render/SalmonRender/Cameras.h index a250f93..d011ead 100644 --- a/include/Render/SalmonRender/Cameras.h +++ b/include/Render/SalmonRender/Cameras.h @@ -43,6 +43,8 @@ struct TPanoramicCamera : public TCameraInterface void CalcCamVec(); void SetCamView(); + + void SetCamShift(const vec3& camShift); }; struct TPitCamera : public TCameraInterface diff --git a/include/TextureManager/SalmonTexture.h b/include/TextureManager/SalmonTexture.h index 6421d89..692f6a0 100644 --- a/include/TextureManager/SalmonTexture.h +++ b/include/TextureManager/SalmonTexture.h @@ -16,6 +16,8 @@ This code contains texture manager #include "include/Utils/Utils.h" #include "include/Utils/PngHelper.h" +#include "include/Utils/JpegHelper.h" +#include "include/Utils/TgaLoader.h" #include "include/ScriptManager/ScriptManager.h" namespace SE @@ -40,7 +42,7 @@ struct TTextureData boost::shared_array Data; }; -typedef std::map > TTextureMap; +typedef std::map> TTextureMap; class TTextureListClass : public TSerializeInterface, public TFunctionBinderInterface @@ -58,6 +60,7 @@ protected: bool CreateTexDataFromBmp32(const std::string& filename, TTextureData& texData); bool CreateTexDataFromTga(const std::string& filename, TTextureData& texData); bool CreateTexDataFromPng(const std::string& filename, TTextureData& texData); + bool CreateTexDataFromJpg(const std::string& filename, TTextureData& texData); cardinal AddTextureBmp24Data(const TTextureData& texData); //MAIN THREAD ONLY cardinal AddTextureBmp32Data(const TTextureData& texData); //MAIN THREAD ONLY diff --git a/include/Utils/FileUtils/FileUtils.h b/include/Utils/FileUtils/FileUtils.h index eb9faf1..92ba725 100644 --- a/include/Utils/FileUtils/FileUtils.h +++ b/include/Utils/FileUtils/FileUtils.h @@ -38,13 +38,83 @@ bool findString(char* in, char* list); bool IsFileExistsInUserData(const std::string& filename); + std::string GetFilePathUserData(const std::string& filename); + +//utitily to process texture uploading +inline char* GetFileName(const char* filename) +{ + char* fname = (char*)filename + strlen(filename); + + while ((*fname != '\\')&&(*fname != '/')&&(fname >= filename )) + --fname; + + ++fname; + + return fname; +} + +inline std::string GetFileName(const std::string& filename) +{ + std::string::const_iterator i = filename.end() - 1; + + while ((i > filename.begin() )&&(*i != '\\')&&(*i != '/')) + --i; + + if (*i == '\\' || *i == '/') + { + i++; + } + + return std::string(i, filename.end()); +} + +//utitily to process texture uploading +inline char* GetFileExt(const char* filename) +{ + char* fext = (char*)filename + strlen(filename); + + while (*fext != '.') + --fext; + + return fext; +} + +inline std::string GetFileExt(const std::string& filename) +{ + std::string::const_iterator i = filename.end() - 1; + + while (*i != '.') + --i; + + return std::string(i, filename.end()); + +} + +inline std::string GetFileNameWithoutExt(const std::string& filename) +{ + std::string result = GetFileName(filename); + + std::string::const_iterator i = result.end() - 1; + + while (*i != '.') + --i; + + return std::string(result.begin(), i); +} + +std::string GetFilePath(const std::string& filename); + + + #ifdef TARGET_WIN32 void GetFileList(const std::string& searchkey, std::vector &list); +std::string AutocompleteExtension(const std::string& fileName); + template boost::shared_array CreateMemFromFile(const std::string& fileName, cardinal& intCount) { @@ -57,11 +127,9 @@ boost::shared_array CreateMemFromFile(const std::string& fileName, car size_t result; TYPENAME* fileData; + - std::string realFileName = fileName; - - - if (fopen_s(&pFile, realFileName.c_str(), "rb" ) != 0) + if (fopen_s(&pFile, fileName.c_str(), "rb" ) != 0) { throw ErrorToLog("File not loaded: " + fileName); } @@ -196,70 +264,6 @@ boost::shared_array CreateMemFromFile(const std::string& fileName, car #endif -//utitily to process texture uploading -inline char* GetFileName(const char* filename) -{ - char* fname = (char*)filename + strlen(filename); - - while ((*fname != '\\')&&(*fname != '/')&&(fname >= filename )) - --fname; - - ++fname; - - return fname; -} - -inline std::string GetFileName(const std::string& filename) -{ - std::string::const_iterator i = filename.end() - 1; - - while ((i > filename.begin() )&&(*i != '\\')&&(*i != '/')) - --i; - - if (*i == '\\' || *i == '/') - { - i++; - } - - return std::string(i, filename.end()); -} - -//utitily to process texture uploading -inline char* GetFileExt(const char* filename) -{ - char* fext = (char*)filename + strlen(filename); - - while (*fext != '.') - --fext; - - return fext; -} - -inline std::string GetFileExt(const std::string& filename) -{ - std::string::const_iterator i = filename.end() - 1; - - while (*i != '.') - --i; - - return std::string(i, filename.end()); - -} - -inline std::string GetFileNameWithoutExt(const std::string& filename) -{ - std::string result = GetFileName(filename); - - std::string::const_iterator i = result.end() - 1; - - while (*i != '.') - --i; - - return std::string(result.begin(), i); -} - -std::string GetFilePath(const std::string& filename); - #ifdef TARGET_IOS //Special for IOS, because Foundation.h conflicts with sq_plus.h diff --git a/include/Utils/JpegHelper.h b/include/Utils/JpegHelper.h new file mode 100644 index 0000000..91faaa6 --- /dev/null +++ b/include/Utils/JpegHelper.h @@ -0,0 +1,16 @@ +#ifndef JPEG_HELPER_H_INCLUDED +#define JPEG_HELPER_H_INCLUDED + +#include + +namespace SE +{ + +struct TTextureData; // Find it in SalmonTexture.h + +bool LoadJpg(const std::string& filename, TTextureData& texData); + +} //namespace SE + + +#endif //JPEG_HELPER_H_INCLUDED \ No newline at end of file diff --git a/include/Utils/TgaLoader.h b/include/Utils/TgaLoader.h new file mode 100644 index 0000000..1d6393e --- /dev/null +++ b/include/Utils/TgaLoader.h @@ -0,0 +1,55 @@ +#ifndef TGA_LOADER_H_INCLUDED +#define TGA_LOADER_H_INCLUDED + +#include "include/Utils/Utils.h" + +//Thanks to NeHe + +namespace SE +{ + + +const int CONST_TGA_OUTER_HEADER_SIZE = 12; + +typedef struct +{ + GLubyte Header[CONST_TGA_OUTER_HEADER_SIZE]; // TGA File Header +} TGAHeader; + +const int CONST_TGA_INNER_HEADER_SIZE = 6; + +typedef struct +{ + GLubyte header[CONST_TGA_INNER_HEADER_SIZE]; // First 6 Useful Bytes From The Header + GLuint bytesPerPixel; // Holds Number Of Bytes Per Pixel Used In The TGA File + GLuint imageSize; // Used To Store The Image Size When Setting Aside Ram + GLuint temp; // Temporary Variable + GLuint type; + GLuint Height; //Height of Image + GLuint Width; //Width ofImage + GLuint Bpp; // Bits Per Pixel +} TGA; + + +//TGAHeader tgaheader; // TGA header +//TGA tga; // TGA image data + + + +extern GLubyte uTGAcompare[12]; // Uncompressed TGA Header +extern GLubyte cTGAcompare[12]; // Compressed TGA Header + + +struct TTextureData; // Find it in SalmonTexture.h + + +bool LoadTGA(const std::string& filename, TTextureData& texture); + +bool LoadUncompressedTGA(TTextureData& texture, boost::shared_array fTGA); // Load an Uncompressed file +bool LoadCompressedTGA(TTextureData& texture, boost::shared_array fTGA); // Load a Compressed file + + +} //namespace SE + + +#endif //TGA_LOADER_H_INCLUDED \ No newline at end of file diff --git a/src/Render/SalmonRender/Cameras.cpp b/src/Render/SalmonRender/Cameras.cpp index a8f7a34..cc0dd82 100644 --- a/src/Render/SalmonRender/Cameras.cpp +++ b/src/Render/SalmonRender/Cameras.cpp @@ -197,6 +197,14 @@ void TPanoramicCamera::SetCamView() } +void TPanoramicCamera::SetCamShift(const vec3& camShift) +{ + CamShift = camShift; + + Renderer->CalcCamPos(); +} + + void TPitCamera::SetCamView() { Renderer->LoadIdentity(); diff --git a/src/TextureManager/SalmonTexture.cpp b/src/TextureManager/SalmonTexture.cpp index 1ac84fb..dfe1f1e 100644 --- a/src/TextureManager/SalmonTexture.cpp +++ b/src/TextureManager/SalmonTexture.cpp @@ -9,6 +9,9 @@ #include "boost/assign.hpp" +#include "jpeglib.h" +#include + namespace SE { @@ -22,13 +25,9 @@ TTextureListClass::TTextureListClass() CreateFunctionMap[".bmp32"] = boost::bind(&TTextureListClass::CreateTexDataFromBmp32, this, _1, _2); CreateFunctionMap[".png"] = boost::bind(&TTextureListClass::CreateTexDataFromPng, this, _1, _2); CreateFunctionMap[".tga"] = boost::bind(&TTextureListClass::CreateTexDataFromTga, this, _1, _2); - - /* - AddFunctionMap["bmp24"] = boost::bind(&TTextureListClass::AddTextureBmp24Data, this, _1); - AddFunctionMap["bmp32"] = boost::bind(&TTextureListClass::AddTextureBmp32Data, this, _1); - - Let's use inner functions! - */ + CreateFunctionMap[".jpg"] = boost::bind(&TTextureListClass::CreateTexDataFromJpg, this, _1, _2); + CreateFunctionMap[".jpeg"] = boost::bind(&TTextureListClass::CreateTexDataFromJpg, this, _1, _2); + AddFunctionMap["bmp24"] = [this](TTextureData& texData) -> cardinal { @@ -396,121 +395,22 @@ bool TTextureListClass::CreateTexDataFromBmp32(const std::string& filename, TTex bool TTextureListClass::CreateTexDataFromTga(const std::string& filename, TTextureData& texData) { + + bool result = LoadTGA(filename, texData); - cardinal fileSize; - boost::shared_array fileArr = CreateMemFromFile(filename, fileSize); - - if (fileSize < 22) + if (!result) + { throw ErrorFileNotCorrect(filename); - - texData.Width = *reinterpret_cast(&fileArr[12]); - texData.Height = *reinterpret_cast(&fileArr[14]); - - char textLength = fileArr[0]; - - char dataType = fileArr[2]; - - char bitsPerPixel = fileArr[16]; - - - if (bitsPerPixel == 24) - { - texData.DataSize = texData.Height * texData.Width * 3; - texData.Data = boost::shared_array(new char [texData.DataSize]); - strcpy(texData.Format, "bmp24"); } - else - if (bitsPerPixel == 32) - { - texData.DataSize = texData.Height * texData.Width * 4; - texData.Data = boost::shared_array(new char [texData.DataSize]); - strcpy(texData.Format, "bmp32"); - } - else - throw ErrorFileNotCorrect(filename); - int bytesPerPixel = bitsPerPixel / 8; + return result; - unsigned char blockInfo; - char whatItIs; - unsigned int numPixels; +} - cardinal n = 0; - int filePos = textLength + 18; - if (dataType == 2) - { - - for(cardinal n = 0; n < texData.Height * texData.Width; n++) - { - texData.Data[n*bytesPerPixel + 2] = fileArr[filePos++]; - texData.Data[n*bytesPerPixel + 1] = fileArr[filePos++]; - texData.Data[n*bytesPerPixel + 0] = fileArr[filePos++]; - if (bitsPerPixel == 32) - { - texData.Data[n*bytesPerPixel + 3] = fileArr[filePos++]; - } - } - - } - else if (dataType == 10) - { - throw ErrorToLog("RLE-compressed TGA is not supported yet: "+filename); - - while (n < texData.Height * texData.Width) - { - blockInfo = fileArr[filePos++]; - whatItIs = blockInfo & 128; - numPixels = blockInfo & 127; - - if (whatItIs) - { - - for (cardinal i=0; i &list) break; } } + + +std::string AutocompleteExtension(const std::string& fileName) +{ + std::string filePath = GetFilePath(fileName); + + std::vector list; + + GetFileList(fileName+".bmp", list); + GetFileList(fileName+".bmp32", list); + GetFileList(fileName+".tga", list); + GetFileList(fileName+".png", list); + GetFileList(fileName+".jpg", list); + + + if (list.size() == 0) + { + throw ErrorToLog("AutocompleteExtension - file not found!"); + } + + return filePath+list[0]; + +} + #endif #ifdef TARGET_IOS diff --git a/src/Utils/JpegHelper.cpp b/src/Utils/JpegHelper.cpp new file mode 100644 index 0000000..609e1a9 --- /dev/null +++ b/src/Utils/JpegHelper.cpp @@ -0,0 +1,116 @@ +#include "include/Utils/JpegHelper.h" +#include "include/Utils/Utils.h" +#include "include/TextureManager/SalmonTexture.h" + + +#include "boost/gil/gil_all.hpp" +#include "boost/gil/extension/numeric/sampler.hpp" +#include "boost/gil/extension/numeric/resample.hpp" + +#include "boost/assign.hpp" + +#include "jpeglib.h" +#include + +namespace SE +{ + +struct my_error_mgr +{ + struct jpeg_error_mgr pub; + jmp_buf setjmp_buffer; +}; + + +METHODDEF(void) +my_error_exit (j_common_ptr cinfo) +{ + my_error_mgr* myerr = (my_error_mgr*) cinfo->err; + (*cinfo->err->output_message) (cinfo); + longjmp(myerr->setjmp_buffer, 1); + + throw ErrorToLog("JPEG Error!"); +} + + + +bool LoadJpg(const std::string& filename, TTextureData& texData) +{ + + jpeg_decompress_struct cinfo; + + my_error_mgr jerr; + + JSAMPARRAY buffer; + int row_stride; + + + cardinal fileSize; + + boost::shared_array fileArr = CreateMemFromFile(filename, fileSize); + + cinfo.err = jpeg_std_error(&jerr.pub); + jerr.pub.error_exit = my_error_exit; + + jpeg_create_decompress(&cinfo); + + jpeg_mem_src(&cinfo, &fileArr[0], fileSize); + + + jpeg_read_header(&cinfo, TRUE); + + jpeg_start_decompress(&cinfo); + + row_stride = cinfo.output_width * cinfo.output_components; + + buffer = (*cinfo.mem->alloc_sarray) + ((j_common_ptr) &cinfo, JPOOL_IMAGE, row_stride, 1); + + + if (cinfo.output_components == 3) + { + strcpy(texData.Format, "bmp24"); + } + else if (cinfo.output_components == 4) + { + strcpy(texData.Format, "bmp32"); + } + else + { + throw ErrorToLog("cinfo.output_components unknown value!"); + } + + texData.Width = cinfo.output_width; + + texData.Height = cinfo.output_height; + + texData.DataSize = cinfo.output_height * cinfo.output_width * cinfo.output_components; + texData.Data = boost::shared_array(new char[texData.DataSize]); + + while (cinfo.output_scanline < cinfo.output_height) + { + JDIMENSION read_now = jpeg_read_scanlines(&cinfo, buffer, 1); + memcpy(&texData.Data[(cinfo.output_scanline - read_now) * cinfo.output_width * cinfo.output_components], buffer[0], row_stride); + } + + jpeg_finish_decompress(&cinfo); + + jpeg_destroy_decompress(&cinfo); + + using namespace boost::gil; + + boost::shared_array newData(new char[texData.Height * texData.Width * 3]); + + rgb8_view_t oldView = interleaved_view(texData.Width, texData.Height, reinterpret_cast(texData.Data.get()), texData.DataSize / texData.Height); + + rgb8_view_t newView = interleaved_view(texData.Width, texData.Height, reinterpret_cast(newData.get()), texData.DataSize / texData.Height); + + copy_pixels(flipped_up_down_view(oldView), newView); + + texData.Data = newData; + + return true; + +} + +} //namespace SE diff --git a/src/Utils/TgaLoader.cpp b/src/Utils/TgaLoader.cpp new file mode 100644 index 0000000..7cd05c3 --- /dev/null +++ b/src/Utils/TgaLoader.cpp @@ -0,0 +1,246 @@ +#include "include/Utils/TgaLoader.h" +#include "include/Utils/Utils.h" + +#include "include/TextureManager/SalmonTexture.h" +//Thanks to NeHe + +namespace SE +{ + + + +GLubyte uTGAcompare[12] = {0,0,2, 0,0,0,0,0,0,0,0,0}; // Uncompressed TGA Header +GLubyte cTGAcompare[12] = {0,0,10,0,0,0,0,0,0,0,0,0}; // Compressed TGA Header + + + + +//bool LoadTGA(Texture * texture, char * filename) // Load a TGA file +bool LoadTGA(const std::string& filename, TTextureData& texture) // Load a TGA file +{ + + cardinal byteCount; + + boost::shared_array fTGA = CreateMemFromFile(filename, byteCount); + + TGAHeader tgaheader; + + tgaheader = *(reinterpret_cast(&fTGA[0])); + + if(memcmp(uTGAcompare, &tgaheader, sizeof(tgaheader)) == 0) // See if header matches the predefined header of + { // an Uncompressed TGA image + return LoadUncompressedTGA(texture, fTGA); // If so, jump to Uncompressed TGA loading code + } + else if(memcmp(cTGAcompare, &tgaheader, sizeof(tgaheader)) == 0) // See if header matches the predefined header of + { // an RLE compressed TGA image + return LoadCompressedTGA(texture, fTGA); // If so, jump to Compressed TGA loading code + } + else // If header matches neither type + { + return false; // Exit function + } + // All went well, continue on +} + + +//bool LoadUncompressedTGA(Texture * texture, char * filename, FILE * fTGA) // Load an uncompressed TGA (note, much of this code is based on NeHe's +bool LoadUncompressedTGA(TTextureData& texture, boost::shared_array fTGA) // Load an uncompressed TGA (note, much of this code is based on NeHe's +{ // TGA Loading code nehe.gamedev.net) + TGA tga; + + int shift = sizeof(TGAHeader); + + memcpy(tga.header, &fTGA[shift], CONST_TGA_INNER_HEADER_SIZE); + + shift += CONST_TGA_INNER_HEADER_SIZE; + + + texture.Width = tga.header[1] * 256 + tga.header[0]; // Determine The TGA Width (highbyte*256+lowbyte) + texture.Height = tga.header[3] * 256 + tga.header[2]; // Determine The TGA Height (highbyte*256+lowbyte) + + int bitsPerPixel = tga.header[4]; + + if (bitsPerPixel == 24) + { + strcpy(texture.Format, "bmp24"); + } + else if (bitsPerPixel == 32) + { + strcpy(texture.Format, "bmp32"); + } + else + { + return false; + } + + //texture->bpp = tga.header[4]; // Determine the bits per pixel + + + tga.Width = texture.Width; // Copy width into local structure + tga.Height = texture.Height; // Copy height into local structure + tga.Bpp = bitsPerPixel; // Copy BPP into local structure + + if((texture.Width <= 0) || (texture.Height <= 0)) // Make sure all information is valid + { + return false; // Return failed + } + + + tga.bytesPerPixel = (tga.Bpp / 8); // Compute the number of BYTES per pixel + + tga.imageSize = (tga.bytesPerPixel * tga.Width * tga.Height); // Compute the total amout ofmemory needed to store data + + texture.DataSize = tga.imageSize; + texture.Data = boost::shared_array(new char [texture.DataSize]); + + memcpy(&texture.Data[0], &fTGA[shift], texture.DataSize); + + + // Byte Swapping Optimized By Steve Thomas + for(GLuint cswap = 0; cswap < (int)tga.imageSize; cswap += tga.bytesPerPixel) + { + texture.Data[cswap] ^= texture.Data[cswap+2] ^= + texture.Data[cswap] ^= texture.Data[cswap+2]; + } + + return true; +} + + + + + +//bool LoadCompressedTGA(Texture * texture, char * filename, FILE * fTGA) // Load COMPRESSED TGAs +bool LoadCompressedTGA(TTextureData& texture, boost::shared_array fTGA) // Load COMPRESSED TGAs +{ + + TGA tga; + + int shift = sizeof(TGAHeader); + + memcpy(tga.header, &fTGA[shift], CONST_TGA_INNER_HEADER_SIZE); + + shift += CONST_TGA_INNER_HEADER_SIZE; + + + + texture.Width = tga.header[1] * 256 + tga.header[0]; // Determine The TGA Width (highbyte*256+lowbyte) + texture.Height = tga.header[3] * 256 + tga.header[2]; // Determine The TGA Height (highbyte*256+lowbyte) + + int bitsPerPixel = tga.header[4]; + + if (bitsPerPixel == 24) + { + strcpy(texture.Format, "bmp24"); + } + else if (bitsPerPixel == 32) + { + strcpy(texture.Format, "bmp32"); + } + else + { + return false; + } + + + tga.Width = texture.Width; // Copy width into local structure + tga.Height = texture.Height; // Copy height into local structure + tga.Bpp = bitsPerPixel; // Copy BPP into local structure + + + + + if((texture.Width <= 0) || (texture.Height <= 0)) //Make sure all texture info is ok + { + return false; // Return failed + } + + tga.bytesPerPixel = (tga.Bpp / 8); // Compute BYTES per pixel + tga.imageSize = (tga.bytesPerPixel * tga.Width * tga.Height); // Compute amout of memory needed to store image + + + texture.DataSize = tga.imageSize; + texture.Data = boost::shared_array(new char [texture.DataSize]); + + GLuint pixelcount = tga.Height * tga.Width; // Nuber of pixels in the image + GLuint currentpixel = 0; // Current pixel being read + GLuint currentbyte = 0; // Current byte + + //GLubyte* colorbuffer = (GLubyte *)malloc(tga.bytesPerPixel); // Storage for 1 pixel + + boost::shared_array colorbuffer(new GLubyte[tga.bytesPerPixel]); + + do + { + GLubyte chunkheader = 0; // Storage for "chunk" header + + + chunkheader = static_cast(fTGA[shift]); + shift += sizeof(GLubyte); + + if(chunkheader < 128) // If the ehader is < 128, it means the that is the number of RAW color packets minus 1 + { // that follow the header + chunkheader++; // add 1 to get number of following color values + for(short counter = 0; counter < chunkheader; counter++) // Read RAW color values + { + + memcpy(&colorbuffer[0], &fTGA[shift], tga.bytesPerPixel); + shift += tga.bytesPerPixel; + + texture.Data[currentbyte] = static_cast(colorbuffer[2]); + texture.Data[currentbyte + 1] = static_cast(colorbuffer[1]); + texture.Data[currentbyte + 2] = static_cast(colorbuffer[0]); + + if(tga.bytesPerPixel == 4) // if its a 32 bpp image + { + texture.Data[currentbyte + 3] = static_cast(colorbuffer[3]); + } + + currentbyte += tga.bytesPerPixel; // Increase thecurrent byte by the number of bytes per pixel + currentpixel++; // Increase current pixel by 1 + + if(currentpixel > pixelcount) // Make sure we havent read too many pixels + { + return false; // Return failed + } + } + } + else // chunkheader > 128 RLE data, next color reapeated chunkheader - 127 times + { + chunkheader -= 127; // Subteact 127 to get rid of the ID bit + + + memcpy(&colorbuffer[0], &fTGA[shift], tga.bytesPerPixel); + shift += tga.bytesPerPixel; + + + for(short counter = 0; counter < chunkheader; counter++) // copy the color into the image data as many times as dictated + { // by the header + + texture.Data[currentbyte] = static_cast(colorbuffer[2]); + texture.Data[currentbyte + 1] = static_cast(colorbuffer[1]); + texture.Data[currentbyte + 2] = static_cast(colorbuffer[0]); + + if(tga.bytesPerPixel == 4) // if its a 32 bpp image + { + texture.Data[currentbyte + 3] = static_cast(colorbuffer[3]); + } + + currentbyte += tga.bytesPerPixel; // Increase current byte by the number of bytes per pixel + currentpixel++; // Increase pixel count by 1 + + if(currentpixel > pixelcount) // Make sure we havent written too many pixels + { + return false; // Return failed + } + } + } + + } while(currentpixel < pixelcount); // Loop while there are still pixels left + + return true; // return success +} + + + +} //namespace SE \ No newline at end of file