Gunakan peta tindakan untuk menetapkan tombol ke perilaku game

Halaman Diperbarui :
Tanggal pembuatan halaman :

Lingkungan verifikasi

Windows
  • jendela 11
Editor Kesatuan
  • 25f1/3/2020
Paket Sistem Input
  • 1.2.0

Prasyarat untuk tip ini

Pengaturan berikut telah dibuat sebelumnya sebagai premis untuk deskripsi tip ini.

Tentang Peta Tindakan

Program input pengguna pada keyboard, mouse, dan gamepad pada dasarnya menyatakan bahwa tindakan tertentu dilakukan ketika tombol ditekan. Di peta tindakan, misalnya, Anda dapat menentukan tindakan "melompat" dan menetapkan tombol pengontrol dan tombol keyboard untuk itu. Akibatnya, program hanya perlu menggambarkan proses ketika tindakan tertentu dilakukan. Bahkan jika Anda menetapkan tombol pada pengontrol lain sebagai renungan, Anda dapat menerapkannya tanpa mengubah program operasi.

Membuat Peta Tindakan

Di sini, saya ingin membuat peta tindakan dan menampilkan informasi input pengguna dalam teks. Ada beberapa cara untuk mendapatkan input pengguna menggunakan Peta Tindakan.

Klik kanan folder mana pun dalam proyek untuk membuat Tindakan Input. Lokasi folder yang akan dibuat sewenang-wenang, tetapi harap kelola sesuai dengan proyek Anda. Nama file juga sewenang-wenang, tetapi ini InputActionSample dia .

Ketika Anda mengklik dua kali file yang dibuat, jendela berikut akan ditampilkan.

Pertama, klik tombol + di Action Maps untuk membuat peta tindakan. Sebagai unit kreasi, jika konten operasi berubah tergantung pada pemandangan, itu akan didefinisikan dalam unit itu. Misalnya, dalam kasus game aksi gulir samping, konten operasi berubah selama aksi dan di menu, jadi Anda akan membuat peta aksi untuk masing-masing.

Di sini, sebagai contoh, kita mendefinisikan tindakan side-scrolling dan menamainya "SideScrollActionMap".

Selanjutnya, buat Tindakan. Karena ini adalah sampel, saya tidak akan membuat banyak dari mereka, tetapi di sini kita akan membuat tindakan "Pindahkan" untuk gerakan dan "Serang" untuk serangan. Karena yang sudah dibuat, silakan ubah nama atau buat yang baru, klik tombol + di sudut kanan atas dan masukkan.

Pertama, konfigurasikan konfigurasi Pindahkan. Pengontrol mengasumsikan bahwa Anda menggunakan tombol kursor tongkat, D-pad, dan keyboard. Dalam kasus tindakan gulir samping, ada kasus di mana hanya kiri dan kanan yang digunakan, tetapi di sini kami berasumsi bahwa Anda menggunakan empat arah mempertimbangkan untuk melompat dengan tombol atas dan berjongkok dengan tombol bawah.

Saat Anda memilih Pindahkan, ada pilihan Jenis Tindakan di sebelah kanan, jadi atur ini ke "Nilai".

Anda akan melihat Control Type di bawah ini, jadi pilih Vector2. Ini karena bagian atas dan bawah ditugaskan ke Y, dan kiri dan kanan ditugaskan ke X.

Kemudian pilih kunci yang ingin Anda tetapkan ke acara ini. Pilih No Binding di tengah dan pilih Path di sebelah kanan. Di sini kita memilih GamePad LeftStick.

Ini mengikat LeftStick GamePad untuk bergerak.

Untuk mengikat pengontrol lain juga, pilih "Add Binding" dari tombol + di sebelah kanan Move.

Sekarang No Binding ditambahkan, kami menetapkan Dpad untuk GamePad.

Dengan cara ini, Anda dapat menambahkan jenis pengontrol yang ingin Anda dukung, serta tombol dan tongkat. Dimungkinkan juga untuk mengaturnya secara khusus untuk konsol game tertentu.

Tongkat dan Dpads adalah tombol yang mengasumsikan atas, bawah, kiri, dan kanan, sehingga mereka dapat ditambahkan dengan ini, tetapi dalam kasus keyboard, semuanya adalah tombol tunggal, jadi tidak ada definisi untuk atas, bawah, kiri, dan kanan. Untuk mengatur keyboard ke atas, bawah, kiri, atau kanan, pilih Add Up Down Left Right Composite dari tombol +.

Vektor 2D kemudian akan ditambahkan dan Anda dapat menetapkannya ke masing-masing Atas Bawah Kiri Kanan, seperti yang ditunjukkan pada gambar di bawah ini.

Misalnya, jika Anda menggunakan Atas, setel "Panah Atas" pada keyboard Anda. Ngomong-ngomong, jika Anda kesulitan menemukan kunci, Anda dapat dengan mudah memilihnya dengan menekan tombol target sambil mengklik tombol "Dengarkan".

Atas sekarang diatur ke Panah Atas.

Demikian pula, atur Bawah, Kiri, dan Kanan dan selesai.

Tentu saja, tidak hanya tombol kursor tetapi juga WASD dapat diatur.

Selanjutnya, konfigurasikan Attack. Serangan mudah ditetapkan karena hanya satu tombol. Pertama, pilih Attack dan pastikan Action Type adalah sebuah tombol.

Kemudian pilih No Binding dan pilih tombol yang ingin Anda tetapkan dari Path.

Jika Anda ingin menambahkan lebih banyak, pilih "Add Binding" dari tombol +.

Tambahkan sebanyak yang Anda butuhkan. Karena diperlakukan sebagai tombol, keyboard dapat diatur dengan cara yang sama seperti pengontrol game.

Ketika semua pengaturan selesai, klik "Simpan Aset" untuk menyimpan. Anda dapat menutup jendela ini.

Akhirnya, dengan file inputactions proyek (dalam hal ini, file InputActionSample yang Anda buat sebelumnya), centang "Generate C# Class" di inspektur. Parameter akan ditambahkan, tetapi klik tombol "Terapkan" apa adanya.

Ini akan menghasilkan file skrip dengan nama yang sama. Ini berisi kelas yang berguna untuk menggunakan peta tindakan dari program.

Cara menerima informasi input

Ada beberapa cara untuk menerima masukan berdasarkan peta tindakan. Tip ini menjelaskan tiga pola, tetapi lebih baik fokus pada salah satunya ketika benar-benar membuat game. Jika Anda menggunakannya secara terpisah, akan merepotkan untuk dikelola.

Juga, jika Anda menggunakan beberapa metode penerimaan input dalam satu adegan, pemrosesan mungkin konflik internal dan tidak berfungsi dengan benar.

Menerima informasi input di Kirim Pesan

Metode pertama di sini adalah bagaimana menerima informasi input dalam "Kirim Pesan".

Kali ini, saya ingin menampilkan informasi yang dimasukkan dalam teks, jadi saya akan menempatkan objek teks.

Juga, karena tip ini akan mencoba untuk mendapatkan beberapa informasi input, kita akan membuat objek kosong untuk mengatur komponen secara terpisah. Namanya bisa apa saja.

Selanjutnya, tambahkan komponen Player Input ke objek kosong. Player Input adalah komponen penting untuk menghubungkan peta tindakan dan skrip.

Di "Add Component", ada "Player Input" di kategori "Input", jadi tambahkan.

Setelah komponen Player Input ditambahkan, atur peta tindakan yang Anda buat di "Tindakan". Jatuhkan dari proyek atau pilih dari ikon + di sebelah kanan.

Verifikasi bahwa Peta Default adalah peta yang Anda buat di peta tindakan.

Verifikasi bahwa Perilaku adalah "Kirim Pesan".

Selanjutnya, buat skrip. Nama file bisa apa saja, tapi ini InputSendMessage dia .

Skripnya terlihat seperti ini:

using UnityEngine;
using UnityEngine.InputSystem;
using UnityEngine.UI;

public class InputSendMessage : MonoBehaviour
{
  /// <summary>情報を表示させるテキストオブジェクト。</summary>
  [SerializeField] private Text TextObject;

  /// <summary>
  /// Move アクションが実行されたときに呼ばれる。
  /// </summary>
  /// <param name="inputValue">入力量。</param>
  public void OnMove(InputValue inputValue)
  {
    var vec = inputValue.Get<Vector2>();
    TextObject.text = $"Move:({vec.x:f2}, {vec.y:f2})\n{TextObject.text}";
  }

  /// <summary>
  /// Attack アクションが実行されたときに呼ばれる。
  /// </summary>
  public void OnAttack(InputValue inputValue)
  {
    TextObject.text = $"Attack:{inputValue.isPressed}\n{TextObject.text}";
  }
}
  • Objek memiliki Input Pemain terlampir yang mengatur Kirim Pesan
  • Mewarisi dari MonoBehaviour

Jika kondisi terpenuhi, maka jika Anda mendefinisikan metode yang disebut "OnXXXXXXXX", Metode target akan dipanggil ketika operasi tindakan yang ditentukan dilakukan. "XXXXXXXX" adalah nama Tindakan yang dibuat di peta tindakan. Di sini, kami telah membuat tindakan "Move" dan "Attack", jadi nama metodenya masing-masing adalah "OnMove" dan "OnAttack".

OnMove Anda bisa mendapatkan jumlah yang dimasukkan dari argumen InputValue . Karena Jenis Kontrol diatur ke "Vektor 2", nilai InputValue.Get<Vector2> input akan diterima dalam format .

OnAttackInputValue.isPressed Anda bisa mendapatkan apakah Anda menekan juga.

Setelah Anda menyimpan skrip, lampirkan ke objek yang memiliki komponen Input Pemutar. Atur objek teks untuk ditampilkan juga.

Jalankan game dan lihatlah. Kali ini, saya telah menyertakan definisi gamepad dan keyboard, jadi itu harus berfungsi tidak peduli yang mana yang Anda operasikan.

Seperti yang Anda lihat ketika Anda memindahkannya, Anda dapat melihat bahwa metode ini dipanggil hanya ketika ada perubahan nilai dari keadaan sebelumnya. Misalnya, saat menggerakkan tongkat ke kiri, itu disebut berpikiran tunggal, tetapi tidak ke kiri (- OnMove 1,0). OnMove Tombol Serangan juga hanya merespons saat ditekan, dan jika ditekan dan ditahan, metode ini tidak dipanggil.

Oleh karena itu, saya pikir penggunaan yang ideal bukanlah untuk melakukan pemrosesan game ketika OnXXXXXXXX dipanggil, tetapi hanya menyimpan konten input dan menggunakan nilai-nilai tersebut dalam pemrosesan pembaruan game.

Ngomong-ngomong, dalam keadaan saat ini, itu tidak dipanggil ketika tombol dilepaskan, jadi tidak mungkin untuk menentukan kapan OnAttack tombol dilepaskan. Untuk menanggapi ini, pilih tindakan Serangan yang mendefinisikan tombol dalam pengaturan peta tindakan dan tambahkan "Tekan" dari "Interaksi". Setelah itu, atur Perilaku Pemicu dari Tekan yang ditambahkan ke "Tekan Dan Lepaskan" dan simpan.

Saat dijalankan, Anda dapat melihat bahwa dipanggil bahkan OnAttack ketika tombol dilepaskan. isPressed false Karena menjadi , juga dimungkinkan untuk menentukan apakah itu waktu rilis.

Omong-omong, harap hapus interaksi ini karena tidak akan digunakan di masa mendatang.

Terima masukan dengan Memanggil Acara Unity

Cara kedua untuk menerima masukan adalah Invoke Unity Events, jadi mari kita coba ini. Seperti disebutkan di atas, menggunakan beberapa metode input dapat menyebabkan pemrosesan yang bertentangan, jadi jika pemrosesan lain diaktifkan, nonaktifkan.

Pertama, tempatkan objek teks sehingga informasi input dapat ditampilkan.

Memanggil Acara Unity membuat objek kosong yang melakukan operasi terkait.

Tambahkan Input > Player Input ke objek kosong.

