|
만들어 봤습니다.^^
void fill_buffer_1(byte*s,byte*d,int*index,int size)
{
for(int i=0;i<size;i++)d[i]=s[index[i]];
}
void fill_buffer_2(byte*s,byte*d,int*index,int size)
{
for(int i=0;i<size;i++){
d[i*2+0]=s[index[i]*2+0];
d[i*2+1]=s[index[i]*2+1];
}
}
void fill_buffer_3(byte*s,byte*d,int*index,int size)
{
for(int i=0;i<size;i++){
d[i*3+0]=s[index[i]*3+0];
d[i*3+1]=s[index[i]*3+1];
d[i*3+2]=s[index[i]*3+2];
}
}
void make_index(int s_size,int d_size,int*d_index)
{
int*temp=new int[s_size];
for(int i=0;i<s_size;i++)temp[i]=i;
for(int i=0;i<d_size;i++)d_index[i]=temp[(int)(s_size*i/d_size)];
delete[] temp;
}
void stretch_copy(byte*src,int s_width,int s_height,byte*dest,int d_width,int d_height,int
byte_per_pixel)
{
int*x_index=new int[d_width];
int*y_index=new int[d_height];
make_index(s_width,d_width,x_index);
make_index(s_height,d_height,y_index);
void (*fill_buffer)(byte*,byte*,int*,int);
switch(byte_per_pixel){
case 1:fill_buffer=fill_buffer_1;break;
case 2:fill_buffer=fill_buffer_2;break;
case 3:fill_buffer=fill_buffer_3;break;
}
for(int j=0;j<d_height;j++){
fill_buffer(src+y_index[j]*s_width*byte_per_pixel,
dest+j*d_width*byte_per_pixel, x_index,d_width);
}
delete[] x_index;
delete[] y_index;
}
void __fastcall TForm1::Button1Click(TObject *Sender)
{
//stretch_copy 를 확인하기 위한 부분
Graphics::TBitmap*a=new Graphics::TBitmap();
// a->LoadFromFile("c:\\a24.bmp"); //24bit
a->LoadFromFile("c:\\a.bmp"); //8bit
Canvas->Draw(0,0,a);
int bpp;
switch(a->PixelFormat){
case pf8bit:bpp=1;break;
case pf16bit:bpp=2;break;
case pf24bit:bpp=3;break;
}
byte*src=new byte[a->Width*a->Height*bpp];
for(int i=0;i<a->Height;i++){
CopyMemory(src+a->Width*i*bpp,a->ScanLine[a->Height-1-i],a->Width*bpp);
}
int new_x_size=320;
int new_y_size=258;
byte*dest=new byte[new_x_size*new_y_size*bpp];
stretch_copy(src,a->Width,a->Height,dest,new_x_size,new_y_size,bpp);
LPBITMAPINFO bmpi=(LPBITMAPINFO)new byte[sizeof(BITMAPINFO)+256*sizeof(RGBQUAD)];
ZeroMemory(bmpi, sizeof(BITMAPINFO));
bmpi->bmiHeader.biSize=sizeof(BITMAPINFOHEADER);
bmpi->bmiHeader.biPlanes=1;
bmpi->bmiHeader.biWidth=new_x_size;
bmpi->bmiHeader.biHeight=new_y_size;
bmpi->bmiHeader.biBitCount=bpp*8;
bmpi->bmiHeader.biSizeImage=bmpi->bmiHeader.biWidth*bmpi->bmiHeader.biHeight
*bmpi->bmiHeader.biBitCount/8;
if(bpp==1){
bmpi->bmiHeader.biClrUsed=256;
bmpi->bmiHeader.biClrImportant=256;
for(int i=0;i<256;i++){
PALETTEENTRY p;
GetPaletteEntries(a->Palette,i,1,&p);
bmpi->bmiColors[i].rgbRed = p.peRed;
bmpi->bmiColors[i].rgbBlue = p.peBlue;
bmpi->bmiColors[i].rgbGreen = p.peGreen;
bmpi->bmiColors[i].rgbReserved = p.peFlags;
}
}
SetDIBitsToDevice(Canvas->Handle,
200,200,bmpi->bmiHeader.biWidth,bmpi->bmiHeader.biHeight,
0,0,0,bmpi->bmiHeader.biHeight,dest,bmpi,DIB_RGB_COLORS);
delete[] src;
delete[] dest;
delete a;
}
^^
김인구.구야 님이 쓰신 글 :
: (Tubo-C/Borland C++채널에서 질문했던 내용입니다.)
:
: 비트맵을 축소/확대 해볼려고 합니다.
: API함수(StretchDIBits)를 이용하지 않고 만들어 볼려고합니다.
: 현재 비트맵파일을 DIB구조에 따라 읽는데 까지 한 상태입니다.
: 래스터 데이타를 요리하고 헤더를 수정해서 WriteFile하면 될꺼 같습니다만
: 래스터 데이타를 어떻게 요리해야할지 막막한 상태입니다...
: StretchDIBits함수는 어떤 알고리즘으로 축소/확대를 하는지 궁금합니다.
: 제가 알고리즘을 만든다는건 불가능할꺼 같기도 하고...
: 일단 StretchDIBits가 하는 방식으로 구현을 해볼려고 합니다.
: 직접 알고리즘을 만들어 보신분들의 조언을 구합니다.
: 이런 알고리즘을 생각할때
: 어디서 어떻게 시작을 해야하고 어떻게 생각을 해야하는지요...
: 당장 생각으론 제 수학 실력으론 불가능할꺼 같기도 합니다만...
|