ウェブ制作

サイト制作のちょっとしたティップスまとめ

当サイトのリンクには広告が含まれています。

【JS不要】CSSだけで作る、横一列の「はみ出しスクロール(スワイプ)」

CSSだけで横一列のはみ出しスクロールUIを作る方法を解説。flex、overflow-x、width: max-contentを使い、パンくずリストやサムネイル一覧に使えるスマホ向けUIを実装します。

ウェブ制作

公開日:2026/06/22

スマホサイトでよく見かける、横スクロールUIの簡単な作り方。

JavaScriptは使わず、CSSだけで実装します。

要素を改行させずに横一列へ並べ、画面幅に収まらない部分はそのまま画面外にはみ出させます

パンくずリスト、タグ一覧、カードレイアウト、横並びメニューなどでよく見かけるアレです。

See the Pen CSSだけで作る、横一列の「はみ出しスクロール(スワイプ)」 by MEMORUKA (@memoruka) on CodePen.

※スマホ実機での閲覧を推奨

デモコード

.parent {
	overflow-x: auto;
}

.flex {
	display: flex;
	flex-wrap: nowrap; /* 改行させない */
	width: max-content; /* 中身の横幅に合わせる */
}

.flex__item {
	flex-shrink: 0; /* 縮まずに要素の幅を確保する */
}
<div class="parent">
    <ul class="flex">
        <li class="flex__item">
            横並びアイテム 1
        </li>
        <li class="flex__item">
            横並びアイテム 2
        </li>
        <li class="flex__item">
            横並びアイテム 3
        </li>
    </ul>
</div>

※要所のみ抜粋

プロパティの役割解説

overflow-x: auto;

親要素に指定。
横幅に収まりきらず、はみ出した部分をスクロールできるようにします。
スマホでは、横方向にスワイプして表示できます。

flex-shrink: 0;

display: flex; の中身が縮むことを防止する。
flex の子要素は、デフォルトでは親要素の幅に収まるように縮もうとするので、これを防止。

ちなみに flex: 0 0 auto; と書いても可。ショートハンドの中身は、

flex-grow: 0;
flex-shrink: 0;
flex-basis: auto;

です。つまり、伸びない。縮まない。幅はwidthや中身に合わせる……という指定です。

flex-wrap: nowrap;

さらに横並びの要素の改行(折り返し)も防止。
一応、display: flex; の初期値は nowrap なので、別に書かなくても良いけど、明示する意味では、書いておくと分かりやすいです。

width: max-content;

これが大事。

親要素の幅を「中身が横に並んだ時の長さ」に自動で計算させる。

通常、ブロック要素は親要素の幅いっぱいに広がろうとしますが、max-content を指定することで、内在的な最大サイズ、つまり「中身が改行せずに並んだ場合に必要な幅」を自動で計算します。これにより、例えば .flex__item が10個あれば、10個分の横幅に合わせて .flex の幅が自動で決まります。

このプロパティのおかげで、横スクロールの終点を中身の幅に合わせやすくなります。
要素の数が増減しても、JavaScriptで幅を計算する必要は無く、HTMLを追加・削除するだけで、スクロールできる範囲も自然に追従します。CMS等とも相性が良い。

実装を想定したスマホデモ

See the Pen CSSだけで作る、横一列の「はみ出しスクロール(スワイプ)」 by MEMORUKA (@memoruka) on CodePen.

※スマホ実機での閲覧を推奨

.main-container {
	--margin: 30px;
	padding-inline: var(--margin);
	margin-inline: auto;
}

.wrapper {
	position: relative;

	&::after {
		content: "";
		position: absolute;
		top: 0;
		right: 0;
		bottom: 0;
		display: block;
		width: var(--margin);
		height: 100%;
		background: linear-gradient(to right,
				rgba(255, 255, 255, 0) 0%,
				rgba(255, 255, 255, .7) 50%,
				rgba(255, 255, 255, .9) 100%);
		transform: translate(100%, 0);
	}
}

.parent {
	position: relative;
	overflow-x: auto;
	margin-right: calc(-1 * var(--margin));
	scrollbar-width: none;

	&::-webkit-scrollbar {
		display: none;
	}
}

.flex {
	display: flex;
	flex-wrap: nowrap;
	width: max-content;
	padding-right: var(--margin);
	gap: 10px;
	line-height: 1;
}

.flex__item {
	flex-shrink: 0;
}
<div class="main-container">

    <div class="wrapper">
        <div class="parent">
            <ul class="flex">
                <li class="flex__item">
                    <img src="thumbnail_1.jpg" alt="サムネイル 1">
                </li>
                <li class="flex__item">
                    <img src="thumbnail_2.jpg" alt="サムネイル 2">
                </li>
                <li class="flex__item">
                    <img src="thumbnail_3.jpg" alt="サムネイル 3">
                </li>
            </ul>
        </div>
    </div>

</div>

※コードは要所のみ抜粋

実際にサイトに組み込むとしたら、こんな感じでしょうか。

CodePenには「パンくずリスト」と「サムネイル一覧」に横スクロールUIを組み込んでみました。

::after

右側にもコンテンツが続いていることを分かりやすくするため、スクロール領域を包む外側の親要素に、疑似要素でグラデーションを重ね、右端に配置しています。「右側にまだ続きがある」ということを視覚的に伝えやすくする工夫です。

scrollbar-width: none;

スクロールバーは、一応CSSで消しましたが、そもそもスマホ実機では消えるので基本は放ったらかしで良し。むしろ消してしまうと、PCのマウス操作では、スマホのように直接「掴む」ことが出来ないので、スクロールバーが無いと操作性が悪いです(一応、ホイール操作でスクロール自体は出来る)。

基本的にこのUIは、スマホ向けに限定するのがおすすめですが、PCでも操作させたい場合は、スクロールバーを表示しつつ、見た目が気になるならばCSSでカスタマイズすれば良いと思います。

現場からは以上です。

上に戻る