Как создать эффект выделения?

Я создаю эффект выделения с помощью анимации CSS3.

#caption {
    position: fixed;
    bottom: 0;
    left: 0;
    font-size: 20px;
    line-height: 30px;
    height:30px;
    width: 100%;
    white-space: nowrap;
    -moz-animation:  caption 50s linear 0s infinite;
    -webkit-animation:  caption 50s linear 0s infinite;
}
@-moz-keyframes caption { 
    0% { margin-left:120%; } 100% { margin-left:-4200px; }  
}
@-webkit-keyframes caption { 
    0% { margin-left:120%; } 100% { margin-left:-4200px; }  
}
<div id="caption">
    The quick brown fox jumps over the lazy dog. The quick brown fox jumps over the lazy dog. the quick brown fox jumps over the lazy dog.
</div>

Теперь я могу получить базовый эффект выделения, но код слишком специфичен для этой демонстрации.

Есть ли способ избежать использования определенных значений, таких как margin-left:-4200px;, чтобы он мог адаптировать текст любой длины?

Вот похожая демонстрация: http://jsfiddle.net/jonathansampson/XxUXD/, в которой используется text-indent, но еще с конкретными значениями.


person Fred Wu    schedule 20.01.2014    source источник


Ответы (4)


Вот мой подход с небольшим изменением разметки (я только что вставил span внутри абзаца):

.marquee {
  width: 450px;
  margin: 0 auto;
  overflow: hidden;
  box-sizing: border-box;
}

.marquee span {
  display: inline-block;
  width: max-content;

  padding-left: 100%;
  /* show the marquee just outside the paragraph */
  will-change: transform;
  animation: marquee 15s linear infinite;
}

.marquee span:hover {
  animation-play-state: paused
}


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


/* Respect user preferences about animations */

@media (prefers-reduced-motion: reduce) {
  .marquee span {
    animation-iteration-count: 1;
    animation-duration: 0.01; 
    /* instead of animation: none, so an animationend event is 
     * still available, if previously attached.
     */
    width: auto;
    padding-left: 0;
  }
}
<p class="marquee">
   <span>
       When I had journeyed half of our life's way, I found myself
       within a shadowed forest, for I had lost the path that 
       does not stray. – (Dante Alighieri, <i>Divine Comedy</i>. 
       1265-1321)
   </span>
   </p>


Никакие жестко закодированные значения, зависящие от ширины абзаца, не были вставлены.

Анимация применяет свойство CSS3 transform (при необходимости используйте префиксы), поэтому она работает хорошо.

Если вам нужно вставить задержку только один раз в начале, также установите animation-delay. Если вместо этого вам нужно вставить небольшую задержку в каждый цикл, попробуйте поиграть с более высоким padding-left (например, 150%)

person Fabrizio Calderan    schedule 20.01.2014
comment
Это не сработало для меня, когда я попробовал это на своем сайте. Я обнаружил, что необходим внешний ресурс prefixfree.js. Я должен был заметить (1) рядом с внешними ресурсами на странице jsfiddle. Для тех, кто просто скопировал приведенный выше текст, не переходя туда, вам также понадобится файл javascript без префикса. - person Recognizer; 25.06.2014
comment
конечно, вам нужно добавить префиксы поставщиков, где это необходимо. - person Fabrizio Calderan; 25.06.2014
comment
@FabrizioCalderan Спасибо, но просто интересно. Можно ли определить, закончилась ли прокрутка текста с помощью какого-либо javascript? - person NiCk Newman; 07.05.2015
comment
Я немного повернул его, чтобы вместо того, чтобы начинать справа, он начинался с первого текста, уже расположенного слева. Небольшое изменение: добавьте .marquee span { animation-delay: -7.5s; } - person Daan; 19.11.2015
comment
@fcalderan Можно ли сделать анимацию без пробела? Я имею в виду, что вторая анимация начинается до завершения первой анимации, чтобы между анимацией не было пробелов. Спасибо. - person Newbie009; 23.03.2017
comment
Очень приятно, но если текстовый символ становится больше или меньше, скорость также меняется. Чем больше текста, тем быстрее текст. Есть ли решение для этого? @fcalderan - person Yasin Okumuş; 28.09.2018
comment
@YasinOkumuş попробуйте увеличить продолжительность анимации - person Fabrizio Calderan; 28.09.2018
comment
Этот ответ сработал, если вы испытываете странное поведение, например: текст замедляется, когда он полностью виден (даже с linear) или: при использовании text-indent: -100% текст останавливается на ~ 50%. Возможно, у вас есть тег css: text-align: center. Из-за этого происходят странные вещи. Просто хотел добавить его сюда на случай, если у кого-то возникнут такие проблемы, как у меня. - person Kerwin Sneijders; 12.02.2019

