ピンホールカメラモデル

Pinhole Camera Model

ピンホールカメラとは

ピンホールカメラは、小さな穴(ピンホール)を通して光が入り、反対側のスクリーンに像を結ぶ最もシンプルなカメラモデルである。レンズを使わないため、理想的な幾何学的モデルとして広く使われる(本記事では穴を 1 点とみなし、穴の大きさによるぼけや回折は扱わない)。

P(X,Y,Z) 3D点 像平面 p(u,v) 像点 f (焦点距離) O (カメラ中心) 光軸 Z Y X(手前向き) 透視投影の特徴 • 遠くの物体は小さく見える • 平行線は消失点に集まる • 深度情報は失われる • 3D→2Dの中心投影
図1. ピンホールカメラモデルによる3D-2D投影(平行線が消失点に集まるのは、像平面と平行でない向きの線。X 軸は紙面の手前を向く=右手系)

透視投影の数学

3D点 $P = (X, Y, Z)$ から像平面上の点 $p = (x, y)$ への透視投影は、相似三角形の関係から導かれる:

記法の注意: 図1 では物理的なピンホール幾何 (像平面が camera 後方、$-Z$ 側) を示したが、以下の数式導出では計算の見通しを良くするため、像平面を camera 前方 ($+Z$ 側、$Z = f$ の位置) に置く仮想像平面モデルを採用する (図2)。両者は像が上下/左右反転するかの違いだけで、相似比の計算は同じ(ただし符号まで含めると、物理的な像平面では $x = -fX/Z,\ y = -fY/Z$ になる)。CV/CG 分野の教科書でもこの仮想像平面表示が標準。

側面図(Y-Z平面) f P(Y, Z) p(y) O Z Y y 相似の関係
$\frac{y}{Y} = \frac{f}{Z}$
$y = f \cdot \frac{Y}{Z}$
(X-Z 平面でも同様)
図2. 透視投影の相似関係(仮想像平面モデル、Y-Z 平面)

透視投影の基本式

カメラ座標(原点=ピンホール、光軸の前方を $+Z$)で表した 3D 点 $(X, Y, Z)$($Z > 0$)から像平面上の点 $(x, y)$ への投影:

$$x = f \dfrac{X}{Z}, \quad y = f \dfrac{Y}{Z}$$

ここで $f$ はピンホールから像平面までの距離(慣例で焦点距離と呼ぶ。ピンホールに光を集める焦点があるわけではない)、$Z$ は奥行き(深度)

重要: $Z$ で割る操作のため、透視投影は通常の (行列との積で表せる) 意味では線形変換ではない。 しかし次章で扱う同次座標 ($(X, Y, Z) \to (X, Y, Z, 1)$ への拡張) を使えば、変換を (1) 行列積で表せる部分と(2) 最後の $Z$ 除算 (同次座標の正規化) の 2 段階に分離できる。 非線形性は (2) の正規化に閉じ込められ、(1) の行列部分は回転・平行移動・投影などを統一的に扱える。

画角(Field of View)

画角はカメラが撮影できる範囲の角度で、焦点距離とセンサーサイズから決まる。

画角 (Field of View, FOV) の定義

カメラが捉えられる視野の最大角度。光軸を中心として、ピンホール $O$ から像平面 (センサー) の両端を結ぶ 2 本の光線がなす角を $\theta$ とする。

センサーの幅 $w$ / 高さ $h$ / 対角線長 $d$ のどれを基準にするかで、それぞれ 水平画角・垂直画角・対角画角が定義される (規格や用途で使い分けられる)。

図3 は焦点距離 $f$ を変えたときの画角の変化を直感的に示している。

広角(短焦点) f 小 θ大 画角 大 標準 f 中 θ中 標準レンズに近い画角 望遠(長焦点) f 大 θ小 画角 小
図3. センサー高さを固定し焦点距離 $f$ のみを変えた比較。$f$ が短いほど (ピンホールがセンサーに近い) 画角 $\theta$ は劇的に広くなる (半角 45°→24°→12°、約 4 倍の差)。

