Mehrere Bilder aus einer Datei lesen

Hutmacher

Bekanntes Mitglied
Hallo!
Ich habe eine Datei, in der mehrere Bilder enthalten sind. Sie sind im JPG-Format und durch zwei "\r\n" getrennt.
So ist sie aufgebaut:
Java:
<binäre Bild-Daten>\r\n\r\n<binäre Bild-Daten>\r\n\r\n<binäre ...

Eine Beispieldatei sieht im Editor so aus:
Java:
ÿØÿà JFIF ...ÿÙ

ÿØÿà JFIF ...ÿÙ
(am Ende von Zeile 1. sind zwei "\r\n", deswegen ist Zeile 2 leer)

Nun möchte ich diese beiden Bilder auslesen in ein BufferedImage und sie wieder speichern. Mein Versuch dazu sieht so aus:
Java:
try 
{
	RandomAccessFile file = new RandomAccessFile("multiple.txt", "rw");
			
	FileImageInputStream input = new FileImageInputStream(file);
	ImageReader reader = ImageIO.getImageReadersByFormatName("jpg").next();
	reader.setInput(input);
			
	BufferedImage i = reader.read(0);
	save(i, "green_output.jpg");

    input.skipBytes(4); //2x \r\n
			
	i = reader.read(0);
	save(i, "red_output.jpg");
} 
catch (FileNotFoundException e)
{
	e.printStackTrace();
} catch (IOException e) {
	e.printStackTrace();
}

In meiner "multiple.txt" sind zwei Bilder:
1. Ein grünes Rechteck
2. Ein rotes Rechteck

Wenn ich den obigen Code allerdings ausführe, erhalte ich zweimal das grüne Rechteck.

Ich habe das Ganze mal verpackt. In der angehängten Datei findet ihr:
- green.jpg
- red.jpg
- MultipleRandomAccessRead.java (und .class)
- multiple.txt (wird erstellt in MultipleRandomAccessRead.createFile)

Es wäre nett, wenn mir jemand etwas auf die Sprünge helfen könnte :)

PS: Falls das was zur Sache tut: Ich benutze ein RandomAccessFile-Objekt anstatt eines File-Objektes, da in meinen "richtigen" Dateien noch mehr Zeugs steht und ich dann sowieso hin- und herspringen muss. Die obige Datei ist nur eine Vereinfachung :)
 

Anhänge

  • example.zip
    10,7 KB · Aufrufe: 2

anti-held

Bekanntes Mitglied
Vill solltest du dann auch nicht 2x das 1. Bild auslesen...

Verwende um das 2. Bild auszulesen

Java:
reader.read(1);
 

Hutmacher

Bekanntes Mitglied
Danke erst mal für deine Antwort. Genau das habe ich schon einmal ausprobiert, aber es hat nicht geklappt. Ich habe mich noch einmal rangesetzt, herausgefunden, warum das nicht funktioniert und wie man das Ganze zum Funktionieren bringt.

Man sollte erwarten, dass
Code:
reader.read(1);
nun einfach das nächste Bild ausliest. Die read-Methode ist so konstruiert, dass sie einfach an der aktuellen Stelle im Stream versucht, das nächste Bild auszulesen.

Und nach
Java:
BufferedImage i = reader.read(0);
input.skipBytes(4); //2x \r\n
sollte der Stream auch an der Stelle vor dem nächsten Image stehen. Dem ist aber nicht so; wenn ich
Code:
reader.read(1);
aufrufe, bekomme ich nämlich folgende Exception:
Code:
javax.imageio.IIOException: Not a JPEG file: starts with 0x0d 0x0a

Nach etwas Rumhackerei im Hex-Editor habe ich bemerkt, dass 0x0d 0x0a genau \r\n entspricht. Man denkt also, dass der Stream das
Code:
input.skipBytes(4);
übergangen hat. Dem ist aber auch nicht so: wenn ich ein paar read-Methoden auf dem Stream aufrufe, sehe ich keine 0x0d 0x0a. Es bleibt also nur die Schlussfolgerung: Der Reader scheint den Stream (zumindest teilweise) gecached zu haben und greift bei der read-Methode zum Bildauslesen nicht (nur) auf den Stream, sondern auch auf seinen Cache zu.

