把Bitmap转换成AVI(不过是C++源程序):WRITEAVI.C
#define  STRICT  #define  INC_OLE2  #include <windows.h>  #include <windowsx.h>  #include <memory.h> 
#include <mmsystem.h>  #include <vfw.h>   #include "writeavi.h" 
//--------------------------------------------------------------------------- 
// Defines 
//--------------------------------------------------------------------------- 
// Our movie is 160x120 and 15 frames long 
// #define BITMAP_X160    #define BITMAP_Y120    #define N_FRAMES15   #define TEXT_HEIGHT20  
#define AVIIF_KEYFRAME0x00000010L // this frame is a key frame.    #define BUFSIZE 260  
#define LPLPBILPBITMAPINFOHEADER *  
//--------------------------------------------------------------------------- 
// Function declarations 
//--------------------------------------------------------------------------- 
static void FreeFrames(LPLPBI) ; 
static void MakeFrames(LPLPBI, UINT, UINT, UINT) ; 
static HANDLE MakeDib(HBITMAP, UINT);  
//--------------------------------------------------------------------------- 
// A quick lookup table for Sin and Cos values 
//--------------------------------------------------------------------------- // 
static int aSin[N_FRAMES] = { 0, 40, 74, 95, 99, 86, 58, 20, -20, -58, -86, -99, -95, -74, -40, } ;  
static int aCos[N_FRAMES] = { 100, 91, 66, 30, -10, -49, -80, -97, -97, -80, -50,-10,30,  66, 91, } ;  
//---------------------------------------------------------------------------- // 
// We don't have a window, we just pop up a dialog // box, write the file, and quit // 
int PASCAL WinMain( 
HINSTANCE hInstance, 
HINSTANCE hPrevInstance, 
LPSTR szCmdLine, 
int sw) 

LPBITMAPINFOHEADER alpbi[N_FRAMES]; 
int i; 
AVISTREAMINFO strhdr; 
PAVIFILE pfile = NULL; 
PAVISTREAM ps = NULL, psCompressed = NULL, psText = NULL; 
char szText[BUFSIZE]; 
int iLen; 
AVICOMPRESSOPTIONS opts; 
AVICOMPRESSOPTIONS FAR * aopts[1] = {&opts}; 
HRESULT hr; 
DWORD dwTextFormat; 
WORD wVer; 
char szTitle[BUFSIZE]; 
char szMessage[BUFSIZE];  
/* first let's make sure we are running on 1.1 */ 
wVer = HIWORD(VideoForWindowsVersion()); 
if (wVer < 0x010a){ 
 /* oops, we are too old, blow out of here */ 
LoadString(hInstance, IDS_APPERR, szTitle, BUFSIZE ); 
LoadString(hInstance, IDS_VFWTOOOLD, szMessage, BUFSIZE ); 
MessageBeep(MB_ICONHAND); 
MessageBox(NULL, szMessage, szTitle, MB_OK|MB_ICONSTOP); 
return FALSE; 
}  
alpbi[0] = NULL;  
LoadString(hInstance, IDS_APPNAME, szTitle, BUFSIZE ); 
LoadString(hInstance, IDS_INTRO, szMessage, BUFSIZE );  
if (MessageBox(NULL, szMessage, szTitle, MB_OKCANCEL) == IDCANCEL) 
return 0;  
//  Set up the bitmaps for the file in an array  
MakeFrames(alpbi, 8, BITMAP_X, BITMAP_Y);  
AVIFileInit();  
// Open the movie file for writing....  
LoadString(hInstance, IDS_FILENAME, szTitle, BUFSIZE );  
hr = AVIFileOpen(&pfile,    // returned file pointer 
       szTitle,            // file name 
       OF_WRITE | OF_CREATE,    // mode to open file with 
       NULL);    // use handler determined 
    // from file extension.... 
if (hr != AVIERR_OK) 
goto error;  
// Fill in the header for the video stream....  
// The video stream will run in 15ths of a second....  
_fmemset(&strhdr, 0, sizeof(strhdr)); 
strhdr.fccType                = streamtypeVIDEO;// stream type 
strhdr.fccHandler             = 0; 
strhdr.dwScale                = 1; 
strhdr.dwRate                 = 15;    // 15 fps 
strhdr.dwSuggestedBufferSize  = alpbi[0]->biSizeImage; 
SetRect(&strhdr.rcFrame, 0, 0,    // rectangle for stream 
    (int) alpbi[0]->biWidth, 
    (int) alpbi[0]->biHeight); 
 
// And create the stream; 
hr = AVIFileCreateStream(pfile,    // file pointer 
         &ps,    // returned stream pointer 
         &strhdr);    // stream header 
if (hr != AVIERR_OK) { 
goto error; 
}  
_fmemset(&opts, 0, sizeof(opts));  
if (!AVISaveOptions(NULL, 0, 1, &ps, (LPAVICOMPRESSOPTIONS FAR *) &aopts)) 
    goto error;  
