そう言えば、昔(中3)くらいの時に長方形の当たり判定で困ったことがある。
というのはどのサイトもベクトルを使っていたからで、私は当時さっぱり分からず涙を飲んだ記憶がある。
しかし、今になって思えば「円と長方形の当たり判定」はベクトルなんぞ要らないのである。
[album]380[/album]
と言う訳でその解説をする。
まず、座標軸を右方向をx軸、上方向をy軸とする(念の為)
さらに面倒を避けるため長方形の中心を原点O、円の中心をC(p,q)とする(平行移動すれば良いだけ)
円の半径をr、長方形の縦の長さを2a、横を2b、x軸からの傾きをθとする。
また、
原点を通り傾きがtanθの直線をL1とし、
原点を通り傾きがtan(θ+π/2)の直線をL2とする(図の通り)
この時、次が成立する。
円と長方形が当たっている ⇔ (点Cと直線L1の距離がa+rより小さい)かつ(点Cと直線L2の距離がb+rより小さい)かつ(長方形をグルッと一回転させた時、円と重なる点を持つ)
L1について考える。
L1:y=(tanθ)x
ところで、tanθ = sinθ/cosθより
L1:(sinθ)x - (cosθ)y = 0 である
ここで以下の補題を用意する
補題 直線ax+by+c=0と点(x',y')の距離dは
d = | ax' + by' + c |/√(a^2 + b^2)
と表される。
この補題を認めれば(頑張って計算すれば良いだけ)
(cosθ)^2 + (sinθ)^2 =1より
L1と点Cの距離は|(sinθ)p - (cosθ)q|と表される。
同様に、tan(θ + π/2)= - sinθ/cosθより
L2と点Cの距離は|(cosθ)p + (sinθ)q|となる
最後の条件を考える。
長方形を回転させると対角線を直径とする円になり、
その円と判定対象の円が重なればいいので
√(p^2 + q^2) < √(a^2 + b^2) + r
よって
p^2 + q^2 < a^2 + b^2 + r^2 + 2r√(a^2 + b^2)
円と長方形が当たっている ⇔ (|(sinθ)p - (cosθ)q| < a+r)かつ(|(cosθ)p + (sinθ)q| < b+r)かつ(p^2 + q^2 < a^2 + b^2 + r^2 + 2r√(a^2 + b^2))
となって定式化が完了した。
長方形の当たり判定
RE: 長方形の当たり判定
人のいうことが素直に信じられなくなって幾年・・・
元無垢な少年GRAMです
同値記号などを見ると突っ込みを入れたくなってしまいます。
このような事例はどうなのかなぁ~と。
なお私は数学があまり得意ではないので、自分なら単純に点を長方形の2つの方向ベクトルに射影して各辺の長さでクランプし、長方形上の最近点を求めるくらいしか思いつきません・・・ってベクトル使ってますね。
ベクトルを使わないならおんなじような感じで、直線との距離を求めクランプの処理を加えればいいかと
元無垢な少年GRAMです
同値記号などを見ると突っ込みを入れたくなってしまいます。
このような事例はどうなのかなぁ~と。
なお私は数学があまり得意ではないので、自分なら単純に点を長方形の2つの方向ベクトルに射影して各辺の長さでクランプし、長方形上の最近点を求めるくらいしか思いつきません・・・ってベクトル使ってますね。
ベクトルを使わないならおんなじような感じで、直線との距離を求めクランプの処理を加えればいいかと
Re: 長方形の当たり判定
指摘ありがとうございます。
やっちゃいましたね、こりゃ。
やっぱり実際に使った事のない処理を書くのは良くないですね。
と言う訳で、もう一個条件を付加しますね。
p^2 + q^2 < a^2 + b^2 + r^2 + 2r√(a^2 + b^2)
とかでどうでしょう。
と言う訳で修正します。
やっちゃいましたね、こりゃ。
やっぱり実際に使った事のない処理を書くのは良くないですね。
と言う訳で、もう一個条件を付加しますね。
p^2 + q^2 < a^2 + b^2 + r^2 + 2r√(a^2 + b^2)
とかでどうでしょう。
と言う訳で修正します。
最後に編集したユーザー lbfuvab on 2011年12月07日(水) 01:18 [ 編集 2 回目 ]
Re: 長方形の当たり判定
良く考えてみたら、長方形が十分長いという仮定の下でなら(b>>a)
一つ目と三つ目が満たされていたら二つ目は大体満たされているんですね。
一つ目と三つ目が満たされていたら二つ目は大体満たされているんですね。