📄 ddsreader.cpp
字号:
CLEANUPIFFAILED(res,CKBITMAPERROR_READERROR);
res= D3DXLoadSurfaceFromSurface(Surface,NULL,NULL,TextureSurface,NULL,NULL,D3DX_FILTER_NONE,0);
TextureSurface->Release();
TextureSurface = NULL;
CLEANUPIFFAILED(res,CKBITMAPERROR_READERROR);
}else{
Texture->GetSurfaceLevel(0,&Surface);
}
//--------- Copy bits from DX surface to our surface...
D3DLOCKED_RECT src;
res= Surface->LockRect(&src,NULL,D3DLOCK_READONLY);
CLEANUPIFFAILED(res,CKBITMAPERROR_READERROR);
//-------- Create the Image in virtools format
VxPixelFormat2ImageDesc(vpf,bp->m_Format);
bp->m_Format.Width = TextureDesc.Width;
bp->m_Format.Height = TextureDesc.Height;
bp->m_Format.BytesPerLine = TextureDesc.Width*(bp->m_Format.BitsPerPixel/8);
BYTE* memory = NULL;
if(bp->m_Format.BytesPerLine){
memory = new BYTE[ bp->m_Format.BytesPerLine * bp->m_Format.Height ];
}else{
memory = new BYTE[ src.Pitch/4 * bp->m_Format.Height ];
}
BYTE* Src = (BYTE *)src.pBits;
BYTE* Dst = memory;
bp->m_Data = memory;
if(bp->m_Format.BytesPerLine){
for (unsigned int i = 0; i< TextureDesc.Height; ++i,Src+=src.Pitch,Dst+=bp->m_Format.BytesPerLine) {
memcpy(Dst,Src,bp->m_Format.BytesPerLine);
}
}else{
memcpy(Dst,Src,src.Pitch/4 * bp->m_Format.Height);
}
Surface->UnlockRect();
Surface->Release();
Texture->Release();
return 0;
}
///------------------------------------------------------------
// Saving Functions
int DDS_Save(void** memptr,DDSBitmapProperties* bp)
{
LPDIRECT3DTEXTURE8 Texture = NULL;
LPDIRECT3DSURFACE8 Surface = NULL;
LPDIRECT3DSURFACE8 TextureSurface = NULL;
HRESULT res;
if(!g_Device){
CreateTemporaryDevice(&g_Device);
}
//--- Source format can only be a 32 bits image
// if (bp->m_Format.BitsPerPixel != 32) return 0;
D3DFORMAT fmt = VxPixelFormatToD3DFormat(VxImageDesc2PixelFormat(bp->m_Format));
//---- Create Source image surface
res = g_Device->CreateImageSurface(bp->m_Format.Width,bp->m_Format.Height,fmt,&Surface);
CLEANUPIFFAILED(res,0);
//--------- Copy bits from our surface to DX 32 bit surface
D3DLOCKED_RECT SrcLock;
res= Surface->LockRect(&SrcLock,NULL,0 );
CLEANUPIFFAILED(res,CKBITMAPERROR_READERROR);
BYTE* Src = (BYTE *)bp->m_Data;
BYTE* Dst = (BYTE*)SrcLock.pBits;
if(bp->m_Format.BytesPerLine){
for (unsigned int i = 0; i< bp->m_Format.Height; ++i,Src+=SrcLock.Pitch,Dst+=bp->m_Format.BytesPerLine) {
memcpy(Dst,Src,bp->m_Format.BytesPerLine);
}
}else{
memcpy(Dst,Src,SrcLock.Pitch/4 * bp->m_Format.Height);
}
Surface->UnlockRect();
if(bp->m_PixelFormat != fmt){
//---- Create destnation image surface
res = g_Device->CreateImageSurface(bp->m_Format.Width,bp->m_Format.Height,bp->m_PixelFormat,&TextureSurface);
CLEANUPIFFAILED(res,0);
//---- Convert formats
res= D3DXLoadSurfaceFromSurface(TextureSurface,NULL,NULL,Surface,NULL,NULL,D3DX_FILTER_NONE,0);
CLEANUPIFFAILED(res,CKBITMAPERROR_READERROR);
}else{
TextureSurface = Surface;
Surface->AddRef();
}
//---- And Save
D3DSURFACE_DESC Desc;
TextureSurface->GetDesc(&Desc);
//-- Prepare a big buffer to store the file
DWORD FileSize = 4 + sizeof(DDS_HEADER) + Desc.Size;
BYTE* FileData = new BYTE[FileSize];
//--------- Copy bits from DX surface to a DDS file buffer...
D3DLOCKED_RECT Dest;
res= TextureSurface->LockRect(&Dest,NULL,D3DLOCK_READONLY);
//memset(&FileData[4 + sizeof(DDS_HEADER)],0xFF,Desc.Size);
memcpy(&FileData[4 + sizeof(DDS_HEADER)],Dest.pBits,Desc.Size);
TextureSurface->UnlockRect();
//---- Release all Dx Objects...
Surface->Release();
TextureSurface->Release();
//------ Now write Header
DWORD MagicDword = MAKEFOURCC('D','D','S',' ');
DDS_HEADER Header;
memset(&Header,0,sizeof(Header));
BOOL Compressed = ((bp->m_PixelFormat == D3DFMT_DXT1) ||
(bp->m_PixelFormat == D3DFMT_DXT2) ||
(bp->m_PixelFormat == D3DFMT_DXT3) ||
(bp->m_PixelFormat == D3DFMT_DXT4) ||
(bp->m_PixelFormat == D3DFMT_DXT5));
Header.dwSize = 124;
Header.dwHeaderFlags = DDSD_CAPS|DDSD_PIXELFORMAT|DDSD_WIDTH|DDSD_HEIGHT;
if (Compressed) {
Header.dwHeaderFlags |= DDS_HEADER_FLAGS_LINEARSIZE;
} else {
Header.dwHeaderFlags |= DDS_HEADER_FLAGS_PITCH;
}
Header.dwHeight = bp->m_Format.Height;
Header.dwWidth = bp->m_Format.Width;
Header.dwPitchOrLinearSize = Compressed ? Desc.Size : Dest.Pitch;
Header.dwSurfaceFlags = DDSCAPS_TEXTURE;
//--- Pixel Format
Header.ddspf.dwSize = 32;
if (Compressed) {
Header.ddspf.dwFlags = DDPF_FOURCC;
Header.ddspf.dwFourCC = bp->m_PixelFormat;
} else {
switch ( bp->m_PixelFormat) {
case D3DFMT_R8G8B8:
case D3DFMT_R5G6B5:
case D3DFMT_R3G3B2:
Header.ddspf.dwFlags = DDS_RGB;
break;
default:
Header.ddspf.dwFlags = DDS_RGBA;
break;
}
VxImageDescEx TempFormat;
VxPixelFormat2ImageDesc(D3DFormatToVxPixelFormat(bp->m_PixelFormat),TempFormat);
Header.ddspf.dwRGBBitCount = TempFormat.BitsPerPixel;
Header.ddspf.dwRBitMask = TempFormat.RedMask;
Header.ddspf.dwGBitMask = TempFormat.GreenMask;
Header.ddspf.dwBBitMask = TempFormat.BlueMask;
Header.ddspf.dwABitMask = TempFormat.AlphaMask;
}
//----- And Write to buffer
memcpy(FileData,&MagicDword,sizeof(DWORD));
memcpy(&FileData[4],&Header,sizeof(Header));
//---- File ? or memory
if (*memptr == NULL) {
// Memory
*memptr = FileData;
} else{
// File
FILE* f = fopen((char*)*memptr,"wb");
if (!f) {
delete[] FileData;
return 0;
}
fwrite(FileData,FileSize,1,f);
fclose(f);
}
return FileSize;
}
///-----------------------------------------------
// Loading Functions
// Synchronous Reading from file or URL
int DDSReader::ReadFile(char* name,CKBitmapProperties** bp)
{
if (!name || !bp) return CKBITMAPERROR_GENERIC;
CKERROR ret=DDS_Read(name,0,&m_Properties);
*bp=&m_Properties;
return ret;
}
// Synchronous Reading from memory
int DDSReader::ReadMemory(void* memory,int size,CKBitmapProperties** bp)
{
if (!bp) return CKBITMAPERROR_GENERIC;
CKERROR ret=DDS_Read(memory,size,&m_Properties);
*bp=&m_Properties;
return ret;
}
///-----------------------------------------------
// Saving Functions
// Synchronous Reading from file or URL
int DDSReader::SaveFile(char* name,CKBitmapProperties* bp)
{
if (!name || !bp) return 0;
DDSBitmapProperties jbp;
if(bp->m_Size == jbp.m_Size) { // It's a Bmp Properties
memcpy(&jbp,bp,bp->m_Size);
} else {
memcpy(&jbp,bp,sizeof(CKBitmapProperties));
}
return DDS_Save((void**)&name,&jbp);
}
// Synchronous Reading from memory, return number of bytes written
int DDSReader::SaveMemory(void** memory,CKBitmapProperties* bp)
{
if (!memory || !bp) return 0;
DDSBitmapProperties jbp;
if(bp->m_Size == jbp.m_Size) { // It's a DDS Properties
memcpy(&jbp,bp,bp->m_Size);
} else {
memcpy(&jbp,bp,sizeof(CKBitmapProperties));
}
*memory=NULL;
return DDS_Save(memory,&jbp);
}
///-----------------------------------------------
// Image Properties
void DDSReader::SetBitmapDefaultProperties(CKBitmapProperties* bm)
{
if(bm->m_Size == m_Properties.m_Size) {
// It's a valid DDS Properties we can copy our properties
memcpy(&m_Properties,bm,bm->m_Size);
} else {
memcpy(&m_Properties,bm,sizeof(CKBitmapProperties));
}
}
void DDSReader::GetBitmapDefaultProperties(CKBitmapProperties** bm)
{
// We return the properties
*bm = &m_Properties;
}
//--------------------------------------------
// Cleaning
void DDSReader::ReleaseMemory(void* memory)
{
delete [] memory;
}
void DDSReader::Release()
{
delete this;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -