Gestione delle collisioni con fisica standard (2D)

Pagina aggiornata :
Data di creazione della pagina :

Ambiente di verifica

Finestre
  • Windows 11
Unity Editor
  • 2021.3.3f1
Pacchetto del sistema di input
  • 1.3.0

Prerequisiti per questo suggerimento

Le seguenti impostazioni sono state effettuate in anticipo come premessa per la descrizione di questo suggerimento.

Dapprima

Questo suggerimento posiziona due oggetti in modo da poter implementare il comportamento di manipolazione di un oggetto e utilizzare la fisica standard di Unity per spingere l'altro quando entra in contatto con l'altro.

A proposito, la maggior parte delle impostazioni sono le stesse della procedura descritta nell'articolo precedente "Determinare se gli oggetti si scontrano tra loro (2D)".

Preparazione

La procedura qui è quasi la stessa dei suggerimenti precedenti , quindi facciamola scorrere senza intoppi.

Dopo aver creato il progetto, prepara due immagini sprite che saranno oggetti e aggiungile. I nomi sono rispettivamente "UnityTips" e "UnityTips_2".

Aggiungere due file di immagine rilasciandoli nella vista.

Aggiungere uno script per spostare l'oggetto sinistro con la tastiera. Il nome Player dello script è .

using UnityEngine;
using UnityEngine.InputSystem;

public class Player : MonoBehaviour
{
  // 一定時間ごとに呼ばれます
  void FixedUpdate()
  {
    // キーボードの情報を取得
    var keyboard = Keyboard.current;

    // スプライトの移動処理
    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);
    }
  }
}

Connettersi all'oggetto su cui si desidera eseguire lo script.

Esegui il gioco e controlla se funziona con i tasti cursore sulla tastiera.

Infine, posizionare un oggetto di testo per visualizzare lo stato di rilevamento delle collisioni. Il nome TextState dell'oggetto è .

Impostazioni di gestione delle collisioni

Da qui, è possibile configurare le impostazioni relative alle collisioni.

Innanzitutto, seleziona l'oggetto che desideri spostare, "UnityTips", e fai clic su "Aggiungi componente" dall'ispettore. Selezionare dall'elenco Physics 2D . Physics è un oggetto 3D, quindi non commettere errori.

Physics 2DBox Collider 2D Selezionare da . Poiché questo sprite è rettangolare, Box è selezionato, ma se è a forma di cerchio, ad esempio, selezionare altre forme come Cerchio.

L'ultima volta, volevo ottenere informazioni solo sul fatto che l'avessi colpito o meno, quindi ho controllato "Make it trigger", ma questa volta non lo farò. Ciò consente la gestione delle collisioni in fisica.

Rigidbody 2D Quindi aggiungere i componenti di . Puoi aggiungerlo da "Fisica 2D -> Rigidbody 2D". Rigidbody fornisce informazioniCollider fisiche all'oggetto e può anche determinare collisioni con oggetti che hanno .

Impostate la scala di gravità su 0 per evitare cadute libere al di sotto.

Allo stesso modo, aggiungere un componente all'altro oggetto "UnityTips_2" per contrassegnare Box Collider 2D i risultati.

Inoltre, questa volta è necessario muoversi con la forza dell'avversario,Rigidbody 2D quindi aggiungi . La scala di gravità dovrebbe essere 0.

Questo è tutto quello che c'è da fare. Al momento non è richiesto alcun programma. Esegui il gioco e prova a toccare un altro oggetto.

Penso che tu possa confermare che se spingi l'avversario in questo modo, l'avversario si comporterà come se fosse spinto. È molto facile usare la fisica della funzione standard perché non è richiesto alcun programma.

Impedire la rotazione degli oggetti

Puoi vedere quando lo tocchi, ma se il punto ferita si sposta anche leggermente, ogni oggetto ruoterà. Come gioco, spesso diventa innaturale, quindi è necessario impostarlo in modo che non ruoti.

Rigidbody 2D Il componente ha un elemento chiamato "Rotazione fissa" in "Vincoli", quindi controlla Z. Ora puoi lavorare in modo che non ruoti. Prova a impostarlo su due oggetti ed esegui il gioco per controllarlo.

Penso che tu possa essere sicuro che non ruota, indipendentemente dall'angolazione da cui lo spingi.

Fai qualcosa quando gli oggetti si colpiscono a vicenda

Ad esempio, potresti voler implementare un proiettile che colpisce un nemico mentre spinge l'avversario riducendo la salute del nemico. Questo è lo stesso dei suggerimenti precedenti , poiché si verificherà l'evento, quindi puoi affrontarlo.

