Home Code About

スライド枚数によって発火

Slide 1
Slide 2
Slide 1
Slide 2
Slide 3
Slide 1
Slide 2
Slide 3
Slide 4

スライドの枚数によって、スライダーが発火したりしなかったりするようになっています。
CMSの記事を出力する箇所で使用しており、「記事の数が一定以上になった時のみスライダーを実行するようにしたい」とのご要望も着手前からあり実装したものです。


本案件自体にはチームで実装していたところに途中から参加したのですが、すでにSwiperを使用していたためSwiperで実装しております。が、Splideならばもっと簡単にできるようなので、こちらも試してみたいです。

<div class="c-tabs js-tab-scope">
    <div class="c-tabs__tab-list">
        <button type="button" data-trigger-id="tab1" class="c-tabs__tab js-tab-trigger is-current">スライド2枚</button>
        <button type="button" data-trigger-id="tab2" class="c-tabs__tab js-tab-trigger">スライド3枚(SPのみ)</button>
        <button type="button" data-trigger-id="tab3" class="c-tabs__tab js-tab-trigger">スライド4枚(両方)</button>
    </div>
    <div class="c-tabs__body">

        <div data-target-id="tab1" class="c-tabs__tab-panel js-tab-target is-current">

            <div class="c-slider-2">
                <div class="swiper c-slider-2__slide js-slider-2">
                    <div class="swiper-wrapper c-slider-2__container">
                        <div class="c-slider-2__item swiper-slide">Slide 1</div>
                        <div class="c-slider-2__item swiper-slide">Slide 2</div>
                    </div>

                    <!-- navigation buttons -->
                    <div class="c-slider-2__btn-wrap">
                        <div class="swiper-button-prev"></div>
                        <div class="swiper-button-next"></div>
                    </div>
                </div>
            </div>
            <!-- [/c-slider-2] -->

        </div>
        <div data-target-id="tab2" class="c-tabs__tab-panel js-tab-target">

            <div class="c-slider-2">
                <div class="swiper c-slider-2__slide js-slider-2">
                    <div class="swiper-wrapper c-slider-2__container">
                        <div class="c-slider-2__item swiper-slide">Slide 1</div>
                        <div class="c-slider-2__item swiper-slide">Slide 2</div>
                        <div class="c-slider-2__item swiper-slide">Slide 3</div>
                    </div>

                    <!-- navigation buttons -->
                    <div class="c-slider-2__btn-wrap">
                        <div class="swiper-button-prev"></div>
                        <div class="swiper-button-next"></div>
                    </div>
                </div>
            </div>
            <!-- [/c-slider-2] -->

        </div>
        <div data-target-id="tab3" class="c-tabs__tab-panel js-tab-target">

            <div class="c-slider-2">
                <div class="swiper c-slider-2__slide js-slider-2">
                    <div class="swiper-wrapper c-slider-2__container">
                        <div class="c-slider-2__item swiper-slide">Slide 1</div>
                        <div class="c-slider-2__item swiper-slide">Slide 2</div>
                        <div class="c-slider-2__item swiper-slide">Slide 3</div>
                        <div class="c-slider-2__item swiper-slide">Slide 4</div>
                    </div>

                    <!-- navigation buttons -->
                    <div class="c-slider-2__btn-wrap">
                        <div class="swiper-button-prev"></div>
                        <div class="swiper-button-next"></div>
                    </div>
                </div>
            </div>
            <!-- [/c-slider-2] -->

        </div>

    </div>
</div>
<!-- [/c-tabs] -->
.c-tabs__tab-list {
  margin-bottom: 10px;
  display: flex;
  gap: 10px;
}

.c-tabs__tab {
  display: inline-block;
  padding: 0.5em;
  color: inherit;
  touch-action: manipulation;
  cursor: pointer;
}

.c-tabs__tab.is-current {
  background-color: black;
  color: #fff;
}

.c-tabs__tab-panel {
  display: none;
}

.c-tabs__tab-panel.is-current {
  display: block;
}

.c-slider-2__item {
  aspect-ratio: 16/9;
  display: grid;
  place-content: center;
  background-color: lightgrey;
}

.c-slider-2 .swiper:not(.swiper-initialized) .c-slider-2__container {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: 30px;
}

@media screen and (max-width: 750px) {
  .c-slider-2 .swiper:not(.swiper-initialized) .c-slider-2__container {
    grid-template-columns: repeat(2, 1fr);
    gap: 15px;
  }
}

.c-slider-2 .swiper:not(.swiper-initialized) .swiper-button-prev,
.c-slider-2 .swiper:not(.swiper-initialized) .swiper-button-next {
  display: none;
}
document.addEventListener('DOMContentLoaded', () => {
    'use strict';

    let swiperInstances = [];

    const sliders = document.querySelectorAll('.js-slider-2'),
        mql = window.matchMedia('(max-width: 767px)');

    checkMediaQuery(mql); //初回実行

    mql.addEventListener('change', checkMediaQuery);

    function checkMediaQuery(mq) {
        // 既存のswiperインスタンスを破棄
        swiperInstances.forEach((swiper) => swiper.destroy(true, true));
        swiperInstances = [];

        sliders.forEach((slider) => {
            const slideCount = slider.querySelectorAll('.swiper-slide').length;
            if (mq.matches && slideCount >= 3) {
                // SP時 3枚以上
                handleSwiper(
                    slider,
                    2,
                    15,
                    '.swiper-button-next',
                    '.swiper-button-prev'
                );
            } else if (!mq.matches && slideCount >= 4) {
                // PC時 4枚以上
                handleSwiper(
                    slider,
                    3,
                    30,
                    '.swiper-button-next',
                    '.swiper-button-prev'
                );
            }
        });
    }

    function handleSwiper(
        slider,
        slidesPerView,
        spaceBetween,
        nextElSelector,
        prevElSelector,
        breakpoints = null
    ) {
        const swiper = new Swiper(slider, {
            loop: true,
            speed: 300,
            slidesPerView: slidesPerView,
            spaceBetween: spaceBetween,
            navigation: {
                nextEl: slider.querySelector(nextElSelector),
                prevEl: slider.querySelector(prevElSelector)
            },
            breakpoints: breakpoints
        });
        swiperInstances.push(swiper);
    }
});

document.addEventListener('DOMContentLoaded', () => {
    'use strict';

    const triggerSelector = '.js-tab-trigger';
    const targetSelector = '.js-tab-target';
    const scopeSelector = '.js-tab-scope';
    const currentClass = 'is-current';
    const triggers = document.querySelectorAll(triggerSelector);

    if (!triggers) return;

    for (const trigger of triggers) {
        trigger.addEventListener('click', () => {
            const targetId = trigger.dataset.triggerId;
            const thisScope = trigger.closest(scopeSelector);
            const thisTriggers = thisScope.querySelectorAll(triggerSelector);
            const thisTargets = thisScope.querySelectorAll(targetSelector);
            const currentTarget = thisScope.querySelector(
                `[data-target-id="${targetId}"]`
            );

            for (const thisTrigger of thisTriggers) {
                thisTrigger.classList.remove(currentClass);
            }
            for (const thisTarget of thisTargets) {
                thisTarget.classList.remove(currentClass);
            }

            trigger.classList.add(currentClass);
            currentTarget.classList.add(currentClass);
        });
    }
});