Club Delphi  
    FTP   CCD     Buscar   Trucos   Trabajo   Foros

Retroceder   Foros Club Delphi > Principal > Conexión con bases de datos
Registrarse FAQ Miembros Calendario Guía de estilo Buscar Temas de Hoy Marcar Foros Como Leídos

Conexión con bases de datos

Respuesta
 
Herramientas Buscar en Tema Desplegado
  #21  
Antiguo 24-07-2012
Avatar de roman
roman roman is offline
Moderador
 
Registrado: may 2003
Ubicación: Ciudad de México
Posts: 20.269
Poder: 10
roman Es un diamante en brutoroman Es un diamante en brutoroman Es un diamante en bruto
Cita:
Empezado por Al González
mira lo que hace TPicture
Pues justamente, se asegura de destruir el objeto Graphic que hubiera antes, o ¿a qué te refieres? En el resto de observaciones estoy de acuerdo.

// Saludos
Responder Con Cita
  #22  
Antiguo 24-07-2012
Avatar de Al González
[Al González] Al González is offline
In .pas since 1991
 
Registrado: may 2003
Posts: 5.604
Poder: 29
Al González Es un diamante en brutoAl González Es un diamante en brutoAl González Es un diamante en brutoAl González Es un diamante en bruto
Hola Román.

Cita:
Empezado por Al González Ver Mensaje
[...] con el desafortunado precio de nunca destruir los objetos TJPEGImage y TBitMap que asignas (copias) a Image1.Picture.Graphic [...]
Código Delphi [-]
procedure TPicture.SetGraphic(Value: TGraphic);
var
  NewGraphic: TGraphic;
begin
  NewGraphic := nil;
  if Value <> nil then
  begin
    NewGraphic := TGraphicClass(Value.ClassType).Create;
    NewGraphic.Assign(Value);
    ...
Es que, como puedes ver, SetGraphic es el método de escritura de la propiedad Graphic. El objeto asignado a dicha propiedad es copiado (con el método Assign que ahí se ve) a NewGraphic / FGraphic (otro objeto).

En el código de ElMug:
Código Delphi [-]
      
      Image1.Picture.Graphic:= TJpegImage.Create; {assume is Jpeg}
      ...
        Image1.Picture.Graphic:= TBitMap.Create; {bitmap}
se crean dos objetos "al vuelo" que luego no son destruidos. Se quedan en la memoria esas instancias TJPEGImage y TBitMap.

Seguro es que no te iba a resultar nada difícil dar con ello, pero creo que no estuvo de más aclararlo.

Cambiando de tema, que bueno que regresaste. ¿Ya podemos irnos de vacaciones el resto de los milenarios? Mira que fue bastante arduo intentar cubrirte estas semanas.

Un abrazo.

Al.
Responder Con Cita
  #23  
Antiguo 25-07-2012
Avatar de roman
roman roman is offline
Moderador
 
Registrado: may 2003
Ubicación: Ciudad de México
Posts: 20.269
Poder: 10
roman Es un diamante en brutoroman Es un diamante en brutoroman Es un diamante en bruto
Sí. Tienes razón.

// Saludos
Responder Con Cita
  #24  
Antiguo 25-07-2012
ElMug ElMug is offline
Miembro
NULL
 
Registrado: jul 2012
Posts: 163
Poder: 12
ElMug Va por buen camino
Estimado Al Gonzalez,

Gracias por el interes y comentar.

Estas son mis observaciones a ellos:

1. Asumes que "Image1.Picture.Graphic:= TJpegImage.Create" no va a causar ningún problema, por lo que BS podría quedar sin destruirse nunca.
...............................
No. No causa problemas, porque "Image1.Picture.Graphic:= TJpegImage.Create" solo crea una INSTANCIA, prepara memoria, e inicializa propiedades. Es uso trivial, ver documentacion.

2. Asumes que si falla el primer LoadFromStream, es definitivamente por no tratarse de una imagen JPEG. ¿Será la única razón por la cual pueda elevarse una excepción al ejecutar esa sentencia?
...............................
En este comentario, no serias tu el que asume que asumo, pues de antemano es sabido que los Try detectan cualquier tipo de factor que le cause falla? A tu pregunta "Sera la unica razon?" la respuesta es obvia. NO. No se piensa que sea la unica razon. Pero LA RAZON de interes es que va a fallar si en el Blob no esta guardado un JPEG. Y lo mismo cuando se hace Try para Bitmap.


