📄 bdi.cpp
字号:
#include "BDI.h"
#include "GScreen.h"
#include "GFileLoader.h"
#include "Compress.h"
unsigned char GBDI::BDI_AlphaBlendTable[16][256][256]; //16级Alpha混合表
unsigned char GBDI::BDI_AdditiveTable[256][256]; //Additive表
unsigned char GBDI::BDI_SubTable[256][256];
unsigned char GBDI::BDI_GrayTable[256]; //灰度表
unsigned char FindBestMatch(unsigned short vVal)
{
int r=GET16Bit565_R(vVal);
int g=GET16Bit565_G(vVal);
int b=GET16Bit565_B(vVal);
int best=0xffff;
unsigned char index=0;
for(int i=0;i<256;i++)
{
unsigned short pal=i|(i<<8);
int resr=(GET16Bit565_R(pal)-r);
int resg=(GET16Bit565_G(pal)-g);
int resb=(GET16Bit565_B(pal)-b);
int res=resr*resr+resg*resg+resb*resb;
if(res<best)
{
index=i;
best=res;
}
}
return index;
}
void GBDI::SaveBDITable(const string & strFile)
{
FILE*fp=fopen(strFile.data(),"wb");
if(!fp)
return;
fwrite(BDI_AlphaBlendTable,sizeof(BDI_AlphaBlendTable),1,fp);
fwrite(BDI_AdditiveTable,sizeof(BDI_AdditiveTable),1,fp);
fwrite(BDI_SubTable,sizeof(BDI_SubTable),1,fp);
fwrite(BDI_GrayTable,sizeof(BDI_GrayTable),1,fp);
fclose(fp);
return;
}
void GBDI::LoadBDITable(GFileLoader*pFileLoader,const string & strFile)
{
GFileData fd;
if(!pFileLoader || !pFileLoader->LoadFile(strFile,fd))
{
goto DefaultInit;
}
else
{
char*pData=fd.GetData();
try
{
memcpy(BDI_AlphaBlendTable,pData,sizeof(BDI_AlphaBlendTable));
pData+=sizeof(BDI_AlphaBlendTable);
memcpy(BDI_AdditiveTable,pData,sizeof(BDI_AdditiveTable));
pData+=sizeof(BDI_AdditiveTable);
memcpy(BDI_SubTable,pData,sizeof(BDI_SubTable));
pData+=sizeof(BDI_SubTable);
memcpy(BDI_GrayTable,pData,sizeof(BDI_GrayTable));
}
catch(...)
{
goto DefaultInit;
}
return;
}
DefaultInit:
InitAlphaBlendTable();
InitAdditiveTable();
InitSubTable();
InitGrayTable();
}
void GBDI::InitAlphaBlendTable()
{
for(int i=0;i<16;i++)
{
for(int j=0;j<256;j++)
{
for(int k=0;k<256;k++)
{
unsigned long dwSour=j|(j<<8);
unsigned long dwDest=k|(k<<8);
dwDest=(dwDest<<16)|(dwDest);
dwSour=(dwSour<<16)|(dwSour);
dwDest&=0x07e0f81f;
dwSour&=0x07e0f81f;
unsigned long value=(dwDest*(16-i)+dwSour*i)>>4;
value&=0x07e0f81f;
value|=(value>>16);
BDI_AlphaBlendTable[i][j][k]=FindBestMatch((unsigned short)value);
}
}
}
}
void GBDI::InitAdditiveTable()
{
for(int i=0;i<256;i++)
{
for(int j=0;j<256;j++)
{
unsigned long dwSour=i|(i<<8);
unsigned long dwDest=j|(j<<8);
unsigned short redSour=GET16Bit565_R(dwSour);
unsigned short greenSour=GET16Bit565_G(dwSour);
unsigned short blueSour=GET16Bit565_B(dwSour);
unsigned short redDest=GET16Bit565_R(dwDest);
unsigned short greenDest=GET16Bit565_G(dwDest);
unsigned short blueDest=GET16Bit565_B(dwDest);
unsigned short Red=redSour+redDest;
unsigned short Green=greenSour+greenDest;
unsigned short Blue=blueSour+blueDest;
if(Red>255)
Red=255;
if(Green>255)
Green=255;
if(Blue>255)
Blue=255;
BDI_AdditiveTable[i][j]=FindBestMatch(RGBTo16Bit565(Red,Green,Blue));
}
}
}
void GBDI::InitSubTable()
{
for(int i=0;i<256;i++)
{
for(int j=0;j<256;j++)
{
unsigned long dwSour=i|(i<<8);
unsigned long dwDest=j|(j<<8);
unsigned short redSour=GET16Bit565_R(dwSour);
unsigned short greenSour=GET16Bit565_G(dwSour);
unsigned short blueSour=GET16Bit565_B(dwSour);
unsigned short redDest=GET16Bit565_R(dwDest);
unsigned short greenDest=GET16Bit565_G(dwDest);
unsigned short blueDest=GET16Bit565_B(dwDest);
short Red=redSour-redDest;
short Green=greenSour-greenDest;
short Blue=blueSour-blueDest;
if(Red<0)
Red=0;
if(Green<0)
Green=0;
if(Blue<0)
Blue=0;
BDI_SubTable[i][j]=FindBestMatch(RGBTo16Bit565(Red,Green,Blue));
}
}
}
void GBDI::InitGrayTable()
{
for(int i=0;i<256;i++)
{
unsigned long dwSour=i|(i<<8);
unsigned short redSour=GET16Bit565_R(dwSour);
unsigned short greenSour=GET16Bit565_G(dwSour);
unsigned short blueSour=GET16Bit565_B(dwSour);
unsigned short gray=(redSour*3+greenSour*6+blueSour)/10;
BDI_GrayTable[i]=FindBestMatch(RGBTo16Bit565(gray,gray,gray));
}
}
void GBDI::SetShowArea(const RECT*pRect)
{
if(pRect)
{
m_rtShowArea=*pRect;
if(m_rtShowArea.left<0)
m_rtShowArea.left=0;
if(m_rtShowArea.top<0)
m_rtShowArea.top=0;
if(m_rtShowArea.right>m_nWidth)
m_rtShowArea.right=m_nWidth;
if(m_rtShowArea.bottom>m_nHeight)
m_rtShowArea.bottom=m_nHeight;
}
else
{
SetRect(&m_rtShowArea,0,0,m_nWidth,m_nHeight);
}
}
void GBDI::Grayed()
{
int nSize=m_nWidth*m_nHeight;
for(register int i=0;i<nSize;i++)
{
m_pData[i]=BDI_GrayTable[m_pData[i]];
}
}
void GBDI::DrawToScreenNoColorKey(unsigned char*pBufDest,int nDestWidth,unsigned char*pBufSour,
int nLine,int nRow)
{
if(nLine>0)
{
for(register int i=0;i<nRow;i++)
{
memcpy(pBufDest,pBufSour,nLine);
pBufDest+=nDestWidth;
pBufSour+=m_nWidth;
}
}
}
void GBDI::DrawToScreenSrcColorKey(unsigned char*pBufDest,int nDestWidth,unsigned char*pBufSour,int nLine,int nRow)
{
unsigned char*pDestAddr=pBufDest;
unsigned char*pSourAddr=pBufSour;
for(register int i=0;i<nRow;i++)
{
for(register int j=0;j<nLine;j++)
{
if(*pSourAddr!=m_byColorKeyIndex)
{
*pDestAddr=*pSourAddr;
}
pDestAddr++;
pSourAddr++;
}
pBufDest+=nDestWidth;
pBufSour+=m_nWidth;
pDestAddr=pBufDest;
pSourAddr=pBufSour;
}
}
void GBDI::DrawToScreenDestColorKey(unsigned char*pBufDest,int nDestWidth,unsigned char*pBufSour,int nLine,int nRow,unsigned char byDestColorKey)
{
unsigned char*pDestAddr=pBufDest;
unsigned char*pSourAddr=pBufSour;
for(register int i=0;i<nRow;i++)
{
for(register int j=0;j<nLine;j++)
{
if(*pDestAddr != byDestColorKey)
{
*pDestAddr=*pSourAddr;
}
pDestAddr++;
pSourAddr++;
}
pBufDest+=nDestWidth;
pBufSour+=m_nWidth;
pDestAddr=pBufDest;
pSourAddr=pBufSour;
}
}
void GBDI::DrawToScreenAlphaNoColorKey(unsigned char*pBufDest,int nDestWidth,unsigned char*pBufSour,int nLine,int nRow,int nAlpha)
{
unsigned char*pDestAddr=pBufDest;
unsigned char*pSourAddr=pBufSour;
for(register int i=0;i<nRow;i++)
{
for(register int j=0;j<nLine;j++)
{
*pDestAddr=GBDI::BDI_AlphaBlendTable[nAlpha][*pSourAddr][*pDestAddr];
pDestAddr++;
pSourAddr++;
}
pBufDest+=nDestWidth;
pBufSour+=m_nWidth;
pDestAddr=pBufDest;
pSourAddr=pBufSour;
}
}
void GBDI::DrawToScreenAlphaSrcColorKey(unsigned char*pBufDest,int nDestWidth,unsigned char*pBufSour,int nLine,int nRow,int nAlpha)
{
unsigned char*pDestAddr=pBufDest;
unsigned char*pSourAddr=pBufSour;
for(register int i=0;i<nRow;i++)
{
for(register int j=0;j<nLine;j++)
{
if(*pSourAddr != m_byColorKeyIndex)
{
*pDestAddr=GBDI::BDI_AlphaBlendTable[nAlpha][*pSourAddr][*pDestAddr];
}
pDestAddr++;
pSourAddr++;
}
pBufDest+=nDestWidth;
pBufSour+=m_nWidth;
pDestAddr=pBufDest;
pSourAddr=pBufSour;
}
}
void GBDI::DrawToScreenAlphaDestColorKey(unsigned char*pBufDest,int nDestWidth,unsigned char*pBufSour,int nLine,int nRow,int nAlpha,unsigned char byDestColorKey)
{
unsigned char*pDestAddr=pBufDest;
unsigned char*pSourAddr=pBufSour;
for(register int i=0;i<nRow;i++)
{
for(register int j=0;j<nLine;j++)
{
if(*pDestAddr != byDestColorKey)
{
*pDestAddr=GBDI::BDI_AlphaBlendTable[nAlpha][*pSourAddr][*pDestAddr];
}
pDestAddr++;
pSourAddr++;
}
pBufDest+=nDestWidth;
pBufSour+=m_nWidth;
pDestAddr=pBufDest;
pSourAddr=pBufSour;
}
}
void GBDI::DrawToScreenGrayNoColorKey(unsigned char*pBufDest,int nDestWidth,unsigned char*pBufSour,int nLine,int nRow)
{
unsigned char*pDestAddr=pBufDest;
unsigned char*pSourAddr=pBufSour;
for(register int i=0;i<nRow;i++)
{
for(register int j=0;j<nLine;j++)
{
*pDestAddr=GBDI::BDI_GrayTable[*pSourAddr];
pDestAddr++;
pSourAddr++;
}
pBufDest+=nDestWidth;
pBufSour+=m_nWidth;
pDestAddr=pBufDest;
pSourAddr=pBufSour;
}
}
void GBDI::DrawToScreenGraySrcColorKey(unsigned char*pBufDest,int nDestWidth,unsigned char*pBufSour,int nLine,int nRow)
{
unsigned char*pDestAddr=pBufDest;
unsigned char*pSourAddr=pBufSour;
for(register int i=0;i<nRow;i++)
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -