如何使无效更新让音频播放直到结束?

Posted

技术标签:

【中文标题】如何使无效更新让音频播放直到结束?【英文标题】:How to make void update let audio play until end? 【发布时间】:2019-09-09 07:55:39 【问题描述】:

我在这件事上大发雷霆。

如何使这段代码使分配的音频文件完全运行?我知道更新方法只运行每一帧,但我如何让它运行直到音频完成?音频开始然后立即中断,因为它是每一帧。

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class checkifdone : MonoBehaviour


public Audiosource checkwin;
private bulbmanager bulbreq;
// Start is called before the first frame update
void Start()

    bulbreq = FindObjectOfType<bulbmanager>();


// Update is called once per frame
void Update()

    checkaudio();


void checkaudio()

    if (bulbreq.bulbcount >= 8)
    
        checkwin.Play();
    



我尝试将它放在 void start() 中,但这根本没有帮助,因为 start 是关卡的开始。

【问题讨论】:

【参考方案1】:

我想通了。基本上,这个脚本在一个空对象上,必须检查bulbcount是否为8,我将检查移到另一个游戏对象并将音频播放功能留在同一个地方。我还将 onEnabled 用于将播放声音的游戏对象,并在一开始使其处于非活动状态。

因此,当另一个游戏对象(检查灯泡计数所在的位置)知道灯泡计数为 8 时,它将启用音频播放器,并且 (OnEnabled) 它将播放声音。

这是另一个游戏对象(检查灯泡计数的对象)上的脚本:

using System.Collections;
using System.Collections.Generic;
using UnityEngine.SceneManagement;
using UnityEngine;

public class LampScript : MonoBehaviour


    private bulbmanager bulbreq;
    public GameObject wincheck;
    //private bulbsmustcollect bulblvl;
    // Start is called before the first frame update
    void Start()
    
        bulbreq = FindObjectOfType<bulbmanager>();

        //bulblvl = FindObjectOfType<bulbsmustcollect>();
    

    // Update is called once per frame
    void Update()
    
        if (bulbreq.bulbcount >= 8)
        
            wincheck.gameObject.SetActive(true);            

        
    

    private void OnTriggerEnter2D(Collider2D other)
    
        if (other.tag == "Player")
        
            if (bulbreq.bulbcount >= 8)
            
                //loop.Stop();
                SceneManager.LoadScene("Level 2");
            

        
    

这是我在音频播放器中输入的代码:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class checkifdone : MonoBehaviour


    public AudioSource checkwin;
    public GameObject wincheck;
    // Start is called before the first frame update
    void Start()
    
        wincheck.gameObject.SetActive(false); //This is the same object where script is.


    

    private void OnEnable()
    
        checkwin.Play();

    

当然,我们不要忘记分配所需的一切。音频现在播放到完整,因为它独立于其他脚本文件的更新功能。不确定这是否是最好的方法,但它有效!

【讨论】:

【参考方案2】:

来自AudioSource.Play

如果 AudioSource.clip 设置为正在播放的同一剪辑,则剪辑听起来像是重新开始。 AudioSource 将假定任何 Play 调用都会有一个新的音频剪辑要播放。

因此,如果您每帧调用Play,它总是从每帧的开头开始。


您可以简单地添加一个 bool 标志来检查它是否已经播放,而不是为此添加多个组件和对象。或者更简单:简单地禁用组件,这样Update 就不再被调用了

public class checkifdone : MonoBehaviour

    public AudioSource checkwin;

    private bulbmanager bulbreq;

    // Flag to control of sound was already played
    private bool alreadyPlayed;

    private void Start()
    
        bulbreq = FindObjectOfType<bulbmanager>();
    

    private void Update()
    
        // If was already played do nothing
        if(alreadyPlayed) return;

        checkaudio();
    

    private void checkaudio()
    
        if (bulbreq.bulbcount < 8) return;

        // Set flag so Update is skipped in the future
        alreadyPlayed = true;

        // Or alternatively simply
        // disable this component:
        enabled = false;

        checkwin.Play();
    

【讨论】:

【参考方案3】:

如果您使用 Unity 3d 和 C#,请尝试使用此功能。 它将在您的检查器面板中播放链接到 checkwin 的音频文件。

source.PlayOneShot(checkwin,vol);
// b is a bool
// this should stop either .play() or PlayOneShot() repeating or restarting
if(b)play audio function; b = false;

【讨论】:

仅此一项无济于事,因为它仍然在每一帧都被调用,因此您将有很多声音并行播放;) 好吧,我假设有人会在 if 语句中使用它来触发它。 :D 它假设播放音频一次不会与 checkwin.play() 连续重叠。 不完全是 ;) checkwin.Play() 启动当前附加的 AudioClip。如果它已经在运行,它会再次从头开始。 checkwin.PlayOneShot(audioClip);(顺便说一句,checkwin 是一个 AudioSource,不能作为 PlayOneShot 的参数;))重播一次完整的音频剪辑。如果它被多次调用,则剪辑将并行播放。 是的,这就是为什么我提到使用 if 语句... -> if(b)play music; b = false 这将完全停止重复播放或重新启动的任何一种方式。 :P

以上是关于如何使无效更新让音频播放直到结束?的主要内容,如果未能解决你的问题,请参考以下文章

如何让音频在 React 中更流畅地循环播放?

我们如何让 NSTimer 在 iOS 中为我​​的音频播放器在后台运行

如何找到 HTMLAudioElement 音频结束播放

如何使我自己编写的音频播放器可以在后台运行(Windows Phone 8.1- WinRT)?

播放和暂停按钮正在工作...但是如何重置按钮以在音频结束后显示播放符号?

如何让我的音频在 socket.io 中播放?