3. No hay ninguna garantía de que el objeto BS sea destruido si falla el segundo LoadFromStream. OK, todos hacemos pequeñas asunciones en nuestro código de cuando en cuando, ¿pero qué tal si aun siendo una imagen BMP, LoadFromStream tuviera dificultades para leerla?
....................
Si hay otra dificultad, el Try se encarga de marcar error. Eso es elemental. En el caso de un archivo defectuoso, el Try al final levanta un dialogo. El programador conocedor del uso del Try le puede agregar mas codigo, inclusive para que no levante dialogo, y el haga sus codigo con determinaciones especificas.

4. La no liberación de los objetos TGraphic que creas.
.....................
El codigo que muestro no se liberan objetos porque hay usos particulares que podrian requerir seguir usando el objeto. La destruccion de objetos creados la considero cuestion particular de la aplicacion. La creacion, que SI es necesaria, es lo que muestro.


Es lo que se puede notar en tu solución a simple vista. Es una mala práctica emplear "excepciones controladas" para determinar el flujo del programa; para tomar decisiones están los Ifs no los Excepts. ¿Que te ahorras campos? Muy bien, PERO siempre que no dejes tu aplicación llena de pequeñas trampas.
...................
No. Todo uso de recurso que facilite la plataforma de desarrollo no es ninguna trampa. Cuando funciona y no se puede demostrar que no funciona, lo que no es apropiado es juzgar en base en ataduras dogmaticas al pasado o a lo "convencional". Ademas, como seguramente sabes, los "ifs" no detectan errores de este tipo. Los "ifs" se usarian si el metodo es escudriñando el Blob en sus bits o bytes. Pero precisamente, porqe mi procedimiento no lo escudriña, los "ifs" NO se pueden usar y NO se usan. De hecho, base del procedimiento ES el uso de los Try's, y el uso de Try's no es ninguna trampa. Que a algunos les parezca "trampa" no creo poder evitarlo.

En cuanto al empleo de objetos auxiliares dentro de las rutinas, ya sabes la regla:
Código:


1. Apertura (creación)
Try
2. Uso
Finally
3. Cierre (destrucción)

...............
Esto es elemental. No se muestra destruccion de objetos creados. La aplicacion puede darle mas uso al objeto creado, y si no lo requiere, se encargue de destruirlo. En otras palabras, el procedimiento trabaja sin destruirlos. La creacion de esos objetos es necesaria, y se muestra. Destruirlos es opcional y en X caso aplicado, es particular, y funcion del programador.

Espero que esto module tus concernimientos y veas que lo compartido si puede ser de utilidad, si no a algunos, a otros si.
Responder Con Cita
  #25  
Antiguo 25-07-2012
Avatar de roman
roman roman is offline
Moderador
 
Registrado: may 2003
Ubicación: Ciudad de México
Posts: 20.269
Poder: 10
roman Es un diamante en brutoroman Es un diamante en brutoroman Es un diamante en bruto
A lo que Al se refiere en el punto 1 es a que la mera asignación:

Código Delphi [-]
Image1.Picture.Graphic:= TJpegImage.Create;

podría causar una excepción, por ejemplo, por falta de memoria o alguna otra razón imprevisible, como son las excepciones. Si ese fuera el caso, dado que tal excepción no está protegida por un bloque try-except, el código donde liberas a BS (creado anteriormente) no llegaría a ejecutarse y tendrías una fuga de memoria.

Por otra parte, estoy de acuerdo en que un objeto no necesariamente debe destruirse en el mismo contexto en donde se creó ya que posteriormente puede usarse. Sin embargo, en el caso particular que muestras, dicha liberación jamás podría darse ya que pierdes toda referencia al objeto creado, que es lo que explica Al. Cuando asignas:

Código Delphi [-]
Image1.Picture.Graphic := TJpegImage.Create;

la parte derecha de la asignación crea un objeto que se pasa como parámetro al método TPicture.SetGraphic que citó Al. Pero este objeto no es el mismo que finalmente se guarda en el campo privado FGraphic de TPicture ya que Assign hará una copia del objeto. Como el parámetro se pierde después de la llamada, no tienes ninguna variable que apunte al objeto y por tanto no podrás hacer invocar al método Free.

Si realmente se piensa usar posteriormente el objeto creado, tendrías que usar asignar el resultado de Create a una variable y ésta asignarla a TPictureGraphic:

