比較と字幕の比較

lang 属性には、関連付けることができる言語が 1 つだけです。つまり、ページに複数の言語が含まれている場合でも、<html> 属性に指定できる言語は 1 つだけです。lang をページのメインの言語に設定します。

すべきでないこと
<html lang="ar,en,fr,pt">...</html>
複数の言語はサポートされていません。
すべきこと
<html lang="ar">...</html>
ページの主要言語のみを設定します。この場合、言語はアラビア語です。

ボタンと同様に、リンクのユーザー補助機能名は主にテキスト コンテンツから取得されます。リンクを作成する際の便利な方法として、「こちら」や「続きを読む」などのあいまいな言葉ではなく、最も意味のあるテキストをリンク自体に含める方法があります。

説明が不十分
Check out our guide to web performance <a href="/guide">here</a>.
役に立つコンテンツ
Check out <a href="/guide">our guide to web performance</a>.

アニメーションがレイアウトをトリガーするかどうかを確認する

transform 以外のものを使用して要素を移動するアニメーションは、遅くなる可能性があります。次の例では、topleft をアニメーション化し、transform を使用して、同じ視覚的な結果を実現しています。

すべきでないこと
.box {
  position: absolute;
  top: 10px;
  left: 10px;
  animation: move 3s ease infinite;
}

@keyframes move {
  50% {
     top: calc(90vh - 160px);
     left: calc(90vw - 200px);
  }
}
すべきこと
.box {
  position: absolute;
  top: 10px;
  left: 10px;
  animation: move 3s ease infinite;
}

@keyframes move {
  50% {
     transform: translate(calc(90vw - 200px), calc(90vh - 160px));
  }
}

次の 2 つの Glitch の例でテストし、DevTools を使用してパフォーマンスを確認できます。

同じマークアップで、padding-top: 56.25%aspect-ratio: 16 / 9 に置き換え、aspect-ratio を指定された比率 width / height に設定できます。

padding-top を使用する
.container {
  width: 100%;
  padding-top: 56.25%;
}
aspect-ratio を使用する
.container {
  width: 100%;
  aspect-ratio: 16 / 9;
}

padding-top ではなく aspect-ratio を使用すると、より明確になり、通常のスコープ外で何かを行うためにパディング プロパティをオーバーホールする必要がなくなります。

reduce を使用して一連の Promise を連結しています。とても賢い。しかしこれは、使用しない方がよい「非常にスマートな」コーディングなのです。

上記を非同期関数に変える場合は、つい順次的になってしまいます。

非推奨 - 過度に順次処理を使用する
async function logInOrder(urls) {
  for (const url of urls) {
    const response = await fetch(url);
    console.log(await response.text());
  }
}
すっきりとしましたが、2 番目のフェッチは最初のフェッチが完全に読み込まれるまで開始されません。これは、フェッチを並行で実行する Promise の例より時間がかかります。幸いなことに、理想的な解決策があります。
推奨 - すっきりとして並行処理する
function markHandled(...promises) {
  Promise.allSettled(promises);
}

async function logInOrder(urls) {
  // fetch all the URLs in parallel
  const textPromises = urls.map(async (url) => {
    const response = await fetch(url);
    return response.text();
  });

  markHandled(...textPromises);

  // log them in sequence
  for (const textPromise of textPromises) {
    console.log(await textPromise);
  }
}
この例では、URL は並行でフェッチされて読み込まれていますが、「スマート」な reduce 部分は、つまらなくて読み取りやすい標準的な for-loop で置き換えられています。

Houdini カスタム プロパティの作成

カスタム プロパティ(CSS 変数など)を設定する例を次に示します。構文(型)、初期値(フォールバック)、継承ブール値(親から値を継承するかどうか)が追加されています。現在、この操作を行う方法は JavaScript の CSS.registerProperty() を使用していますが、Chromium 85 以降では、CSS ファイルで @property 構文がサポートされます。

個別の JavaScript ファイル(Chromium 78)
CSS.registerProperty({
  name: '--colorPrimary',
  syntax: '',
  initialValue: 'magenta',
  inherits: false
});
CSS ファイルに含まれる(Chromium 85)
@property --colorPrimary {
  syntax: '';
  initial-value: magenta;
  inherits: false;
}

これで、他の CSS カスタム プロパティと同様に、var(--colorPrimary) を介して --colorPrimary にアクセスできるようになりました。ただし、ここでの違いは、--colorPrimary が文字列として読み取られるだけではないことです。データがあります。

CSS backdrop-filter は、半透明または透明の要素に 1 つ以上の効果を適用します。以下の画像を例に説明します。

フォアグラウンドの透明性なし
円の上に重ねて表示された三角形。三角形を通して円は見えません。
.frosty-glass-pane {
  backdrop-filter: blur(2px);
}
フォアグラウンドの透明度
円の上に重ねて表示された三角形。三角形は半透明で、円が透けて見えます。
.frosty-glass-pane {
  opacity: .9;
  backdrop-filter: blur(2px);
}

左側の画像は、backdrop-filter が使用されていない場合やサポートされていない場合に、重なり合う要素がどのようにレンダリングされるかを示しています。右の画像は、backdrop-filter を使用してぼかし効果を適用しています。backdrop-filter に加えて opacity を使用していることに注意してください。opacity がないと、ぼかしを適用する対象がありません。opacity1(完全に不透明)に設定されている場合、背景には影響しません。

