output.js 3.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162
  1. /*jshint node:true*/
  2. 'use strict';
  3. var utils = require('../utils');
  4. /*
  5. *! Output-related methods
  6. */
  7. module.exports = function(proto) {
  8. /**
  9. * Add output
  10. *
  11. * @method FfmpegCommand#output
  12. * @category Output
  13. * @aliases addOutput
  14. *
  15. * @param {String|Writable} target target file path or writable stream
  16. * @param {Object} [pipeopts={}] pipe options (only applies to streams)
  17. * @return FfmpegCommand
  18. */
  19. proto.addOutput =
  20. proto.output = function(target, pipeopts) {
  21. var isFile = false;
  22. if (!target && this._currentOutput) {
  23. // No target is only allowed when called from constructor
  24. throw new Error('Invalid output');
  25. }
  26. if (target && typeof target !== 'string') {
  27. if (!('writable' in target) || !(target.writable)) {
  28. throw new Error('Invalid output');
  29. }
  30. } else if (typeof target === 'string') {
  31. var protocol = target.match(/^([a-z]{2,}):/i);
  32. isFile = !protocol || protocol[0] === 'file';
  33. }
  34. if (target && !('target' in this._currentOutput)) {
  35. // For backwards compatibility, set target for first output
  36. this._currentOutput.target = target;
  37. this._currentOutput.isFile = isFile;
  38. this._currentOutput.pipeopts = pipeopts || {};
  39. } else {
  40. if (target && typeof target !== 'string') {
  41. var hasOutputStream = this._outputs.some(function(output) {
  42. return typeof output.target !== 'string';
  43. });
  44. if (hasOutputStream) {
  45. throw new Error('Only one output stream is supported');
  46. }
  47. }
  48. this._outputs.push(this._currentOutput = {
  49. target: target,
  50. isFile: isFile,
  51. flags: {},
  52. pipeopts: pipeopts || {}
  53. });
  54. var self = this;
  55. ['audio', 'audioFilters', 'video', 'videoFilters', 'sizeFilters', 'options'].forEach(function(key) {
  56. self._currentOutput[key] = utils.args();
  57. });
  58. if (!target) {
  59. // Call from constructor: remove target key
  60. delete this._currentOutput.target;
  61. }
  62. }
  63. return this;
  64. };
  65. /**
  66. * Specify output seek time
  67. *
  68. * @method FfmpegCommand#seek
  69. * @category Input
  70. * @aliases seekOutput
  71. *
  72. * @param {String|Number} seek seek time in seconds or as a '[hh:[mm:]]ss[.xxx]' string
  73. * @return FfmpegCommand
  74. */
  75. proto.seekOutput =
  76. proto.seek = function(seek) {
  77. this._currentOutput.options('-ss', seek);
  78. return this;
  79. };
  80. /**
  81. * Set output duration
  82. *
  83. * @method FfmpegCommand#duration
  84. * @category Output
  85. * @aliases withDuration,setDuration
  86. *
  87. * @param {String|Number} duration duration in seconds or as a '[[hh:]mm:]ss[.xxx]' string
  88. * @return FfmpegCommand
  89. */
  90. proto.withDuration =
  91. proto.setDuration =
  92. proto.duration = function(duration) {
  93. this._currentOutput.options('-t', duration);
  94. return this;
  95. };
  96. /**
  97. * Set output format
  98. *
  99. * @method FfmpegCommand#format
  100. * @category Output
  101. * @aliases toFormat,withOutputFormat,outputFormat
  102. *
  103. * @param {String} format output format name
  104. * @return FfmpegCommand
  105. */
  106. proto.toFormat =
  107. proto.withOutputFormat =
  108. proto.outputFormat =
  109. proto.format = function(format) {
  110. this._currentOutput.options('-f', format);
  111. return this;
  112. };
  113. /**
  114. * Add stream mapping to output
  115. *
  116. * @method FfmpegCommand#map
  117. * @category Output
  118. *
  119. * @param {String} spec stream specification string, with optional square brackets
  120. * @return FfmpegCommand
  121. */
  122. proto.map = function(spec) {
  123. this._currentOutput.options('-map', spec.replace(utils.streamRegexp, '[$1]'));
  124. return this;
  125. };
  126. /**
  127. * Run flvtool2/flvmeta on output
  128. *
  129. * @method FfmpegCommand#flvmeta
  130. * @category Output
  131. * @aliases updateFlvMetadata
  132. *
  133. * @return FfmpegCommand
  134. */
  135. proto.updateFlvMetadata =
  136. proto.flvmeta = function() {
  137. this._currentOutput.flags.flvmeta = true;
  138. return this;
  139. };
  140. };