Código Delphi [-]
Graphic := TJpegImage.Create;
Image1.Picture.Graphic := Graphic;

Por otra parte, me da la impresión que nos hemos alejado de tu pregunta inicial. ¿Sigues teniendo el mismo problema que mencionas en el comentariio original?

// Saludos
Responder Con Cita
  #26  
Antiguo 25-07-2012
ElMug ElMug is offline
Miembro
NULL
 
Registrado: jul 2012
Posts: 163
Poder: 12
ElMug Va por buen camino
Cita:
Empezado por roman Ver Mensaje
A lo que Al se refiere en el punto 1 es a que la mera asignación:

Código Delphi [-]Image1.Picture.Graphic:= TJpegImage.Create;


podría causar una excepción, por ejemplo, por falta de memoria o alguna otra razón imprevisible, como son las excepciones. Si ese fuera el caso, dado que tal excepción no está protegida por un bloque try-except, el código donde liberas a BS (creado anteriormente) no llegaría a ejecutarse y tendrías una fuga de memoria.

Por otra parte, estoy de acuerdo en que un objeto no necesariamente debe destruirse en el mismo contexto en donde se creó ya que posteriormente puede usarse. Sin embargo, en el caso particular que muestras, dicha liberación jamás podría darse ya que pierdes toda referencia al objeto creado, que es lo que explica Al. Cuando asignas:

Código Delphi [-]Image1.Picture.Graphic := TJpegImage.Create;


la parte derecha de la asignación crea un objeto que se pasa como parámetro al método TPicture.SetGraphic que citó Al. Pero este objeto no es el mismo que finalmente se guarda en el campo privado FGraphic de TPicture ya que Assign hará una copia del objeto. Como el parámetro se pierde después de la llamada, no tienes ninguna variable que apunte al objeto y por tanto no podrás hacer invocar al método Free.

Si realmente se piensa usar posteriormente el objeto creado, tendrías que usar asignar el resultado de Create a una variable y ésta asignarla a TPictureGraphic:

Código Delphi [-]Graphic := TJpegImage.Create; Image1.Picture.Graphic := Graphic;


Por otra parte, me da la impresión que nos hemos alejado de tu pregunta inicial. ¿Sigues teniendo el mismo problema que mencionas en el comentariio original?

// Saludos
Hola Roman,

Esta linea
Image1.Picture.Graphic:= TJpegImage.Create; NO causa excepcion (Lo verifique desde el inicio de mi desarrollo).

Ahora que si la computadora tenga falla de hardware, pues yo creo que primero fallarian otras cosas, no crees? Por que quererle echar ese chango en la espalda a este leve desarrollo que les deseo compartir?

Yo no veo nada practico en programar este procedimiento considerando que pueda fallar la memoria o el CPU, o alguna otra cosa de hardware.

Ademas, acuerdate que mi procedimiento se basa en que la imagen YA ESTA GUARDADA en el archivo, independientemente de mi proceso, lo cual demuestra que seria dificil que hubiera problema para manejar esa imagen.

Ahora, que si hay guardados en el Blob archivos defectuosos, o invalidos, eso pues no lo causa mi procedimiento, aunque SI los atrapa como error y los rechaza.

Ahora, si puede alguien mostrarme ejemplos, manuales, o documentacion donde alguien use el Try para CREATE, pues favor de hacerlo.

Yo si les puedo mostrar esta pagina de expertos donde NO usan Try en ningun CREATE, pues como les digo anteriormente, CREATE no levanta EXEPTion.

Y lo pueden ver aqui, donde el titulo del tema es :
How to correctly write Try..Finally..Except statements?

Bueno, hasta luego, y gracias por los comentarios.
.......................

P.S. El problema del mensaje original, es que no me entendieron la pregunta. No es un problema que "tenga". Ya recibi aclaracion en el foro de Lazarus. Pero parece ser que no hay respuesta definitiva.

Última edición por ElMug fecha: 25-07-2012 a las 10:15:00.
Responder Con Cita
  #27  
Antiguo 25-07-2012
Avatar de Casimiro Notevi
Casimiro Notevi Casimiro Notevi is offline
Moderador
 
Registrado: sep 2004
Ubicación: En algún lugar.
Posts: 32.038
Poder: 10
Casimiro Notevi Tiene un aura espectacularCasimiro Notevi Tiene un aura espectacular
Cita:
Empezado por ElMug Ver Mensaje
Yo si les puedo mostrar esta pagina de expertos...
Eso me ha hecho gracia
Responder Con Cita
  #28  
