すとーぶろぐ

主にUnity。実質備忘録。

【Unity】Sprite(Collider2D)の重なりをBounds.Containsを使って取得しようとしたら、思ってたのと違った話

とある案件で「ドラッグで動かしているSpriteが指定したSpriteと重なっているかどうか」を取得する必要があったので

そんなの簡単じゃん。Bounds.Containsを使えばよくね?

と安易な考えで実装を行ったところ、思ってたのと違う!結果になってしまいました。

本記事ではその原因と解決方法について記します。

 

思ってたのと違う!結果になった実装

はじめはよく考えずに以下のように実装しました。

①シーンに2つのSprite(2DCollider付き)、EventSystemを配置。

②CameraにPysicsRaycaster2Dをアタッチ。

③Spriteの片方に以下のようなスクリプトをアタッチ。

 

 

そして実行した結果がこちらです。 

f:id:t_stove_k:20180707035329g:plain Sprite同士(黄緑色の星とテキスト入りのサークル)は重なってないのに、DebugLogで「重なってるよー!」と陽気に叫んじゃってますね。

思ってたのと違う…

なぜ?

 

 

 

思ってたのと違う!結果になった原因

まず、Boundsってそもそも何なのかよくわかってなかったので、調べてみました。

そして、わかりました。

Boundsがオブジェクト(Collider)をピッタリ包む箱である。ただひたすらに箱である。

ということが。 

 

下の画像のカプセルを包んでいる赤い箱がBoundsです。 

f:id:t_stove_k:20180706171917p:plain

ピッタリと包んではいますが、箱なので、余白ができてしまってます

でも、この余白部分もBoundsなんです。

 

ここでもう一度思ってたのと違う!実行結果を見てみましょう。

f:id:t_stove_k:20180707042944g:plain 赤い枠内がBoundsになります。

ご覧の通り、ドラッグされたSprite(2DCollider)は確かにBoundsと重なってるんです。

スクリプトは間違ってなかった!間違ってたのは私だ!

 

調べる以前はBoundsはそれを含むSprite(2DCollider)と形状、サイズともに一致するものだと勝手に思い込んでましたが、それは間違いでした。そして、その間違った思い込みのせいでスクリプトの実行結果自分の頭の中で思い描いていた実行結果との間に誤差が生じたようです。結局、思ってたのと違う!結果になったのは自分の勉強不足が原因でした。

 

もう一度再確認

・Boundsは箱

・オブジェクトをピッタリと包んではいるが、包むオブジェクトの形状が複雑だと、どうしても余白ができてしまう

 

思ってたのと違う!結果になったときの解決方法

原因がわかったところで、解決方法を。

Collider2D.OverlapPoint(Vector2 point)

を使いましょう。

pointがCollider2Dと重なっていたらtrueが、

重なっていなかったらfalseが返ってきます。

オブジェクトにアタッチするスクリプトを少し書き換えるだけで、あとは最初にやった手順と同じです。

 

 

では、実行してみましょう! 

f:id:t_stove_k:20180707044611g:plain

いいですね。こういうのが欲しかった。

 

結構悩んだ割に解決方法はかなりあっさりでした…

まあ、今回はBoundsについての知識を得られたんでよしとします。

これで、Boundsとも友達!