Contrôler le nombre d’effets sonores simultanés joués

Page mise à jour :
Date de création de la page :

Environnement de vérification

Windows
  • Fenêtres 11
Éditeur Unity
  • 2021.3.3f1
Package système d’entrée
  • 1.3.0

Conditions préalables à cette astuce

Les paramètres suivants ont été définis à l’avance comme prémisse pour la description de cette astuce.

À propos du matériel inclus avec l’échantillon

Les effets sonores sont empruntés aux sites suivants.

À propos des fichiers audio

Les formats de fichiers audio suivants peuvent être lus avec les fonctionnalités standard de Unity : Veuillez le préparer à l’avance car il sera utilisé dans ces conseils.

  • WAV (.wav)
  • OggVorbis (.ogg)
  • Couche MPEG 3 (.mp3)

Pour plus d’informations, consultez la documentation officielle de Unity.

À propos de la limite supérieure et du volume de la lecture audio simultanée multiple

Dans les conseils précédents, AudioClip il est maintenant possible de jouer plusieurs voix en les lisant tout en préparant AudioSource.PlayOneShot les données audio dans . Cependant, il n’y a pas de limite au nombre de jeux qui peuvent être joués, donc si vous ne le limitez pas pendant le jeu, beaucoup de son peut être joué et un volume fort peut être joué.

Ici, je voudrais créer mon propre programme et contrôler le nombre d’effets sonores pouvant être joués en même temps.

Créer l’exemple

Cette fois, l’effet sonore sera lu chaque fois que vous cliquez sur le bouton, alors créez l’interface utilisateur comme indiqué dans la figure. Les détails sont appropriés et bons.

Déposez et ajoutez le fichier audio que vous souhaitez lire dans votre projet.

Jusqu’à la dernière fois, la fonction AudioSource standard de a été ajoutée à la hiérarchie, Cette fois, nous allons ajouter un script car nous allons mettre notre propre contrôle. SoundPlayManager Conservez le nom .

Créez le script comme suit :

using System.Collections.Generic;
using UnityEngine;

/// <summary>音声再生管理クラスです。</summary>
public class SoundPlayManager : MonoBehaviour
{
  /// <summary>1つの種類の音声の再生情報を保持するクラスです。</summary>
  private class PlayInfo
  {
    /// <summary>再生している AudioSource の一覧です。</summary>
    public AudioSource[] AudioSource { get; set; }

    /// <summary>現在の再生インデックスです。</summary>
    public int NowIndex { get; set; }
  }

  /// <summary>再生しようとしている音声データのキューです。</summary>
  private HashSet<AudioClip> Queue = new HashSet<AudioClip>();

  /// <summary>再生している音声を管理している一覧です。</summary>
  private Dictionary<AudioClip, PlayInfo> Sources = new Dictionary<AudioClip, PlayInfo>();

  /// <summary>
  /// 同一音声同時再生最大数。
  /// </summary>
  [SerializeField, Range(1, 32)] private int MaxSimultaneousPlayCount = 2;

  protected void Update()
  {
    foreach (var item in Queue)
    {
      AudioSource source;
      if (Sources.ContainsKey(item) == false)
      {
        // 一度も再生されていない Clip がある場合は PlayInfo を生成します
        var info = new PlayInfo()
        {
          AudioSource = new AudioSource[MaxSimultaneousPlayCount],
        };
        for (int i = 0; i < MaxSimultaneousPlayCount; i++)
        {
          var s = gameObject.AddComponent<AudioSource>();
          s.clip = item;
          info.AudioSource[i] = s;
        }
        Sources.Add(item, info);
        source = info.AudioSource[0];
      }
      else
      {
        // 再生に使用する AudioSource を順番に取得します
        var info = Sources[item];
        info.NowIndex = (info.NowIndex + 1) % MaxSimultaneousPlayCount;
        source = info.AudioSource[info.NowIndex];
      }

      source.Play();
    }
    Queue.Clear();
  }

  /// <summary>
  /// 効果音を再生します。
  /// </summary>
  public void Play(AudioClip clip)
  {
    // 同一フレームで複数再生しないようにすでにキューに入っているか確認します
    if (Queue.Contains(clip) == false)
    {
      Queue.Add(clip);
    }
  }

  public void OnDestroy()
  {
    // 不要になった参照をすべて外します
    foreach (var source in Sources)
    {
      source.Value.AudioSource = null;
    }
    Sources.Clear();
    Queue.Clear();
  }
}

Comme le script est long, l’explication détaillée est omise, mais il a les fonctions suivantes.

  • AudioClip Vous pouvez lire de l’audio en passant
  • Lorsque le même type d’audio est lu les uns sur les autres, si vous essayez de lire plus d’un certain nombre de voix, les anciennes données de lecture s’arrêtent (la valeur initiale est jusqu’à 2 lectures).
  • La lecture qui se chevauche à la même image n’est pas autorisée

Cela empêche le volume d’augmenter lorsque le même audio est lu l’un à la suite de l’autre. En termes de fonctionnalité, seul le minimum est inclus, veuillez donc l’ajouter si vous en avez besoin.

Le script est attaché à EventSystem.

Ensuite, créez un script pour le bouton.

Créez le script comme suit :

using UnityEngine;

public class ButtonEvent : MonoBehaviour
{
  /// <summary>再生する音声データ。</summary>
  [SerializeField] private AudioClip AudioClip;

  /// <summary>自作した音声再生管理クラス。</summary>
  [SerializeField] private SoundPlayManager SoundPlayManager;

  /// <summary>ボタンをクリックしたとき。</summary>
  public void OnClick()
  {
    SoundPlayManager.Play(AudioClip);
  }
}

Le processus de lecture est effectué par le self-made SoundPlayManager self, donc dans l’événement du bouton, il suffit de passer les données audio et de les lire.

Le script est attaché à EventSystem. La gestion des attaches n’est pas le sujet principal de ce conseil, elle est donc appropriée.

Pour le clip audio, définissez le fichier audio à lire. Définissez le Gestionnaire de lecture audio sur l’objet SoundPlayManager auquel vous attachez. Puisque nous attachons à l’EventSystem, nous allons définir l’EventSystem.

Enfin, affectez à l’événement OnClick de clic de bouton.

Lancez le jeu lorsque vous avez terminé. Par défaut, le nombre maximum de lectures simultanées est défini sur 2, veuillez donc cliquer à nouveau sur le bouton pendant la lecture de deux sons et assurez-vous que le premier son disparaît.

Le programme créé cette fois a une limite supérieure sur le nombre de temps de lecture pour chaque type de son, de sorte qu’il semble naturel même si vous entrelacez d’autres effets sonores. Cependant, selon le type de son, la limite supérieure de 2 peut ne pas suffire, il peut donc être judicieux de pouvoir définir une limite supérieure pour chaque type de son. Eh bien, je ne sais pas s’il y a une telle opportunité de superposer le son, mais ...