TImage im RAM, PixelFormat pf8bit: Picture hat 0x0 Pixel
TImage im RAM, PixelFormat pf8bit: Picture hat 0x0 Pixel
Ich möchte gern zur Laufzeit ein TImage, das im 8-bit-Palettenmodus arbeitet, im RAM (unsichtbar) erzeugen, eine Graustufenpalette zuweisen, über Canvas.Pixels[] den Inhalt füllen, und am Ende mit Picture.SaveToFile('*.png') das ganze als Graustufen-PNG speichern.
Im Ergebnis habe ich bisher aber immer nur eine PNG-Datei von 65 Bytes erhalten, offensichtlich völlig leer.
Nun musste ich feststellen: Nach dem Erzeugen der Instanz und Zuweisen der Bildfläche haben sowohl Image.Width als auch Image.Canvas.Width und Image.Picture.Width die erwartete Größe. Aber sobald ich Image.Picture.Bitmap.PixelFormat auf pf8bit setze, werden für Image.Canvas.Width und Image.Picture.Width nur noch 0 zurückgegeben.
Unterstützt TImage in FreePascal überhaupt nichts anderes als pf24bit? Oder funktioniert das ganze nur, wenn Owner und Parent oder noch weitere Properties bestimmte Inhalte haben, die ich vielleicht aus Unkenntnis nicht oder nicht korrekt eingestellt habe?
Im Ergebnis habe ich bisher aber immer nur eine PNG-Datei von 65 Bytes erhalten, offensichtlich völlig leer.
Nun musste ich feststellen: Nach dem Erzeugen der Instanz und Zuweisen der Bildfläche haben sowohl Image.Width als auch Image.Canvas.Width und Image.Picture.Width die erwartete Größe. Aber sobald ich Image.Picture.Bitmap.PixelFormat auf pf8bit setze, werden für Image.Canvas.Width und Image.Picture.Width nur noch 0 zurückgegeben.
Unterstützt TImage in FreePascal überhaupt nichts anderes als pf24bit? Oder funktioniert das ganze nur, wenn Owner und Parent oder noch weitere Properties bestimmte Inhalte haben, die ich vielleicht aus Unkenntnis nicht oder nicht korrekt eingestellt habe?
Re: TImage im RAM, PixelFormat pf8bit: Picture hat 0x0 Pixel
Das ist ein Fall für OpBitmap http://www.theo.ch/lazarus/opbitmap64.zip , sowas geht mit Lazarus direkt meist nicht so toll.
Einfach package opbitmapforlazcompat.lpk in Package -> Package Datei (lpk) öffnen.
Es sind keine visuellen Komponenten, also muss man das (sic!) IDE nicht neu bauen.
Abhängigkeit ins Projekt aufnehmen.
Einfach package opbitmapforlazcompat.lpk in Package -> Package Datei (lpk) öffnen.
Es sind keine visuellen Komponenten, also muss man das (sic!) IDE nicht neu bauen.
Abhängigkeit ins Projekt aufnehmen.
Code: Alles auswählen
uses ... opbitmap, opbitmapformats;
....
var Png:TPNGImage;
begin
PNG:=TPNGImage.Create;
PNG.Width:=300;
PNG.Height:=300;
PNG.Canvas.Brush.Color:=clWhite;
PNG.Canvas.FillRect(Rect(0,0,300,300));
PNG.Canvas.Pen.Color:=clGray;
PNG.Canvas.MoveTo(0,0);
PNG.Canvas.LineTo(200,200);
PNG.PixelFormat:=pf8bit;
PNG.SaveToFile('test.png');
PNG.Free;
end;
Re: TImage im RAM, PixelFormat pf8bit: Picture hat 0x0 Pixel
Damit bekomme ich schon mal gewünschte Ergebnisse. Auch wenn ich noch nicht so recht verstehe, warum und wie hier die Farbreduktion funktioniert, weil ich offenbar doch RGB-Farben an die Pixel übergeben muss statt Palettenindizes. Aber egal.
Dennoch bin ich auch weiter neugierig, warum wohl der ursprüngliche Ansatz nicht funktionieren wollte.
Dennoch bin ich auch weiter neugierig, warum wohl der ursprüngliche Ansatz nicht funktionieren wollte.
Re: TImage im RAM, PixelFormat pf8bit: Picture hat 0x0 Pixel
So wird einfach am Schluss reduziert. Ist am einfachsten. Mit der Palette kannst du auch arbeiten, wenn du es auf die harte Tour haben möchtest.LigH hat geschrieben:Damit bekomme ich schon mal gewünschte Ergebnisse. Auch wenn ich noch nicht so recht verstehe, warum und wie hier die Farbreduktion funktioniert, weil ich offenbar doch RGB-Farben an die Pixel übergeben muss statt Palettenindizes. Aber egal.
Z.B. so
Code: Alles auswählen
var Png:TPNGImage;
i:integer;
begin
PNG:=TPNGImage.Create;
PNG.PixelFormat:=pf8bit;
PNG.ColorTable:=@Gray256Colors;
// PNG.ColorTable:=@WebColors;
PNG.Width:=300;
PNG.Height:=300;
for i:=0 to 300*300 do TBitmapData8(PNG.Data).RawArray^[i]:=200; //oder:
for i:=0 to 300 do TBitmapData8(PNG.Data).NativePixels[2,i]:=1;
PNG.SaveToFile('test.png');
PNG.Free;
end;
Re: TImage im RAM, PixelFormat pf8bit: Picture hat 0x0 Pixel
Leo, du scheinst ja richtige Schätze auf deiner Seite zu haben. Nach den Thumbnails nun das! Was hast du denn noch? Ich finde, diese Schätze wären im Lazarus CCR besser aufgehoben als auf dieser "geheimen" Seite. Ich weiß, du möchtest nicht gezwungen sein, die Komponenten groß zu pflegen, aber ich denke, im CCR sind 90% der Projekte ohnehin tot, aber immerhin ist das die zentrale Stelle für Packages außerhalb der offiziellen Distribution.
Re: TImage im RAM, PixelFormat pf8bit: Picture hat 0x0 Pixel
NativePixels[] klingt gut, nehm ich. 
Und ... woher wusstest du, dass ich greade 300×300-Bilder brauche?
— Ich versuche gerade, mir ein paar algorithmische "Pinsel" für MediaChance Dynamic Auto-Painter zu berechnen. Schöööönes Spielzeug! 