Antiguo 25-07-2012
ElMug ElMug is offline
Miembro
NULL
 
Registrado: jul 2012
Posts: 163
Poder: 12
ElMug Va por buen camino
Cita:
Empezado por Casimiro Notevi Ver Mensaje
Eso me ha hecho gracia
Quien quiere ver circo en todo, pues muy su parecer.
Responder Con Cita
  #29  
Antiguo 25-07-2012
Avatar de Casimiro Notevi
Casimiro Notevi Casimiro Notevi is offline
Moderador
 
Registrado: sep 2004
Ubicación: En algún lugar.
Posts: 32.038
Poder: 10
Casimiro Notevi Tiene un aura espectacularCasimiro Notevi Tiene un aura espectacular
¡Qué atrevida es la ignorancia!
Responder Con Cita
  #30  
Antiguo 25-07-2012
Avatar de roman
roman roman is offline
Moderador
 
Registrado: may 2003
Ubicación: Ciudad de México
Posts: 20.269
Poder: 10
roman Es un diamante en brutoroman Es un diamante en brutoroman Es un diamante en bruto
Cita:
Empezado por ElMug Ver Mensaje

P.S. El problema del mensaje original, es que no me entendieron la pregunta. No es un problema que "tenga". Ya recibi aclaracion en el foro de Lazarus. Pero parece ser que no hay respuesta definitiva.
Yo sí entendí la pregunta: quieres saber si el formato con que se guarda una imagen en un campo blob es independiente de la aplicación con que se guarde o lea. También sé la respuesta: sí es independiente (creo que Delphius también lo mencionó). Si no puedes leer en una aplicación la imagen guardada en otra aplicación entonces hay un problema en la forma de leer la imagen.

// Saludos
Responder Con Cita
  #31  
Antiguo 26-07-2012
ElMug ElMug is offline
Miembro
NULL
 
Registrado: jul 2012
Posts: 163
Poder: 12
ElMug Va por buen camino
Cita:
Empezado por roman Ver Mensaje
Yo sí entendí la pregunta: quieres saber si el formato con que se guarda una imagen en un campo blob es independiente de la aplicación con que se guarde o lea. También sé la respuesta: sí es independiente (creo que Delphius también lo mencionó). Si no puedes leer en una aplicación la imagen guardada en otra aplicación entonces hay un problema en la forma de leer la imagen.

// Saludos
Hola Roman,

Es un poco mas alla el asunto de "independiente de la aplicacion".

Creo que lo diria asi "independiente de los diversos generadores de aplicaciones", mi cuestion, y aun me interesa saber de otras personas al respecto, porque el asunto se aboca a la centralizacion de bases de datos, en las que diversas aplicaciones clientes accedan al dato Blob.

Si digo "un poco mas alla", es porque aunque se llene el viejo criterio de C. F. Codd en el significado de "la data debe de ser independiente de la aplicacion", pues si lo llena en si, cada plataforma generadora de aplicaciones. Eso ya es rutina en bases de datos actuales.

Pero, por ejemplo, si centralizamos una base de datos y generamos, por decir un .exe de acceso con Lazarus, y uno con Delphi, usando practicamente el mismo codigo, DEBERIA de leer las imagenes que guarde uno, el otro, y viceversa. Pero no estoy seguro que eso pase con los campos Blob, asi como se puden leer los textos y numericos con plena compatibilidad.

Se me ha informado que Lazarus (indebidamente segun mi punto de vista) le AGREGA unos bytes al archivo Blob, lo cual haria la data dependiente de la aplicacion que genere el generador de aplicaciones Lazarus. Y tambien se me ha informado que Delphi no le agrega nada.

Pero es un poco mas complicado de concluir, porque en Lazarus, puede uno utilizar otros componentes que no sean los "default" de Lazarus.

Mi plan es, ya indagando un poco mas, usar los componentes que mas sea compatibles en eso con los demas generadores de aplicaciones.

Averiguar todo esto, debido a que hay bastantes plataformas generadoras de aplicaciones, que usan diversas tecnologias como Java, C++, etc., no es tan facil para uno encarar todo eso, pues tendria uno que instalar varias plataformas y generar sus aplicaciones para ello.