Основываясь на предыдущем ответе, в основном @fcalderan, эта бегущая строка прокручивается при наведении курсора, с тем преимуществом, что анимация прокручивается полностью, даже если текст короче, чем пространство внутри нее прокручивается, также любая длина текста занимает одинаковое количество времени (это может быть плюсами или минусами) когда текст не зависает, он возвращается в исходное положение.

Нет жестко заданного значения, кроме времени прокрутки, что лучше всего подходит для небольших пространств прокрутки.

.marquee {
    width: 100%;
    margin: 0 auto;
    white-space: nowrap;
    overflow: hidden;
    box-sizing: border-box;
    display: inline-flex;    
}

.marquee span {
    display: flex;        
    flex-basis: 100%;
    animation: marquee-reset;
    animation-play-state: paused;                
}

.marquee:hover> span {
    animation: marquee 2s linear infinite;
    animation-play-state: running;
}

@keyframes marquee {
    0% {
        transform: translate(0%, 0);
    }    
    50% {
        transform: translate(-100%, 0);
    }
    50.001% {
        transform: translate(100%, 0);
    }
    100% {
        transform: translate(0%, 0);
    }
}
@keyframes marquee-reset {
    0% {
        transform: translate(0%, 0);
    }  
}
<span class="marquee">
    <span>This is the marquee text (hover the mouse here)</span>
</span>

person Mosè Bottacini    schedule 17.06.2019
comment
Совет будущим читателям: наведите курсор на текст в демо. - person BarryCap; 16.07.2021

Анимация принятых ответов не работает в Safari. Я обновил ее, используя перевод вместо padding-left, что делает анимацию более плавной и надежной.

Кроме того, в демо-скрипке принятых ответов много ненужных стилей.

Поэтому я создал простую версию, если вы просто хотите вырезать и вставить полезный код, а не тратить 5 минут на очистку демоверсии.

http://jsfiddle.net/e8ws12pt/

.marquee {
    margin: 0 auto;
    white-space: nowrap;
    overflow: hidden;
    box-sizing: border-box;
    padding: 0;
    height: 16px;
    display: block;
}
.marquee span {
    display: inline-block;
    text-indent: 0;
    overflow: hidden;
    -webkit-transition: 15s;
    transition: 15s;
    -webkit-animation: marquee 15s linear infinite;
    animation: marquee 15s linear infinite;
}

@keyframes marquee {
    0% { transform: translate(100%, 0); -webkit-transform: translateX(100%); }
    100% { transform: translate(-100%, 0); -webkit-transform: translateX(-100%); }
}
<p class="marquee"><span>Simple CSS Marquee - Lorem ipsum dolor amet tattooed squid microdosing taiyaki cardigan polaroid single-origin coffee iPhone. Edison bulb blue bottle neutra shabby chic. Kitsch affogato you probably haven't heard of them, keytar forage plaid occupy pitchfork. Enamel pin crucifix tilde fingerstache, lomo unicorn chartreuse plaid XOXO yr VHS shabby chic meggings pinterest kickstarter.</span></p>

person Pixelomo    schedule 14.06.2019
comment
Привет, спасибо за предупреждение о сафари, но один вопрос: если вы говорите, что убираете лишние стили... зачем добавлять padding: 0; высота: 16 пикселей; и тому подобное? Некоторые браузеры отображают правильно? Благодарю вас! - person Juanma Guerrero; 05.10.2020
comment
Я тестирую Safari версии 13.1.1, и принятый ответ работает нормально (OSX Mojave, октябрь 2020 г.) - person Juanma Guerrero; 05.10.2020
comment
Похоже на скоростной поезд :D - person divy3993; 18.02.2021

Следующее должно делать то, что вы хотите.

@keyframes marquee {
    from  { text-indent:  100% }
    to    { text-indent: -100% }
}
person Lars Beck    schedule 20.01.2014
comment
Нет, так как для этого учитывается родительская ширина: пусть он прокручивается до конца и видит, что текст исчезает до того, как он полностью исчезнет из поля зрения: jsfiddle.net/XxUXD/712 - person Christoph; 20.01.2014
comment
Я только что проголосовал за ваши комментарии, вы правы ... никто не сказал мне, что это работает бесконечно. ;) - person Lars Beck; 20.01.2014