平滑缩放 img 并自动 scrollIntoView

Smoothly scale an img and automatically scrollIntoView

我正在尝试设置一个基本功能,以便在点击时平滑地切换 img 从比屏幕长到显示在显示器上(适合 window 大小)(来回)。它有点已经使用百分比等

我的问题是我想在两种状态之间进行平滑的动画过渡,但 img 正在被粗暴地缩放。 此外,每当我尝试使用“过渡”或“动画”时,当 img 恢复到其原始大小时,它会阻止滚动。我尝试使用关键帧后发生了同样的问题。

<!DOCTYPE html>
<html>
<head>
    <script src="jquery.js"></script>
    <style>
        img {
            margin: auto;
            display: block;
            padding: 2%;
            width: 90vw;
            box-sizing: border-box;
        }
        .scaled {
            width: auto;
            height: 100vh;
        }
        
    </style>
</head>
<body>
    <img class="item" src="images/kitten1.png"> 
    <img class="item" src="images/kitten2.png">
    <img class="item" src="images/kitten3.png">
</body>
<script>
    $(".item").click(function() {
        $(this).toggleClass('scaled');
        $(this).scrollIntoView();
    });
</script>
</html>

我还希望 window 视图(我指的是页面上滚动的位置)在缩放时以 img 为中心。我目前正尝试为此目的使用 scrollIntoView,但似乎什么也没发生。

提前谢谢你。第一次在这里发帖。我觉得这不应该太难,但可能与我现在能弄清楚的水平不同ଘ(੭ˊᵕˋ)੭ ̀ˋ


也尝试了以下方法,但 img 停留在 90vw 和 100vh ...

<!DOCTYPE html>
<html>

<head>
    <script src="jquery.js"></script>
    <style>
        img {
            margin: auto;
            display: block;
            padding: 2%;
            width: 90vw;
            box-sizing: border-box;
            object-fit: contain;
        }
    </style>
</head>

<body>

    <img class="item" src="images/kitten1.png">
    <img class="item" src="images/kitten2.png">
    <img class="item" src="images/kitten3.png">

</body>
<script>
    $(".item").click(function() {
    if ($(this).hasClass('scaled')) {
        $(this).animate({
            height: "none",
            width: "90vw"
        }, 1000);
        $(this).removeClass('scaled');
    }
        else {
            $(this).animate({
            width: "none",
            height: "100vh"
        }, 1000);
        $(this).addClass('scaled');
        }
    });

</script></html>

要滚动到单击的项目,请使用 $(this)[0].scrollIntoView();,因为 .scrollIntoView() 是 JavaScript 函数,而不是 jQuery。

平滑比例(过渡)。

CSS 不支持从自动宽度到特定宽度或相同到高度的过渡。参考:1, 2

选项 1。改用一侧。

您只能使用 max-heightmax-width。好处是你少写 JavaScript 和 CSS 响应式(媒体查询)也支持,无需任何添加。不好的是它只支持一侧(宽度或高度)。

完整代码:

<!DOCTYPE html>
<html>
<head>
    <script src="jquery.js"></script>
    <style>
        img {
            margin: auto;
            display: block;
            padding: 2%;
            max-width: 100vw;
            box-sizing: border-box;
            transition: all .3s;
        }

        .scaled {
            max-width: 50vw;
        }
    </style>
</head>
<body>
    <img class="item" src="images/kitten1.png"> 
    <img class="item" src="images/kitten2.png">
    <img class="item" src="images/kitten3.png">
</body>
<script>
    $(".item").click(function() {
        $(this).toggleClass('scaled');
        $(this)[0].scrollIntoView({
            behavior: "smooth"
        });
    });
</script>
</html>

See it in action

选项 2. 使用 JavaScript。

下面的代码将使用大量 JavaScript 来使 CSS 从宽度到高度的过渡正常工作。好事:当然支持宽度和高度之间的转换。坏事:CSS 响应图像的媒体查询将无法正常工作。为此需要更多 JS。

<!DOCTYPE html>
<html>
<head>
    <script src="jquery.js"></script>
    <style>
        img {
        margin: auto;
        display: block;
        padding: 2%;
        box-sizing: border-box;
        transition: all .3s;
        height: auto;
        width: 90vw;
    }

    .scaled {
        height: 100vh;
        width: auto;
    }
    </style>
</head>
<body>
    <img class="item" src="images/kitten1.png"> 
    <img class="item" src="images/kitten2.png">
    <img class="item" src="images/kitten3.png">
</body>
<script>
  $(window).on("load", function() {
    // wait until all images loaded.
    // loop each <img> that has class `item` and set height.
    $('img.item').each((index, item) => {
      $(item).attr('data-original-height', $(item)[0].offsetHeight);
      $(item).css({
        'height': $(item)[0].offsetHeight
      });
    });
  });


  $(".item").click(function() {
    if ($(this).hasClass('scaled')) {
      // if already has class `scaled`
      // going to remove that class after this.
      if ($(this).attr('data-scaled-width') === undefined) {
        // get and set original width to data attribute.
        $(this).attr('data-scaled-width', $(this)[0].offsetWidth);
      }
      $(this).css({
        'height': $(this).data('originalHeight'),
        'width': ''
      });
      $(this).removeAttr('data-original-height');

      $(this).removeClass('scaled');
    } else {
      // if going to add `scaled` class.
      if ($(this).attr('data-original-height') === undefined) {
        // get and set original height to data attribute.
        $(this).attr('data-original-height', $(this)[0].offsetHeight);
      }
      $(this).css({
        'height': '',
        'width': $(this).data('scaledWidth')
      });
      $(this).removeAttr('data-scaled-width');

      $(this).addClass('scaled');
      // check again to make sure that width has been set.
      if ($(this)[0].style.width === '') {
        setTimeout(() => {
          console.log($(this)[0].style.width);
          $(this).css({
            'width': $(this)[0].offsetWidth
          });
          console.log('css width for image was set after added class.');
        }, 500);// set timeout more than transition duration in CSS.
      }
    }

    $(this)[0].scrollIntoView({
      behavior: "smooth"
    });
  });
</script>
</html>

See it in action