hr = AVIMakeCompressedStream(&psCompressed, ps, &opts, NULL); 
if (hr != AVIERR_OK) { 
goto error; 
}  
hr = AVIStreamSetFormat(psCompressed, 0, 
       alpbi[0],    // stream format 
       alpbi[0]->biSize +   // format size 
       alpbi[0]->biClrUsed * sizeof(RGBQUAD)); 
if (hr != AVIERR_OK) { 
goto error; 
}  
// Fill in the stream header for the text stream....  
// The text stream is in 60ths of a second....  
_fmemset(&strhdr, 0, sizeof(strhdr)); 
strhdr.fccType                = streamtypeTEXT; 
strhdr.fccHandler             = mmioFOURCC('D', 'R', 'A', 'W'); 
strhdr.dwScale                = 1; 
strhdr.dwRate                 = 60; 
strhdr.dwSuggestedBufferSize  = sizeof(szText); 
SetRect(&strhdr.rcFrame, 0, (int) alpbi[0]->biHeight, 
    (int) alpbi[0]->biWidth, (int) alpbi[0]->biHeight + TEXT_HEIGHT);  
// ....and create the stream. 
hr = AVIFileCreateStream(pfile, &psText, &strhdr); 
if (hr != AVIERR_OK) { 
goto error; 
} dwTextFormat = sizeof(dwTextFormat); 
hr = AVIStreamSetFormat(psText, 0, &dwTextFormat, sizeof(dwTextFormat)); 
if (hr != AVIERR_OK) { 
goto error; 

// Now write out each video frame, along with a text label. 
// The video frames are 2/3 of a second apart, which is 10 
// in the video time scale and 40 in the text stream's time scale.  
for (i = 0; i < N_FRAMES; i++) { 
hr = AVIStreamWrite(psCompressed,// stream pointer 
i * 10,// time of this frame 
1,// number to write 
(LPBYTE) alpbi[i] +// pointer to data 
alpbi[i]->biSize + 
alpbi[i]->biClrUsed * sizeof(RGBQUAD), 
alpbi[i]->biSizeImage,// size of this frame 
AVIIF_KEYFRAME, // flags.... 
NULL, 
NULL); 
if (hr != AVIERR_OK) 
break;  
// Make some text to put in the file ... 
LoadString(hInstance, IDS_TEXTFORMAT, szMessage, BUFSIZE );  
iLen = wsprintf(szText, szMessage, (int)(i + 1));  
// ... and write it as well. 
hr = AVIStreamWrite(psText, 
i * 40, 
1, 
szText, 
iLen + 1, 
AVIIF_KEYFRAME, 
NULL, 
NULL); 
if (hr != AVIERR_OK) 
break; 

 
error: 
// 
// Now close the file 
// 
if (ps) 
AVIStreamClose(ps);  
if (psCompressed) 
AVIStreamClose(psCompressed);  
if (psText) 
AVIStreamClose(psText);  
if (pfile) 
AVIFileClose(pfile);  
AVIFileExit(); 
FreeFrames(alpbi);  
if (hr != NOERROR) { 
LoadString(hInstance, IDS_APPERR, szTitle, BUFSIZE ); 
LoadString(hInstance, IDS_WRITEERR, szMessage, BUFSIZE );  
MessageBox(NULL, szMessage, szTitle, MB_OK); 

return 0; 
}  
// // Fill an array of LPBI's with the frames for this movie // 
static void MakeFrames(LPLPBI alpbi, UINT bits, UINT wXSize,UINT wYSize ) 

HDC         hdc ; 
HDC         hdcMem ; 
HBITMAP     hbitmap,hbitmapOld ; 
HPEN        hpen3,hpen1,hpenwhite,hpenOld ; 
HFONT       hfont,hfontOld ; 
HBRUSH      hbrush,hbrushOld ; 
RECT        rc ; 
RECT        rcFrameNo ; 
int         wXCent,wYCent ; 
int         cxPixInch ; 
int         cyPixInch ; 
int         cxPixels ; 
int         cyPixels ; 
int         radius ; 
int         x0,y0,x1,y1 ; 
int         i,j ; 
char        szNumber[3] ; 
// // Make sure our resources are freed // 
FreeFrames(alpbi);  
// // Find the center of the movie // 
wXCent = wXSize/2 ; 
wYCent = wYSize/2 ;  
hdc = GetDC(NULL) ; 
hdcMem = CreateCompatibleDC(NULL) ; 
 /// We need some gray and white brushes and pens, and a bitmap // 
hpen3 = CreatePen(PS_SOLID,3,RGB(128,128,128)) ; 
hpen1 = CreatePen(PS_SOLID,1,RGB(64,64,64)); 
hpenwhite = CreatePen(PS_SOLID,1,RGB(255,255,255)); 
hpenOld = SelectPen(hdcMem, hpen3); 
hbrush = CreateSolidBrush(RGB(192,192,192)) ; 
hbrushOld = SelectBrush(hdcMem,hbrush) ; 
hbitmap = CreateCompatibleBitmap(hdc,wXSize,wYSize) ; 
 

解决方案 »

  1.   

    cxPixInch = GetDeviceCaps(hdc,LOGPIXELSX) ; 
    cyPixInch = GetDeviceCaps(hdc,LOGPIXELSY) ; 
     //// What radius of circle can we fit in this frame?  Make sure it's round 
    // regardless of the aspect ratio // 
    radius = ( wXSize < wYSize ) ? wXSize : (wYSize*cxPixInch)/cyPixInch ; 
    radius = ( radius * 95 ) / 200 ;  
    // // Make a Rectangle in the center where the number will go // 
    /* x0 = radius / sqrt(2) */ 
    x0 = (radius*100)/141 ; 
    y0 = (x0*cyPixInch)/cxPixInch ; 
    x0 = (x0*9)/10 ; 
    y0 = (y0*9)/10 ; 
    SetRect( &rcFrameNo,wXCent-x0,wYCent-y0,wXCent+x0,wYCent+y0 ) ;  
    // // Move the rectangle in a little and make a font big enough for it // 
    x0 = (x0*9)/10 ; 
    y0 = (y0*9)/10 ; 
     
    hfont = CreateFont( 
    y0*2, 
    x0, 
    0, 
    0, 
    FW_BOLD, 
    0, 
    0, 
    0, 
    ANSI_CHARSET, 
    OUT_DEVICE_PRECIS, 
    CLIP_DEFAULT_PRECIS, 
    DEFAULT_QUALITY, 
    DEFAULT_PITCH|FF_SWISS, 
    NULL 
    );  
    hfontOld = SelectFont(hdcMem, hfont);  
    // // Now walk through and make all the frames // 
    for ( i=0; i<N_FRAMES; i++ ) { 
    hbitmapOld = SelectBitmap(hdcMem, hbitmap); 
    // // Fill the whole frame with white // 
    SetRect(&rc,0,0,wXSize,wYSize) ; 
    FillRect(hdcMem,&rc,GetStockBrush(WHITE_BRUSH)) ;  
    // // Draw the circle inside the previously calculated radius // 
    cxPixels = radius ; 
    cyPixels = (cxPixels*cyPixInch)/cxPixInch ; 
     
    SelectPen(hdcMem,hpen3) ; 
    Ellipse(hdcMem,wXCent-cxPixels,wYCent-cyPixels,wXCent+cxPixels, 
    wYCent+cyPixels) ; 
     
    SelectPen(hdcMem,hpen1) ; 
    // // Draw the number in the previously calculated area // 
    wsprintf(szNumber,"%02u",i+1) ; 
     
    SetBkColor(hdcMem,RGB(192,192,192)) ; 
    SetTextColor(hdcMem,RGB(255,255,255)) ; 
    ExtTextOut( 
    hdcMem, 
    rcFrameNo.left, 
    rcFrameNo.top+(rcFrameNo.bottom-rcFrameNo.top)/20, 
    ETO_CLIPPED, 
    &rcFrameNo, 
    szNumber, 
    2, 
    NULL); 
    // // Draw tic s around the inside of the circle in equal divisions // 
    for ( j=0; j<N_FRAMES; j++ ) { 
    x0 = (radius*aSin[j])/100 ; 
    y0 = (radius*aCos[j])/100 ; 
    x1 = (((radius*aSin[j])/100)*11)/12 ; 
    y1 = (((radius*aCos[j])/100)*11)/12 ; 
     
    y0 = -(y0*cyPixInch)/cxPixInch ; 
    y1 = -(y1*cyPixInch)/cxPixInch ; 
     
    MoveToEx(hdcMem,wXCent+x0,wYCent+y0,NULL) ; 
    LineTo(hdcMem,wXCent+x1,wYCent+y1) ; 
    }  
    // // Now draw the hand of the clock in the appropriate position // 
    x1 = (((radius*aSin[i])/100)*5)/8 ; 
    y1 = (((radius*aCos[i])/100)*5)/8 ; 
    y1 = -(y1*cyPixInch)/cxPixInch ; 
     
    MoveToEx(hdcMem,wXCent,wYCent,NULL) ; 
    LineTo(hdcMem,wXCent+x1,wYCent+y1) ; 
     
    SelectBitmap(hdcMem, hbitmapOld); 
    // // Make this into a DIB and stuff it into the array // 
    alpbi[i] = (LPBITMAPINFOHEADER)GlobalLock(MakeDib(hbitmap, bits));  
    // // For an error, just duplicate the last frame if we can // 
    if (alpbi[i] == NULL && i ) 
    alpbi[i] = alpbi[i-1] ; 

     //// Select all the old objects back and delete resources // 
    SelectPen(hdcMem, hpenOld); 
    SelectBrush(hdcMem,hbrushOld) ; 
    SelectFont(hdcMem,hfontOld) ; 
    DeletePen(hpen1) ; 
    DeletePen(hpen3) ; 
    DeletePen(hpenwhite) ; 
    DeleteBrush(hbrush) ; 
    DeleteBitmap(hbitmap) ; 
    DeleteFont(hfont) ; 
    DeleteObject(hdcMem) ; 
    ReleaseDC(NULL,hdc) ; 

     // // Walk through our array of LPBI's and free them // 
    static void FreeFrames(LPLPBI alpbi) 

    UINT        w ; 
     
    if (!alpbi[0]) 
    return ; 
    // // Don't free a frame if it's a duplicate of the previous one // 
    for (w=0; w<N_FRAMES; w++) 
    if (alpbi[w] && alpbi[w] != alpbi[w-1]) 
    GlobalFreePtr(alpbi[w]); 
    for (w=0; w<N_FRAMES; w++) 
    alpbi[w] = NULL; 

     
    /* 
    ** MakeDib(hbitmap) 
    ** 
    ** Take the given bitmap and transform it into a DIB with parameters: 
    ** 
    ** BitsPerPixel:    8 
    ** Colors:          palette 
    ** 
    */ 
    static HANDLE  MakeDib( HBITMAP hbitmap, UINT bits ) 

    HANDLE              hdib ; 
    HDC                 hdc ; 
    BITMAP              bitmap ; 
    UINT                wLineLen ; 
    DWORD               dwSize ; 
    DWORD               wColSize ; 
    LPBITMAPINFOHEADER  lpbi ; 
    LPBYTE              lpBits ; 
     
    GetObject(hbitmap,sizeof(BITMAP),&bitmap) ; 
     //// DWORD align the width of the DIB 
    // Figure out the size of the colour table 
    // Calculate the size of the DIB // 
    wLineLen = (bitmap.bmWidth*bits+31)/32 * 4; 
    wColSize = sizeof(RGBQUAD)*((bits <= 8) ? 1<<bits : 0); 
    dwSize = sizeof(BITMAPINFOHEADER) + wColSize + 
    (DWORD)(UINT)wLineLen*(DWORD)(UINT)bitmap.bmHeight;  
    // // Allocate room for a DIB and set the LPBI fields // 
    hdib = GlobalAlloc(GHND,dwSize); 
    if (!hdib) 
    return hdib ; 
     
    lpbi = (LPBITMAPINFOHEADER)GlobalLock(hdib) ; 
     
    lpbi->biSize = sizeof(BITMAPINFOHEADER) ; 
    lpbi->biWidth = bitmap.bmWidth ; 
    lpbi->biHeight = bitmap.bmHeight ; 
    lpbi->biPlanes = 1 ; 
    lpbi->biBitCount = (WORD) bits ; 
    lpbi->biCompression = BI_RGB ; 
    lpbi->biSizeImage = dwSize - sizeof(BITMAPINFOHEADER) - wColSize ; 
    lpbi->biXPelsPerMeter = 0 ; 
    lpbi->biYPelsPerMeter = 0 ; 
    lpbi->biClrUsed = (bits <= 8) ? 1<<bits : 0; 
    lpbi->biClrImportant = 0 ; 
     
    // 
    // Get the bits from the bitmap and stuff them after the LPBI 
    // 
    lpBits = (LPBYTE)(lpbi+1)+wColSize ; 
     
    hdc = CreateCompatibleDC(NULL) ; 
     
    GetDIBits(hdc,hbitmap,0,bitmap.bmHeight,lpBits,(LPBITMAPINFO)lpbi, DIB_RGB_COLORS); 
     
    // Fix this if GetDIBits messed it up.... 
    lpbi->biClrUsed = (bits <= 8) ? 1<<bits : 0; 
     
    DeleteDC(hdc) ; 
    GlobalUnlock(hdib); 
     
    return hdib ; 
    }
      

  2.   

    如果那位有delphi的原程序的话!
    我多加点分哈!!!说话算话!
      

  3.   

    绝大多数制作gif的图像工具都有导入一组BMP并导出到avi的功能,比方说ulead的一些动画制作工具. 
      

  4.   

    www.51delphi.com  下载一个Animate Gif 控件,它是用来增强TImage以显示gif图片的。
    它的Demo目录下有几个例子不错,有 bmp/gif/avi互相转化的例子。 
      

  5.   

    我怎么没有找到啊??
    你能不能给我发一个到我的邮箱去啊!
    谢谢了先!
    我的邮箱是 [email protected]
    谢谢