Pero, si el detalle es solo con Lazarus, y todos las demas plataformas guardan el Blob igual, tal como lo extraen del archivo de la grafica, pues es mas simple de resolver.

Asi que el problema no es de "leer" sino de como se "guarda" o almacena el archivo segun las diversas plataformas de programacion, o los componentes que se usen.

Y si este tema ya se vio antes, y hay respuestas y conclusiones, y asesoria al respecto, pues mucho les agradeceria saber de ello, pues de mi parte no encuentro aun nada conclusivo.

Lo que si, es que ya verifique que hay deferencia entre como guarda Lazarus y como guarda el SQLite Administrator.

Aclaro tambien que esto no debe de tener nada que ver con cual database se use.

Tambien aclaro que me inclino a pensar que tal vez el problema sea solo con los componentes default de Lazarus, pero no puedo concluir eso aun, en definitiva.

Tampoco descarto que haya algo que no he considerado.

Gracias por el interes en ayudar a resolver esto.

Última edición por ElMug fecha: 26-07-2012 a las 03:56:40.
Responder Con Cita
  #32  
Antiguo 26-07-2012
Avatar de roman
roman roman is offline
Moderador
 
Registrado: may 2003
Ubicación: Ciudad de México
Posts: 20.269
Poder: 10
roman Es un diamante en brutoroman Es un diamante en brutoroman Es un diamante en bruto
Cita:
Empezado por ElMug Ver Mensaje
Lo que si, es que ya verifique que hay deferencia entre como guarda Lazarus y como guarda el SQLite Administrator.

Aclaro tambien que esto no debe de tener nada que ver con cual database se use.
Pues sí; estoy de acuerdo. No uso Lazarus de manera que no he probado, pero si es como dices, que agrega unos bytes extra pues sería, a mi parecer también, un comportamiento incorrecto. Lo que se guarde en el blob debe ser tal como si se guardara en un archivo en disco.

Si consigo algo de tiempo, haré unas pruebas con Lazarus y SQLite.

// Saludos
Responder Con Cita
  #33  
Antiguo 26-07-2012
ElMug ElMug is offline
Miembro
NULL
 
Registrado: jul 2012
Posts: 163
Poder: 12
ElMug Va por buen camino
Gracias, Roman.
Responder Con Cita
  #34  
Antiguo 02-08-2012
Avatar de roman
roman roman is offline
Moderador
 
Registrado: may 2003
Ubicación: Ciudad de México
Posts: 20.269
Poder: 10
roman Es un diamante en brutoroman Es un diamante en brutoroman Es un diamante en bruto
Bueno, hasta ahora es que he podido hacer algunas pruebas. A reserva de confirmalo más tarde, lo que puedo ver hasta el momento es que el problema no está en SQLite, sino en Lázarus.

Si guardo una imagen BMP en una tabla de SQLite usando el SQL Administrator, no puedo leerla con una aplicación Lázarus con el código esbozado anteriormente.

Sin embargo, si esa misma imagen la leo con una aplicación Delphi (usando ZEOS), la leo sin problema, tal como debe ser.

De aquí concluyo que el problema está en Lázarus. De hecho, si guardo la imagen que leo desde Lázarus en un archivo y examino el archivo con un editor binario, veo que su contenido no tiene nada que ver con el de la imagen original.

Habrá que estudiar si algo estamos haciendo mal con Lázarus o si es simple y llanamente un bug.

Seguiré probando...

// Saludos
Responder Con Cita
  #35  
Antiguo 02-08-2012
Avatar de Casimiro Notevi
Casimiro Notevi Casimiro Notevi is offline
Moderador
 
Registrado: sep 2004
Ubicación: En algún lugar.
Posts: 32.038
Poder: 10
Casimiro Notevi Tiene un aura espectacularCasimiro Notevi Tiene un aura espectacular
Por curiosidad, ¿cómo la guardas desde lazarus?
Responder Con Cita
  #36  
Antiguo 03-08-2012
Avatar de roman
roman roman is offline
Moderador
 
Registrado: may 2003
Ubicación: Ciudad de México
Posts: 20.269
Poder: 10
roman Es un diamante en brutoroman Es un diamante en brutoroman Es un diamante en bruto
Esa parte no la he visto; únicamente he tratado de leer desde lázarus una imagen guardada con SQLite Administrator.

// Saludos
Responder Con Cita
  #37  
Antiguo 03-08-2012
Avatar de roman
roman roman is offline
Moderador
 
Registrado: may 2003
Ubicación: Ciudad de México
Posts: 20.269
Poder: 10
roman Es un diamante en brutoroman Es un diamante en brutoroman Es un diamante en bruto
¡Ah! ¿Te refieres a cómo la guardo en un archivo? Pues desde el Stream con el método SaveToFile.

// Saludos
Responder Con Cita
  #38  
Antiguo 03-08-2012
ElMug ElMug is offline
Miembro
NULL
 
Registrado: jul 2012
Posts: 163
Poder: 12
ElMug Va por buen camino
Cita:
Empezado por roman Ver Mensaje
Bueno, hasta ahora es que he podido hacer algunas pruebas. A reserva de confirmalo más tarde, lo que puedo ver hasta el momento es que el problema no está en SQLite, sino en Lázarus.

Si guardo una imagen BMP en una tabla de SQLite usando el SQL Administrator, no puedo leerla con una aplicación Lázarus con el código esbozado anteriormente.

Sin embargo, si esa misma imagen la leo con una aplicación Delphi (usando ZEOS), la leo sin problema, tal como debe ser.

De aquí concluyo que el problema está en Lázarus. De hecho, si guardo la imagen que leo desde Lázarus en un archivo y examino el archivo con un editor binario, veo que su contenido no tiene nada que ver con el de la imagen original.

Habrá que estudiar si algo estamos haciendo mal con Lázarus o si es simple y llanamente un bug.

Seguiré probando...

// Saludos
Muchas gracias, Roman.

Tengo esto que platicar al respecto:

Concuerdo contigo y posible cambie de componentes, o vea forma de modificar para que no agregue headers a la imagen. Sin embargo, tal vez requiera tambien cambiar la rutina que las lee.

Pero esta novedad me pone algunas dudas:
--------------------------------------------------
Hice la inversa, o sea de mandar a un archivo xxx.jpg o yyy.bmp con aplicacion Lazaro, y la guarda. Entonces, hice click en ella y el Windows image-viewer la abrio perfectamente, a pesar de que mande el blob identico como estaba en la base de datos (sqlite3).

Lo mismo con imagen .bmp.

Luego cree igualmente un archivo sin extension, solo xxx o yyy, y lo creo. Lo explore con Windows 7, y "no sabe" que tipo es (se hace el inocente). Entonce force al image viewer y si, las abre aun SIN extension.

Luego hago click en las imagenes sin extension, y me pide con QUE abrirlas, le obligue a Opera (browser) y las abre inmediatamente y correctamente sin chistar.

El archivo lo cree, segun yo, sin que se le quiten headers, mas si es asi, tendria que ver con CreateBlobStream, la cual yo considero que es generica para todo tipo de Blob.

Si acaso CreateBlobStream checa y quita headers, entonces Lazarus se la ha complicado demasiado, diria.

Lo bueno es que en Lazarus se puede meter uno al source-code y examinarlo/cambiarlo, pero eso seria algo delicado, y aun no lo contemplo.

No me es claro si una imagen grabada con Lazarus la lees con Delphi?

De inicio, no quise usar Zeus porque lei que ya esta sin desarrollos, pero lo voy a tratar. Que bien que me indicas al respecto.

Me les reporto si hay novedad, y te repito que te agradezco mucho la ayuda. Me es muy util saber que Delphi lee correctamente a SQLite Adminstrator.

Saludos a todos.
Responder Con Cita
  #39  
Antiguo 03-08-2012
Avatar de roman
roman roman is offline
Moderador
 
Registrado: may 2003
Ubicación: Ciudad de México
Posts: 20.269
Poder: 10
roman Es un diamante en brutoroman Es un diamante en brutoroman Es un diamante en bruto
A ver, creo que ya está un poco más claro, aunque sigue bastante oscuro .

Parece ser que siempre sí, la culpa es de SQLite, pero componentes como ZEOS saben cómo arreglar las cosas mientras que los componentes nativos de Lázarus no, o al menos todavía no encuentro como.

El problema con SQLite (y es que apenas hago mis pininos con este gestor) no es tanto que añada encabezados a un blob o que lo guarde en una forma no estándar. El problema es que SQLite usa los caracteres #0 (NULL) como separador de columnas de manera que no puede guardar bytes cero en un campo BLOB. Tal parece entonces que sustituye los ceros por un caracter de porcentaje %. Se supone que esto ya no es así en la versión 3 pero es con la que he estado haciendo pruebas y así es como guarda las imágenes.

No he instalado los componentes ZEOS en Lázarus (no pude ) pero examinando el código fuente, me encontré esto:

Código Delphi [-]
function DecodeString(Value: string): string;
var
  SrcLength, DestLength: Integer;
  SrcBuffer, DestBuffer: PChar;
begin
  SrcLength := Length(Value);
  SrcBuffer := PChar(Value);
  SetLength(Result, SrcLength);
  DestLength := 0;
  DestBuffer := PChar(Result);

  while SrcLength > 0 do
  begin
    if SrcBuffer^ = '%' then
    begin
      Inc(SrcBuffer);
      if SrcBuffer^ <> '0' then
        DestBuffer^ := SrcBuffer^
      else DestBuffer^ := #0;
      Inc(SrcBuffer);
      Dec(SrcLength, 2);
    end
    else
    begin
      DestBuffer^ := SrcBuffer^;
      Inc(SrcBuffer);
      Dec(SrcLength);
    end;
    Inc(DestBuffer);
    Inc(DestLength);
  end;
  SetLength(Result, DestLength);
end;

Esta función la usa en el método GetBlob de la clase TZSQLiteResultSet:

Código Delphi [-]
function TZSQLiteResultSet.GetBlob(ColumnIndex: Integer): IZBlob;
var
  Stream: TStream;
begin
{$IFNDEF DISABLE_CHECKING}
  CheckBlobColumn(ColumnIndex);
{$ENDIF}
  Stream := nil;
  try
    if not IsNull(ColumnIndex) then
    begin
      if TZAbstractResultSetMetadata(Metadata).GetColumnType(ColumnIndex)
        <> stBinaryStream then
        Stream := TStringStream.Create(GetString(ColumnIndex))
      else Stream := TStringStream.Create(DecodeString(GetString(ColumnIndex)));
      Result := TZAbstractBlob.CreateWithStream(Stream)
    end else
      Result := TZAbstractBlob.CreateWithStream(nil);
  finally
    if Assigned(Stream) then
      Stream.Free;
  end;
end;

Con un aplicación delphi abrí el archivo guardado desde el BlobField, le pase la función anterior y vacié la cadena nuevamente en un archivo y voilà, la imagen ya era la correcta.

La función compila sin problemas en Lázarus, pero no he podido usarla porque la clase TStringStream no es compatible con la de delphi así que todavía no encuentro cómo usarla para almacenar el blob, convertirlo y vaciarlo en un TBitmap.

Seguiremos informando...

// Saludos
Responder Con Cita
  #40  
Antiguo 03-08-2012
Avatar de Casimiro Notevi
Casimiro Notevi Casimiro Notevi is offline
Moderador
 
Registrado: sep 2004
Ubicación: En algún lugar.
Posts: 32.038
Poder: 10
Casimiro Notevi Tiene un aura espectacularCasimiro Notevi Tiene un aura espectacular
Qué extraño resulta ese asunto
Responder Con Cita
Respuesta


Herramientas Buscar en Tema
Buscar en Tema:

Búsqueda Avanzada
Desplegado

Normas de Publicación
no Puedes crear nuevos temas
no Puedes responder a temas
no Puedes adjuntar archivos
no Puedes editar tus mensajes

El código vB está habilitado
Las caritas están habilitado
Código [IMG] está habilitado
Código HTML está deshabilitado
Saltar a Foro

Temas Similares
Tema Autor Foro Respuestas Último mensaje
TClienDataSet Problemas con Campos Blob y Campos Calculados LEVV Conexión con bases de datos 2 11-05-2012 01:25:43
DB firebird meter y sacar texto e imagenes a campos blob , con delphi JXJ Firebird e Interbase 1 11-10-2010 11:52:34
Imagenes en campos BLOB y Delphi 7 s_dominguez Varios 0 15-02-2005 17:08:01
Imagenes en Campos Blob subzero Firebird e Interbase 11 26-11-2004 17:27:59
Imagenes(BLOB) Firebird con VB6 pzhero Firebird e Interbase 5 06-05-2004 15:32:45


La franja horaria es GMT +2. Ahora son las 01:35:30.


Powered by vBulletin® Version 3.6.8
Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
Traducción al castellano por el equipo de moderadores del Club Delphi
Copyright 1996-2007 Club Delphi