Atur file peta tindakan yang Anda buat untuk Tindakan (dalam hal ini, InputActionSample) dan atur Peta Tindakan yang Anda buat (dalam hal ini, SideScrollActionMap) ke Peta Default. Atur perilaku untuk memanggil peristiwa Unity.

Buat skrip. Namanya sewenang-wenang, tetapi dalam kasus InputInvokeUnityEvents ini adalah .

Skripnya terlihat seperti ini:

using UnityEngine;
using UnityEngine.InputSystem;
using UnityEngine.UI;

public class InputInvokeUnityEvents : MonoBehaviour
{
  /// <summary>情報を表示させるテキストオブジェクト。</summary>
  [SerializeField] private Text TextObject;

  /// <summary>
  /// Move 操作を行ったときに呼ばれる。
  /// </summary>
  /// <param name="context">コールバック内容。</param>
  public void OnMove(InputAction.CallbackContext context)
  {
    var vec = context.ReadValue<Vector2>();
    TextObject.text = $"Move:({vec.x:f2}, {vec.y:f2})\n{TextObject.text}";
  }

  /// <summary>
  /// Move 操作を行ったときに呼ばれる。
  /// </summary>
  /// <param name="context">コールバック内容。</param>
  public void OnAttack(InputAction.CallbackContext context)
  {
    var value = context.ReadValueAsButton();
    TextObject.text = $"Attack:{value}\n{TextObject.text}";
  }
}

Nama OnMoveOnAttack metode yang dipanggil ketika pengguna berinteraksi dengannya adalah , seperti dalam kasus Kirim Pesan. Di Memanggil Acara Unity, Anda dapat mengatur nama metode ini sesuka Anda.

Ketika masing-masing dipanggil, itu diteruskan sebagai InputAction.CallbackContext argumen, sehingga Anda bisa mendapatkan status input dari sana. Jika Anda menetapkan "nilai" dalam tindakan, Anda dapat menerimanya dalam metode, dan jika Anda menetapkan ReadValueAsButton "tombol", Anda ReadValue dapat menerimanya dalam metode.

Setelah menyimpan skrip, lampirkan Player Input ke objek yang Anda atur dan atur objek teks tampilan.

Selanjutnya, perluas "Event" dan "Action Map Name (SideScrollActionMap)" di Player Input dan Anda akan melihat tindakan "Move" dan "Attack" yang Anda buat.

Pertama, klik tombol + pada Move untuk menambahkannya.

Objek di sudut kiri bawah adalah objek Anda sendiri, dan Fungsi diatur ke metode yang baru saja Anda buat OnMove .

Konfigurasikan juga peristiwa Serangan.

Jalankan game untuk melihat cara kerjanya.

Pada dasarnya, ini dipanggil hanya ketika nilai yang sama dengan Kirim Pesan berubah, tetapi untuk beberapa alasan metode ini dapat dipanggil dua kali pada saat yang bersamaan. Saya tidak tahu penyebabnya, tapi saya pikir itu mungkin karena proses awal dan proses berkelanjutan berjalan pada saat yang bersamaan. Namun, saya pikir tidak ada masalah jika Anda hanya menyimpan nilai yang dimasukkan seperti dalam kasus Kirim Pesan dan melakukan pemrosesan game yang sebenarnya secara terpisah dalam proses Pembaruan.

Menggunakan skrip yang dibuat secara otomatis untuk menerima informasi input

Bagian ketiga menjelaskan cara mendapatkan informasi input menggunakan skrip yang dihasilkan dari file peta tindakan.

Karena ada kemungkinan konflik dengan proses akuisisi lainnya, harap nonaktifkan proses akuisisi lainnya.

Tempatkan objek teks untuk menampilkan informasi input.

Juga, buat objek kosong untuk mengambil informasi input. Artikel ini menggunakan skrip yang dibuat secara otomatis, jadi Anda tidak perlu menambahkan Input Pemutar.

Skrip yang dihasilkan secara otomatis dari peta tindakan hanyalah pustaka, jadi buat skrip kontrol terpisah. Namanya sewenang-wenang, tetapi dalam kasus InputScript ini adalah .

Skripnya terlihat seperti ini:

using UnityEngine;
using UnityEngine.InputSystem;
using UnityEngine.UI;

