簡體   English   中英

在AKSequencer中調用具有重復隨機結果的隨機AKPlayers

[英]Calling random AKPlayers in AKSequencer with repeated random results

這是我目前正在處理的一個多音頻文件播放項目,其中通過AKSequencer以隨機順序播放多個AKPlayers。

首先,我有一個文件名數組:

Let filenames = [“1.mp3”, “2.mp3, “3.mp3”, … “10.mp3”]

這是分別加載到AKPlayer上的,以后以隨機順序調用它:

Let players: [AKPlayer] = {
    Do {
        Let filenames = [“1.mp3”, “2.mp3, “3.mp3”, … “10.mp3”]
        Return try filenames.map { AKPlayer(audioFile: try AKAudioFile(readRileName: $0)) }
    } catch {
        fatalError()
    }
}()

然后,我通過AKsequencer調用了AKPlayer,方法是通過“ playRandom ”函數觸發它:

Let sequencer = AKSequencer()
Let callbackInst = AKCallbackInstrument()

func playRandom() {
    let playerIndex = Int(arc4random_uniform(UInt32(players.count)))
    players[playerIndex].play()
}

func addTracks() {
    let track = sequencer.newTrack()!
    track.add(noteNumber: 48, velocity: 127, position: AKDuration(beats: 0), duration: AKDuration(beats: 16), channel: 0)
    track.setMIDIOutput(callbackInst.midiIn)
    callbackInst.callback = { status, note, vel in
        guard status == .noteOn else { return }
        self.playRandom()
        }
    }

最后,我將AKPlayer設置為AudioKit.output,然后啟動音序器。 到目前為止,這是成功的! 音序器以隨機順序無縫播放AKPlayer。

但是我想嘗試另一種隨機性:重復2到3次隨機選擇的玩家。 (例如playRandom …)。現在,“ playRandom ”在每次重復中僅選擇不同的AKPlayer。

作為一種解決方案,多虧了StackOverFlow大師,我嘗試了以下方法:

class RandomWithRepeats {
var range: ClosedRange<Int>
var repeatRange: ClosedRange<Int>
var repeatCount = 0
var value = 0

init(range: ClosedRange<Int>, repeatRange: ClosedRange<Int>) {
    self.range = range
    self.repeatRange = repeatRange
}

// generate a random number in a range
// Just use Int.random(in:) with Swift 4.2 and later
func random(in range: ClosedRange<Int>) -> Int {
    return Int(arc4random_uniform(UInt32(range.upperBound - range.lowerBound + 1))) + range.lowerBound
}

func nextValue() -> Int {
    // if repeatCount is 0, its time to generate a new value and
    // a new repeatCount
    if repeatCount == 0 {
        // For Swift 4.2, just use Int.random(in:) instead
        value = self.random(in: range)
        repeatCount = self.random(in: repeatRange)
    }

    repeatCount -= 1
    return value
}
}

然后我修改了playRandom函數,例如:

func playRandom() {
    Let rand = randomWithRepeats(range: 1…players.count, repeatRange: 2…3)
    Do { players[rand.nextValue()].play() }
}

事實證明,這是完全相同的結果,因為playRandom函數本身(由AKSequencer觸發)每次重復觸發,因此實際上並沒有“重復”隨機AKPlayer 2到3次。 我可以用其他方式解決這個問題嗎? 非常感激。 <3

RandomWithRepeats類的工作是跟蹤何時向您提供另一個AKPlayer實例,但是每次調用playRandom()時您都在創建一個RandomWithRepeats的新實例,因此它無法跟蹤任何內容。

創建玩家數組並在playRandom()方法中使用此實例時,請創建一個RandomWithRepeats實例。

let rand = RandomWithRepeats(range: 0 ... players.count, repeatRange: 2 ... 3)

func playRandom() {
     try? players[rand.nextValue()].play() 
}

為清潔溶液,則可能封裝的邏輯RandomWithRepeats與一起AKPlayer陣列成一個類,諸如RandomlyRepeatingPlayer類。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM