【问题标题】:Marquee div in flexflex中的选框div
【发布时间】:2026-01-15 01:05:02
【问题描述】:

我正在尝试创建一个无限的水平“滚动”,如选框效果(例如like this one)。

这是我的代码:

.parent {
  border: 1px solid black;
  width: 100%;
  height: 2rem;
}

.container {
  height: 100%;
  display: flex;
  padding-left: 10%;
  border: 1px solid tomato;
  animation: marquee 5s linear infinite;
}

@keyframes marquee {
  0% {
    transform: translate(0%, 0);
  }
  100% {
    transform: translate(-100%, 0);
  }
}

.child1 {
  width: 10rem;
  height: 100%;
  background-color: #84B7DF;
}
.child2 {
  width: 18rem;
  height: 100%;
  background-color: #f58db6;
}
.child3 {
  width: 13rem;
  height: 100%;
  background-color: #ffc410;
}
.child4 {
  width: 21rem;
  height: 100%;
  background-color: #C8E7C1;
}
<div class="parent">
  <div class="container">
    <div class="child1"></div>
    <div class="child2"></div>
    <div class="child3"></div>
    <div class="child4"></div>
  </div>
</div>

如您所见,它有效,但并不完美。 我希望绿色矩形移动后,立即出现蓝色(略微间隔)的矩形,我不希望有一个完整的白色屏幕。

我希望我的意思很清楚......

非常感谢!

【问题讨论】:

  • 您必须手动循环元素。这意味着复制开头的那些并将其附加到后面。你不断地这样做,然后你就有了效果。
  • 调整.child元素的宽度,使其总和等于.container的宽度
  • @Nimsrules 你能举个例子吗?这是一个简单的例子,假设我没有固定宽度的子元素,但它们的宽度取决于它们的内容..
  • @CodeSpirit 你能举个例子吗?
  • 查看这篇文章 - *.com/questions/36433961/…

标签: javascript css scroll marquee


【解决方案1】:
.marquee {
    position: relative;
    width: 100%;
    height: 1.5em;
    line-height: 1.5em;
    overflow: hidden;
    > div {
        position: absolute;
        display: flex;
        flex-wrap: nowrap;
        animation: marquee 10s linear infinite;
        transform: translateX(100%);
        > * {
            display: inline;
            white-space: nowrap;
            &:last-child {
                padding-right: 100%;
            }
        }
    }
}
@keyframes marquee {
    0% {
        -moz-transform: translateX(100%);
        -webkit-transform: translateX(100%);
        transform: translateX(100%);
    }
    100% {
        -moz-transform: translateX(-100%);
        -webkit-transform: translateX(-100%);
        transform: translateX(-100%);
    }
}

【讨论】:

    【解决方案2】:

    您可以再添加一个具有相同子元素的容器元素,然后在父元素上使用 display: flexoverflow: hidden。您还可以使用vw 单位和flex 属性将.container 元素的宽度设置为大于窗口宽度。

    如果需要,请调整 container 上的 widthpadding 属性。

    .parent {
      border: 1px solid black;
      width: 100%;
      height: 2rem;
      display: flex;
      overflow: hidden;
    }
    
    .container {
      height: 100%;
      flex: 0 0 120vw;
      display: flex;
      padding-right: 10%;
      border: 1px solid tomato;
      animation: marquee 5s linear infinite;
    }
    
    @keyframes marquee {
      0% {
        transform: translate(0%, 0);
      }
      100% {
        transform: translate(-100%, 0);
      }
    }
    
    .child1 {
      width: 10rem;
      height: 100%;
      background-color: #84B7DF;
    }
    
    .child2 {
      width: 18rem;
      height: 100%;
      background-color: #f58db6;
    }
    
    .child3 {
      width: 13rem;
      height: 100%;
      background-color: #ffc410;
    }
    
    .child4 {
      width: 21rem;
      height: 100%;
      background-color: #C8E7C1;
    }
    <div class="parent">
      <div class="container">
        <div class="child1"></div>
        <div class="child2"></div>
        <div class="child3"></div>
        <div class="child4"></div>
      </div>
    
      <div class="container other">
        <div class="child1"></div>
        <div class="child2"></div>
        <div class="child3"></div>
        <div class="child4"></div>
      </div>
    </div>

    另一种解决方案是在container 上添加padding-right 宽度vw 单位。

    .parent {
      border: 1px solid black;
      width: 100%;
      height: 2rem;
      display: flex;
      overflow: hidden;
    }
    
    .container {
      height: 100%;
      display: flex;
      padding-right: 50vw;
      border: 1px solid tomato;
      animation: marquee 5s linear infinite;
    }
    
    @keyframes marquee {
      0% {
        transform: translate(0%, 0);
      }
      100% {
        transform: translate(-100%, 0);
      }
    }
    
    .child1 {
      width: 10rem;
      height: 100%;
      background-color: #84B7DF;
    }
    
    .child2 {
      width: 18rem;
      height: 100%;
      background-color: #f58db6;
    }
    
    .child3 {
      width: 13rem;
      height: 100%;
      background-color: #ffc410;
    }
    
    .child4 {
      width: 21rem;
      height: 100%;
      background-color: #C8E7C1;
    }
    <div class="parent">
      <div class="container">
        <div class="child1"></div>
        <div class="child2"></div>
        <div class="child3"></div>
        <div class="child4"></div>
      </div>
    
      <div class="container other">
        <div class="child1"></div>
        <div class="child2"></div>
        <div class="child3"></div>
        <div class="child4"></div>
      </div>
    </div>

    Javascript / jQuery 解决方案,您可以先创建原始元素的克隆并将其附加到父元素。创建一个函数,该函数将使用 setInterval 函数减少元素的左侧位置。如果偏移量小于同一元素的-width,则表示该元素不在屏幕上。在这种情况下,您应该将元素移动到窗口的末尾或带有一些偏移量的另一个元素的末尾。

    const parent = $(".parent");
    const container = $(".container");
    const offset = 250;
    
    const clone = cloner(container, parent, offset);
    
    function cloner(element, parent, offset) {
      const clone = element.clone();
      const width = element.width();
    
      clone.css({left: width + offset})
      parent.append(clone)
      return clone;
    }
    
    function move(element, size = 1) {
      const position = element.position().left;
      const width = element.width();
    
      if (position < -width) {
        const next = element.siblings().first();
        const nPosition = next.position().left;
        const nWidth = next.width();
        const wWidth = $(window).width();
    
        if (nPosition + nWidth < wWidth) {
          element.css({left: wWidth})
        } else {
          element.css({left: nPosition + nWidth + offset})
        }
    
      } else {
        element.css({left: position - size})
      }
    }
    
    window.mover = setInterval(() => {
      move(container)
      move(clone)
    }, 5)
    .parent {
      border: 1px solid black;
      width: 100%;
      height: 2rem;
      display: flex;
      overflow: hidden;
      position: relative;
    }
    
    .parent>div {
      position: absolute;
      left: 0;
    }
    
    .container {
      height: 100%;
      display: flex;
      border: 1px solid tomato;
    }
    
    .child1 {
      width: 10rem;
      height: 100%;
      background-color: #84B7DF;
    }
    
    .child2 {
      width: 18rem;
      height: 100%;
      background-color: #f58db6;
    }
    
    .child3 {
      width: 13rem;
      height: 100%;
      background-color: #ffc410;
    }
    
    .child4 {
      width: 21rem;
      height: 100%;
      background-color: #C8E7C1;
    }
    <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
    <div class="parent">
      <div class="container">
        <div class="child1"></div>
        <div class="child2"></div>
        <div class="child3"></div>
        <div class="child4"></div>
      </div>
    </div>

    【讨论】: