UTexture2D* ULRRTextureManager::GetTexture(FString path, bool alpha) {
	TArray<uint8> RawFileData;
	FFileHelper::LoadFileToArray(RawFileData, *path, 0);
	if (RawFileData.Num() != 0)
	{
		IImageWrapperModule& ImageWrapperModule = FModuleManager::LoadModuleChecked<IImageWrapperModule>(FName(TEXT("ImageWrapper")));
		// Note: PNG format.  Other formats are supported
		IImageWrapperPtr ImageWrapper = ImageWrapperModule.CreateImageWrapper(EImageFormat::BMP);
		if (ImageWrapper.IsValid() && ImageWrapper->SetCompressed(RawFileData.GetData(), RawFileData.Num()))
		{
			const TArray<uint8>* UncompressedBGRA = nullptr;
			TArray<uint8> UncompressedRGBA;
			if (ImageWrapper->GetRaw(ERGBFormat::BGRA, 8, UncompressedBGRA))
			{
				// Create the UTexture for rendering
				UncompressedRGBA.AddZeroed(UncompressedBGRA->Num());
				for (int i = 0; UncompressedBGRA->Num() > i; i += 4) {
					UncompressedRGBA[i] = (*UncompressedBGRA)[i + 2];
					UncompressedRGBA[i + 1] = (*UncompressedBGRA)[i + 1];
					UncompressedRGBA[i + 2] = (*UncompressedBGRA)[i];
					UncompressedRGBA[i + 3] = (*UncompressedBGRA)[i + 3];
					if (alpha) {
						if ((UncompressedRGBA[i] + UncompressedRGBA[i + 1] + UncompressedRGBA[i + 2]) < 3) {
							UncompressedRGBA[i + 3] = 0;
						}
					}
				}

				UTexture2D* MyTexture = UTexture2D::CreateTransient(ImageWrapper->GetWidth(), ImageWrapper->GetHeight(), PF_R8G8B8A8);

				// Fill in the source data from the file
				uint8* TextureData = (uint8*)MyTexture->PlatformData->Mips[0].BulkData.Lock(LOCK_READ_WRITE);
				FMemory::Memcpy(TextureData, UncompressedRGBA.GetData(), UncompressedRGBA.Num());
				MyTexture->PlatformData->Mips[0].BulkData.Unlock();

				// Update the rendering resource from data.
				MyTexture->UpdateResource();
				return MyTexture;
			}
		}
	}
	return nullptr;
}
TSharedPtr<FSlateDynamicImageBrush> FNewsFeedCache::RawDataToBrush( FName ResourceName, const TArray< uint8 >& InRawData ) const
{
	TSharedPtr<FSlateDynamicImageBrush> Brush;

	uint32 BytesPerPixel = 4;
	int32 Width = 0;
	int32 Height = 0;

	bool bSucceeded = false;
	TArray<uint8> DecodedImage;
	IImageWrapperModule& ImageWrapperModule = FModuleManager::LoadModuleChecked<IImageWrapperModule>(FName("ImageWrapper"));
	IImageWrapperPtr ImageWrapper = ImageWrapperModule.CreateImageWrapper( EImageFormat::PNG );

	if (ImageWrapper.IsValid() && ImageWrapper->SetCompressed(InRawData.GetData(), InRawData.Num()))
	{
		Width = ImageWrapper->GetWidth();
		Height = ImageWrapper->GetHeight();

		const TArray<uint8>* RawData = NULL;

		if (ImageWrapper->GetRaw( ERGBFormat::BGRA, 8, RawData))
		{
			DecodedImage.AddUninitialized( Width * Height * BytesPerPixel );
			DecodedImage = *RawData;
			bSucceeded = true;
		}
	}

	if (bSucceeded && FSlateApplication::Get().GetRenderer()->GenerateDynamicImageResource(ResourceName, ImageWrapper->GetWidth(), ImageWrapper->GetHeight(), DecodedImage))
	{
		Brush = MakeShareable(new FSlateDynamicImageBrush(ResourceName, FVector2D(ImageWrapper->GetWidth(), ImageWrapper->GetHeight())));
	}

	return Brush;
}
TSharedPtr< FSlateDynamicImageBrush > FEpicSurvey::LoadRawDataAsBrush( FName ResourceName, const TArray< uint8 >& RawData ) const
{
	TSharedPtr< FSlateDynamicImageBrush > Brush;

	uint32 BytesPerPixel = 4;
	int32 Width = 0;
	int32 Height = 0;

	bool bSucceeded = false;
	TArray<uint8> DecodedImage;
	IImageWrapperModule& ImageWrapperModule = FModuleManager::LoadModuleChecked<IImageWrapperModule>( FName("ImageWrapper") );
	IImageWrapperPtr ImageWrapper = ImageWrapperModule.CreateImageWrapper( EImageFormat::PNG );
	if ( ImageWrapper.IsValid() && ImageWrapper->SetCompressed( RawData.GetData(), RawData.Num() ) )
	{
		Width = ImageWrapper->GetWidth();
		Height = ImageWrapper->GetHeight();

		const TArray<uint8>* RawImageData = NULL;
		if (ImageWrapper->GetRaw(ERGBFormat::BGRA, 8, RawImageData))
		{
			DecodedImage.AddUninitialized( Width * Height * BytesPerPixel );
			DecodedImage = *RawImageData;
			bSucceeded = true;
		}
	}

	if ( bSucceeded )
	{
		Brush = FSlateDynamicImageBrush::CreateWithImageData( ResourceName, FVector2D(ImageWrapper->GetWidth(), ImageWrapper->GetHeight()), DecodedImage );
	}

	return Brush;
}
TSharedPtr<FSlateDynamicImageBrush> FContentSourceViewModel::CreateBrushFromRawData(FString ResourceNamePrefix, const TArray< uint8 >& RawData) const
{
	TSharedPtr< FSlateDynamicImageBrush > Brush;

	uint32 BytesPerPixel = 4;
	int32 Width = 0;
	int32 Height = 0;

	bool bSucceeded = false;
	TArray<uint8> DecodedImage;
	IImageWrapperModule& ImageWrapperModule = FModuleManager::LoadModuleChecked<IImageWrapperModule>(FName("ImageWrapper"));
	IImageWrapperPtr ImageWrapper = ImageWrapperModule.CreateImageWrapper(EImageFormat::PNG);
	if (ImageWrapper.IsValid() && (RawData.Num() > 0) && ImageWrapper->SetCompressed(RawData.GetData(), RawData.Num()))
	{
		Width = ImageWrapper->GetWidth();
		Height = ImageWrapper->GetHeight();

		const TArray<uint8>* RawImageData = NULL;
		if (ImageWrapper->GetRaw(ERGBFormat::BGRA, 8, RawImageData))
		{
			DecodedImage.AddUninitialized(Width * Height * BytesPerPixel);
			DecodedImage = *RawImageData;
			bSucceeded = true;
		}
	}

	if (bSucceeded)
	{
		FString UniqueResourceName = ResourceNamePrefix + "_" + FString::FromInt(ImageID++);
		Brush = FSlateDynamicImageBrush::CreateWithImageData(FName(*UniqueResourceName), FVector2D(ImageWrapper->GetWidth(), ImageWrapper->GetHeight()), DecodedImage);
	}

	return Brush;
}
uint8* FTextureSource::LockMip(int32 MipIndex)
{
	uint8* MipData = NULL;
	if (MipIndex < NumMips)
	{
		if (LockedMipData == NULL)
		{
			LockedMipData = (uint8*)BulkData.Lock(LOCK_READ_WRITE);
			if (bPNGCompressed)
			{
				bool bCanPngCompressFormat = (Format == TSF_G8 || Format == TSF_RGBA8 || Format == TSF_BGRA8 || Format == TSF_RGBA16);
				check(NumSlices == 1 && bCanPngCompressFormat);
				if (MipIndex != 0)
				{
					return NULL;
				}

				IImageWrapperModule& ImageWrapperModule = FModuleManager::LoadModuleChecked<IImageWrapperModule>( FName("ImageWrapper") );
				IImageWrapperPtr ImageWrapper = ImageWrapperModule.CreateImageWrapper( EImageFormat::PNG );
				if ( ImageWrapper.IsValid() && ImageWrapper->SetCompressed( LockedMipData, BulkData.GetBulkDataSize() ) )
				{
					check( ImageWrapper->GetWidth() == SizeX );
					check( ImageWrapper->GetHeight() == SizeY );
					const TArray<uint8>* RawData = NULL;
					// TODO: TSF_BGRA8 is stored as RGBA, so the R and B channels are swapped in the internal png. Should we fix this?
					ERGBFormat::Type RawFormat = (Format == TSF_G8) ? ERGBFormat::Gray : ERGBFormat::RGBA;
					if (ImageWrapper->GetRaw( RawFormat, Format == TSF_RGBA16 ? 16 : 8, RawData ))
					{
						if (RawData->Num() > 0)
						{
							LockedMipData = (uint8*)FMemory::Malloc(RawData->Num());
							// PVS-Studio does not understand that IImageWrapper::GetRaw's return value validates the pointer, so we disable
							// the warning that we are using the RawData pointer before checking for null:
							FMemory::Memcpy(LockedMipData, RawData->GetData(), RawData->Num()); //-V595
						}
					}
					if (RawData == NULL || RawData->Num() == 0)
					{
						UE_LOG(LogTexture, Warning, TEXT("PNG decompression of source art failed"));
					}
				}
				else
				{
					UE_LOG(LogTexture, Log, TEXT("Only pngs are supported"));
				}
			}
		}

		MipData = LockedMipData + CalcMipOffset(MipIndex);
		LockedMips |= (1 << MipIndex);
	}
	return MipData;
}
/** 
 * Loads a UTexture2D from a package and stores it in the cache
 *
 * @param TextureName	The name of the texture to load
 */
