diff --git a/audiosprite.js b/audiosprite.js index 70f8300..a69df99 100755 --- a/audiosprite.js +++ b/audiosprite.js @@ -3,6 +3,7 @@ const path = require('path') const async = require('async') const _ = require('underscore')._ const glob = require('glob'); +const ffmpegPath = require('ffmpeg-static'); const defaults = { output: 'output', @@ -30,40 +31,40 @@ const defaults = { module.exports = function(files) { let opts = {}, callback = function(){} - + if (arguments.length === 2) { callback = arguments[1] } else if (arguments.length >= 3) { opts = arguments[1] callback = arguments[2] } - + if (!files || !files.length) { return callback(new Error('No input files specified.')) } else { files = _.flatten(files.map(file => glob.sync(file))); } - + opts = _.extend({}, defaults, opts) - + // make sure output directory exists const outputDir = path.dirname(opts.output) if (!fs.existsSync(outputDir)) { require('mkdirp').sync(outputDir) } - + let offsetCursor = 0 const wavArgs = ['-ar', opts.samplerate, '-ac', opts.channels, '-f', 's16le'] const tempFile = mktemp('audiosprite') - + opts.logger.debug('Created temporary file', { file: tempFile }) - + const json = { resources: [] , spritemap: {} } - - spawn('ffmpeg', ['-version']).on('exit', code => { + + spawn(ffmpegPath, ['-version']).on('exit', code => { if (code) { callback(new Error('ffmpeg was not found on your path')) } @@ -84,17 +85,17 @@ module.exports = function(files) { processFiles() } }) - + function mktemp(prefix) { var tmpdir = require('os').tmpdir() || '.'; return path.join(tmpdir, prefix + '.' + Math.random().toString().substr(2)); } - + function spawn(name, opt) { opts.logger.debug('Spawn', { cmd: [name].concat(opt).join(' ') }); return require('child_process').spawn(name, opt); } - + function pad(num, size) { var str = num.toString(); @@ -104,17 +105,17 @@ module.exports = function(files) { return str; } - + function makeRawAudioFile(src, cb) { var dest = mktemp('audiosprite') - + opts.logger.debug('Start processing', { file: src }) - + fs.exists(src, function(exists) { if (exists) { let code = -1 let signal = undefined - let ffmpeg = spawn('ffmpeg', ['-i', path.resolve(src)] + let ffmpeg = spawn(ffmpegPath, ['-i', path.resolve(src)] .concat(wavArgs).concat('pipe:')) let streamFinished = _.after(2, function () { if (code) { @@ -135,13 +136,13 @@ module.exports = function(files) { signal = _signal streamFinished() }) - } + } else { cb({ msg: 'File does not exist', file: src }) } }) } - + function appendFile(name, src, dest, cb) { var size = 0 var reader = fs.createReadStream(src) @@ -176,7 +177,7 @@ module.exports = function(files) { }) reader.pipe(writer) } - + function appendSilence(duration, dest, cb) { var buffer = new Buffer(Math.round(opts.samplerate * 2 * opts.channels * duration)) buffer.fill(0) @@ -188,11 +189,11 @@ module.exports = function(files) { cb() }) } - + function exportFile(src, dest, ext, opt, store, cb) { var outfile = dest + '.' + ext; - - spawn('ffmpeg',['-y', '-ar', opts.samplerate, '-ac', opts.channels, '-f', 's16le', '-i', src] + + spawn(ffmpegPath, ['-y', '-ar', opts.samplerate, '-ac', opts.channels, '-f', 's16le', '-i', src] .concat(opt).concat(outfile)) .on('exit', function(code, signal) { if (code) { @@ -220,12 +221,12 @@ module.exports = function(files) { } }) } - + function exportFileCaf(src, dest, cb) { if (process.platform !== 'darwin') { return cb(true) } - + spawn('afconvert', ['-f', 'caff', '-d', 'ima4', src, dest]) .on('exit', function(code, signal) { if (code) { @@ -240,7 +241,7 @@ module.exports = function(files) { return cb() }) } - + function processFiles() { var formats = { aiff: [] @@ -253,14 +254,14 @@ module.exports = function(files) { , opus: ['-acodec', 'libopus', '-ab', opts.bitrate + 'k'] , webm: ['-acodec', 'libvorbis', '-f', 'webm', '-dash', '1'] }; - + if (opts.vbr >= 0 && opts.vbr <= 9) { formats.mp3 = formats.mp3.concat(['-aq', opts.vbr]) } else { formats.mp3 = formats.mp3.concat(['-ab', opts.bitrate + 'k']) } - + // change quality of webm output - https://trac.ffmpeg.org/wiki/TheoraVorbisEncodingGuide if (opts['vbr:vorbis'] >= 0 && opts['vbr:vorbis'] <= 10) { formats.webm = formats.webm.concat(['-qscale:a', opts['vbr:vorbis']]) @@ -268,7 +269,7 @@ module.exports = function(files) { else { formats.webm = formats.webm.concat(['-ab', opts.bitrate + 'k']) } - + if (opts.export.length) { formats = opts.export.split(',').reduce(function(memo, val) { if (formats[val]) { @@ -277,7 +278,7 @@ module.exports = function(files) { return memo }, {}) } - + var rawparts = opts.rawparts.length ? opts.rawparts.split(',') : null var i = 0 opts.logger.info(files); @@ -289,12 +290,12 @@ module.exports = function(files) { opts.logger.debug(err); return cb(err) } - + function tempProcessed() { fs.unlinkSync(tmp) cb() } - + var name = path.basename(file).replace(/\.[a-zA-Z0-9]+$/, '') appendFile(name, tmp, tempFile, function(err) { if (rawparts != null ? rawparts.length : void 0) { @@ -312,7 +313,7 @@ module.exports = function(files) { if (err) { return callback(new Error('Error adding file ' + err.message)) } - + async.forEachSeries(Object.keys(formats), function(ext, cb) { opts.logger.debug('Start export', { format: ext }) exportFile(tempFile, opts.output, ext, formats[ext], true, cb) @@ -323,15 +324,15 @@ module.exports = function(files) { if (opts.autoplay) { json.autoplay = opts.autoplay } - + json.resources = json.resources.map(function(e) { return opts.path ? path.join(opts.path, path.basename(e)) : e }) - + var finalJson = {} - + switch (opts.format) { - + case 'howler': case 'howler2': finalJson[opts.format === 'howler' ? 'urls' : 'src'] = [].concat(json.resources) @@ -344,7 +345,7 @@ module.exports = function(files) { } } break - + case 'createjs': finalJson.src = json.resources[0] finalJson.data = {audioSprite: []} @@ -357,13 +358,13 @@ module.exports = function(files) { }) } break - + case 'default': default: finalJson = json break } - + fs.unlinkSync(tempFile) callback(null, finalJson) }) diff --git a/package.json b/package.json index c3800df..267a121 100644 --- a/package.json +++ b/package.json @@ -8,7 +8,7 @@ "ffmpeg" ], "author": "Tõnis Tiigi ", - "version": "0.7.2", + "version": "0.7.3", "licenses": [ { "type": "MIT", @@ -25,6 +25,7 @@ }, "dependencies": { "async": "~0.9.0", + "ffmpeg-static": "^4.4.0", "glob": "^6.0.4", "mkdirp": "^0.5.0", "optimist": "~0.6.1", @@ -37,7 +38,6 @@ "engines": { "node": ">=0.10" }, - "optionalDependencies": {}, "scripts": { "test": "mocha" }