Player Aprire lo script e aggiungere ogni campo e metodo utilizzando come segue:

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 OnCollisionEnter2D(Collision2D partner)
  {
    TextState.text = $"OnCollisionEnter2D : {partner.collider.tag} {DateTime.Now:HH:mm:ss.fff}{Environment.NewLine}{TextState.text}";
  }

  /// <summary>衝突している間呼ばれます。ただしスリープモードになった場合は呼ばれません。</summary>
  /// <param name="partner">衝突した相手のコリジョン情報。</param>
  private void OnCollisionStay2D(Collision2D partner)
  {
    TextState.text = $"OnCollisionStay2D : {partner.collider.tag} {DateTime.Now:HH:mm:ss.fff}{Environment.NewLine}{TextState.text}";
  }

  /// <summary>衝突状態でなくなったタイミングで呼ばれます。</summary>
  /// <param name="partner">衝突した相手のコリジョン情報。</param>
  private void OnCollisionExit2D(Collision2D partner)
  {
    TextState.text = $"OnCollisionExit2D : {partner.collider.tag} {DateTime.Now:HH:mm:ss.fff}{Environment.NewLine}{TextState.text}";
  }
}

Poiché vogliamo visualizzare informazioni sul fatto che sia stato colpito o meno, renderemo possibile visualizzarlo in un oggetto di testo come segue.

/// <summary>状態表示用テキストオブジェクト。</summary>
[SerializeField] private Text TextState;

Il processo di rilevamento delle collisioni è descritto come segue.

/// <summary>衝突した瞬間に呼ばれます。</summary>
/// <param name="partner">衝突した相手のコリジョン情報。</param>
private void OnCollisionEnter2D(Collision2D partner)
{
  TextState.text = $"OnCollisionEnter2D : {partner.collider.tag} {DateTime.Now:HH:mm:ss.fff}{Environment.NewLine}{TextState.text}";
}

/// <summary>衝突している間呼ばれます。ただしスリープモードになった場合は呼ばれません。</summary>
/// <param name="partner">衝突した相手のコリジョン情報。</param>
private void OnCollisionStay2D(Collision2D partner)
{
  TextState.text = $"OnCollisionStay2D : {partner.collider.tag} {DateTime.Now:HH:mm:ss.fff}{Environment.NewLine}{TextState.text}";
}

/// <summary>衝突状態でなくなったタイミングで呼ばれます。</summary>
/// <param name="partner">衝突した相手のコリジョン情報。</param>
private void OnCollisionExit2D(Collision2D partner)
{
  TextState.text = $"OnCollisionExit2D : {partner.collider.tag} {DateTime.Now:HH:mm:ss.fff}{Environment.NewLine}{TextState.text}";
}

Simile ai suggerimenti precedenti------, ma il nome del metodo è ora "OnCollision------2D" anziché "OnTrigger2D".

Rigidbody 2D Ciascuno degli eventi precedenti si verifica quando un oggetto che si è scontrato con un altro oggetto Collider 2D che ha . Ciò ti consentirà di determinare ed elaborare se è corretto o meno.

Ci sono tre eventi, ognuno dei quali è chiamato al seguente orario.

OnCollisionEnter2D Quando gli oggetti si colpiscono a vicenda
OnCollisionStay2D Mentre gli oggetti si colpiscono a vicenda
OnCollisionExit2D Quando gli oggetti lasciano lo stato di collisione

In entrambi i casi, l'oggetto avversario riceve l'oggetto dell'avversario come argomento, quindi puoi ottenere l'oggetto dell'avversario Collision2D cercando Collider2D.gameObject il tipo di bersaglio colpito da (nemico, oggetto, Collider2D.collider.tag ecc.).

Dei OnCollisionEnter2D tre eventi precedenti, e sono chiamati una volta per collisione OnCollisionExit2D .

OnCollisionStay2D viene chiamato ogni fotogramma durante la collisione, ma l'evento non viene più chiamato dopo che è trascorso un certo periodo di tempo da quando entrambi gli oggetti si sono fermati. Questo perché si ritiene che sia entrato in uno stato di sonno, ed è considerato uno spreco di elaborazione calcolare le collisioni ogni fotogramma con qualcosa che non si muove.

Se non vuoi Rigidbody 2D che dorma, cambia la modalità di sospensione del parametro in "Non dormire".

Dopo aver modificato il codice, impostare il testo per la visualizzazione delle informazioni.

Esegui il gioco e sposta l'oggetto con la tastiera per toccare un altro sprite. Puoi vedere che sono chiamate tre funzioni per ciascuna.

A proposito, se tocchi un oggetto e poi smetti di muoverti, il metodo verrà chiamato per OnCollisionStay2D un breve periodo. Dovresti essere in grado di vedere che il metodo non viene più chiamato dopo OnCollisionStay2D un certo periodo di tempo.

Questo indica che sei entrato in uno stato di sospensione, ma se vuoi cambiare il tempo fino a quando non entri in questo sospensione, puoi modificarlo selezionando "Fisica 2D" dalle impostazioni del progetto e specificando il parametro "Tempo di sonno" in secondi. Non può essere impostato su 0, ma se OnCollisionStay2D è impostato su infinitamente piccolo, il metodo stesso non verrà chiamato.