2021-10-16 Pinterest

by Ttt Yyy

HTML

<ul id="pinboard" class="pinboard"></ul>
<div id="console" />

CSS

ul#pinboard {
    height: 400px;
    margin: 12px;
    position: relative;
    
}

ul.pinboard li {
    border: 1px solid red;
    background-color: light-gray;
    margin: 12px;
    position: absolute;
    width: 150px;
}
ul.pinboard li img {
    vertical-align: bottom;
}

JavaScript

// https://docs.google.com/document/d/1fKQzmaLf7i2u3Y94W9hF_zY0gNL7oCeVEwmkdEI0n4Q/edit
const list = document.getElementById("pinboard");
function processImages(images, cols) {
  // Fixed width (hard-coded margin)
  const width = 160;
  const margin = 12;

  // Array of column heights, initialize at 0;
  const heights = new Array(cols).fill(0);

  // get shortest column
  function getShortestColumnIndex() {
    let minColIndex = 0;
    for (let colIndex = 1; colIndex < heights.length; colIndex++) {
      if (heights[colIndex] < heights[minColIndex]) {
        minColIndex = colIndex;
      }
    }
    return minColIndex;
  }

  function getItemHeight(item) {
    return item.offsetHeight + margin;
  }

  function renderImage(img) {
    const li = document.createElement("li");
    li.appendChild(img);
    list.appendChild(li);

    const columnIndex = getShortestColumnIndex();
    const height = getItemHeight(img);

    li.style.left = `${width * columnIndex}px`;
    li.style.top = `${heights[columnIndex]}px`;

    heights[columnIndex] += height;
  }

  let lastDisplayedPointer = 0;
  const loadedImages = new Array(images.length);

  // when image loaded, assign to image
  // then check previous to see if loaded and render only when previous has loaded
  function onImageLoad(img, index) {
    loadedImages[index] = img;
    for (let i = lastDisplayedPointer; i < loadedImages.length; i++) {
      if (loadedImages[i]) {
        // let console = document.getElementById("console");
        // console.innerHTML += i + "...";
        renderImage(loadedImages[i]);
      } else {
        lastDisplayedPointer = i;
        break;
      }
    }
  }

  for (let i = 0; i < images.length; i++) {
    const img = new Image();
    // img.onload = onImageLoad.bind(null, img, i);
    img.onload = () => {
      onImageLoad(img, i);
    };
    img.src = images[i];
  }
}

const url1 = "https://img.pokemondb.net/sprites/red-blue/normal/mewtwo.png";
const url2 =
 ...