Lecture-écriture d'images dans des MemoryStream
Bonjour,
Je fais une base de données avec tous les drapeaux des pays du monde. J'ai récupéré les codes iso et entré les petites images qui étaient au format *.png.
En revanche pour extraire et lire les images, je n'y arrive pas. Je peux sortir les images de la base et les mettre sur disque. Paint et les autres afficheurs les lisent sans problème.
Par contre, les composants Delphi refusent de les lire (Voir ci-dessous)
Code:
1 2 3 4 5 6 7 8 9 10 11 12 13 14
| procedure TMainForm.Button3Click(Sender: TObject);
var
MS: TMemoryStream;
PNG: TPNGImage;
begin
PNG:= TPNGImage.create;
Ms:=TMemoryStream.Create; //<==Je crée un flux
png.LoadFromFile('.\Z.png');//<== Je charge un fichier *PNG (j'een ai téléchargé plusieurs, c'est pareil
png.SaveToStream(Ms); //<== Je mets l'image dans le flux
png.free;png:=nil; //Pour être sûr je réinitialise complètement l'image
PNG:= TPNGImage.create;
//C'est ici que l'erreur se produit (ligne ci-dessous)
png.LoadFromStream(Ms); //Message d'erreur : le fichier lu n'est pas une image png ou il est possible que ce
end; //Fichier soit endommagé |
Faut dire qu'en graphisme et images, je suis pas très fort, mais là c'est des heures et des heures de tests. :calim2:
Si ça se trouve, la réponse est simple. Si quelqu'un l'a... :merci:
Vadim
C'était donc tout simple! Ca marche aussi avec les bases de données
Bonjour Jipété,
Merci pour cette réponse claire, courte et explicite :roi: qui a tout résolu. Là, j'ai appris quelque chose d'important que je ne suis pas prêt d'oublier.
L'exemple de la cassette est bien vu!:yaisse:
En fait , je me servais des flux pour entrer et sortir de bases de données des images et autres fichiers pour des programmes externes (paint, pdfViewer etc) et il n'y avait aucun problème...
C'est en fait la première fois que je dois les ré-utiliser en Delphi. Et là avec Delphi, il y a eu un souci.
Ne connaissant pas trop les flux, je m'imaginais des lignes et des lignes de paramètres à régler et me perdais dans des tests aussi compliqués qu'inutiles..:marteau:.
"Pourquoi faire simple alors que l'on peut faire compliqué?" (devise Shadock) .... Au bout de 3 heures de vains essais : "Au secours le club!"
Ta réponse m'a permis également d'enregistrer proprement des images et autres fichiers dans une base de données. En effet, les éditeurs d'images (paint et autres)
pouvaient lire les images que j'enregistrais sans remettre le flux à zéro, mais ce n'était pas "propre". Là, grâce à ta réponse, maintenant, c'est du VRAI .png, sans le moindre défaut.
Code:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36
| procedure TMAD.remplitlistepays(Repertoire:String);
Var
fich :string;
MS: TMemoryStream;
PNG: TPNGImage;
begin
Repertoire:= IncludeTrailingPathDelimiter(repertoire);
//Met les drapeaux dans la base
nb:=0;
MS := TMemoryStream.Create();
/// MS.Position:=0; <== Sert à rien, car au create position est déjà à zéro
Pays.Open;
PNG:= TPNGImage.Create;
png.CleanupInstance;
While not Pays.eof do
begin
fich:=Pays.fieldByname('ALPHA2')+'.png'; //Les fichiers ont pour nom le Code pays ISO 3166 sur deux lettres
if not fileexists(fich) then
begin;
pays.next;
continue;
end;
png.LoadFromFile(fich);
MS.position:=0;///<=== Important si on veut utiliser le même TMemorystream (Ici, c'est le cas : nous sommes dans une boucle)
png.SaveToStream(MS);// On met l'image dans le flux comme on enregistre une K7
fich:=trim(fich);
MS.position:=0;//<=== Important pour lire, il faut être au début, comme pour une K7
pays.edit;
TBlobField(pays.fieldbyname('DRAPEAU')).LoadFromStream(MS);//<==lecture
pays.post; //autocommit activé
pays.next;
end;
end; |
Et pour lire, c'est pareil (Dans la procédure ci-dessous, je lis juste le premier enregistrement pour ne pas mettre trop de code) :
Code:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
| procedure TMainForm.btV2Click(Sender: TObject);
var
MS: TMemoryStream;
begin
Ms:=TMemoryStream.Create;
mad.Pays.open; //table où sont les drapeaux
/// MS.position:=0;<=== Inutile : a la création la position est forcément à zéro
TBlobField(Mad.PAYS.FieldByname('DRAPEAU')).SaveToStream(ms);//On enregistre, la position change
Ms.Position := 0;//<==maintenant on veut lire le flux : on remet la position au début
Image1.AutoSize := True;
Image1.Picture.LoadFromStream(Ms); //Affiche l'image dans un TImage sur la fiche
end; |
Maintenant, j'ai pas mal de programmes à corriger et de données à remettre "au carré".
En effet, comme je l'ai expliqué, les éditeurs externes (paint,pdfArchitect et autres) n'avaient pas détecté l'erreur.
Et je réalise (honteux et confus) que mes bases de données sont pleines de fichiers incorrects bien que les éditeurs externes peuvent peuvent les lire.
Au boulot!
Donc voilà, Jipété, je te tire mon chapeau! :merci: Discussion résolue pour ma part.
Vadim