bool FSlateRHIResourceManager::LoadTexture( const FName& TextureName, const FString& ResourcePath, uint32& Width, uint32& Height, TArray<uint8>& DecodedImage )
{
	check( IsThreadSafeForSlateRendering() );

	bool bSucceeded = true;
	uint32 BytesPerPixel = 4;

	TArray<uint8> RawFileData;
	if( FFileHelper::LoadFileToArray( RawFileData, *ResourcePath ) )
	{
		IImageWrapperModule& ImageWrapperModule = FModuleManager::LoadModuleChecked<IImageWrapperModule>( FName("ImageWrapper") );
		IImageWrapperPtr ImageWrapper = ImageWrapperModule.CreateImageWrapper( EImageFormat::PNG );
		if ( ImageWrapper.IsValid() && ImageWrapper->SetCompressed( RawFileData.GetData(), RawFileData.Num() ) )
		{
			Width = ImageWrapper->GetWidth();
			Height = ImageWrapper->GetHeight();
			
			const TArray<uint8>* RawData = NULL;
			if (ImageWrapper->GetRaw( ERGBFormat::BGRA, 8, RawData))
			{
				DecodedImage.AddUninitialized( Width*Height*BytesPerPixel );
				DecodedImage = *RawData;
			}
			else
			{
				UE_LOG(LogSlate, Log, TEXT("Invalid texture format for Slate resource only RGBA and RGB pngs are supported: %s"), *TextureName.ToString() );
				bSucceeded = false;
			}
		}
		else
		{
			UE_LOG(LogSlate, Log, TEXT("Only pngs are supported in Slate"));
			bSucceeded = false;
		}
	}
	else
	{
		UE_LOG(LogSlate, Log, TEXT("Could not find file for Slate resource: %s"), *TextureName.ToString() );
		bSucceeded = false;
	}

	return bSucceeded;
}
bool FSlateD3DTextureManager::LoadTexture( const FSlateBrush& InBrush, uint32& OutWidth, uint32& OutHeight, TArray<uint8>& OutDecodedImage )
{
	FString ResourcePath = GetResourcePath( InBrush );

	uint32 BytesPerPixel = 4;
	bool bSucceeded = true;
	TArray<uint8> RawFileData;
	if( FFileHelper::LoadFileToArray( RawFileData, *ResourcePath ) )
	{
		IImageWrapperModule& ImageWrapperModule = FModuleManager::LoadModuleChecked<IImageWrapperModule>( FName("ImageWrapper") );
		IImageWrapperPtr ImageWrapper = ImageWrapperModule.CreateImageWrapper( EImageFormat::PNG );
		if ( ImageWrapper.IsValid() && ImageWrapper->SetCompressed( RawFileData.GetData(), RawFileData.Num() ) )
		{
			OutWidth = ImageWrapper->GetWidth();
			OutHeight = ImageWrapper->GetHeight();

			const TArray<uint8>* RawData = NULL;
			if (ImageWrapper->GetRaw(ERGBFormat::RGBA, 8, RawData) == false)
			{
				UE_LOG(LogSlateD3D, Log, TEXT("Invalid texture format for Slate resource only RGBA and RGB pngs are supported: %s"), *InBrush.GetResourceName().ToString() );
				bSucceeded = false;
			}
			else
			{
				OutDecodedImage = *RawData;
			}
		}
		else
		{
			UE_LOG(LogSlateD3D, Log, TEXT("Only pngs are supported in Slate"));
			bSucceeded = false;
		}
	}
	else
	{
		UE_LOG(LogSlateD3D, Log, TEXT("Could not find file for Slate resource: %s"), *InBrush.GetResourceName().ToString() );
		bSucceeded = false;
	}

	return bSucceeded;
}
void FSSTBatchCombinerModule::PluginButtonClicked()
{
	TArray<FString> OutFileNames;
	TArray<FString> OutFileNames2;
	FDesktopPlatformModule::Get()->OpenFileDialog(nullptr, "select First Image Files", "", "", "Image Files (*.png)|*.png", 1, OutFileNames);
	FDesktopPlatformModule::Get()->OpenFileDialog(nullptr, "select Second Image Files", "", "", "Image Files (*.png)|*.png", 1, OutFileNames2);
	
	if (OutFileNames.Num() && OutFileNames2.Num())
	{
		if (OutFileNames.Num() != OutFileNames2.Num())
		{
			FString DialogText = "Error! first set quantity does not match second set!";
			FMessageDialog::Open(EAppMsgType::Ok, FText::FromString(DialogText));
			return;
		}

		IImageWrapperModule& ImageWrapperModule = FModuleManager::LoadModuleChecked<IImageWrapperModule>(FName("ImageWrapper"));

		for (int32 i = 0; i < OutFileNames.Num(); i++)
		{
			TArray<uint8> RawFileData;
			TArray<uint8> RawFileData2;

			if (FFileHelper::LoadFileToArray(RawFileData, *OutFileNames[i]) && FFileHelper::LoadFileToArray(RawFileData2, *OutFileNames2[i]))
			{
				IImageWrapperPtr ImageWrapper = ImageWrapperModule.CreateImageWrapper(EImageFormat::PNG);
				IImageWrapperPtr ImageWrapper2 = ImageWrapperModule.CreateImageWrapper(EImageFormat::PNG);

				if (ImageWrapper.IsValid() && ImageWrapper->SetCompressed(RawFileData.GetData(), RawFileData.Num())
					&& ImageWrapper2.IsValid() && ImageWrapper2->SetCompressed(RawFileData2.GetData(), RawFileData2.Num()))
				{
					const TArray<uint8>* RawData = nullptr;
					const TArray<uint8>* RawData2 = nullptr;
					if (ImageWrapper->GetRaw(ERGBFormat::BGRA, ImageWrapper->GetBitDepth(), RawData)
						&& ImageWrapper2->GetRaw(ERGBFormat::BGRA, ImageWrapper2->GetBitDepth(), RawData2))
					{
						
						uint32 ImageWidth = ImageWrapper->GetWidth();
						uint32 ImageHeight = ImageWrapper->GetHeight();
						uint32 ImageWidth2 = ImageWrapper2->GetWidth();
						uint32 ImageHeight2 = ImageWrapper2->GetHeight();

						if ((ImageWidth != ImageWidth2) || (ImageHeight != ImageHeight2))
						{
							FString DialogText = "Error! Image dimensions do not match for frame " + FString::FromInt(i);
							FMessageDialog::Open(EAppMsgType::Ok, FText::FromString(DialogText));
							return;
						}

						TArray<uint8> newdata;
						newdata = *RawData;
						
						for (int32 a = 0; a < RawData->Num() - 4; a = a + 4)
						{
							newdata[a + 1] = (*RawData2)[a];
						}
						//save
						ImageWrapper->SetRaw(newdata.GetData(), newdata.GetAllocatedSize(), ImageWidth, ImageHeight, ERGBFormat::BGRA, 8);
						const TArray<uint8>& PNGData = ImageWrapper->GetCompressed(100);
						FFileHelper::SaveArrayToFile(PNGData, *OutFileNames[i]);
					} //if imagewrapper.getraw
				} //if imagewrapper.valid
			} //if load file
		}// for files loop
	} //if files
}
void ULandscapeEditorObject::RefreshImportLayersList()
{
	UTexture2D* ThumbnailWeightmap = LoadObject<UTexture2D>(NULL, TEXT("/Engine/EditorLandscapeResources/LandscapeThumbnailWeightmap.LandscapeThumbnailWeightmap"), NULL, LOAD_None, NULL);
	UTexture2D* ThumbnailHeightmap = LoadObject<UTexture2D>(NULL, TEXT("/Engine/EditorLandscapeResources/LandscapeThumbnailHeightmap.LandscapeThumbnailHeightmap"), NULL, LOAD_None, NULL);

	UMaterialInterface* Material = NewLandscape_Material.Get();
	TArray<FName> LayerNames = ALandscapeProxy::GetLayersFromMaterial(Material);

	const TArray<FLandscapeImportLayer> OldLayersList = MoveTemp(ImportLandscape_Layers);
	ImportLandscape_Layers.Reset(LayerNames.Num());

	for (int32 i = 0; i < LayerNames.Num(); i++)
	{
		const FName& LayerName = LayerNames[i];

		bool bFound = false;
		FLandscapeImportLayer NewImportLayer;
		for (int32 j = 0; j < OldLayersList.Num(); j++)
		{
			if (OldLayersList[j].LayerName == LayerName)
			{
				NewImportLayer = OldLayersList[j];
				bFound = true;
				break;
			}
		}

		if (bFound)
		{
			UMaterialInstanceConstant* CombinationMaterialInstance = CastChecked<UMaterialInstanceConstant>(NewImportLayer.ThumbnailMIC->Parent);
			if (CombinationMaterialInstance->Parent != Material)
			{
				CombinationMaterialInstance->SetParentEditorOnly(Material);
				//NewImportLayer.ThumbnailMIC = ALandscapeProxy::GetLayerThumbnailMIC(Material, LayerName, ThumbnailWeightmap, ThumbnailHeightmap, NULL);
			}

			NewImportLayer.ImportError = ELandscapeImportLayerError::None;
			if (!NewImportLayer.SourceFilePath.IsEmpty())
			{
				if (NewImportLayer.LayerInfo == NULL)
				{
					NewImportLayer.ImportError = ELandscapeImportLayerError::MissingLayerInfo;
				}
				else
				{
					if (NewImportLayer.SourceFilePath.EndsWith(".png"))
					{
						TArray<uint8> ImportData;
						if (!FFileHelper::LoadFileToArray(ImportData, *NewImportLayer.SourceFilePath, FILEREAD_Silent))
						{
							NewImportLayer.ImportError = ELandscapeImportLayerError::FileNotFound;
						}
						else
						{
							IImageWrapperModule& ImageWrapperModule = FModuleManager::LoadModuleChecked<IImageWrapperModule>("ImageWrapper");
							IImageWrapperPtr ImageWrapper = ImageWrapperModule.CreateImageWrapper(EImageFormat::PNG);

							if (!ImageWrapper->SetCompressed(ImportData.GetData(), ImportData.Num()))
							{
								NewImportLayer.ImportError = ELandscapeImportLayerError::CorruptFile;
							}
							else if (ImageWrapper->GetWidth() != ImportLandscape_Width || ImageWrapper->GetHeight() != ImportLandscape_Height)
							{
								NewImportLayer.ImportError = ELandscapeImportLayerError::FileSizeMismatch;
							}
							else if (ImageWrapper->GetFormat() != ERGBFormat::Gray)
							{
								NewImportLayer.ImportError = ELandscapeImportLayerError::ColorPng;
							}
						}
					}
					else
					{
						int64 ImportFileSize = IFileManager::Get().FileSize(*NewImportLayer.SourceFilePath);

						if (ImportFileSize < 0)
						{
							NewImportLayer.ImportError = ELandscapeImportLayerError::FileNotFound;
						}
						else if (ImportFileSize != ImportLandscape_Width * ImportLandscape_Height)
						{
							NewImportLayer.ImportError = ELandscapeImportLayerError::FileSizeMismatch;
						}
					}
				}
			}
		}
		else
		{
			NewImportLayer.LayerName = LayerName;
			NewImportLayer.ThumbnailMIC = ALandscapeProxy::GetLayerThumbnailMIC(Material, LayerName, ThumbnailWeightmap, ThumbnailHeightmap, NULL);
		}

		ImportLandscape_Layers.Add(MoveTemp(NewImportLayer));
	}
}
const TArray<uint16>& ULandscapeEditorObject::GetImportLandscapeData()
{
	if (ImportLandscape_HeightmapFilename.EndsWith(".png"))
	{
		if (ImportLandscape_Data.Num() == 0)
		{
			ImportLandscape_Data.Empty();

			TArray<uint8> ImportData;
			if (!FFileHelper::LoadFileToArray(ImportData, *ImportLandscape_HeightmapFilename, FILEREAD_Silent))
			{
				ImportLandscape_HeightmapError = ELandscapeImportHeightmapError::FileNotFound;
			}
			else
			{
				IImageWrapperModule& ImageWrapperModule = FModuleManager::LoadModuleChecked<IImageWrapperModule>("ImageWrapper");
				IImageWrapperPtr ImageWrapper = ImageWrapperModule.CreateImageWrapper(EImageFormat::PNG);

				const TArray<uint8>* RawData = NULL;
				if (ImageWrapper->SetCompressed(ImportData.GetData(), ImportData.Num()) &&
					ImageWrapper->GetWidth() == ImportLandscape_Width && ImageWrapper->GetHeight() == ImportLandscape_Height)
				{
					if (ImageWrapper->GetBitDepth() <= 8)
					{
						ImageWrapper->GetRaw(ERGBFormat::Gray, 8, RawData);

						if (ensure(RawData->Num() == ImportLandscape_Width * ImportLandscape_Height))
						{
							ImportLandscape_Data.Empty(ImportLandscape_Width * ImportLandscape_Height);
							ImportLandscape_Data.AddUninitialized(ImportLandscape_Width * ImportLandscape_Height);

							for (int32 i = 0; i < RawData->Num(); i++)
							{
								ImportLandscape_Data[i] = (*RawData)[i] * 0x101; // Expand to 16-bit
							}
						}
					}
					else
					{
						ImageWrapper->GetRaw(ERGBFormat::Gray, 16, RawData);

						if (ensure(RawData->Num() == ImportLandscape_Width * ImportLandscape_Height * 2))
						{
							ImportLandscape_Data.Empty(ImportLandscape_Width * ImportLandscape_Height);
							ImportLandscape_Data.AddUninitialized(ImportLandscape_Width * ImportLandscape_Height);
							FMemory::Memcpy(ImportLandscape_Data.GetData(), RawData->GetData(), RawData->Num());
						}
					}
				}
			}
		}
	}
	else
	{
		if (ImportLandscape_Width * ImportLandscape_Height != ImportLandscape_Data.Num())
		{
			ImportLandscape_Data.Empty();

			TArray<uint8> ImportData;
			if (ImportLandscape_Width > 0 && ImportLandscape_Height > 0 &&
				FFileHelper::LoadFileToArray(ImportData, *ImportLandscape_HeightmapFilename, FILEREAD_Silent) &&
				ImportData.Num() == ImportLandscape_Width * ImportLandscape_Height * 2)
			{
				ImportLandscape_Data.Empty(ImportLandscape_Width * ImportLandscape_Height);
				ImportLandscape_Data.AddUninitialized(ImportLandscape_Width * ImportLandscape_Height);
				FMemory::Memcpy(ImportLandscape_Data.GetData(), ImportData.GetData(), ImportData.Num());
			}
		}
	}

	return ImportLandscape_Data;
}
Exemple #11
0
bool FTextureSource::GetMipData(TArray<uint8>& OutMipData, int32 MipIndex)
{
	bool bSuccess = false;
	if (MipIndex < NumMips && BulkData.GetBulkDataSize() > 0)
	{
		void* RawSourceData = BulkData.Lock(LOCK_READ_ONLY);
		if (bPNGCompressed)
		{
			bool bCanPngCompressFormat = (Format == TSF_G8 || Format == TSF_RGBA8 || Format == TSF_BGRA8 || Format == TSF_RGBA16);
			if (MipIndex == 0 && NumSlices == 1 && bCanPngCompressFormat)
			{
				IImageWrapperModule& ImageWrapperModule = FModuleManager::LoadModuleChecked<IImageWrapperModule>( FName("ImageWrapper") );
				IImageWrapperPtr ImageWrapper = ImageWrapperModule.CreateImageWrapper( EImageFormat::PNG );
				if ( ImageWrapper.IsValid() && ImageWrapper->SetCompressed( RawSourceData, BulkData.GetBulkDataSize() ) )
				{
					if (ImageWrapper->GetWidth() == SizeX
						&& ImageWrapper->GetHeight() == SizeY)
					{
						const TArray<uint8>* RawData = NULL;
						// TODO: TSF_BGRA8 is stored as RGBA, so the R and B channels are swapped in the internal png. Should we fix this?
						ERGBFormat::Type RawFormat = (Format == TSF_G8) ? ERGBFormat::Gray : ERGBFormat::RGBA;
						if (ImageWrapper->GetRaw( RawFormat, Format == TSF_RGBA16 ? 16 : 8, RawData ))
						{
							OutMipData = *RawData;
							bSuccess = true;
						}
						else
						{
							UE_LOG(LogTexture, Warning, TEXT("PNG decompression of source art failed"));
							OutMipData.Empty();
						}
					}
					else
					{
						UE_LOG(LogTexture, Warning,
							TEXT("PNG decompression of source art failed. ")
							TEXT("Source image should be %dx%d but is %dx%d"),
							SizeX, SizeY,
							ImageWrapper->GetWidth(), ImageWrapper->GetHeight()
							);
					}
				}
				else
				{
					UE_LOG(LogTexture, Log, TEXT("Only pngs are supported"));
				}
			}
		}
		else
		{
			int32 MipOffset = CalcMipOffset(MipIndex);
			int32 MipSize = CalcMipSize(MipIndex);
			if (BulkData.GetBulkDataSize() >= MipOffset + MipSize)
			{
				OutMipData.Empty(MipSize);
				OutMipData.AddUninitialized(MipSize);
				FMemory::Memcpy(
					OutMipData.GetTypedData(),
					(uint8*)RawSourceData + MipOffset,
					MipSize
					);
			}
			bSuccess = true;
		}
		BulkData.Unlock();
	}
	return bSuccess;
}