FOV 計算式の導出

画角は単純な直角三角形の関係から導ける。光軸とセンサーは直交するので、ピンホール $O$・センサー中心・センサー上端を結ぶと直角三角形になる。

f (焦点距離) 像平面 (センサー) w/2 O (ピンホール) θ/2 θ
図4. FOV 導出の幾何 — 直角三角形 $O$-(センサー中心)-(センサー上端) から半角 $\theta/2$ を求める

図4 のように、直角三角形の隣辺は焦点距離 $f$、対辺はセンサーの半幅 $w/2$(図は縦方向に描いたが、幅でも高さでも同じ式になる。縦方向なら $w$ を高さ $h$ と読み替える)。半角 $\theta/2$ について

$$\tan\!\left(\dfrac{\theta}{2}\right) = \dfrac{w/2}{f} = \dfrac{w}{2f}$$

両辺 $\arctan$ を取って 2 倍すると全画角 $\theta$ が得られる。

画角 (FOV) の計算式

$$\boxed{\;\theta = 2\,\arctan\!\left(\dfrac{w}{2f}\right)\;}$$

$w$ にセンサーの幅を入れれば水平画角、高さを入れれば垂直画角、対角線長 $d$ を入れれば対角画角。

$f$ が大きいほど $\theta$ は小さく (望遠)、$f$ が小さいほど $\theta$ は大きく (広角) なる。

この式は主点がセンサーの中央にある場合。主点がずれるときは、左右(上下)それぞれの角を別々に求めて足す。

主点とスキュー

実際のカメラでは、光軸が画像中心を通らない場合がある。

(cx, cy) 主点 画像中心 u → v ↓ (0,0) 主点 (Principal Point) 光軸と像平面の交点 理想: 画像中心 実際: ずれることが多い
図5. 主点の位置と光軸の関係(ピクセル座標の原点は画像の左上、$u$ は右向き・$v$ は下向き)

ピクセル座標への変換

正規化画像座標 $(x_n, y_n) = (X/Z,\ Y/Z)$(像平面上の点 $(x, y)$ を焦点距離 $f$ で割ったもの)からピクセル座標 $(u, v)$ への変換:

$$u = f_x\, x_n + c_x, \quad v = f_y\, y_n + c_y$$
  • $f_x, f_y$: ピクセル単位の焦点距離($f_x = f / p_x$、$f_y = f / p_y$。$p_x, p_y$ は横・縦のピクセルサイズ)
  • $(c_x, c_y)$: 主点のピクセル座標

ここでは画素の軸が直交するとしてスキュー($K$ の (1,2) 成分 $s$)を 0 とした。$s \neq 0$ なら $u = f_x\, x_n + s\, y_n + c_x$ になる。現代のカメラではほぼ 0 とみなせる。

カメラモデルの統合

透視投影とピクセル座標変換を統合すると:

$$\begin{pmatrix} u \\ v \\ 1 \end{pmatrix} = \dfrac{1}{Z} \begin{pmatrix} f_x & 0 & c_x \\ 0 & f_y & c_y \\ 0 & 0 & 1 \end{pmatrix} \begin{pmatrix} X \\ Y \\ Z \end{pmatrix}$$

右辺の行列積を計算すると $(f_x X + c_x Z,\; f_y Y + c_y Z,\; Z)^\top$ になり、$1/Z$ 倍 (= 同次座標の正規化) で第 3 成分が 1 になる。これを行ごとに展開すると次のスカラー式が得られる:

$$u = f_x \dfrac{X}{Z} + c_x, \quad v = f_y \dfrac{Y}{Z} + c_y$$

この行列はカメラの内部パラメータ行列 $K$(intrinsic matrix)と呼ばれ、次章で詳しく扱う。

