2013-06-04 188 views
2

我基本上想要播放一系列的mp3文件。 它不應該很難,但我努力保持解碼器和揚聲器通道打開,以便在播放一首歌后播放新的mp3數據。 下面是我迄今爲止播放一個mp3文件的精簡版。Node.js音頻播放器

var audioOptions = {channels: 2, bitDepth: 16, sampleRate: 44100}; 

// Create Decoder and Speaker 
var decoder = lame.Decoder(); 
var speaker = new Speaker(audioOptions); 

// My Playlist 
var songs = ['samples/Piano11.mp3','samples/Piano12.mp3','samples/Piano13.mp3']; 

// Read the first file 
var inputStream = fs.createReadStream(songs[0]); 

// Pipe the read data into the decoder and then out to the speakers 
inputStream.pipe(decoder).pipe(speaker); 

speaker.on('flush', function(){ 
    // Play next song 
}); 

我使用TooTallNate的模塊node-lame(用於解碼)和node-speaker(用於音頻輸出通過揚聲器)。

回答

2

沒有任何關於您提到的模塊的經驗,但我認爲您需要在每次播放歌曲時重新打開揚聲器(因爲您將解碼後的音頻輸入到它,解碼器完成後它將被關閉) 。你可以將你的代碼改寫成這樣(未經測試);

var audioOptions = {channels: 2, bitDepth: 16, sampleRate: 44100}; 

// Create Decoder and Speaker 
var decoder = lame.Decoder(); 

// My Playlist 
var songs = ['samples/Piano11.mp3','samples/Piano12.mp3','samples/Piano13.mp3']; 

// Recursive function that plays song with index 'i'. 
function playSong(i) { 
    var speaker  = new Speaker(audioOptions); 
    // Read the first file 
    var inputStream = fs.createReadStream(songs[i]); 
    // Pipe the read data into the decoder and then out to the speakers 
    inputStream.pipe(decoder).pipe(speaker); 
    speaker.on('flush', function(){ 
    // Play next song, if there is one. 
    if (i < songs.length - 1) 
     playSong(i + 1); 
    }); 
} 

// Start with the first song. 
playSong(0); 

另一種解決方案(其中一個我寧願)是使用非常漂亮的async模塊:

var async = require('async'); 
... 
async.eachSeries(songs, function(song, done) { 
    var speaker  = new Speaker(audioOptions); 
    var inputStream = fs.createReadStream(song); 

    inputStream.pipe(decoder).pipe(speaker); 

    speaker.on('flush', function() { 
    // signal async that it should process the next song in the array 
    done(); 
    }); 
}); 
+0

酷......工作真棒! –