PDA

Ver la Versión Completa : Problemas con la libreria FreeImage y Graphics::TBitmap


aguml
19-12-2014, 13:44:01
Pues amigos mi problema es que uso esa libreria para convertir imagenes bmp a otros formatos y si uso para ello un TImage y guardo esa imagen y luego uso las funciones de FreeImage para convertir la imagen pues va genial pero si en vez de un TImage uso un Graphics::TBitmap y creo la imagen con el y luego intento convertir ese archivo me falla la funcion de la libreria aunque sean ambas .bmp.

La que usa el Graphics::TBitmap es esta:
void __fastcall TForm1::CopyCatImagesTo(int Option)
{
unsigned int DataHandle;
HPALETTE APalette;
unsigned short MyFormat;
const int separacion = 15;
int x=separacion,y=0;
TRect ARect, BRect;
int altoMax=0, anchoFinal=separacion;
int error;

//Solicito memoria para el bitmap que contendrá el concatenado de imagenes
Graphics::TBitmap *FullMap = new (nothrow) Graphics::TBitmap();

if(FullMap != NULL)
{
//FullMap->HandleType = 1;
//FullMap->IgnorePalette = false;
Graphics::TBitmap *Aux = new (nothrow) Graphics::TBitmap();

if(Aux != NULL)
{ //Si se obtuvo memoria correctamente...
try
{
for(int i=0; i < CheckListBox->Count; i++, anchoFinal += separacion)
{
//Meto cada imagen en su Bitmap
Aux->LoadFromFile(ChangeFileExt(CheckListBox->Items->Strings[i],".bmp"));
anchoFinal += Aux->Width;
if(altoMax < Aux->Height)
altoMax = Aux->Height;
}

FullMap->Height = altoMax;
FullMap->Width = anchoFinal;

for(int i=0; i < CheckListBox->Count; i++)
{ //Si se obtuvo memoria correctamente...
//Meto cada imagen en su Bitmap
Aux->LoadFromFile(ChangeFileExt(CheckListBox->Items->Strings[i],".bmp"));

//Le sumo el ancho de la imagen actual a y
y += Aux->Width;

//Relleno el TRect para la imagen actual
ARect.Left = 0;
ARect.Top = 0;
ARect.Right = Aux->Width;
ARect.Bottom = Aux->Height;

//Relleno el TRect para la imagen concatenada
BRect.Left = x;
BRect.Top = 0;
BRect.Right = y;
BRect.Bottom = Aux->Height;

// Añado el canvas a la imagen que contendrá el concatenado de imagenes
FullMap->Canvas->CopyRect(BRect, Aux->Canvas, ARect);

//Le sumo el ancho de la imagen actual a x
x += Aux->Width + separacion;
}

if(Option == COPY_TO_CLIPBOARD)
{
// generate a clipboard format, with data and palette
FullMap->SaveToClipboardFormat(MyFormat,DataHandle,APalette);

// save the data to the clipboard using that format and
// the generated data
Clipboard()->SetAsHandle(MyFormat,DataHandle);
}
else if(Option == SAVE_TO_FILE)
{
if(SavePictureDialog->Execute())
{
error = GuardarImagen(FullMap, SavePictureDialog->FileName.c_str());

switch(error)
{
case 0:
Application->MessageBoxA("La imagen se guardó correctamente.", "Informacion", MB_OK | MB_ICONINFORMATION | MB_APPLMODAL);
break;

case -1:
Application->MessageBoxA("La extension introducida no es correcta.", "Error", MB_OK | MB_ICONERROR | MB_APPLMODAL);
break;

default:
Application->MessageBoxA("La extension introducida no es correcta.", "Error", MB_OK | MB_ICONERROR | MB_APPLMODAL);
}
}
}

delete Aux;
delete FullMap;
}
catch(...)
{ //Si huvo algun error libero toda la memoria obtenida
delete Aux;
delete FullMap;
Application->MessageBoxA("Hubo un error al copiar las imagenes concatenadas al portapapeles", "Error", MB_OK | MB_ICONERROR);
}
}else{ //Si no se pudo obtener la memoria suficiente...
//Libero toda la memoria obtenida
delete FullMap;
Application->MessageBoxA("Hubo un error al copiar las imagenes concatenadas al portapapeles", "Error", MB_OK | MB_ICONERROR);
}
}else{
Application->MessageBoxA("Hubo un error al copiar las imagenes concatenadas al portapapeles", "Error", MB_OK | MB_ICONERROR);
}
}

