マテリアル

ジオメトリの「見た目」を担当する。ライトに反応するかPBR か、で選ぶのが基本軸。

選び方の早見表

やりたいことマテリアル
UI/HUD/影なしのフラット表示MeshBasicMaterial
軽い影ありMeshLambertMaterial
古典的なハイライトありMeshPhongMaterial
定番 PBR(デフォルトはこれ)MeshStandardMaterial
ガラス・クリアコート・スポンジ等の高度な PBRMeshPhysicalMaterial
セルシェーディングMeshToonMaterial
キャプチャベースの質感(ライト不要で金属/有機)MeshMatcapMaterial
法線可視化MeshNormalMaterial
深度マップMeshDepthMaterial / MeshDistanceMaterial
LineBasicMaterial / LineDashedMaterial
点群PointsMaterial
ビルボード(カメラ向く板)SpriteMaterial
完全自作シェーダShaderMaterial / RawShaderMaterial

共通プロパティ

すべてのマテリアルが受ける主なオプション。

プロパティ意味
color基本色("#fff" / 0xffffff / new THREE.Color(...)
opacity不透明度。使うには transparent: true も必須
transparent半透明を有効化
alphaTestこのαより小さい所を破棄(葉っぱ・髪型に有効、影も抜ける)
sideFrontSide(既定)/ BackSide / DoubleSide
wireframeワイヤフレーム表示
visible非表示
depthWrite深度バッファ書き込み(パーティクル/ガラスで false
depthTest深度テスト
blendingNormalBlending / AdditiveBlending / MultiplyBlending
vertexColors頂点カラーを使う
toneMappedレンダラのトーンマッピングを適用するか(HUD は false

ライト無視系

MeshBasicMaterial

ライトに一切反応しない。常に同じ色。デバッグや HUD、輪郭線で使う。

new THREE.MeshBasicMaterial({ color: "#7dd3fc", wireframe: true })

MeshNormalMaterial

面法線を RGB として可視化。デバッグ用。

MeshDepthMaterial

深度を白黒で可視化。シャドウマップの内部実装でも使われる。

MeshMatcapMaterial

matcap(球状にプレレンダされたライト・反射)画像をテクスチャとして渡す。ライト不要でリッチに見える。 プロトタイプや軽量シーンで重宝する。

const matcap = new THREE.TextureLoader().load("/matcaps/clay.png")
matcap.colorSpace = THREE.SRGBColorSpace
new THREE.MeshMatcapMaterial({ matcap })

ライト反応系(PBR系)

MeshLambertMaterial

拡散反射(マット)。ハイライト無し。軽量だが古臭い。

MeshPhongMaterial

Lambert + 鏡面ハイライト。shininessspecular。古典的な見た目。

MeshStandardMaterial ★定番

現代的な PBR。roughness(ラフネス)と metalness(金属度)の2軸で材質を表現。 環境光(IBL)に反応する。

new THREE.MeshStandardMaterial({
  color: "#9bd1ff",
  roughness: 0.4,        // 0=鏡面、1=完全拡散
  metalness: 0.0,        // 0=非金属、1=金属
  envMapIntensity: 1.0,
})

テクスチャマップで質感を作り込む:

マップ役割
mapカラー(ベースカラー)
normalMap法線マップ(凹凸)
roughnessMapラフネスマップ
metalnessMap金属度マップ
aoMapアンビエントオクルージョン(要 uv2)
emissiveMap + emissive自発光
alphaMapα マップ
displacementMap頂点を実際に動かす(要セグメント)
bumpMap擬似凹凸(normal map のほうが良い)
envMap環境マップ(普通は scene.environment でまとめて指定)

MeshPhysicalMaterial

Standard を拡張。クリアコート(車のクリア塗装)、トランスミッション(ガラス)、シーン(布の艶)、 反射面の異方性などをサポート。

追加プロパティ意味
clearcoat / clearcoatRoughnessクリアコート層
transmission透過(ガラス)。thickness + ior も使う
ior屈折率(ガラス 1.5、水 1.33)
iridescence玉虫色(CD裏、シャボン玉)
sheen / sheenColor布の艶
specularIntensity / specularColorスペキュラの色(非金属)
anisotropy異方性反射(ヘアラインや髪)
ガラス球
new THREE.MeshPhysicalMaterial({
  transmission: 1.0,
  thickness: 0.5,
  roughness: 0.05,
  ior: 1.5,
  metalness: 0,
})

MeshToonMaterial

セルシェーディング。gradientMap諧調を段階的にする。

const grad = new THREE.TextureLoader().load("/grad/three.jpg")
grad.minFilter = THREE.NearestFilter
grad.magFilter = THREE.NearestFilter

new THREE.MeshToonMaterial({ color: "#fbbf24", gradientMap: grad })

線・点・スプライト

LineBasicMaterial / LineDashedMaterial

const geom = new THREE.BufferGeometry().setFromPoints([
  new THREE.Vector3(-1, 0, 0),
  new THREE.Vector3( 1, 0, 0),
])
const mat = new THREE.LineBasicMaterial({ color: "white", linewidth: 1 })
const line = new THREE.Line(geom, mat)

linewidthWebGL の制約で大半のブラウザで無効(常に1px)。 太い線が欲しい時は addons の Line2 を使う。

PointsMaterial

new THREE.PointsMaterial({
  size: 0.02,
  sizeAttenuation: true,    // カメラから遠いほど小さく
  color: "white",
  map: pointTexture,        // 各点をテクスチャに
  transparent: true,
  depthWrite: false,
})

SpriteMaterial

カメラに常に正面を向く板(ビルボード)。HUD ラベルや UI に。

const sprite = new THREE.Sprite(new THREE.SpriteMaterial({ map: tex }))
sprite.scale.set(1, 1, 1)

ShaderMaterial / RawShaderMaterial

自分で GLSL を書きたいときの脱出口。シェーダ・ポストプロセスに詳しく書く。

共有して使い回す

マテリアルとジオメトリは複数の Mesh で共有可能。インスタンスを再利用するとメモリと コンパイル時間を節約できる。

const sharedGeom = new THREE.BoxGeometry()
const sharedMat  = new THREE.MeshStandardMaterial({ color: "#7dd3fc" })

for (let i = 0; i < 100; i++) {
  const m = new THREE.Mesh(sharedGeom, sharedMat) // 共有
  m.position.x = i * 0.5
  scene.add(m)
}

マテリアルの更新

プロパティの一部は変更後に再コンパイルが必要。 通常 material.needsUpdate = true をセットして次フレームで反映。

material.map = newTexture
material.needsUpdate = true

ホットパスで needsUpdate を頻繁に立てない。 コンパイルが走り画面がカクつく。

onBeforeCompile で既存マテリアルを拡張

標準マテリアルに少しだけシェーダ追記したい場合の常套手段。シェーダ参照。

マテリアルにも dispose()

マテリアルはシェーダプログラムをキャッシュしている。シーンから外すだけでは GPU リソースが 残り続ける。material.dispose() + 内部のテクスチャも dispose()