分类: C/C++
2008-08-22 14:11:23
In this article I want to show the following:
These functions are implemented using freeimage (see below). The code for opening and saving looks is very simple and looks like this (simplified):
BOOL CGraphicSuiteDoc::OnOpenDocument(LPCTSTR lpszPathName) { FREE_IMAGE_FORMAT fif; DeleteContents(); fif = FreeImage_GetFIFFromFilename(lpszPathName); if( fif != FIF_UNKNOWN ) m_handleFI = FreeImage_Load(fif, lpszPathName); return (m_handleFI != NULL); } void CGraphicSuiteDoc::OnFileSaveAs() { CString filter, szDest; DWORD dwFlags = OFN_OVERWRITEPROMPT | OFN_EXPLORER | OFN_LONGNAMES | OFN_PATHMUSTEXIST | OFN_HIDEREADONLY; FREE_IMAGE_FORMAT fif; BOOL bErg; filter.LoadString(IDS_STRING_FILTER_GRAPHICS); CFileDialog dlg(FALSE, NULL, szDest, dwFlags, filter, AfxGetMainWnd()); if( dlg.DoModal() != IDOK) return; fif = FreeImage_GetFIFFromFilename(dlg.GetPathName()); if( fif == FIF_UNKNOWN ) { AfxMessageBox("Unknown type."); return; } bErg = FALSE; try { bErg = FreeImage_Save(fif, m_handleFI, dlg.GetPathName()); } catch(...) { } if( !bErg ) AfxMessageBox("Failed saving !"); }
The MDI-sample uses freeimage to do all the image-stuff, except the display. In this sample the display is handled using the API-function StretchDIBits
. In the real-code also the clip-box is used in order only to extract the pixels that have to be repainted. Thus the code shown here is a little simplified to the the technique. I've choosen mapping-mode MM_HIMETRIC
, because then you can print the images using the correct resolution and metrics.
void CGraphicSuiteView::OnDraw(CDC* pDC) { CGraphicSuiteDoc *pDoc = GetDocument(); pDC->SetMapMode(MM_HIMETRIC); double dpiX = FreeImage_GetDotsPerMeterX(pDoc->m_handleFI), dpiY = FreeImage_GetDotsPerMeterY(pDoc->m_handleFI), width = FreeImage_GetWidth(pDoc->m_handleFI), height = FreeImage_GetHeight(pDoc->m_handleFI), sizeX, // 1/100 mm == HIMETRIC sizeY; BYTE *pData = FreeImage_GetBits(pDoc->m_handleFI); if( dpiX==0.0 ) dpiX = 72.0 * 100.0 / 2.54; if( dpiY==0.0 ) dpiY = 72.0 * 100.0 / 2.54; sizeX = m_Zoom * 100.0 * 1000.0 * width / dpiX; sizeY = m_Zoom * 100.0 * 1000.0 * height / dpiY; // stretched ::StretchDIBits(pDC->m_hDC, // x-y-coord of destination upper-left corner sizeX, -sizeY, // width-height of destination rectangle (int)(sizeX+0.5), -(int)(sizeY+0.5), // x-y-coord of source upper-left corner 0, 0, // width-height of source rectangle (int)(width+0.5), (int)(height+0.5), pData, // bitmap bits FreeImage_GetInfo(pDoc->m_handleFI), // bitmap data DIB_RGB_COLORS, // usage options SRCCOPY // raster operation code ); } .. or use (see code for how the parameters are to be initialized) // no stretching ::SetDIBitsToDevice( pDC->m_hDC, // handle to DC xDst, yDst, // x-y-coord of destination upper-left corner dxSrc, dySrc, // width-height of source rectangle xSrc, ySrc, // x-y-coord of source upper-left corner 0,//uStartScan,// first scan line in array FreeImage_GetHeight(pFIBitmap), // number of scan lines FreeImage_GetBits(pFIBitmap), // array of DIB bits FreeImage_GetInfo(pFIBitmap), // bitmap information DIB_RGB_COLORS); // RGB or palette indexes
To complete the program, the relevant image information is shown in a dialog:
(Text taken from the freeimage-introduction ! )
FreeImage is an Open Source library project for developers who would like to support popular graphics image formats like BMP, JPEG, TIFF and PCX and others as needed by today's multimedia applications. The libraries comes in two versions: a binary distribution that can be linked against any 32-bit c++ compiler and a source distribution. Workspace files for Microsoft Visual C++ 6 are provided, as well as makefiles for linux.
* only via external plugin
** only grayscale
Freeimage loads the various file-formats using different libraries, e.g. libtiff or zlib. When loading a file, the data is converted internally using the structure BITMAPINFO
from the Win32-API (even when it is compiled under linux). This approach makes it easy converting from format x to format y. To support a specific file-format there are needed only 2 converters, one for loading from the file to a BITMAPINFO
and the other for saving from BITMAPINFO
into the file:
FIBITMAP *FreeImage_Load(FREE_IMAGE_FORMAT fif, const char *filename, int flags); BOOL FreeImage_Save(FREE_IMAGE_FORMAT fif, FIBITMAP *dib, const char *filename, int flags); FREE_IMAGE_FORMAT FreeImage_GetFIFFromFilename(const char *filename);
If you need more infos, download the source, want to discuss or, even better, want to develop additional features, you can visit the freeimage homepage.
Some programming hints can be found here: FreeImage FAQ.
The code was written using:
freeimage | freeimage-homepage |
Vassili Bourdo | code for the shell |
Chris Maunder | for the CDIBSectionLite-class |
Version 1.0 | 25. Sept. 2001 |
|
Version 2.4.2 | 7. Oct. 2001 |
|
Version 2.5.1 | 14. March 2002 |
|
Version 2.5.2 | 26. March 2002 |
|
Version 2.5.3 | 22. April 2002 |
|