LaravelのBladeテンプレートで、データの有無に応じて表示や非表示を切り替える必要がある場面がしばしばあります。@issetや@ifを使って分岐させるのがシンプルですが、これらを多用するとコードが冗長になりがちです。この記事ではこれを変えてコードを簡潔にし一目で読める範囲を増やす方法を紹介します。
素朴に @isset を使って書いた Blade の例が次です。
@php
/**
* @property string|null $name 名前
* @property string|null $email メールアドレス
* @property string|null $tag タグ
*/
class Member extends \Illuminate\Database\Eloquent\Model {}
/** @var Member $member */
@endphp
<body>
<header>
<h1>プロフィール</h1>
@isset($member->tag)
{{-- .tagには背景色あり角丸のタグっぽい見た目のスタイルがあてられる --}}
<div class="tag">{{ $member->tag }}</div>
@endisset
</header>
<main>
<div>メールアドレス</div>
@isset($member->email)
<div>{{ $member->email }}</div>
@endisset
<div>名前</div>
@isset($member->name)
<div>{{ $member->name }}様</div>
@endisset
</main>
</body>
@isset と @endisset で行が増えています。例のコードなので簡素な作りではありますが、実際はリレーションがネストしていて値の参照が長くなったり、@ifになったりもします。これを読みやすくしていきます。
まず表示する内容が空の場合、それで問題ないのであれば分岐自体を省略できます。冒頭の例でいえば、メールアドレスがそれにあたります。この時、分岐は不要です。
<main>
<div>メールアドレス</div>
<div>{{ $member->email }}</div>
</main>
もし空欄でもスペースを取ってしまう要素であり、それが消えて欲しいのであればCSSの:emptyが便利です。これを使う次のように要素の中身に文字列もノードもない場合はdisplay: noneとなるようにできます。
<style>
.tag:empty {
display: none;
}
</style>
<header>
<h1>プロフィール</h1>
<div class="tag">{{ $member->tag }}</div>
</header>
データがない場合に要素が空にならない場合でも見た目を消すコードの短縮はできます。これは class にあてたスタイルで消えるようにし、@class を使ってそれを呼び出すことで実現できます。
<main>
<div>名前</div>
<div @class(['u-hidden' => $member->name])>
{{ $member->name }}様
</div>
</main>
上記の方法を全て組み合わせると初めのコードは次のように素のHTMLに近い文量になり、一目で読めるようになります。
<style>
.tag:empty {
{{-- 実際の場合このスタイルはCSSファイルの中に入れておく --}}
display: none;
}
</style>
<body>
<header>
<h1>プロフィール</h1>
<div class="tag">{{ $member->tag }}</div>
</header>
<main>
<div>メールアドレス</div>
<div>{{ $member->email }}</div>
<div>名前</div>
<div @class(['u-hidden' => $member->name])>
{{ $member->name }}様
</div>
</main>
</body>
Blade は Laravel で長く使われているテンプレート機能であり、よくあるユースケースではそれに適した使い方が粗方用意されています。検索したり、最近ではAIに尋ねたりすると、それっぽい解決策が見つかりやすいです。