public class InputScript : MonoBehaviour
{
  /// <summary>情報を表示させるテキストオブジェクト。</summary>
  [SerializeField] private Text TextObject;

  /// <summary>アクションマップから自動生成されたクラス。</summary>
  private InputActionSample _actionMap;

  private void Awake()
  {
    // 各操作を行ったときに呼ばれるイベントを設定する
    _actionMap = new InputActionSample();
    _actionMap.SideScrollActionMap.Move.performed += context => OnMove(context);
    _actionMap.SideScrollActionMap.Attack.performed += context => OnAttack(context);
  }

  private void OnEnable()
  {
    // このオブジェクトが有効になったときにアクションマップを有効にする
    _actionMap.Enable();
  }

  private void OnDisable()
  {
    // このオブジェクトが無効になったときにアクションマップが余計な動作を起こさないように無効にする
    _actionMap.Disable();
  }

  /// <summary>
  /// Move 操作をした時に呼ばれるメソッドです。
  /// </summary>
  /// <param name="context">コールバックパラメータ。</param>
  public void OnMove(InputAction.CallbackContext context)
  {
    // Move の入力量を取得
    var vec = context.ReadValue<Vector2>();
    TextObject.text = $"Move:({vec.x:f2}, {vec.y:f2})\n{TextObject.text}";
  }

  /// <summary>
  /// Attack 操作をした時に呼ばれるメソッドです。
  /// </summary>
  /// <param name="context">コールバックパラメータ。</param>
  public void OnAttack(InputAction.CallbackContext context)
  {
    // Attack ボタンの状態を取得
    var value = context.ReadValueAsButton();
    TextObject.text = $"Attack:{value}\n{TextObject.text}";
  }
}

Tentukan kelas InputActionSample yang dibuat secara otomatis dari peta tindakan di bidang. Kelas ini mendefinisikan setiap tindakan yang ditetapkan dalam peta tindakan, dan Anda dapat mengatur peristiwa yang dipanggil saat tindakan tersebut dilakukan.

Awake Dalam metode ini, InputActionSample sebuah instance dari dibuat dan peristiwa yang dipanggil pada saat tindakan diatur. Ketika OnMoveAnda melakukan operasi ini, metode , OnAttack sekarang disebut.

Namun, karena kita hanya mengatur acara di sini, kita OnEnable perlu memanggil metode ketika Enable dipanggil untuk mengaktifkan peta tindakan.

Juga, karena perilaku input pengguna diperlakukan sebagai operasi global, Untuk mencegah OnDisable peta tindakan melakukan ekstra setelah objek ini tidak valid, kita memanggil metode dalam Disable metode untuk menonaktifkannya.

Setelah menyimpan skrip, lampirkan ke objek kosong yang Anda buat dan atur objek teks untuk ditampilkan.

Jalankan game untuk melihat cara kerjanya.

Seperti yang Anda lihat, metode ini tidak dipanggil ketika OnMove operasi Move menjadi (0, 0). Saya tidak yakin mengapa, tetapi tampaknya acara yang dilakukan hanya benar-benar mengambil satu dengan penekanan tombol diaktifkan.

Omong-omong, jika Anda belum mengatur Interaksi di peta aksi untuk Serangan, itu tidak akan dipanggil saat OnAttack Anda melepaskan tombol.

Untuk canceled menangani ini, Anda perlu mengatur acara. Jika Anda tidak ingin melakukan pemrosesan khusus pada (0, 0), Anda dapat memanggil metode apa adanya OnMove . Hal yang sama berlaku untuk Attack.

private void Awake()
{
  // 各操作を行ったときに呼ばれるイベントを設定する
  _actionMap = new InputActionSample();
  _actionMap.SideScrollActionMap.Move.performed += context => OnMove(context);
  _actionMap.SideScrollActionMap.Attack.performed += context => OnAttack(context);
  _actionMap.SideScrollActionMap.Move.canceled += context => OnMove(context);       // 追加
  _actionMap.SideScrollActionMap.Attack.canceled += context => OnAttack(context);   // 追加
}

Jalankan dan verifikasi bahwa Move:(0, 0) atau Attack:False muncul.