diff --git a/BeefTools/ImgCreate/ImgCreate.cpp b/BeefTools/ImgCreate/ImgCreate.cpp index 3ad9e72f..2eb05ea3 100644 --- a/BeefTools/ImgCreate/ImgCreate.cpp +++ b/BeefTools/ImgCreate/ImgCreate.cpp @@ -159,13 +159,39 @@ int main() layerIndices.insert(layerIndices.begin(), layerIdx); } - imageData = reader.MergeLayers(NULL, layerIndices, NULL); + imageData = reader.ReadImageData(); + if (imageData == NULL) + { + ImageData* rawImageData = reader.MergeLayers(NULL, layerIndices, NULL);; + if ((rawImageData->mX == 0) && (rawImageData->mY == 0) && + (rawImageData->mWidth == reader.mWidth) && + (rawImageData->mHeight == reader.mHeight)) + { + imageData = rawImageData; + } + else + { + imageData = new ImageData(); + imageData->CreateNew(reader.mWidth, reader.mHeight); + imageData->CopyFrom(rawImageData, 0, 0); + delete rawImageData; + } + } +// else +// { +// PNGData pngData; +// pngData.mWidth = imageData->mWidth; +// pngData.mHeight = imageData->mHeight; +// pngData.mBits = imageData->mBits; +// pngData.WriteToFile("c:\\temp\\test.png"); +// pngData.mBits = NULL; +// } } } int numCols = baseWidth / 20; int numRows = baseHeight / 20; - + auto _HasImage = [&](int col, int row, int pass, int size) { int scale = 1 << size; @@ -267,7 +293,7 @@ int main() for (int row = 0; row < numRows; row++) { for (int col = 0; col < numCols; col++) - { + { int srcPass = 0; int srcSize = size; diff --git a/BeefySysLib/img/ImageData.cpp b/BeefySysLib/img/ImageData.cpp index 7b5800bd..879b93b3 100644 --- a/BeefySysLib/img/ImageData.cpp +++ b/BeefySysLib/img/ImageData.cpp @@ -61,6 +61,26 @@ void ImageData::CreateNew(int width, int height, bool clear) memset(mBits, 0, mWidth*mHeight*sizeof(uint32)); } +void ImageData::CopyFrom(ImageData* img, int x, int y) +{ + int destStartX = BF_MAX(x + img->mX - mX, 0); + int destStartY = BF_MAX(y + img->mY - mY, 0); + + int destEndX = BF_MIN(x + img->mX - mX + img->mWidth, mWidth); + int destEndY = BF_MIN(y + img->mY - mY + img->mHeight, mHeight); + + int srcXOfs = -x - img->mX; + int srcYOfs = -y - img->mY; + + for (int y = destStartY; y < destEndY; y++) + { + for (int x = destStartX; x < destEndX; x++) + { + mBits[x + y * mWidth] = img->mBits[(x + srcXOfs) + (y + srcYOfs)*img->mWidth]; + } + } +} + void ImageData::Fill(uint32 color) { int size = mWidth*mHeight; diff --git a/BeefySysLib/img/ImageData.h b/BeefySysLib/img/ImageData.h index 38853b88..1662cf1f 100644 --- a/BeefySysLib/img/ImageData.h +++ b/BeefySysLib/img/ImageData.h @@ -39,9 +39,10 @@ public: void SwapRAndB(); void CreateNew(int x, int y, int width, int height, bool clear = true); void CreateNew(int width, int height, bool clear = true); + void CopyFrom(ImageData* img, int x, int y); void Fill(uint32 color); virtual ImageData* Duplicate(); - void SetSrcData(uint8* data, int dataLen); + void SetSrcData(uint8* data, int dataLen); virtual bool LoadFromFile(const StringImpl& path); virtual bool ReadData() { return false; } virtual void PremultiplyAlpha(); diff --git a/BeefySysLib/img/PSDReader.cpp b/BeefySysLib/img/PSDReader.cpp index 5c08ab4f..fddcf59d 100644 --- a/BeefySysLib/img/PSDReader.cpp +++ b/BeefySysLib/img/PSDReader.cpp @@ -172,6 +172,7 @@ PSDReader::PSDReader() mFS = NULL; mGlobalAltitude = 0; mGlobalAngle = 30; + mImageDataSectStart = -1; } PSDReader::~PSDReader() @@ -1398,9 +1399,100 @@ bool PSDReader::Init(const StringImpl& fileName) mFS->SetPos(startPos + layerAndMaskLen); pos = mFS->GetPos(); + mImageDataSectStart = mFS->GetPos(); + return true; } +ImageData* PSDReader::ReadImageData() +{ + mFS->SetPos(mImageDataSectStart); + + int compression = mFS->ReadInt16(); + if ((compression != 0) && (compression != 1)) + return NULL; + + ImageData* imageData = new ImageData(); + imageData->CreateNew(mWidth, mHeight); + if (mChannels < 4) + imageData->Fill(0xFF000000); + + int16** rowLengths = NULL; + int horz = mWidth; + int vert = mHeight; + int aSize = horz*vert; + + if (compression == 1) + { + rowLengths = new int16*[mChannels]; + for (int channel = 0; channel < mChannels; channel++) + { + rowLengths[channel] = new int16[vert]; + for (int aY = 0; aY < vert; aY++) + rowLengths[channel][aY] = mFS->ReadInt16(); + } + } + + for (int channel = 0; channel < mChannels; channel++) + { + int shift = channel * 8; + // if (channel == mC + 1) + // shift = 24; + + if (channel == 4) + break; + + if (compression == 0) + { + for (int pos = 0; pos < aSize; pos++) + imageData->mBits[pos] |= ((uint32)(uint8)mFS->ReadInt8()) << shift; + } + else + { + for (int aY = 0; aY < vert; aY++) + { + int pos = aY * horz; + int readSize = rowLengths[channel][aY]; + + while (readSize > 0) + { + int chunkSize = mFS->ReadInt8(); + readSize--; + if (chunkSize >= 0) + { + // String of literal data + chunkSize++; + readSize -= chunkSize; + while (chunkSize > 0) + { + imageData->mBits[pos++] |= ((uint32)(uint8)mFS->ReadInt8()) << shift; + chunkSize--; + } + } + else if (chunkSize > -128) + { + // One byte repeated + chunkSize = 1 - chunkSize; + uint32 aData = ((uint32)(uint8)mFS->ReadInt8()) << shift; + readSize--; + while (chunkSize > 0) + { + imageData->mBits[pos++] |= aData; + chunkSize--; + } + } + } + } + } + } + if (rowLengths != NULL) + { + for (int i = 0; i < mChannels; i++) + delete rowLengths[i]; + } + return imageData; +} + Texture* PSDReader::LoadLayerTexture(int layerIdx, int* ofsX, int* ofsY) // -1 = composited image { if ((layerIdx < 0) || (layerIdx >= (int) mPSDLayerInfoVector.size())) diff --git a/BeefySysLib/img/PSDReader.h b/BeefySysLib/img/PSDReader.h index d5864a20..83605c28 100644 --- a/BeefySysLib/img/PSDReader.h +++ b/BeefySysLib/img/PSDReader.h @@ -191,12 +191,13 @@ public: int mGlobalAltitude; int mChannels; + int mImageDataSectStart; PSDLayerInfoVector mPSDLayerInfoVector; PSDPatternMap mPSDPatternMap; public: - String ReadIdString(); + String ReadIdString(); void ReadPSDValue(PSDValue* value); void ReadPSDDescriptor(PSDDescriptor* descriptor); void ReadEffectColor(PSDDescriptor* colorDesc, uint32* color); @@ -215,6 +216,7 @@ public: bool Init(const StringImpl& fileName); + ImageData* ReadImageData(); Texture* LoadLayerTexture(int layerIdx, int* ofsX, int* ofsY); // -1 = composited image ImageData* MergeLayers(PSDLayerInfo* group, const std::vector& layerIndices, ImageData* bottomImage); Texture* LoadMergedLayerTexture(const std::vector& layerIndices, int* ofsX, int* ofsY); diff --git a/IDE/dist/images/ImgCreate.exe b/IDE/dist/images/ImgCreate.exe index f348bddd..925bbfda 100644 Binary files a/IDE/dist/images/ImgCreate.exe and b/IDE/dist/images/ImgCreate.exe differ