简体   繁体   中英

How can I compensate for longer load times when dynamically setting div dimensions with CSS and JS?

I am creating a Polymer app which displays information in rows in a custom element "table". I am using polymer flexbox classes to initially position elements. I need to take measurements with JS after the elements have loaded and assign widths to elements in the table accordingly. The problem goes something like this:

row 1
*--------------------*
|       *-----------*|
|       |    el a   ||
|       *-----------*|
*--------------------*
row 2
*--------------------*
|            *------*|
|            | el b ||
|            *------*|
*--------------------*

Row 1 and row 2 have fixed widths, but el a or b could be of any width. Regardless of contents of el a or b , I want the el's contained in the rows to be all the same width as the widest. So in this case, a is widest so el b should adjust its width to match a .

I am using polymers attached method to ensure the elements are loaded before taking scrollWidth measurements via JS. I initially ran into the problem of getting undefined elements when I tried to grab them with querySelector , but I fixed this using Polymer's async . I can style the elements fine in a modern browser just fine. Consider the following code.

attached: {
  this.async(function() {
    console.log(Polymer.dom(this.root).querySelector('#a').scrollWidth);
    console.log(Polymer.dom(this.root).querySelector('#b').scrollWidth);
  }, 100);
}

A modern version of chrome will return something like 100px for a and 60px for b . If I test an older version of chrome or a different browser like firefox, a and b will be 5-15px less than what modern chrome measured. I found out that if I increase the async time enough, no matter the age of the browser, I will eventually get a measurement matching what modern chrome returned. This is to say while it appears the div exists on the page and I can grab it with querySelector , it seems to be fluctuating so that it is not at its full width yet.

I don't like guessing how long it will take for the elements to fully load before I can take measurements. I am trying to figure out a way I can be 100% confident that the elements are done loading or perhaps an alternate method of styling these elements I have overlooked. I have had the most success with using setTimeout on the function that is doing the measuring and waiting for it to measure the same thing several times in a row. But even that has been inconsistent at times and occasionally b will be slightly less wide than a when the web page appears.

One option when you need to keep checking things, even if it's been true a couple times, is to continue to use setTimeout infinitely until the values are no longer changing for a certian # of iterations. For example, if they are still the same after 10 timeouts, stop the timeouts from going all together.

something like...

var count = 0;
function check() {
   do_something();
   if (same_as_last_time == true) {count++}
   if (count < 10) setTimeout (check,100);
}
setTimeout (check,100);

Although this could be wildly inefficient and possibly ineffective depending on how staggered your data is appearing.

I believe the actual solution here lies in the fact that you are using the variable ".scrollWidth" as your measurement point, which is a terrible measurement to standardize your widths across browsers. See this SO post for more info on that ( https://stackoverflow.com/a/33672058/3479741 )

I would recommend instead using a different method of acquiring the width and compare to see whether your results are more consistent. There are many options that remain more consistent than ".scrollWidth" in the article above.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM