Determine if objects collide with each other (2D)
Verification environment
- Windows
-
- Windows 11
- Unity Editor
-
- 2021.3.3f1
- Input System Package
-
- 1.3.0
Prerequisites for this tip
The following settings have been made in advance as a premise for the description of this tip.
At first
This tip explains how to determine if two objects are in contact. Move one object with the keyboard.
Preparation
After creating the project, prepare two images of the sprite that will be the object. If you are troublesome to prepare, you can place two identical sprites, but this time we will separate them for clarity. The names are "UnityTips" and "UnityTips_2" respectively.
Add two image files by dropping them into the view.
Add a script to move the left object with the keyboard. The script name Player
is .
The script content is similar to the tips in Move, rotate, and scale a sprite.
using UnityEngine;
using UnityEngine.InputSystem;
public class Player : MonoBehaviour
{
// 一定時間ごとに呼ばれます
void FixedUpdate()
{
// キーボードの情報を取得
var keyboard = Keyboard.current;
if (keyboard == null)
{
Debug.Log("キーボードがありません。");
return;
}
// スプライトの移動処理
// Translate メソッドでスプライトの位置が移動します
// Space.World を指定すると回転の影響をうけません
if (keyboard.leftArrowKey.isPressed)
{
transform.Translate(-0.1f, 0, 0, Space.World);
}
if (keyboard.rightArrowKey.isPressed)
{
transform.Translate(0.1f, 0, 0, Space.World);
}
if (keyboard.upArrowKey.isPressed)
{
transform.Translate(0, 0.1f, 0, Space.World);
}
if (keyboard.downArrowKey.isPressed)
{
transform.Translate(0, -0.1f, 0, Space.World);
}
}
}
Attach to the object on which you want to run the script.
Run the game and check if it works with the cursor keys on your keyboard.
Finally, place a text object to display the collision detection status.
The object name TextState
is .
Collision Handling Settings
From here, you can configure the settings related to collisions.
First, select the object you want to move, "UnityTips", and click "Add Component" from the inspector.
Select from Physics 2D
the list. Physics
is a 3D object, so make no mistake.
Physics 2D
Box Collider 2D
Select from . Since this sprite is rectangular, Box is selected, but if it is circle-shaped, for example, select other shapes such as Circle.
Box Collider 2D
Since the component will be added, check "Make it trigger" from the parameters.
This will allow you to get information only about "whether you hit or not".
Rigidbody 2D
Then add the components of . You can add it from "Physics 2D -> Rigidbody 2D".
Rigidbody
gives physics informationCollider
to the object and can also determine collisions with objects that have .
Rigidbody
However, if you have a component, it will also contain gravity information in the -Y direction, so if you execute it, it will fall down.
So set the "Gravity Scale" to 0 from the parameters.
By the way, if it is a side-scrolling action game, it may be convenient to use the gravity scale in the sense that it is free fall down.
Similarly, add a component to the Box Collider 2D
other object "UnityTips_2".
This is the affected side this time, so you don't need to change any settings.
Player
Open the script and add each field and method using as follows:
using System;
using UnityEngine;
using UnityEngine.InputSystem;
using UnityEngine.UI;
public class Player : MonoBehaviour
{
<summary>状態表示用テキストオブジェクト。</summary>
[SerializeField] private Text TextState;
// 中略
<summary>衝突した瞬間に呼ばれます。</summary>
<param name="partner">衝突した相手のコリジョン情報。</param>
private void OnTriggerEnter2D(Collider2D partner)
{
TextState.text = $"OnTriggerEnter2D : {partner.tag} {DateTime.Now:HH:mm:ss.fff}{Environment.NewLine}{TextState.text}";
}
<summary>衝突している間呼ばれます。ただしスリープモードになった場合は呼ばれません。</summary>
<param name="partner">衝突した相手のコリジョン情報。</param>
private void OnTriggerStay2D(Collider2D partner)
{
TextState.text = $"OnTriggerStay2D : {partner.tag} {DateTime.Now:HH:mm:ss.fff}{Environment.NewLine}{TextState.text}";
}
<summary>衝突状態でなくなったタイミングで呼ばれます。</summary>
<param name="partner">衝突した相手のコリジョン情報。</param>
private void OnTriggerExit2D(Collider2D partner)
{
TextState.text = $"OnTriggerExit2D : {partner.tag} {DateTime.Now:HH:mm:ss.fff}{Environment.NewLine}{TextState.text}";
}
}
Since we want to display information on whether or not it was hit, we will make it possible to display it in a text object as follows.
<summary>状態表示用テキストオブジェクト。</summary>
[SerializeField] private Text TextState;
The collision detection process is described as follows.
<summary>衝突した瞬間に呼ばれます。</summary>
<param name="partner">衝突した相手のコリジョン情報。</param>
private void OnTriggerEnter2D(Collider2D partner)
{
TextState.text = $"OnTriggerEnter2D : {partner.tag} {DateTime.Now:HH:mm:ss.fff}{Environment.NewLine}{TextState.text}";
}
<summary>衝突している間呼ばれます。ただしスリープモードになった場合は呼ばれません。</summary>
<param name="partner">衝突した相手のコリジョン情報。</param>
private void OnTriggerStay2D(Collider2D partner)
{
TextState.text = $"OnTriggerStay2D : {partner.tag} {DateTime.Now:HH:mm:ss.fff}{Environment.NewLine}{TextState.text}";
}
<summary>衝突状態でなくなったタイミングで呼ばれます。</summary>
<param name="partner">衝突した相手のコリジョン情報。</param>
private void OnTriggerExit2D(Collider2D partner)
{
TextState.text = $"OnTriggerExit2D : {partner.tag} {DateTime.Now:HH:mm:ss.fff}{Environment.NewLine}{TextState.text}";
}
Rigidbody 2D
Each of the above events occurs when an object that has collides with another object Collider 2D
that has .
This will allow you to determine and process whether it is correct or not.
There are three events, each of which is called at the following timing.
OnTriggerEnter2D | When objects hit each other |
OnTriggerStay2D | While objects are hitting each other |
OnTriggerExit2D | When objects leave the collision state |
In both cases, the opponent object receives the opponent's object as an argument, so you can get the opponent's Collider2D
object by looking up Collider2D.gameObject
the type of target hit by (enemy, Collider2D.tag
item, etc.).
Of the OnTriggerEnter2D
above three events, and OnTriggerExit2D
are called once per collision.
OnTriggerStay2D
is called every frame during the collision, but the event is no longer called after a certain amount of time has passed since both objects stopped.
This is because it is considered to have entered a sleep state, and it is considered a waste of processing to calculate collisions every frame with something that is not moving.
If you Rigidbody 2D
do not want it to sleep, change the sleep mode of the parameter to "Do not sleep".
After changing the code, set the text for displaying information.
Run the game and move the object with the keyboard to touch another sprite. You can see that three functions are called for each.
By the way, if you touch an object and then stop moving, the method will be called for OnTriggerStay2D
a short time.
You should be able to see that the method is no longer called after OnTriggerStay2D
a certain amount of time.
This indicates that you have entered a sleep state, but if you want to change the time until you enter this sleep, you can change it by selecting "2D Physics" from the project settings and specifying the "Sleep time" parameter in seconds.
It cannot be set to 0, but if it OnTriggerStay2D
is set to infinitely small, the method itself will not be called.