Nachdem ich auch etwas im Sourcecode der JPEGImageReader-Klasse rumgeforstet habe, habe ich gesehen, dass diese einiges an nativem Code ausführt. Die native Library, die sie benutzt, scheint einen internen Buffer zu haben. Wenn wir aber einfach nur so im Stream herumseeken oder -skippen, wird der interne Buffer natürlich nicht aktualisiert/invalidiert.

Leider habe ich keine gute Möglichkeit gefunden, den Buffer zu invalidieren. Wenn man von der JPEGImageReader-Klasse erben würde, könnte man da vielleicht irgendwo etwas (über-)schreiben und es möglich machen. Da fast alle Methoden/Attribute in der Klasse aber private sind, wäre auch das bestimmt nicht einfach. Zusätzlich liegt diese Klasse im com.sun.imageio.plugins-Package und ist nicht Teil der öffentlichen Java-API (was auch immer genau das bedeuten mag).

Allerdings kann man die setInput-Methode aufrufen. Diese ruft nämlich als einzige die Methode
Code:
private native void setSource(long structPointer, ImageInputStream source);
auf, die den internen nativen Buffer zu erneuern scheint.

So, lange Rede, kurzer Sinn:
Damit das
Code:
input.skipBytes(4);
auch "wirkt", muss ich danach
Code:
reader.setInput(input);
erneut aufrufen. Danach sieht der Reader aber das erste Bild im Stream nicht mehr (vermutlich, da es vor der aktuellen Position im Stream liegt). In meinem Fall muss ich also wieder
Code:
reader.read(0);
aufrufen.

So funktioniert's:

Java:
try 

{

    RandomAccessFile file = new RandomAccessFile("multiple.txt", "rw");
    FileImageInputStream input = new FileImageInputStream(file);

    ImageReader reader = ImageIO.getImageReadersByFormatName("jpg").next();
    reader.setInput(input);

    BufferedImage i = reader.read(0);
    save(i, "green_output.jpg");

    input.skipBytes(4); //2x \r\n
    reader.setInput(input); //nativen Reader-Buffer erneuern

    i = reader.read(0);
    save(i, "red_output.jpg");
} 

catch (FileNotFoundException e)
{
    e.printStackTrace();
} catch (IOException e) {
    e.printStackTrace();
}

Nun werden das grüne und das rote Bild wieder ausgegeben. Vielleicht hilft das hier ja mal irgendjemandem :)
 
Zuletzt bearbeitet:
Ähnliche Java Themen
  Titel Forum Antworten Datum