コード例(Python)

import numpy as np

# カメラパラメータ
fx, fy = 800, 800  # 焦点距離(ピクセル単位)
cx, cy = 320, 240  # 主点
f = 50  # 焦点距離(mm)

# 3D点(カメラ座標系)
P = np.array([1.0, 0.5, 5.0])  # (X, Y, Z) in meters

# 透視投影
x = P[0] / P[2]  # X/Z
y = P[1] / P[2]  # Y/Z

# ピクセル座標への変換
u = fx * x + cx
v = fy * y + cy
print(f"Pixel coordinates: ({u:.1f}, {v:.1f})")

# 画角の計算
sensor_width = 36  # mm(フルサイズ。上の fx・f とは独立に置いた例の値)
fov = 2 * np.arctan(sensor_width / (2 * f))
print(f"Field of View: {np.degrees(fov):.1f}°")

# 行列形式での投影
K = np.array([
    [fx, 0, cx],
    [0, fy, cy],
    [0,  0,  1]
])

P_camera = P  # カメラ座標の 3D 点(同次座標なのは、次の行で得る 2D 像点のほう)
p_homogeneous = K @ P_camera
p = p_homogeneous[:2] / p_homogeneous[2]
print(f"Pixel (matrix): ({p[0]:.1f}, {p[1]:.1f})")

まとめ

  • ピンホールカメラは透視投影の理想モデル
  • 透視投影: $x = fX/Z$, $y = fY/Z$(非線形変換)
  • 焦点距離が小さいほど画角が広い
  • 主点は光軸と像平面の交点(画像中心からずれることがある)
  • 内部パラメータ行列 $K$ で投影を表現できる

よくある質問

ピンホールカメラモデルとは何ですか?

ピンホールカメラは、小さな穴 (ピンホール) を通って光が入り、反対側のスクリーンに像を結ぶ最もシンプルなカメラモデルです。穴を 1 点とみなした理想的な幾何モデルとして、コンピュータビジョン・コンピュータグラフィックスで標準的に使われます。カメラ座標の 3D 点 $P(X, Y, Z)$($Z > 0$)は、像平面上の点 $p(x, y)$ に $x = fX/Z,\ y = fY/Z$ で写されます($f$ はピンホールから像平面までの距離=焦点距離)。

仮想像平面モデルと物理的なピンホール幾何の違いは?

物理的なピンホール幾何では像平面がカメラ後方 ($-Z$ 側) にあり、像が上下/左右反転します。一方、仮想像平面モデルでは像平面をカメラ前方 ($+Z$ 側、$Z = f$ の位置) に置き、反転を解消します。相似比の計算は同じですが、符号まで含めると物理的な像平面では $x = -fX/Z$ になります。仮想像平面のほうが符号反転がなく扱いやすいため、CV/CG の数式導出では標準的に用いられます。

透視投影の式 x = fX/Z はどう導かれますか?

カメラ中心 $O$ から 3D 点 $P(X, Y, Z)$ への光線が像平面 ($Z = f$ の位置) と交わる点を $p(x, y)$ とすると、$O$・像点・3D 点で形成される 2 つの相似三角形から $x : f = X : Z$ および $y : f = Y : Z$ が成り立ちます。これを整理して $x = fX/Z,\ y = fY/Z$ を得ます。

なぜ透視投影では深度情報が失われるのですか?

透視投影では $x = fX/Z,\ y = fY/Z$ と $Z$ で割るため、3D 点 $(X, Y, Z)$ と $(kX, kY, kZ)$(任意の $k > 0$)が同じ 2D 点に写されます。つまり光線上のすべての点が 1 つの像点に集約されるため、1 枚の像の点だけから元の $Z$ (深度) を一意に復元することはできません。復元には、別の視点からの画像(ステレオ・SfM など)、大きさが既知の物体、深度センサなどの追加の情報が要ります。