はじめに (対象読者・この記事でわかること)

本記事は、Webフロントエンドの見た目を動的に変化させたいと考えている PHP開発者・フロントエンドエンジニア を対象としています。
特に、既に slick‑slider を導入しているプロジェクトで、スワイプ(スライド)するたびに slidesToShow の数をランダムに変える実装方法を知りたい方に最適です。

この記事を読むと、以下ができるようになります。

  1. PHP から JavaScript に設定値を渡す基本的な手法。
  2. slick‑slider のオプション slidesToShow をスワイプイベントで動的に書き換えるコーディングパターン。
  3. 実装中にハマりやすいポイントとその回避策。

背景として、ユーザー体験(UX)向上のために「見える枚数が毎回変わる」ようなインタラクティブなスライダーを求める声が増えていることがあります。PHP だけで完結できない部分を、最小限の JavaScript と組み合わせて実装する手順を丁寧に紹介します。

前提知識

この記事を読み進める上で、以下の知識があるとスムーズです。
- HTML と CSS の基本的な知識(特に要素の幅やレイアウト)。
- PHP(7.4 以上)でサーバーサイドからデータを JSON 形式で出力できること。
- 基本的な JavaScript(ES5/ES6)と jQuery の使い方。

slick‑slider の概要とランダム表示の背景

slick‑slider は jQuery プラグインとして広く利用されているカルーセルライブラリで、slidesToShow オプションで一度に表示するスライド数を指定します。デフォルトでは固定値ですが、ユーザーの操作(スワイプ・クリック)に合わせてこの値を変えると、以下のような効果が得られます。

  • 視覚的な変化:毎回異なる枚数が表示されるため、ページに動的感が生まれます。
  • コンテンツの多様性:例えば商品一覧で「3枚→5枚→2枚」と変えると、ユーザーは新しい商品配置を自然に探せます。
  • レスポンシブな柔軟性:ウィンドウ幅に合わせて固定値で調整するだけでなく、運営側が意図的に変化させることが可能です。

このような目的を達成するために、PHP でランダムな整数列を生成し、JavaScript 側でスワイプイベントごとに取得して slick('slickSetOption') を呼び出す手法を採ります。

PHP と JavaScript の連携で実装する手順

以下では、実際に動くサンプルコードを交えて、全体の流れをステップごとに解説します。

ステップ 1 ― PHP 側でランダムな slidesToShow の候補を出力

まずはサーバーサイドで、許容する slidesToShow の範囲(例:1〜5)を決め、ページ読み込み時に JSON 配列として埋め込みます。

Php
<?php // config.php などで設定値を管理しても OK $minShow = 1; $maxShow = 5; // 1 から 5 の整数を 10 個作成し、重複しても構わない $randomValues = []; for ($i = 0; $i < 10; $i++) { $randomValues[] = mt_rand($minShow, $maxShow); } // JSON にエンコードして JavaScript へ渡す ?> <!DOCTYPE html> <html lang="ja"> <head> <meta charset="UTF-8"> <title>Slick Slider ランダム表示例</title> <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/slick-carousel/1.8.1/slick.min.css"/> <style> .slider img { width: 100%; } .slider { margin: 30px auto; width: 80%; } </style> </head> <body> <div class="slider"> <div><img src="img1.jpg" alt="1"></div> <div><img src="img2.jpg" alt="2"></div> <div><img src="img3.jpg" alt="3"></div> <div><img src="img4.jpg" alt="4"></div> <div><img src="img5.jpg" alt="5"></div> </div> <script src="https://code.jquery.com/jquery-3.6.0.min.js"></script> <script src="https://cdnjs.cloudflare.com/ajax/libs/slick-carousel/1.8.1/slick.min.js"></script> <script> // PHP が生成した JSON 配列をそのまま JavaScript 変数へ const slideShowCandidates = <?= json_encode($randomValues, JSON_UNESCAPED_SLASHES) ?>; console.log('候補配列:', slideShowCandidates); </script> </body> </html>

ポイントは json_encode で PHP 配列をそのまま JavaScript の配列リテラルに変換している点です。これによりサーバー側で生成したランダムな数列をクライアント側が即座に取得できます。

ステップ 2 ― slick‑slider の初期化とスワイプイベントハンドラの設定

次に、スライダーを初期化し、afterChange(スライドが切り替わった直後)イベントで slidesToShow を再設定します。

