skip to Main Content

I have a slider with a html like this

<div id="bilder">                 | height: 70vh;
  <div id="pappediv">             | height: 100%;
    <div id="slider">             | height: 70%;
      <div id="imagecontainer">   | height: 100%;
        <p>                       | height: 100%;
          <img>                   | height: 100%;
          <img>                   | height: 100%; 
          <iframe>                | height: 100%;

(about 12 images and one iframe. all elements are closed, not shown here for brevety.)

I need to fill an array with the rendered widths of all images.
To this i use the following javascript:

$(document).ready(function(){

var elements = $('#imagecontainer>p').children();
var widths = [];
elements.each(function() {
    widths.push(this.width);
});
console.log(widths);
});

The code works and delivers width values for each image. This also means that the code is run after the photos are available.

the problem is, that the width values returned are not the rendered width, which is viewport-height dependent but always the same "ideal" width value intrinsic to the images.

instead of "this.width" I tried a couple of other properties:

outerWidth - the images have a padding, which is then included 
offsetWidth - same as outerWidth
clientWidth - same

     elements.each(function() {
              rect = this.getBoundingClientRect();
              widths.push(rect.width);
     });

yields same

elements.each(function() {
        var thiswidth = getComputedStyle(this).width;
        widths.push(thiswidth);
    });

yields widths as a string but also the wrong values.

also, I used

$(window).on('load', function(){..}

instead of

$(document).ready(function(){..} 

without success.

Maybe it’s a timing problem? Any hints are welcome.

2

Answers


  1. Chosen as BEST ANSWER

    I found out, that the only thing working was to make the script wait a little before evaluating the width property, using setTimeout(). Apparently, the javascript does evaluate things after loading but before complete rendering of the page. I wonder whether there is a command like

     $(window).on("render", ...)
    

    So the following code worked for me:

    elements = $('#imagecontainer>p').children();
    widths = [];
    
    setTimeout(function() {
        elements.each(function() {
            widths.push(parseInt(this.width));
        });
        /* do stuff here */
    },200);
    

  2. Using

    $(window).on("load", function( ){ … })

    is what you need in order to wait for the images to be loaded.

    See the code snippet below. Note I based the css on the height info that you included in your html. The intrinsic widths of the images are 200 and 210.

    $(window).on("load", function(){
      var elements = $('#imagecontainer>p').children();
      var widths = [];
    
      elements.each(function() {
        widths.push(this.width);
      });
    
      console.log(widths);
    });
    #bilder {
      height: 70vh;
      background-color: red;
      padding: 20px;
    }
    div {
      height: 100%;
      border: 2px solid black;
    }
    #slider {
      height: 70%;
      background-color: green;
      padding: 20px;
    }
    p {
      height: 100%;
      border: 2px solid yellow;
    }
    img {
      height: 100%;
    }
    <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.7.1/jquery.min.js"></script>
    <div id="bilder">                 | height: 70vh;
      <div id="pappediv">             | height: 100%;
        <div id="slider">             | height: 70%;
          <div id="imagecontainer">   | height: 100%;
            <p>                       | height: 100%;
              <img src="https://placebear.com/g/200/300">                | height: 100%;
              <img src="https://picsum.photos/210/300">                  | height: 100%;
              <iframe>
              </iframe>
            </p>
          </div>  <!-- END imagecontainer -->
        </div>  <!-- END slider -->
      </div>  <!-- END pappediv -->
    </div>  <!-- END bilder -->
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search