Stefan: Größe (width/height) eines Bildes ermitteln

Hallo,

ich möchte gerne mittels Javascript Bilder an ein Fenster anpassen. Das ist auch weiter kein Problem, damit ich aber das Bild nicht verzerre, brauche ich die Originalgröße des Bildes. Ich habe mir gedacht, das mache ich einfach durch auslesen der width/height Attribute bevor ich das Bild anpasse.
Das klappt aber nicht immer: Wenn das Bild noch nicht geladen wurde, wenn ich die Attribute auslese (was beim ersten mal immer der Fall ist) gibt es keine korrekten Werte. Ich kenne leider weder eine Funktion mit der ich darauf warten kann, bis das Bild geladen wurde, noch gibt es für Bilder ein onload-handler.

Mir fallen da nur zwei Möglichkeiten ein:
1.) Die Größe aller Bilder wird irgendwo hinterlegt, in einem Array oder so
Nachteil: Man muss für jedes neue/geänderte Bild immer diese Liste anpassen
2.) Mittels xmlhttprequest das Bild (oder zumindest den Anfang) laden und aus dem Header die Größe auslesen.
Nachteil: Mehr Traffic, aufwendig zu programmieren

Kennt irgendjemand noch andere Möglichkeiten?

Viele Grüße,
Stefan

  1. 2.) Mittels xmlhttprequest das Bild (oder zumindest den Anfang) laden und aus dem Header die Größe auslesen.

    schicke einen xmlhttprequest auf ein script, welches dir die bildgröße ermittelt und dir nur diese daten zurückschickt - damit hälst du den traffic in grenzen oder lasse die bildgröße bzw die dimensionen direkt als attribute setzen (vorher serverseitig berechnen lassen) - dann kannst du sie per javascript nachher wieder lesen

    1. 2.) Mittels xmlhttprequest das Bild (oder zumindest den Anfang) laden und aus dem Header die Größe auslesen.
      schicke einen xmlhttprequest auf ein script, welches dir die bildgröße ermittelt und dir nur diese daten zurückschickt - damit hälst du den traffic in grenzen oder lasse die bildgröße bzw die dimensionen direkt als attribute setzen (vorher serverseitig berechnen lassen) - dann kannst du sie per javascript nachher wieder lesen

      So ähnlich habe ich es jetzt gemacht, ich lese die Größe schon vorher beim Seitenaufruf mittels PHP aus und schreibe sie direkt in die Ausgabe der Seite.

      Vielen Dank,
      Stefan

  2. Hi,

    1.) Die meisten Browser kennen sehr wohl ein load-Event, welcher aber evtl. nicht zuverlässig funktioniert.

    2.) Ich habe es mal so gemacht, in dem ich in einem setInterval die complete eigenschaft des Bildes abgefragt habe. Wenn complete === true, dann clearInterval.

    Gruß!

    1. 2.) Ich habe es mal so gemacht, in dem ich in einem setInterval die complete eigenschaft des Bildes abgefragt habe. Wenn complete === true, dann clearInterval.

      complete funktionierte lange Zeit ebenfalls nicht zuverlässig, wobei ich glaube die Browser die damit Probleme haben sind mittlerweile ausgestorben, trotzdem halte ich onload für ausreichend.

      Struppi.

  3. Hallo Stefan,

    Das klappt aber nicht immer: Wenn das Bild noch nicht geladen wurde, wenn ich die Attribute auslese (was beim ersten mal immer der Fall ist) gibt es keine korrekten Werte. Ich kenne leider weder eine Funktion mit der ich darauf warten kann, bis das Bild geladen wurde, noch gibt es für Bilder ein onload-handler.

    Du kannst die Eigenschaft complete in einer Warteschleife abfragen:

    var img;  
    var intervalId;  
      
    function checkImg() {  
     if (img.complete) {  
      window.clearInterval(intervalId);  
      alert("Size: " + img.width + ":" + img.height);  
     }  
    }  
      
    function start() {  
     img = new Image();  
     img.src = "pavatar.png";  
     intervalId = window.setInterval("checkImg()", 10);  
    }  
      
    window.onload = start;
    

    Eine statische Variante (Arrays) wäre aber trotzdem zu bevorzugen, das geht schneller und die Bilder müssen hierzu noch nicht zum Client übertragen werden.

    Grüße

    Marc Reichelt || http://www.marcreichelt.de/

    --
    panic("Oh boy, that early out of memory?");
            linux-2.2.16/arch/mips/mm/init.c
    Selfcode: ie:{ fl:| br:> va:} ls:< fo:} rl:( n4:( ss:) de:> js:| ch:? sh:| mo:) zu:)
  4. Hallo Stefan,

    ich hatte dazu mal einige Versuche gemacht. Alles ohne Gewähr! Getestet mit FF3 und IE7. Vielleicht kann jemand ergänzen, wie das bei weiteren Browsern aussieht.

    Wenn der Ereignis-Handler vor dem Beginn des Ladevorgangs gesetzt wird, dann werden die Ereignisse ausgelöst, unabhängig davon, ob sich das Bild im Cache befindet oder nicht.
    Getestet: FF3; IE7

    meinBild.onload  = ... Ereignis-Handler
    meinBild.onerror  = ... Ereignis-Handler
    meinBild.src = ... Ladevorgang

    Wenn die Ereignis-Handler nach Beginn des Ladevorgangs gesetzt werden, gibt’s Probleme.

    meinBild.src = ... Ladevorgang
    meinBild.onload  = ... Ereignis-Handler
    meinBild.onerror  = ... Ereignis-Handler

    Für IE7 gilt.
    Ist das Bild im Cache, wird das onload-Ereignis für dieses Bild nicht ausgelöst.

    Für FF3 gilt: Das onload-Ereignis wird ausgelöst - auch wenn sich das Bild im Cache befindet.

    Folgendes funktioniert im FF3 und IE7

      
    if (meinBild.complete) {  
        bildGeladen(meinBild, "complete");  
    } else {  
        meinBild.onload  = function() { bildGeladen(this, "onload"); };  
        meinBild.onerror = function() { bildGeladen(this, "onerror"); };  
    };  
    
    

    FF3 ist in bezug auf »complete« allerdings fehlerhaft.

    Wenn ein Bild nicht geladen werden kann, dann ist - erwartungsgemäß - beim ersten Aufruf (leerer Cache; Strg+F5) »complete==false«, »onerror« wird ausgelöst.
    Bei einem Refresh (F5) ist - wider Erwarten - bei dem fehlerhaften Bild »complete==true«.

    Der IE7 verhält sich hier korrekt.

    Gruß Uwe