Html
<script> $(function() { // 初期表示はランダム配列の 0 番目を使用 let currentIdx = 0; const getNextShow = () => { // 配列を循環させる(インデックスが末尾を超えたら 0 に戻す) const val = slideShowCandidates[currentIdx]; currentIdx = (currentIdx + 1) % slideShowCandidates.length; return val; }; const $slider = $('.slider').slick({ slidesToShow: getNextShow(), slidesToScroll: 1, infinite: true, arrows: true, dots: true, // 必要に応じてレスポンシブ設定も入れる responsive: [ { breakpoint: 768, settings: { slidesToShow: 1 } } ] }); // スワイプや矢印クリック後に呼び出されるイベント $slider.on('afterChange', function(event, slick, currentSlide){ const newShow = getNextShow(); // slickSetOption で動的にオプションを書き換える $slider.slick('slickSetOption', 'slidesToShow', newShow, true); console.log(`slide ${currentSlide} 完了 → slidesToShow を ${newShow} に変更`); }); }); </script>

解説

  • getNextShow(): 事前に用意したランダム配列から次の値を取得し、インデックスを循環させます。これにより「スワイプごとに異なる」数値が順番に供給されます。
  • slickSetOption: slick‑slider が提供する API で、初期化後でもオプションを上書き可能です。第 4 引数に true を渡すと、内部的にスライダーを再描画します。
  • afterChange: ユーザーがスワイプした瞬間にトリガーされ、次の slidesToShow が即座に適用されます。

ステップ 3 ― レスポンシブ対応とパフォーマンスチューニング

1. ビューポート幅に応じた上限・下限設定

ランダム値が極端に大きいと、モバイル端末でレイアウトが崩れる恐れがあります。そこで、幅に応じて slidesToShow の上限と下限を制御します。

Js
function clamp(value, min, max) { return Math.min(Math.max(value, min), max); } function getResponsiveShow() { const base = getNextShow(); // 例: 4 const width = $(window).width(); if (width < 480) return clamp(base, 1, 2); // スマホは 1~2 枚に限定 if (width < 768) return clamp(base, 2, 3); // タブレットは 2~3 枚 return clamp(base, 3, 5); // デスクトップは 3~5 枚 }

afterChange 内で getResponsiveShow() を呼び出せば、端末ごとに適切な枚数が自動的に選択されます。

2. 再描画コストの低減

slickSetOption は内部でスライド幅の再計算を行うため、頻繁に呼び出すと若干のカクつきが出ることがあります。対策として デバウンス を導入します。

Js
let debounceTimer; $slider.on('afterChange', function(){ clearTimeout(debounceTimer); debounceTimer = setTimeout(() => { const newShow = getResponsiveShow(); $slider.slick('slickSetOption', 'slidesToShow', newShow, true); }, 150); // 150ms 待機 });

このように少し遅延させるだけで、ユーザーが連続でスワイプした場合でも無駄な再描画を抑制できます。

ハマった点やエラー解決

発生した症状 原因 解決策
スワイプ後にスライドが突然横にずれる slidesToShow の変更後に slickSetOption の第4引数を false にしていた 第4引数に true を渡し、スライダーを再計算させる
モバイルで 1 枚しか表示されず、ページ全体が崩れた slidesToShow が画面幅以上の数になっていた clamp 関数で上限・下限を設定し、幅に合わせて制御
コンソールに Uncaught TypeError: $slider.slick is not a function jQuery の読み込み順序が slick.min.js の前だった jQuery を先に読み込み、$(function(){ ... }) 内で初期化する
ランダム配列が毎回同じになる PHP の乱数シードが固定されていた(mt_srand を明示的に設定) mt_rand のみ使用し、シードはデフォルトに任せる

完全版サンプルコード

以下に、上記すべてを統合した完成形を掲載します。ローカル環境で index.php として保存し、画像ファイルを相対パスで配置すればすぐに動作します。

Php
<?php $minShow = 1; $maxShow = 5; $randomValues = []; for ($i = 0; $i < 12; $i++) { $randomValues[] = mt_rand($minShow, $maxShow); } ?> <!DOCTYPE html> <html lang="ja"> <head> <meta charset="UTF-8"> <title>PHP + Slick Slider ランダム slidesToShow</title> <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/slick-carousel/1.8.1/slick.min.css"/> <style> .slider img { width: 100%; display: block; } .slider { margin: 40px auto; width: 90%; } </style> </head> <body> <div class="slider"> <?php for ($i = 1; $i <= 8; $i++): ?> <div><img src="images/img<?= $i ?>.jpg" alt="img<?= $i ?>"></div> <?php endfor; ?> </div> <script src="https://code.jquery.com/jquery-3.6.0.min.js"></script> <script src="https://cdnjs.cloudflare.com/ajax/libs/slick-carousel/1.8.1/slick.min.js"></script> <script> const slideShowCandidates = <?= json_encode($randomValues, JSON_UNESCAPED_SLASHES) ?>; let idx = 0; function getNextShow() { const val = slideShowCandidates[idx]; idx = (idx + 1) % slideShowCandidates.length; return val; } function clamp(v, min, max) { return Math.min(Math.max(v, min), max); } function responsiveShow() { const base = getNextShow(); const w = $(window).width(); if (w < 480) return clamp(base, 1, 2); if (w < 768) return clamp(base, 2, 3); return clamp(base, 3, 5); } $(function() { const $s = $('.slider').slick({ slidesToShow: responsiveShow(), slidesToScroll: 1, infinite: true, arrows: true, dots: true }); let timer; $s.on('afterChange', function(){ clearTimeout(timer); timer = setTimeout(() => { $s.slick('slickSetOption', 'slidesToShow', responsiveShow(), true); }, 120); }); }); </script> </body> </html>

このコードは以下の点で汎用性があります。

  • PHP 側でランダム性を制御 → 配列の長さや範囲を簡単に変更可能。
  • クライアント側でレスポンシブ対応 → ウィンドウ幅に応じた slidesToShow の上限・下限が自動調整。
  • デバウンス実装 → 高速スワイプ時でも滑らかな表示が保たれる。

まとめ

本記事では、PHP で生成したランダムな数列を JavaScript に渡し、slick‑slider の slidesToShow をスワイプごとに動的に変更する具体的な実装手順を解説しました。

  • PHP から JSON 配列を出力し、クライアント側で取得する方法。
  • slickSetOptionafterChange イベントを組み合わせ、スライド切り替え時に枚数をランダム化。
  • レスポンシブ対応とデバウンス によるパフォーマンス最適化。

これにより、ユーザーに毎回異なるレイアウト体験を提供でき、サイトのインタラクティブ性を高められます。次回は、ユーザーのスクロール位置や閲覧履歴に基づくスライド枚数の最適化について掘り下げる予定です。

参考資料