7
3

More than 5 years have passed since last update.

Vue.jsで要素を表示したままアニメーション

Last updated at Posted at 2018-11-28

Vueのアニメーションで実装方法を検索すると、「transition」がよく出てくるかと思います。
この「transition」もとても便利なのですが、
コンポーネントが表示・非表示になる時以外でも要素にアニメーションをつけたかったので、
CSSとVueを使って実装してみました。

今回はよく見かけるカルーセルの一種で、
次の画像がちら見えしてるパターンを作成した方法を紹介したいと思います。
↓こんな感じの!
sample_animation.png

transform、transition-durationを使ってこんなに簡単に!

動かしたい要素に対して
translateとtransition-durationを指定することで簡単にアニメーションを実装することが出来ます。

■こちらのページから動くデモを確認できます

App.vue
<template>
  <div id="app">
    <div class="sample">
      <div class="sample__wrap">
        //スライドさせたい要素のstyleにtransformを指定し、位置が動的に変わるように設定する(${position}pxの部分)
        <ul
          class="sample__list"
          :style="{ transform: `translate(${position}px, 0)` }"
        >
          <li class="sample__item sample__item--pink">1</li>
          <li class="sample__item sample__item--green">2</li>
          <li class="sample__item sample__item--orange">3</li>
          <li class="sample__item sample__item--blue">4</li>
          <li class="sample__item sample__item--yellow">5</li>
          <li class="sample__item sample__item--red">6</li>
        </ul>
      </div>
      <div
        class="sample__btn sample__btn--prev"
        @click="moveContainer('left');"
        :class="{ isDisabled: this.rightEnd }"
      ></div>
      <div
        class="sample__btn sample__btn--next"
        @click="moveContainer('right');"
        :class="{ isDisabled: this.leftEnd }"
      ></div>
    </div>
  </div>
</template>

<script>
export default {
  data() {
    return {
      itemWidth: 200,
      position: 0,
      leftEnd: true,
      rightEnd: false
    };
  },
  methods: {
    moveContainer(turn) {
      if (turn === "left") {
        if (this.position < -(this.itemWidth * 4)) {
          return;
        }
        this.position = this.position - this.itemWidth;
      } else {
        if (this.position === 0) {
          return;
        }
        this.position = this.position + this.itemWidth;
      }
      this.leftEnd = this.position === 0 ? true : false;
      this.rightEnd = this.position < -(this.itemWidth * 4) ? true : false;
    }
  }
};
</script>

<style lang="scss">
.sample {
  position: relative;
  margin: 100px auto;
  width: 300px;
  &__wrap {
    overflow: hidden;
    border: 5px solid #848484;
  }
  &__list {
    //translateの値が変化した時に、
    //ここのtransition-durationの指定でアニメーションしながら要素が動く
    transition-duration: 0.8s;
    margin: 0;
    padding: 0;
    display: flex;
    width: 1200px;
  }
  &__item {
    list-style: none;
    width: 200px;
    height: 200px;
    line-height: 200px;
    color: #fff;
    font-size: 50px;
    font-weight: bold;
    text-align: center;
    &--pink {
      background: #ff69b4;
    }
    &--green {
      background: #3cb371;
    }
    &--orange {
      background: #ffa500;
    }
    &--blue {
      background: #6495ed;
    }
    &--yellow {
      background: #ffd700;
    }
    &--red {
      background: #ff6347;
    }
  }
  &__btn {
    position: absolute;
    width: 40px;
    height: 40px;
    background-color: rgba(0, 0, 0, 0.5);
    border-radius: 50%;
    &:hover {
      opacity: 0.8;
    }
    &:before {
      position: absolute;
      top: 0;
      bottom: 0;
      left: 0;
      margin: auto;
      content: "";
      vertical-align: middle;
    }
    &--prev {
      bottom: 80px;
      left: -60px;
      &:before {
        left: 13px;
        width: 14px;
        height: 14px;
        border-bottom: 4px solid #fff;
        border-left: 4px solid #fff;
        -webkit-transform: rotate(45deg);
        transform: rotate(45deg);
      }
    }
    &--next {
      bottom: 80px;
      right: -60px;
      &:before {
        left: 9px;
        width: 14px;
        height: 14px;
        border-top: 4px solid #fff;
        border-right: 4px solid #fff;
        -webkit-transform: rotate(45deg);
        transform: rotate(45deg);
      }
    }
  }
}
.isDisabled {
  opacity: 0.2;
  &:hover {
    opacity: 0.2;
  }
}
</style>

translateの値を動的にする事でユーザーがクリックしたら、何か表示が変わったら、などなど色んな応用ができます。

まとめ

Vueのアニメーションで検索すると、「transition」の記事ばかりがでて、やりたいことが出来なかったりしましたが、
CSSを使う事でJQueryで実装していたようなUIも実装できるようになります。
(「transition」で実装できる箇所は「transition」を使うべきですが)
CSSのアニメーションも大分充実してきたので、うまくVue.jsと合わせて使っていきたいですね。

7
3
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
7
3