ただし、unload イベントとは異なり、beforeunload には正当な用途があります。たとえば、ページを離れると保存されていない変更が失われることをユーザーに警告する場合などです。この場合、ユーザーが保存されていない変更を行った場合にのみ beforeunload リスナーを追加し、保存されていない変更が保存された直後に削除することをおすすめします。

すべきでないこと
window.addEventListener('beforeunload', (event) => {
  if (pageHasUnsavedChanges()) {
    event.preventDefault();
    return event.returnValue = 'Are you sure you want to exit?';
  }
});
上記のコードは、無条件で beforeunload リスナーを追加します。
すべきこと
function beforeUnloadListener(event) {
  event.preventDefault();
  return event.returnValue = 'Are you sure you want to exit?';
};

// A function that invokes a callback when the page has unsaved changes.
onPageHasUnsavedChanges(() => {
  window.addEventListener('beforeunload', beforeUnloadListener);
});

// A function that invokes a callback when the page's unsaved changes are resolved.
onAllChangesSaved(() => {
  window.removeEventListener('beforeunload', beforeUnloadListener);
});
上記のコードでは、beforeunload リスナーは必要に応じてのみ追加され(必要ない場合は削除されます)。

Cache-Control: no-store の使用を最小限に抑える

Cache-Control: no-store は、ウェブサーバーがレスポンスに設定できる HTTP ヘッダーで、ブラウザにレスポンスを HTTP キャッシュに保存しないように指示します。これは、ログインが必要なページなど、機密性の高いユーザー情報が含まれるリソースに使用する必要があります。

各入力グループ(.fieldset-item)を含む fieldset 要素は、gap: 1px を使用して要素間の細い線の境界を作成しています。複雑な境界ソリューションは不要です。

塗りつぶしギャップ
.grid {
  display: grid;
  gap: 1px;
  background: var(--bg-surface-1);

  & > .fieldset-item {
    background: var(--bg-surface-2);
  }
}
ボーダー トリック
.grid {
  display: grid;

  & > .fieldset-item {
    background: var(--bg-surface-2);

    &:not(:last-child) {
      border-bottom: 1px solid var(--bg-surface-1);
    }
  }
}

自然なグリッドの折り返し

最も複雑なレイアウトは、<main><form> 間の論理レイアウト システムであるマクロ レイアウトになりました。

入力
<input
  type="checkbox"
  id="text-notifications"
  name="text-notifications"
>
ラベル
<label for="text-notifications">
  <h3>Text Messages</h3>
  <small>Get notified about all text messages sent to your device</small>
</label>

各入力グループ(.fieldset-item)を含む fieldset 要素は、gap: 1px を使用して要素間の細い線の境界を作成しています。複雑な境界ソリューションは不要です。

塗りつぶしギャップ
.grid {
  display: grid;
  gap: 1px;
  background: var(--bg-surface-1);

  & > .fieldset-item {
    background: var(--bg-surface-2);
  }
}
ボーダー トリック
.grid {
  display: grid;

  & > .fieldset-item {
    background: var(--bg-surface-2);

    &:not(:last-child) {
      border-bottom: 1px solid var(--bg-surface-1);
    }
  }
}

タブ <header> レイアウト

次のレイアウトはほぼ同じです。flex を使用して縦方向の順序付けを作成しています。

HTML
<snap-tabs>
  <header>
    <nav></nav>
    <span class="snap-indicator"></span>
  </header>
  <section></section>
</snap-tabs>
CSS
header {
  display: flex;
  flex-direction: column;
}

.snap-indicator はリンクのグループとともに水平方向に移動する必要があります。このヘッダー レイアウトは、そのステージを設定するために役立ちます。絶対位置の要素は使用しないでください。

ジェントル フレックスは、より正確な中央配置のみの戦略です。place-content: center とは異なり、中央揃え中に子のボックスサイズが変更されないため、ソフトで優しい配置です。すべてのアイテムが可能な限り慎重に積み重ねられ、中央に配置され、間隔が空けられます。

.gentle-flex {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 1ch;
}
長所
  • 位置揃え、向き、分散のみを処理
  • 編集とメンテナンスが 1 か所で完結
  • Gap は、n 個の子要素の間隔を均等に保証します。
短所
  • コード行数の最小値

マクロ レイアウトとマイクロ レイアウトの両方に適しています

用途

gap は、値として任意の CSS 長さまたは割合を受け入れます。

.gap-example {
  display: grid;
  gap: 10px;
  gap: 2ch;
  gap: 5%;
  gap: 1em;
  gap: 3vmax;
}


Gap には 1 つの長さを渡すことができます。この長さは行と列の両方に使用されます。

ショートカット
.grid {
  display: grid;
  gap: 10px;
}
行と列の両方を同時に設定
開きました
.grid {
  display: grid;
  row-gap: 10px;
  column-gap: 10px;
}


Gap には 2 つの長さを渡すことができます。これは行と列に使用されます。

ショートカット
.grid {
  display: grid;
  gap: 10px 5%;
}
行と列の両方を個別に一度に設定
開きました
.grid {
  display: grid;
  row-gap: 10px;
  column-gap: 5%;
}