TL;DR;
タイトルの通りで、古典的なImage.onloadよりImage.decode使おうね
2024年なら、という話です
そもそもImage.onloadってなに?
const image = new Image();
image.src = 'hoge.jpg'
image.onload = {
//読みこまれたら実行するよ
}
// なんかしら処理
画像ファイルが読みこまれたらonloadイベントが呼ばれて、なんか処理をするというやつです
動的に画像をどうこうするコードでは誰もが使うやつですよね
Image.decodeとは?
やってることは同じですがdecode()はPromiseを返します
https://developer.mozilla.org/ja/docs/Web/API/HTMLImageElement/decode
const img = new Image();
img.src = "nebula.jpg";
img
.decode()
.then(() => {
document.body.appendChild(img);
})
.catch((encodingError) => {
// エラー時に何かをする。
});
コードはMDNのやつのコピペな
どうしてdecodeの方がいいの?
人間の脳にとってイベント処理は複雑すぎるからです
たとえばこちらのコードの実行順序を把握できるでしょうか?
const image = new Image();
image.src = 'hoge.jpg'
image.onload = {
// 2読みこまれたら実行するよ
// こちらはあとで処理される。つまり
console.log('画像がよみこまれたら実行されるよ')
}
//
console.log('こちらが先に処理される')
読みこんだあとの処理はonloadで書かれるので、コードの実行フローが下にいってまたもどることになります
読みこんだときの処理と読みこんでない状態の処理をきちんと意識しないと不具合を起こします
ではdecodeでは?となるのですが、async/awaitつかうと話がかわります
const loadImage = async() => {
const img = new Image();
img.src = "nebula.jpg";
try {
await img.decode()
document.body.appendChild(img);
}catch(encodingError){
// エラー時に何かをする。
}
}
loadImage()
loadImageのなかでは
- ファイルを読みこむ
- 読みこんだらなんかする
という処理が上から下にながれます。この方が読みやすいし間違いがないですね
イベントモデル vs Promise
もともとJavascriptにはイベントモデルしかなかったわけですが、今はPromise時代に生きてるわけですので、そちらが使えるところでは使わないといけないし、理解していないと火傷しますね
(これの理解の不足で障害とかやらかしてますよね、きっと)
まとめ
この記事は画像の動的読みこみを調べると古典であるonloadが基本的にヒットしてくるのでdecodeをつかうといいですよ、という目的のために書かれました
おまけ
new Promise((resolve, reject) => {
const img = new Image();
img.onload = () => resolve(img);
img.onerror = (e) => reject(e);
img.src = 'hoge.jog';
})
アーニャなみだでる