JPEG aus Blob als ImageIcon anzeigen

  • Themenstarter Themenstarter Gast
  • Beginndatum Beginndatum
Status
Nicht offen für weitere Antworten.
G

Gast

Gast
Irgendwie google ich mir seit mehreren Stunden die Finger wund:

Ich habe in eine Informix-Datenbank ein 6kB großes JPEG in einem BLOB zu liegen. Irgendwie kriege ich es nicht hin, dieses JPEG als ImageIcon in einem JLabel auszugeben.

Code:
public void BildAnzeigen(int logname, JLabel ma_foto)
{
    this.logname = logname;
    this.ma_foto = ma_foto;
		
    logname = Integer.parseInt(CheckLogin.personalNummer);
		
    try
    {
        String getImage = "select persnr, foto from zeit_ma where persnr = " + logname;
        
        Connection mCon = getCon();
        Statement mstmt = mCon.createStatement();
        mstmt.execute(getImage);
        ResultSet mReSet = mstmt.executeQuery(getImage);
			
			
        while (mReSet.next())
        {
	System.out.println("Persnr: " + mReSet.getInt("persnr"));
	System.out.println("Foto: " + mReSet.getBlob("foto"));
				
				
				
	Blob bild = mReSet.getBlob("foto"); 
	InputStream is = bild.getBinaryStream(); 
	ByteArrayOutputStream out = new ByteArrayOutputStream(); 
	byte[] buffer = new byte[4096]; 
	try 
                {
	    for (int n; (n = is.read(buffer)) != -1; out.write(buffer, 0, n));
                } 
                catch (IOException e) 
                {
	    e.printStackTrace();
	} 
	
                try 
                {
	    is.close();
	} 
                catch (IOException e) 
                {
                    e.printStackTrace();
	} 
	
	ImageIcon icon = new ImageIcon(out.toByteArray()); 
	ma_foto.setIcon(icon);
           }
            mReSet.close();
            mstmt.close();
			
    }
    catch(SQLException sqlEx)
    {
        sqlEx.printStackTrace();
    }
}


Wenn ich mir mit einem sysout den Inhalt von mReSet.getBlob("foto") ausgeben lasse, erhalte ich "com.informix.jdbc.IfxBblob@e35bb7". Ist das überhaupt richtig so wie ich das versuche oder bin ich da völlig auf dem Holzweg?
Fehler werden vom Debugger keine gezeigt, allerdings erhalte ich eine NullPointerException, sobald das JLabel ma_foto geladen werden soll.

Für Hilfe wär ich dankbar 🙂
 
hi,


das ist etwas komplexer da hier konvertiert werden muss.

zuerst musst du das bild bereits konvertiert in die datenbank schreiben. es kann aber auch sein daß diese vielleicht ja schon korrekt in der DB vorliegen. falls du sie selber hineinschreibst musst du diese vorker konvertieren.

Code:
	 public static ByteArrayOutputStream convertToByteArrayOutputStream(InputStream istream, int quality) throws IOException {
		BufferedImage image = ImageIO.read(istream);
		ByteArrayOutputStream out =new ByteArrayOutputStream();
		JPEGImageEncoder encoder = JPEGCodec.createJPEGEncoder(out);
		JPEGEncodeParam param = encoder.getDefaultJPEGEncodeParam(image);
		quality = Math.max(0, Math.min(quality, 100));
		param.setQuality((float) quality / 100.0f, false);
		encoder.setJPEGEncodeParam(param);
		encoder.encode(image);
		out.close(); 
		return out;
	 }
.......

dbImage = new SerialBlob(ImageUtils.convertToByteArrayOutputStream(new FileInputStream(filepath), 100).toByteArray());

Beim Auslesen kannst Du es dann einfach mit:

Code:
image =  new ImageIcon(dbImage.getBytes(1, (int) getObject().getPageImage().length()));

erzeugen.
Frag aber bitte nicht nach Details. Das hat mich 3 Tage Nerven gekostet.... 😀

mfg
 
Mhm... schaut ja so ganz gut aus? Aber wie wende ich das an? Tschuldigung für die Frage, aber ich bin noch relativ frisch in java :###
 
