2025.03.22

ダークモードでのElevation(標高)について考える

ダークモードでのElevation(標高)について考える

Elevationの考え方

まず、Elevation(標高)について考えていく。 具体的には次の画像のようなものになる。

Elevationの例https://design.digital.go.jp/foundations/elevation/ から引用

各コンポーネントの背面に強さの異なるシャドウが描画されているのが見て取れる。 高い物体の影は大きく地面に投影され、逆も然りといった現実に即した見え方を表すことにより 2Dの画面の中でも高さ情報を付加することができる。

これにより、直感的なデザインを可能にしているということになる。 Elevationの役割が分かったところで、今度はダークモードでの実装の問題点について考えようと思う。

Elevationのダークモードでの実装の問題点

まず、ライトモードでのサンプルを示しておく。

ライトモードでのElevationの例

今度、背景などを含めて灰色にして、ダークモードに寄せていく。

背景が灰色でのElevationの例

この時点でElevationを表現するシャドウが見えなくなっているのがわかる。 そのため、このシャドウでのアプローチは厳しいことがわかる。

念の為、シャドウではなく、光らせるアプローチもしてみた。

光らせた場合でのElevationの例

思ったより悪くはないが、何か違和感がある。

Elevationをダークモードで実装する

Elevationの考え方で、現実に即した見え方と言及した。 つまり、暗い場所で高さが異なる物体が並んでいる状態を考えれば良い。

ここで、暗い場所といっても実際は何も光源がない訳ではない(光源が全く無ければ何も見えない)。 また、光源は基本的に上にあるのは私たちの経験で分かっているはずである。

さらに、光源が上にあるので高い場所にあるものは明るく見えると考えても矛盾はない。

その考え方に基づいて再現したのがこちら。

現実に即したダークモードでのElevation

良い感じであるが浮いている感じがない。

Elevationをダークモードで実装する(改良)

全てのエレベーションレベルで一律にカードを絶妙に光らせる(box-shadow: 0px 0px 6px rgba(255, 255, 255, 0.4);)ことで、浮いていることを表現した。 光らせるというより縁取りをしていると表現する方が正しいかもしれない。

現実に即したダークモードでのElevation(改良)

付録

HTMLとCSSのサンプルコードを掲載しておく。

<body>
  <div class="card elevation-1">Elevation 1</div>
  <div class="card elevation-2">Elevation 2</div>
  <div class="card elevation-3">Elevation 3</div>
  <div class="card elevation-4">Elevation 4</div>
</body>
body {
  font-family: sans-serif;
  display: flex;
  justify-content: center;
  align-items: center;
  height: 100vh;
  background-color: #202020;
  flex-direction: column;
  gap: 20px;
}
.card {
  width: 200px;
  height: 100px;
  background: white;
  display: flex;
  justify-content: center;
  align-items: center;
  font-size: 18px;
  font-weight: bold;
  border-radius: 8px;
}
.elevation-1 {
  box-shadow: 0px 0px 6px rgba(255, 255, 255, 0.4);
  background: rgb(130, 130, 130);
}
.elevation-2 {
  box-shadow: 0px 0px 6px rgba(255, 255, 255, 0.4);
  background: rgb(160, 160, 160);
}
.elevation-3 {
  box-shadow: 0px 0px 6px rgba(255, 255, 255, 0.4);
  background: rgb(190, 190, 190);
}
.elevation-4 {
  box-shadow: 0px 0px 6px rgba(255, 255, 255, 0.4);
  background: rgb(210, 210, 210);
}