Und ... woher wusstest du, dass ich greade 300×300-Bilder brauche?


Re: TImage im RAM, PixelFormat pf8bit: Picture hat 0x0 Pixel
Ich bin Hellseher im Nebenjob.LigH hat geschrieben: Und ... woher wusstest du, dass ich greade 300×300-Bilder brauche?![]()

Re: TImage im RAM, PixelFormat pf8bit: Picture hat 0x0 Pixel
Meinst du mich?wp_xyz hat geschrieben:Leo,
Re: TImage im RAM, PixelFormat pf8bit: Picture hat 0x0 Pixel
Sorry, ja (genaueres Lesen meinerseits wäre von Vorteil...)
Re: TImage im RAM, PixelFormat pf8bit: Picture hat 0x0 Pixel
Leider muss ich dir von einem Fehler im TPNGImage berichten:
Sobald ich das Bild gespeichert habe, ist irgend etwas durcheinander. Ich kann daraufhin den Bildinhalt nicht korrekt weiter verändern, die NativePixels[] verändern daraufhin nur noch einen kleinen Teilbereich, irgendwie "interleaved".
Wenn ich aber nach dem Speichern gleich noch mal die wichtigsten Attribute neu setze (ich vermute mal, das PixelFormat wird das wichtigste sein, hab noch nicht weiter geforscht), dann läuft es wieder korrekt.
Sobald ich das Bild gespeichert habe, ist irgend etwas durcheinander. Ich kann daraufhin den Bildinhalt nicht korrekt weiter verändern, die NativePixels[] verändern daraufhin nur noch einen kleinen Teilbereich, irgendwie "interleaved".
Wenn ich aber nach dem Speichern gleich noch mal die wichtigsten Attribute neu setze (ich vermute mal, das PixelFormat wird das wichtigste sein, hab noch nicht weiter geforscht), dann läuft es wieder korrekt.
Code: Alles auswählen
imgAlpha.SaveToFile(FName);
imgAlpha.PixelFormat := pf8bit;
Re: TImage im RAM, PixelFormat pf8bit: Picture hat 0x0 Pixel
Du meinst, du speicherst das Objekt und arbeitest dann damit weiter (ohne neu von File zu laden)?LigH hat geschrieben:Leider muss ich dir von einem Fehler im TPNGImage berichten:
Kann schon sein und ist nicht direkt ein Fehler. Manchmal macht man aus Optimierungsgründen so etwas.
Am einfachsten kopierst du das PNG vor dem speichern:
Code: Alles auswählen
PNGSave:=TPNGImage.Create;
PNGSave.Assign(PNG);
PNGSave.SaveToFile('test.png');
PNGSave.free;
Nach dem Speichern (Exportieren nach PNG) kannst du natürlich sowieso nicht davon ausgehen, dass die interne Struktur des OpBitmap beim erneuten laden von PNG erhalten bleibt. Das kann nur das Format OPB.
Beispiel:
Code: Alles auswählen
procedure TForm1.Button1Click(Sender: TObject);
var Pic:TOPPicture;
i:integer;
PNGSave:TPNGImage;
begin
Pic:=TOPPicture.Create;
Pic.Bitmap.Width:=300;
Pic.Bitmap.Height:=300;
Pic.Bitmap.PixelFormat:=pf8bit;
Pic.Bitmap.ColorTable:=@Gray256Colors;
for i:=0 to 300*300 do TBitmapData8(Pic.Bitmap.Data).RawArray^[i]:=200; //oder:
for i:=0 to 300 do TBitmapData8(Pic.Bitmap.Data).NativePixels[2,i]:=1;
Pic.SaveToFile('testar.png'); //Export nach PNG
Pic.SaveToFile('testar.opb'); //Original speichern für spätere Nachbearbeitung
Pic.free;
end;
procedure TForm1.Button2Click(Sender: TObject);
var Pic:TOPPicture;
Str:String;
begin
Pic:=TOPPicture.Create;
Pic.LoadFromFile('testar.png');
WriteStr(Str,Pic.Bitmap.PixelFormat,' ',Pic.Bitmap.ColorTableSize);
ShowMessage(Str);
Pic.LoadFromFile('testar.opb');
WriteStr(Str,Pic.Bitmap.PixelFormat,' ',Pic.Bitmap.ColorTableSize);
ShowMessage(Str);
Pic.SaveToFile('testar2.png');
Pic.free;
end;
Re: TImage im RAM, PixelFormat pf8bit: Picture hat 0x0 Pixel
Ich denke es ist schon gut, so wie es ist.wp_xyz hat geschrieben:Leo, du scheinst ja richtige Schätze auf deiner Seite zu haben. Nach den Thumbnails nun das! Was hast du denn noch? Ich finde, diese Schätze wären im Lazarus CCR besser aufgehoben als auf dieser "geheimen" Seite. Ich weiß, du möchtest nicht gezwungen sein, die Komponenten groß zu pflegen, aber ich denke, im CCR sind 90% der Projekte ohnehin tot, aber immerhin ist das die zentrale Stelle für Packages außerhalb der offiziellen Distribution.