Gast hat gesagt.:
Mhm... schaut ja so ganz gut aus? Aber wie wende ich das an? Tschuldigung für die Frage, aber ich bin noch relativ frisch in java :###

wenn dein bild (JPG!!) korrekt in der DB vorliegt sollte es nachdem du es ausgelesen hast ja als Blob vorliegen, was scheinbar auch der fall ist (du "nimmst" das ding allerdings in einen String). aus dem Blob machst du ein byte[] und gibst es dem ImageIcon-Konstruktor über.


wenn du die bilder selber in die datenbank schreibst bevor du sie wieder ausliest musst du sie mit der angegegeben methode konvertieren.

prüfe doch erstmal ob die bilder in korrekter form vorliegen. da gibt's doch bestimmt ein tool um sich die inhalte von blobs auf die platte zu kopieren. schau mal nach ob das sich wirklich als bild darstellt. wenn das schon nicht geht liegen sie schon in falscher form in der DB.
 
Mhm... der Hinweis war gut! Ich habe das JPG vorher über den DBVisualizer in die Datenbank eingefügt. Fehlermeldungen gabs dabei nicht. Offensichtlich scheint das Insert aber nicht wirklich geklappt zu haben. Ein Auslesen klappt zwar problemlos, allerdings ist das erzeugte Bild, leer.

Anbei mal meine Test-Klasse:

Code:
public class Test41 extends DBConnection{

    

   

    public static void main(String[] args) {
        new Test41().doIt();
    }

    private void doIt() {
        saveImgInDB();
        loadImgFromDB();
    }

    private void loadImgFromDB() {
        try {
        	Connection mCon = getCon();

            Statement stmt = mCon.createStatement();
            ResultSet rs = stmt.executeQuery("SELECT persnr, foto  FROM zeit_ma where persnr = 1234");
            if (!rs.next()) {
                return;
            }
            byte[] bytes = rs.getBytes(2);

            BufferedImage img = ImageIO.read(new ByteArrayInputStream(bytes));
            System.out.println(img);
            JFrame frm = new JFrame();
            frm.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            frm.getContentPane().add(new JLabel(new ImageIcon(img)),
                    BorderLayout.CENTER);
            frm.pack();
            frm.setVisible(true);

            stmt.close();
            rs.close();
            mCon.close();

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

    }

    private void saveImgInDB() {

        try {
            File file = new File("c:/image.jpg");

            BufferedImage img = ImageIO.read(file);

            ByteArrayOutputStream baos = new ByteArrayOutputStream();
            ImageIO.write(img, "jpeg", baos);
            baos.flush();

            Connection mCon = getCon();
            PreparedStatement ps = mCon
                    .prepareStatement("INSERT INTO zeit_ma(persnr,foto) VALUES (?,?)");
            ps.setInt(1, 1234);
            ps.setBytes(2, baos.toByteArray());

            System.out.println("Updated " + ps.executeUpdate() + " rows!");

            ps.close();
            baos.close();

            mCon.close();
        } catch (SQLException e1) {
            e1.printStackTrace();
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}


Außerdem wirft er mir beim Insert über die Klasse folgende Exception.

java.sql.SQLException: Smart-large-object error.


Könnte das dafür sprechen, dass der Informix-JDBC-Driver einen an der Klatsche hat?
 
wenn das bild leer ist liegt es falsch in der datenbank.

leg mal ein bild irgendwo auf die platte (ein "nicht-leeres" 🙂 ) und generiere mal auf diese weise ein Blob:
Code:
SerialBlob dbImage = new SerialBlob(ImageUtils.convertToByteArrayOutputStream(new FileInputStream(filepath), 100).toByteArray());
wie das nun speziell in deiner umgebung in die DB wandert kann ich dir nicht sagen, aber für Blobs sollte es eine direkte unterstützung geben.

wenn es dann "drin" ist nimm es normal mit dem visualizer heraus und schau es dir an. es sollte dann korrekt sein.
 
Status
Nicht offen für weitere Antworten.

Neue Themen


Zurück
Oben