La que usa el TImage es esta:
void __fastcall TForm1::Guardarimagencomo1Click(TObject *Sender)
{
int error;

if(SavePictureDialog->Execute())
{
error = GuardarImagen(Image->Picture->Bitmap, SavePictureDialog->FileName.c_str());

switch(error)
{
case 0:
Application->MessageBoxA("La imagen se guardó correctamente.", "Informacion", MB_OK | MB_ICONINFORMATION | MB_APPLMODAL);
break;

case -1:
Application->MessageBoxA("La extension introducida no es correcta.", "Error", MB_OK | MB_ICONERROR | MB_APPLMODAL);
break;

default:
Application->MessageBoxA("La extension introducida no es correcta.", "Error", MB_OK | MB_ICONERROR | MB_APPLMODAL);
}
}
}

Esta es la funcion encargada de llamar a la funcion que convierte la imagen:
int __fastcall TForm1::GuardarImagen(Graphics::TBitmap *bmp, char *name)
{
FREE_IMAGE_FORMAT formatoSalida;
AnsiString extension;
AnsiString fileAux;
int retval = -2;

fileAux = ChangeFileExt(name, ".bmp");
bmp->SaveToFile(fileAux);
extension = ExtractFileExt(name).UpperCase();
if(extension != NULL)
{
formatoSalida = SaberFormatoImagen(extension);

if(formatoSalida == FIF_BMP)
{
retval = 0;
}
else if(formatoSalida != FIF_BMP && formatoSalida != FIF_UNKNOWN)
{
ConvertirImagen(fileAux,
formatoSalida,
extension,
0);
DeleteFile(fileAux);
retval = 0;
}
else
{
retval = -1;
}
}
else
{
retval = -1;
}
return retval;
}

Son diferentes ya que una guardaria una imagen en concreto y la otra guardaria todas las imagenes concatenadas en una sola imagen.
En la de concatenar la parte del portapapeles funciona bien pero la de guardar a archivo solo funciona bien si lo guardo en formato .bmp ya que es el unico que no convierto.
¿Como puedo solucionar eso?

escafandra
19-12-2014, 14:05:07
No tengo el gusto de haber trabajado con esa librería, pero si con la conversión de formatos con GDIplus (Extensión del GDI de Windows).
Te aconsejo la lectura de estos enlaces:

Leer archivos graficos en varios formatos. (http://www.delphiaccess.com/forum/trucos-y-consejos-16/%28multilenguaje%29-leer-archivos-graficos-en-varios-formatos/msg49670/#msg49670)
Como guardar archivos gráficos en varios formatos. (http://www.delphiaccess.com/forum/trucos-y-consejos-16/%28multilenguaje%29-como-guardar-archivos-graficos-en-varios-formatos/msg77583/#msg77583)
Leer archivos gráficos multipágina en varios formatos (http://www.delphiaccess.com/forum/trucos-y-consejos-16/%28multilenguaje%29-leer-archivos-graficos-multipagina/msg84486/#msg84486)
Escribir archivos gráficos multipágina (http://www.delphiaccess.com/forum/trucos-y-consejos-16/escribir-archivos-graficos-multipagina/msg84632/#msg84632)


Saludos.

aguml
19-12-2014, 15:49:11
Está muy bien tu codigo para hacer las conversiones con las GDI pero lo que pasa es que la aplicacion sobre la que estoy trabajando ya usa la dll FreeImage para otras cosas y poner mas codigo cuando ya tengo una dll que lo hace lo veo innecesario. Lo que necesito es saber donde está el fallo aunque me quedo con tu codigo para otra ocasion :D.
Mira lo que puedo ver entre la que me lo crea bien y la que me da error:
http://postimg.org/image/qsstjp62x/
Cambian algunas cosas pero he intentado hacer que la que falla llegue con los mismos valores pero ni por esa funciona.

aguml
19-12-2014, 18:20:49
lo solucioné. Al parecer me lié y el que funcionaba era el de la imagen de arriba y el que fallaba era el de abajo. Le puse la propiedad PixelFormat como pf8bit y ya hace la conversion sin problemas.