Laravelでアイキャッチを自動生成したい!【Intervention Image】を使って背景画像に自動でタイトルを入れる

QiitaやZenn、はてなブログなどで、タイトルから自動でアイキャッチ生成してくれるものがありますよね。
それをLaravel上でやりたいです。
▼こういうのです。
バージョン
- Laravel Framework 8.83.23
用意してあるもの
- アイキャッチの背景ベース
- 自動挿入したいテキストのフォントファイル
どちらもstorageフォルダに入れておきます。
アイキャッチの背景ベースは、今回こちらを使用します。
Intervention Imageを入れる
まずはこちらでIntervention Imageというライブラリを入れます。
composer require intervention/image
続いてapp.phpのprovidersとaliasesに以下を追加。
'providers' => [
Intervention\Image\ImageServiceProvider::class // 追加
]
'aliases' => [
'Image' => Intervention\Image\Facades\Image::class // 追加
]
あと、シンボリックリンクを作成していない場合はこちらをやっておきましょう。
php artisan storage:link
画像にテキストを入れて、storageに保存する
画像を生成(=背景画像に記事タイトルを挿入)し、storageに保存する処理をつくります。
下記のようになります。
$file_name = 'creatopia_eyecatch_base.png'; // アイキャッチ背景にしたい画像のファイル名
$path = storage_path('app/public/images/' . $file_name );
$img = \Image::make($path);
// 画像にテキストを入れる。のちほど調整
$img->text($title, 500, 220, function ($font) { // $title = 記事のタイトル
$font->file(storage_path('app/public/fonts/Montserrat-SemiBold.ttf'));
$font->size(40);
$font->color("#FFF");
$font->align("center");
$font->valign("top");
});
// 名前を指定してstorageに保存
$save_path = storage_path('app/public/images/eyecatch_' . $id . '.png'); // $id = 記事のidで、これをアイキャッチのファイル名につけます。
$img->save($save_path);
画像を生成してみる
以上のやり方で、画像を生成を行ってみます。
すると、日本語が文字化けしてしまいました。
Montserratというフォントファイルを入れていたのですが、これは日本語フォントでないため、日本語はダメみたいです。
日本語を表示させるには、日本語フォントファイルを指定する必要があります。
ということでNoto Sans Japaneseに変更し、日本語を表示させることに成功しました。
そして今回は、自動生成アイキャッチなので、記事タイトルの長さによって改行するなど、テキスト長さによって調節が必要です。
ということで、PHPで「日本語」を任意の文字数で改行する方法を調べていたところ、まさに欲しい関数を自作されている記事を発見しました。
同じような状況の方はぜひ上記記事を。
とりあえず関数をお借りし、10文字で改行されるようにしてみます。
$title = $this->mb_wordwrap($title, 10);
いい感じです!!
あとは、「Image::text | Intervention Image v2 | intervention.io」を参考にしながら、好みの配置になるまで調整を続けていきます。
完成
こちらで完成!
調整後、最終的には下記のような感じです。
$title = $this->mb_wordwrap($title, 18); // https://nullnull.dev/blog/i-made-a-perfect-mb-wordwrap-function/ を参考
$img->text($title, 100, 220, function ($font) { // x = 100、y = 200
$font->file(storage_path('app/public/fonts/NotoSansJP-SemiBold.ttf')); // フォントファイルを日本語対応に
$font->size(54); // フォントサイズ54に
$font->color("#FFF");
$font->align("left"); // 左よせに
$font->valign("top");
});
ここで悩ましいのですが、Intervention Imageバージョン2では行間が調整できないようで、やや狭苦しい仕上がりになってしまいました。
もう少し行間広くしたい。。
執筆時現在(2023/5)アルファ版のIntervention Imageバージョン3なら「行間=Line height」が設定できるみたいです。
・・・と思ったら、なぜか行間が広くなるときもある。
そして時間を置いたら、また狭く戻りました。まったく同じ設定のはずなんですが、なぜでしょう?
Intervention Imageを使えば、画像にテキストを入れるだけでなく、リサイズしてファイル容量を小さくしたり、カラーや色彩を変化させたりなど、さまざまな画像処理ができます。また活用したいです。