M Input/Output Mehrere Bilder aus Resourcen auslesen Allgemeine Java-Themen 8
F Mehrere Bilder zu einem Großen zusammenkleben Allgemeine Java-Themen 3
I Mehrere Klassen mit den selben Daten Allgemeine Java-Themen 5
berserkerdq2 Ist es schlechter Programmierstyle mehrere Panes aufeinander zu machen? Allgemeine Java-Themen 1
Tarrew OpenAPI Schnittstelle - Mehrere Kunden mit unterschiedlichen Zugriffsrechten Allgemeine Java-Themen 2
A Mehrere for-Schleifen Allgemeine Java-Themen 2
M Mehrere Sounds Allgemeine Java-Themen 3
M Mehrere Ressourcen in einem package ablegen Allgemeine Java-Themen 1
Avalon DTO aus mehrere Entitäten erstellen Allgemeine Java-Themen 5
H Mehrere PNG-Files in einer Datei Allgemeine Java-Themen 9
H Mehrere Datentypen in einer Arraylist speichern Allgemeine Java-Themen 9
Curtis_MC Collections Liste anhand mehrere Kriterien sortieren Allgemeine Java-Themen 6
bueseb84 Git : Mehrere Server verwenden Allgemeine Java-Themen 3
L Mehrere .Jar Files aufrufen Allgemeine Java-Themen 9
L mehrere Methoden Allgemeine Java-Themen 19
W Variablenübergabe über mehrere Klassen Allgemeine Java-Themen 4
B StAX Parser - mehrere Methoden, ein XML Allgemeine Java-Themen 4
T String mehrere Worte Allgemeine Java-Themen 2
N Bei Mouse Events nicht mehrere Objekte erstellen Allgemeine Java-Themen 13
J Variablen Mehrere int-variablen in txt abspeichern und danach wieder auslesen Allgemeine Java-Themen 1
S JTable - mehrere ausgewählte Rows in ArrayList Allgemeine Java-Themen 5
H Java FX 2 Fragen um Programm in mehrere sprachen zu übersetzen in Gluon Framwork Allgemeine Java-Themen 3
F Listen - Mehrere Objekte Allgemeine Java-Themen 1
R Variable durch mehrere Methoden ändern und nutzen Allgemeine Java-Themen 17
S libGDX mehrere Texturen zu Einer zusammenfassen Allgemeine Java-Themen 0
X Mehrere booleans in Datei Speichern, Updaten und Laden Allgemeine Java-Themen 1
OnDemand CSV parsen mehrere Zeilen Allgemeine Java-Themen 22
K Mehrere Programmiersprachen gleichzeitig lernen Allgemeine Java-Themen 3
C Mehrere Seiten drucken in Hoch- und Querformat Allgemeine Java-Themen 0
perlenfischer1984 Mehrere Komponenten erstellen Allgemeine Java-Themen 3
F AWT Mehrere Tastatureingaben verarbeiten Allgemeine Java-Themen 5
J Mehrere Wörter getrennt in eine Array einlesen, wie ? Allgemeine Java-Themen 7
HarleyDavidson Best Practice Integer-Zahlenfolge über mehrere Programmstarts Allgemeine Java-Themen 7
F Mehrere JTables' drucken Allgemeine Java-Themen 0
2 mehrere Json Werte Parsen Allgemeine Java-Themen 3
stylegangsta Mehrere html seiten einer Homepage einlesen und als Textdatei ausgeben Allgemeine Java-Themen 14
P Mehrere Java Versionen auf dem Rechner Allgemeine Java-Themen 3
B JAVA - mehrere Clienten gleichzeitig starten. Nicht bei Code! Allgemeine Java-Themen 3
S PrintWriter.println() schreibt mehrere Zeilen Allgemeine Java-Themen 19
2 Mehrere Uhrzeiten Sortieren Allgemeine Java-Themen 2
T Jsoup: Mehrere Links nacheinander parsen Allgemeine Java-Themen 11
T Schlüsselworte mehrere public-Klassen in einem Paket Allgemeine Java-Themen 7
E Lesen von mehrere Csv-Datei und ihre Inhalte vergleichen Allgemeine Java-Themen 3
K GUI-Entwicklung - Dispose, enabling und mehrere Controller Allgemeine Java-Themen 1
M Eclipse Mehrere Threads, mehrere Konsolen Allgemeine Java-Themen 4
A Threads Lock über mehrere Abschnitte in verschiedenen Methoden Allgemeine Java-Themen 5
B Mehrere Objekte verschlüsselt serialisieren Allgemeine Java-Themen 6
S Tool um mehrere Klassen in einer Klasse vereinen? Allgemeine Java-Themen 6
K Mehrere Arrays auf einmal erstellen Allgemeine Java-Themen 2
R ListIterator über mehrere Arrays Allgemeine Java-Themen 13
J JFreeChart - Mehrere X-Achsen Einteilungen Allgemeine Java-Themen 3
S Mehrere Shapes "malen" Allgemeine Java-Themen 3
J Erste Schritte Mehrere Mauszeiger für Ping Pong Game Allgemeine Java-Themen 7
P Mehrere MP3s abspielen Allgemeine Java-Themen 3
M Mehrere CRLF entfernen Allgemeine Java-Themen 13
F Mehrere Threads - ein Stack Allgemeine Java-Themen 6
K Mehrere JVMs die auf eine Klasse mit statischen Variablen zugreift Allgemeine Java-Themen 19
B JUnit und mehrere Instanzen der selben Applikation Allgemeine Java-Themen 4
G mehrere Threads starten/stoppen Allgemeine Java-Themen 4
A Email versenden mehrere Zeilen Allgemeine Java-Themen 10
D Mehrere String-Werte in eine Tabellen-Zelle schreiben Allgemeine Java-Themen 8
R JTree - Mehrere Roots Allgemeine Java-Themen 6
Beckenbauer Mehrere Paragraphe in eine Word Datei schreiben Allgemeine Java-Themen 4
H Mehrere Anwendungen von Java kontrollieren lassen Allgemeine Java-Themen 10
T Edit: JLabel+MouseListener oeffnet mehrere Instanzen Allgemeine Java-Themen 5
O split mit einem ODER mehrere Tabulatoren oder Leerzeichen Allgemeine Java-Themen 6
M JFreeChart mehrere PieCharts erstellen Allgemeine Java-Themen 2
S Wie kann ein Observer mehrere Observables beobachten? Allgemeine Java-Themen 9
T Synchronisation von Listen bei Zugriffen durch mehrere Prozesse Allgemeine Java-Themen 15
D befehl auf mehrere objekte anwenden Allgemeine Java-Themen 7
B mehrere services in einem client Allgemeine Java-Themen 10
Meldanor Speichern der Datenbank - Lohnen sich mehrere Threads? Allgemeine Java-Themen 2
G Process - mehrere Commands?! Allgemeine Java-Themen 2
O Mehrere Exemplare(Kopieen) drucken Allgemeine Java-Themen 2
S log4j Logging über mehrere Klassen Allgemeine Java-Themen 13
F 1 Key - mehrere Values Allgemeine Java-Themen 3
G JOGL mehrere GLCanvas erstellen Allgemeine Java-Themen 2
S Mehrere Listen ineinander verschachteln Allgemeine Java-Themen 22
P Java3D mehrere Ebenen parallel zu yz-Ebene Allgemeine Java-Themen 9
R mehrere jar Dateien kompinieren Allgemeine Java-Themen 14
P Mehrere Instanzen der selben Appl. verhindern Allgemeine Java-Themen 12
M Scanner-Methode: Mehrere Eingaben mit Exception behandeln Allgemeine Java-Themen 10
I Wie kann ich mehrere Mp3 Tags ausgeben? Allgemeine Java-Themen 6
I Mehrere MP3 Dateien einlesen? Allgemeine Java-Themen 3
G String.replaceall - mehrere Zeichen durch eines ersetzen Allgemeine Java-Themen 5
C ArrayList sortieren (mehrere Kriterien) Allgemeine Java-Themen 6
N mehrere klassen extenden Allgemeine Java-Themen 33
G Oracle will mehrere hundert Produkte patchen Allgemeine Java-Themen 5
F Logger in mehrere Dateien mit log4J Allgemeine Java-Themen 4
W Properties-Klasse: mehrere Parameter-Belegungen übergeben? Allgemeine Java-Themen 2
Daniel_L Mehrere (XML-)Datei aus einer ZIP-Datei auslesen Allgemeine Java-Themen 4
V Mehrere main() in jar, wie starten? Allgemeine Java-Themen 4
A Problem: Mehrere PDF-Files nacheinander Öffnen Allgemeine Java-Themen 12
D Mit Linux mehrere Kommandos in einem Subprozeß Allgemeine Java-Themen 3
D Suche sowas wie Map nur für mehrere Werte Allgemeine Java-Themen 13
V JFilechooser, mehrere Datein selektieren und Reihenfolge? Allgemeine Java-Themen 2
G mehrere Threads verwalten? Allgemeine Java-Themen 14
K Applet dass auf mehrere Bibliotheken zugreift Allgemeine Java-Themen 13
F mehrere Verzeichnisse als Parameter Allgemeine Java-Themen 15
G mehrere url's in ein array (problem mit // ) Allgemeine Java-Themen 7

Ähnliche Java Themen

Neue Themen


Oben