Alien-FreeImage
view release on metacpan or search on metacpan
src/Source/FreeImage/MultiPage.cpp view on Meta::CPAN
if (create_new) {
read_only = FALSE;
}
// retrieve the plugin list to find the node belonging to this plugin
PluginList *list = FreeImage_GetPluginList();
if (list) {
PluginNode *node = list->FindNodeFromFIF(fif);
if (node) {
std::auto_ptr<FreeImageIO> io (new FreeImageIO);
SetDefaultIO(io.get());
if (!create_new) {
handle = fopen(filename, "rb");
if (handle == NULL) {
return NULL;
}
}
std::auto_ptr<FIMULTIBITMAP> bitmap (new FIMULTIBITMAP);
std::auto_ptr<MULTIBITMAPHEADER> header (new MULTIBITMAPHEADER);
header->m_filename = new char[strlen(filename) + 1];
strcpy(header->m_filename, filename);
header->node = node;
header->fif = fif;
header->io = io.get ();
header->handle = handle;
header->changed = FALSE;
header->read_only = read_only;
header->m_cachefile = NULL;
header->cache_fif = fif;
header->load_flags = flags;
// store the MULTIBITMAPHEADER in the surrounding FIMULTIBITMAP structure
bitmap->data = header.get();
// cache the page count
header->page_count = FreeImage_InternalGetPageCount(bitmap.get());
// allocate a continueus block to describe the bitmap
if (!create_new) {
header->m_blocks.push_back((BlockTypeS *)new BlockContinueus(0, header->page_count - 1));
}
// set up the cache
if (!read_only) {
std::string cache_name;
ReplaceExtension(cache_name, filename, "ficache");
std::auto_ptr<CacheFile> cache_file (new CacheFile(cache_name, keep_cache_in_memory));
if (cache_file->open()) {
// we can use release() as std::bad_alloc won't be thrown from here on
header->m_cachefile = cache_file.release();
} else {
// an error occured ...
fclose(handle);
return NULL;
}
}
// return the multibitmap
// std::bad_alloc won't be thrown from here on
header.release(); // now owned by bitmap
io.release(); // now owned by bitmap
return bitmap.release(); // now owned by caller
}
}
} catch (std::bad_alloc &) {
/** @todo report error */
}
if (handle)
fclose(handle);
return NULL;
}
FIMULTIBITMAP * DLL_CALLCONV
FreeImage_OpenMultiBitmapFromHandle(FREE_IMAGE_FORMAT fif, FreeImageIO *io, fi_handle handle, int flags) {
try {
BOOL read_only = FALSE; // modifications (if any) will be stored into the memory cache
if (io && handle) {
// retrieve the plugin list to find the node belonging to this plugin
PluginList *list = FreeImage_GetPluginList();
if (list) {
PluginNode *node = list->FindNodeFromFIF(fif);
if (node) {
std::auto_ptr<FIMULTIBITMAP> bitmap (new FIMULTIBITMAP);
std::auto_ptr<MULTIBITMAPHEADER> header (new MULTIBITMAPHEADER);
std::auto_ptr<FreeImageIO> tmp_io (new FreeImageIO (*io));
header->io = tmp_io.get();
header->m_filename = NULL;
header->node = node;
header->fif = fif;
header->handle = handle;
header->changed = FALSE;
header->read_only = read_only;
header->m_cachefile = NULL;
header->cache_fif = fif;
header->load_flags = flags;
// store the MULTIBITMAPHEADER in the surrounding FIMULTIBITMAP structure
bitmap->data = header.get();
// cache the page count
header->page_count = FreeImage_InternalGetPageCount(bitmap.get());
// allocate a continueus block to describe the bitmap
header->m_blocks.push_back((BlockTypeS *)new BlockContinueus(0, header->page_count - 1));
if (!read_only) {
// set up the cache
std::auto_ptr<CacheFile> cache_file (new CacheFile("", TRUE));
if (cache_file->open()) {
header->m_cachefile = cache_file.release();
}
src/Source/FreeImage/MultiPage.cpp view on Meta::CPAN
return FALSE;
}
int DLL_CALLCONV
FreeImage_GetPageCount(FIMULTIBITMAP *bitmap) {
if (bitmap) {
MULTIBITMAPHEADER *header = FreeImage_GetMultiBitmapHeader(bitmap);
if (header->page_count == -1) {
header->page_count = 0;
for (BlockListIterator i = header->m_blocks.begin(); i != header->m_blocks.end(); ++i) {
switch((*i)->m_type) {
case BLOCK_CONTINUEUS :
header->page_count += ((BlockContinueus *)(*i))->m_end - ((BlockContinueus *)(*i))->m_start + 1;
break;
case BLOCK_REFERENCE :
header->page_count++;
break;
}
}
}
return header->page_count;
}
return 0;
}
static BlockReference*
FreeImage_SavePageToBlock(MULTIBITMAPHEADER *header, FIBITMAP *data) {
if (header->read_only || !header->locked_pages.empty())
return NULL;
DWORD compressed_size = 0;
BYTE *compressed_data = NULL;
// compress the bitmap data
// open a memory handle
FIMEMORY *hmem = FreeImage_OpenMemory();
if(hmem==NULL) return NULL;
// save the file to memory
if(!FreeImage_SaveToMemory(header->cache_fif, data, hmem, 0)) {
FreeImage_CloseMemory(hmem);
return NULL;
}
// get the buffer from the memory stream
if(!FreeImage_AcquireMemory(hmem, &compressed_data, &compressed_size)) {
FreeImage_CloseMemory(hmem);
return NULL;
}
// write the compressed data to the cache
int ref = header->m_cachefile->writeFile(compressed_data, compressed_size);
// get rid of the compressed data
FreeImage_CloseMemory(hmem);
return new(std::nothrow) BlockReference(ref, compressed_size);
}
void DLL_CALLCONV
FreeImage_AppendPage(FIMULTIBITMAP *bitmap, FIBITMAP *data) {
if (!bitmap || !data)
return;
MULTIBITMAPHEADER *header = FreeImage_GetMultiBitmapHeader(bitmap);
BlockReference *block = FreeImage_SavePageToBlock(header, data);
if(block==NULL) return;
// add the block
header->m_blocks.push_back((BlockTypeS *)block);
header->changed = TRUE;
header->page_count = -1;
}
void DLL_CALLCONV
FreeImage_InsertPage(FIMULTIBITMAP *bitmap, int page, FIBITMAP *data) {
if (!bitmap || !data)
return;
if (page >= FreeImage_GetPageCount(bitmap))
return;
MULTIBITMAPHEADER *header = FreeImage_GetMultiBitmapHeader(bitmap);
BlockReference *block = FreeImage_SavePageToBlock(header, data);
if(block==NULL) return;
// add a block
if (page > 0) {
BlockListIterator block_source = FreeImage_FindBlock(bitmap, page);
header->m_blocks.insert(block_source, (BlockTypeS *)block);
} else {
header->m_blocks.push_front((BlockTypeS *)block);
}
header->changed = TRUE;
header->page_count = -1;
}
void DLL_CALLCONV
FreeImage_DeletePage(FIMULTIBITMAP *bitmap, int page) {
if (bitmap) {
MULTIBITMAPHEADER *header = FreeImage_GetMultiBitmapHeader(bitmap);
if ((!header->read_only) && (header->locked_pages.empty())) {
if (FreeImage_GetPageCount(bitmap) > 1) {
BlockListIterator i = FreeImage_FindBlock(bitmap, page);
if (i != header->m_blocks.end()) {
switch((*i)->m_type) {
case BLOCK_CONTINUEUS :
delete *i;
header->m_blocks.erase(i);
break;
src/Source/FreeImage/MultiPage.cpp view on Meta::CPAN
if ((!header->read_only) && (header->locked_pages.empty())) {
if ((target != source) && ((target >= 0) && (target < FreeImage_GetPageCount(bitmap))) && ((source >= 0) && (source < FreeImage_GetPageCount(bitmap)))) {
BlockListIterator block_source = FreeImage_FindBlock(bitmap, target);
BlockListIterator block_target = FreeImage_FindBlock(bitmap, source);
header->m_blocks.insert(block_target, *block_source);
header->m_blocks.erase(block_source);
header->changed = TRUE;
return TRUE;
}
}
}
return FALSE;
}
BOOL DLL_CALLCONV
FreeImage_GetLockedPageNumbers(FIMULTIBITMAP *bitmap, int *pages, int *count) {
if ((bitmap) && (count)) {
MULTIBITMAPHEADER *header = FreeImage_GetMultiBitmapHeader(bitmap);
if ((pages == NULL) || (*count == 0)) {
*count = (int)header->locked_pages.size();
} else {
int c = 0;
for (std::map<FIBITMAP *, int>::iterator i = header->locked_pages.begin(); i != header->locked_pages.end(); ++i) {
pages[c] = i->second;
c++;
if (c == *count)
break;
}
}
return TRUE;
}
return FALSE;
}
// =====================================================================
// Memory IO Multipage functions
// =====================================================================
FIMULTIBITMAP * DLL_CALLCONV
FreeImage_LoadMultiBitmapFromMemory(FREE_IMAGE_FORMAT fif, FIMEMORY *stream, int flags) {
BOOL read_only = FALSE; // modifications (if any) will be stored into the memory cache
// retrieve the plugin list to find the node belonging to this plugin
PluginList *list = FreeImage_GetPluginList();
if (list) {
PluginNode *node = list->FindNodeFromFIF(fif);
if (node) {
FreeImageIO *io = new(std::nothrow) FreeImageIO;
if (io) {
SetMemoryIO(io);
FIMULTIBITMAP *bitmap = new(std::nothrow) FIMULTIBITMAP;
if (bitmap) {
MULTIBITMAPHEADER *header = new(std::nothrow) MULTIBITMAPHEADER;
if (header) {
header->m_filename = NULL;
header->node = node;
header->fif = fif;
header->io = io;
header->handle = (fi_handle)stream;
header->changed = FALSE;
header->read_only = read_only;
header->m_cachefile = NULL;
header->cache_fif = fif;
header->load_flags = flags;
// store the MULTIBITMAPHEADER in the surrounding FIMULTIBITMAP structure
bitmap->data = header;
// cache the page count
header->page_count = FreeImage_InternalGetPageCount(bitmap);
// allocate a continueus block to describe the bitmap
header->m_blocks.push_back((BlockTypeS *)new BlockContinueus(0, header->page_count - 1));
if (!read_only) {
// set up the cache
CacheFile *cache_file = new(std::nothrow) CacheFile("", TRUE);
if (cache_file && cache_file->open()) {
header->m_cachefile = cache_file;
}
}
return bitmap;
}
delete bitmap;
}
delete io;
}
}
}
return NULL;
}
BOOL DLL_CALLCONV
FreeImage_SaveMultiBitmapToMemory(FREE_IMAGE_FORMAT fif, FIMULTIBITMAP *bitmap, FIMEMORY *stream, int flags) {
if (stream && stream->data) {
FreeImageIO io;
SetMemoryIO(&io);
return FreeImage_SaveMultiBitmapToHandle(fif, bitmap, &io, (fi_handle)stream, flags);
}
return FALSE;
}
( run in 0.674 second using v1.01-cache-2.11-cpan-cdf2f3d4e48 )