@remotion/media-parser 4.0.229 → 4.0.231

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (182) hide show
  1. package/dist/boxes/iso-base-media/esds/decoder-specific-config.d.ts +3 -2
  2. package/dist/boxes/iso-base-media/esds/decoder-specific-config.js +7 -8
  3. package/dist/boxes/iso-base-media/esds/esds-descriptors.d.ts +4 -2
  4. package/dist/boxes/iso-base-media/esds/esds-descriptors.js +5 -4
  5. package/dist/boxes/iso-base-media/esds/esds.d.ts +3 -1
  6. package/dist/boxes/iso-base-media/esds/esds.js +2 -2
  7. package/dist/boxes/iso-base-media/make-track.js +2 -1
  8. package/dist/boxes/iso-base-media/mdat/mdat.js +13 -7
  9. package/dist/boxes/iso-base-media/moov/moov.d.ts +3 -1
  10. package/dist/boxes/iso-base-media/moov/moov.js +2 -2
  11. package/dist/boxes/iso-base-media/mvhd.js +11 -9
  12. package/dist/boxes/iso-base-media/parse-icc-profile.d.ts +36 -0
  13. package/dist/boxes/iso-base-media/parse-icc-profile.js +115 -0
  14. package/dist/boxes/iso-base-media/process-box.d.ts +5 -4
  15. package/dist/boxes/iso-base-media/process-box.js +17 -14
  16. package/dist/boxes/iso-base-media/stsd/colr.d.ts +14 -4
  17. package/dist/boxes/iso-base-media/stsd/colr.js +13 -1
  18. package/dist/boxes/iso-base-media/stsd/mebx.d.ts +1 -2
  19. package/dist/boxes/iso-base-media/stsd/mebx.js +2 -2
  20. package/dist/boxes/iso-base-media/stsd/samples.d.ts +5 -2
  21. package/dist/boxes/iso-base-media/stsd/samples.js +7 -6
  22. package/dist/boxes/iso-base-media/stsd/stsd.js +1 -0
  23. package/dist/boxes/iso-base-media/to-date.d.ts +1 -0
  24. package/dist/boxes/iso-base-media/to-date.js +9 -1
  25. package/dist/boxes/iso-base-media/trak/trak.d.ts +3 -1
  26. package/dist/boxes/iso-base-media/trak/trak.js +2 -2
  27. package/dist/boxes/webm/av1-codec-private.js +1 -1
  28. package/dist/boxes/webm/ebml.d.ts +1 -1
  29. package/dist/boxes/webm/get-sample-from-block.d.ts +4 -4
  30. package/dist/boxes/webm/get-sample-from-block.js +4 -2
  31. package/dist/boxes/webm/make-track.js +1 -0
  32. package/dist/boxes/webm/parse-webm-header.js +23 -4
  33. package/dist/boxes/webm/segments/parse-children.d.ts +12 -7
  34. package/dist/boxes/webm/segments/parse-children.js +67 -57
  35. package/dist/boxes/webm/segments.d.ts +8 -3
  36. package/dist/boxes/webm/segments.js +70 -39
  37. package/dist/buffer-iterator.d.ts +1 -1
  38. package/dist/buffer-iterator.js +1 -8
  39. package/dist/create/iso-base-media/codec-specific/avc1.d.ts +2 -0
  40. package/dist/create/iso-base-media/codec-specific/avc1.js +48 -0
  41. package/dist/create/iso-base-media/codec-specific/create-codec-specific-data.d.ts +22 -0
  42. package/dist/create/iso-base-media/codec-specific/create-codec-specific-data.js +36 -0
  43. package/dist/create/iso-base-media/codec-specific/mp4a.d.ts +2 -0
  44. package/dist/create/iso-base-media/codec-specific/mp4a.js +90 -0
  45. package/dist/create/iso-base-media/create-colr.d.ts +6 -0
  46. package/dist/create/iso-base-media/create-colr.js +26 -0
  47. package/dist/create/iso-base-media/create-ftyp.d.ts +10 -0
  48. package/dist/create/iso-base-media/create-ftyp.js +22 -0
  49. package/dist/create/iso-base-media/create-ilst.d.ts +1 -0
  50. package/dist/create/iso-base-media/create-ilst.js +14 -0
  51. package/dist/create/iso-base-media/create-iso-base-media.d.ts +2 -0
  52. package/dist/create/iso-base-media/create-iso-base-media.js +167 -0
  53. package/dist/create/iso-base-media/create-mdia.d.ts +5 -0
  54. package/dist/create/iso-base-media/create-mdia.js +18 -0
  55. package/dist/create/iso-base-media/create-moov.d.ts +5 -0
  56. package/dist/create/iso-base-media/create-moov.js +18 -0
  57. package/dist/create/iso-base-media/create-mvhd.d.ts +10 -0
  58. package/dist/create/iso-base-media/create-mvhd.js +48 -0
  59. package/dist/create/iso-base-media/create-trak.d.ts +4 -0
  60. package/dist/create/iso-base-media/create-trak.js +17 -0
  61. package/dist/create/iso-base-media/create-udta.d.ts +1 -0
  62. package/dist/create/iso-base-media/create-udta.js +14 -0
  63. package/dist/create/iso-base-media/create-url.d.ts +1 -0
  64. package/dist/create/iso-base-media/create-url.js +16 -0
  65. package/dist/create/iso-base-media/example-stts.d.ts +3 -0
  66. package/dist/create/iso-base-media/example-stts.js +2797 -0
  67. package/dist/create/iso-base-media/ilst/create-cmt.d.ts +1 -0
  68. package/dist/create/iso-base-media/ilst/create-cmt.js +26 -0
  69. package/dist/create/iso-base-media/ilst/create-too.d.ts +1 -0
  70. package/dist/create/iso-base-media/ilst/create-too.js +27 -0
  71. package/dist/create/iso-base-media/mdia/create-mdhd.d.ts +6 -0
  72. package/dist/create/iso-base-media/mdia/create-mdhd.js +33 -0
  73. package/dist/create/iso-base-media/mp4-header.d.ts +6 -0
  74. package/dist/create/iso-base-media/mp4-header.js +47 -0
  75. package/dist/create/iso-base-media/primitives.d.ts +15 -0
  76. package/dist/create/iso-base-media/primitives.js +133 -0
  77. package/dist/create/iso-base-media/serialize-track.d.ts +9 -0
  78. package/dist/create/iso-base-media/serialize-track.js +63 -0
  79. package/dist/create/iso-base-media/trak/create-tkhd.d.ts +27 -0
  80. package/dist/create/iso-base-media/trak/create-tkhd.js +97 -0
  81. package/dist/create/iso-base-media/trak/mdia/create-minf.d.ts +4 -0
  82. package/dist/create/iso-base-media/trak/mdia/create-minf.js +19 -0
  83. package/dist/create/iso-base-media/trak/mdia/minf/create-dinf.d.ts +1 -0
  84. package/dist/create/iso-base-media/trak/mdia/minf/create-dinf.js +22 -0
  85. package/dist/create/iso-base-media/trak/mdia/minf/create-smhd.d.ts +1 -0
  86. package/dist/create/iso-base-media/trak/mdia/minf/create-smhd.js +20 -0
  87. package/dist/create/iso-base-media/trak/mdia/minf/create-stbl.d.ts +6 -0
  88. package/dist/create/iso-base-media/trak/mdia/minf/create-stbl.js +35 -0
  89. package/dist/create/iso-base-media/trak/mdia/minf/create-vmhd.d.ts +1 -0
  90. package/dist/create/iso-base-media/trak/mdia/minf/create-vmhd.js +20 -0
  91. package/dist/create/iso-base-media/trak/mdia/minf/stbl/create-ctts.d.ts +2 -0
  92. package/dist/create/iso-base-media/trak/mdia/minf/stbl/create-ctts.js +45 -0
  93. package/dist/create/iso-base-media/trak/mdia/minf/stbl/create-stco.d.ts +2 -0
  94. package/dist/create/iso-base-media/trak/mdia/minf/stbl/create-stco.js +28 -0
  95. package/dist/create/iso-base-media/trak/mdia/minf/stbl/create-stsc.d.ts +2 -0
  96. package/dist/create/iso-base-media/trak/mdia/minf/stbl/create-stsc.js +56 -0
  97. package/dist/create/iso-base-media/trak/mdia/minf/stbl/create-stss.d.ts +2 -0
  98. package/dist/create/iso-base-media/trak/mdia/minf/stbl/create-stss.js +23 -0
  99. package/dist/create/iso-base-media/trak/mdia/minf/stbl/create-stsz.d.ts +2 -0
  100. package/dist/create/iso-base-media/trak/mdia/minf/stbl/create-stsz.js +25 -0
  101. package/dist/create/iso-base-media/trak/mdia/minf/stbl/create-stts.d.ts +2 -0
  102. package/dist/create/iso-base-media/trak/mdia/minf/stbl/create-stts.js +48 -0
  103. package/dist/create/iso-base-media/trak/mdia/minf/stbl/stsd/create-avc1.d.ts +1 -0
  104. package/dist/create/iso-base-media/trak/mdia/minf/stbl/stsd/create-avc1.js +20 -0
  105. package/dist/create/iso-base-media/trak/mdia/minf/stbl/stsd/create-avcc.d.ts +1 -0
  106. package/dist/create/iso-base-media/trak/mdia/minf/stbl/stsd/create-avcc.js +16 -0
  107. package/dist/create/iso-base-media/trak/mdia/minf/stbl/stsd/create-pasp.d.ts +1 -0
  108. package/dist/create/iso-base-media/trak/mdia/minf/stbl/stsd/create-pasp.js +13 -0
  109. package/dist/create/iso-base-media/udta/create-meta.d.ts +4 -0
  110. package/dist/create/iso-base-media/udta/create-meta.js +20 -0
  111. package/dist/create/iso-base-media/udta/meta/create-hdlr.d.ts +1 -0
  112. package/dist/create/iso-base-media/udta/meta/create-hdlr.js +32 -0
  113. package/dist/create/make-track-info.d.ts +20 -0
  114. package/dist/create/make-track-info.js +2 -0
  115. package/dist/create/{cluster-segment.d.ts → matroska/cluster-segment.d.ts} +1 -1
  116. package/dist/create/{cluster-segment.js → matroska/cluster-segment.js} +2 -2
  117. package/dist/create/{cluster.d.ts → matroska/cluster.d.ts} +12 -5
  118. package/dist/create/{cluster.js → matroska/cluster.js} +23 -20
  119. package/dist/create/matroska/create-matroska-media.d.ts +2 -0
  120. package/dist/create/{create-media.js → matroska/create-matroska-media.js} +49 -25
  121. package/dist/create/matroska/make-duration-with-padding.d.ts +1 -0
  122. package/dist/create/{make-duration-with-padding.js → matroska/make-duration-with-padding.js} +1 -1
  123. package/dist/create/{matroska-cues.d.ts → matroska/matroska-cues.d.ts} +1 -1
  124. package/dist/create/{matroska-cues.js → matroska/matroska-cues.js} +1 -1
  125. package/dist/create/matroska/matroska-header.d.ts +1 -0
  126. package/dist/create/{matroska-header.js → matroska/matroska-header.js} +1 -1
  127. package/dist/create/{matroska-info.d.ts → matroska/matroska-info.d.ts} +1 -1
  128. package/dist/create/{matroska-info.js → matroska/matroska-info.js} +1 -1
  129. package/dist/create/matroska/matroska-seek.d.ts +6 -0
  130. package/dist/create/{matroska-seek.js → matroska/matroska-seek.js} +1 -1
  131. package/dist/create/{matroska-segment.d.ts → matroska/matroska-segment.d.ts} +1 -1
  132. package/dist/create/{matroska-segment.js → matroska/matroska-segment.js} +1 -1
  133. package/dist/create/matroska/matroska-trackentry.d.ts +10 -0
  134. package/dist/create/{matroska-trackentry.js → matroska/matroska-trackentry.js} +9 -3
  135. package/dist/create/{create-media.d.ts → media-fn.d.ts} +17 -4
  136. package/dist/create/media-fn.js +2 -0
  137. package/dist/create/timescale.d.ts +1 -1
  138. package/dist/create/timescale.js +2 -2
  139. package/dist/emit-available-info.d.ts +1 -1
  140. package/dist/emit-available-info.js +23 -10
  141. package/dist/esm/buffer.mjs +3 -3
  142. package/dist/esm/index.mjs +2104 -735
  143. package/dist/esm/web-fs.mjs +2 -2
  144. package/dist/get-audio-codec.d.ts +2 -1
  145. package/dist/get-audio-codec.js +29 -10
  146. package/dist/get-duration.d.ts +5 -0
  147. package/dist/get-duration.js +7 -3
  148. package/dist/get-fps.d.ts +1 -0
  149. package/dist/get-fps.js +24 -13
  150. package/dist/get-sample-positions.d.ts +1 -0
  151. package/dist/get-sample-positions.js +1 -0
  152. package/dist/get-tracks.d.ts +1 -0
  153. package/dist/get-video-codec.d.ts +2 -2
  154. package/dist/get-video-codec.js +6 -6
  155. package/dist/has-all-info.d.ts +1 -1
  156. package/dist/has-all-info.js +8 -8
  157. package/dist/index.d.ts +6 -8
  158. package/dist/index.js +7 -3
  159. package/dist/options.d.ts +10 -1
  160. package/dist/parse-media.js +42 -14
  161. package/dist/parse-result.d.ts +15 -0
  162. package/dist/parse-video.d.ts +3 -1
  163. package/dist/parse-video.js +6 -14
  164. package/dist/parser-state.d.ts +3 -3
  165. package/dist/readers/reader.d.ts +2 -2
  166. package/dist/samples-from-moof.js +1 -0
  167. package/dist/version.d.ts +1 -0
  168. package/dist/version.js +5 -0
  169. package/dist/webcodec-sample-types.d.ts +7 -20
  170. package/dist/writers/buffer-implementation/writer.d.ts +2 -2
  171. package/dist/writers/buffer-implementation/writer.js +3 -3
  172. package/dist/writers/web-fs.js +2 -3
  173. package/dist/writers/writer.d.ts +5 -3
  174. package/package.json +3 -3
  175. package/dist/create/make-duration-with-padding.d.ts +0 -1
  176. package/dist/create/matroska-header.d.ts +0 -1
  177. package/dist/create/matroska-seek.d.ts +0 -6
  178. package/dist/create/matroska-trackentry.d.ts +0 -27
  179. package/dist/create/polyfill-audio-sample.d.ts +0 -3
  180. package/dist/create/polyfill-audio-sample.js +0 -15
  181. package/dist/writers/buffer-implementation/multi-buffer.d.ts +0 -0
  182. package/dist/writers/buffer-implementation/multi-buffer.js +0 -1
@@ -3,26 +3,44 @@ Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.expectSegment = void 0;
4
4
  const parse_ebml_1 = require("./parse-ebml");
5
5
  const parse_children_1 = require("./segments/parse-children");
6
- const parseSegment = async ({ segmentId, iterator, length, parserContext, headerReadSoFar, }) => {
7
- if (length < 0) {
8
- throw new Error(`Expected length of ${segmentId} to be greater or equal 0`);
6
+ const continueAfterMatroskaParseResult = async ({ result, iterator, parserContext, segment, }) => {
7
+ if (result.status === 'done') {
8
+ throw new Error('Should not continue after done');
9
9
  }
10
- iterator.counter.decrement(headerReadSoFar);
11
- const offset = iterator.counter.getOffset();
12
- const ebml = await (0, parse_ebml_1.parseEbml)(iterator, parserContext);
13
- const remapped = await (0, parse_ebml_1.postprocessEbml)({ offset, ebml, parserContext });
14
- return remapped;
10
+ const proceeded = await result.continueParsing();
11
+ if (proceeded.status === 'done') {
12
+ return {
13
+ status: 'done',
14
+ segment,
15
+ };
16
+ }
17
+ return {
18
+ continueParsing() {
19
+ return continueAfterMatroskaParseResult({
20
+ result: proceeded,
21
+ iterator,
22
+ parserContext,
23
+ segment,
24
+ });
25
+ },
26
+ segment: null,
27
+ status: 'incomplete',
28
+ };
15
29
  };
16
- const expectSegment = async (iterator, parserContext) => {
17
- const offset = iterator.counter.getOffset();
30
+ const expectSegment = async ({ iterator, parserContext, offset, children, }) => {
31
+ iterator.counter.decrement(iterator.counter.getOffset() - offset);
18
32
  if (iterator.bytesRemaining() === 0) {
19
33
  return {
20
34
  status: 'incomplete',
21
- segments: [],
22
35
  continueParsing: () => {
23
- return Promise.resolve((0, exports.expectSegment)(iterator, parserContext));
36
+ return (0, parse_children_1.expectAndProcessSegment)({
37
+ iterator,
38
+ parserContext,
39
+ offset,
40
+ children,
41
+ });
24
42
  },
25
- skipTo: null,
43
+ segment: null,
26
44
  };
27
45
  }
28
46
  const segmentId = iterator.getMatroskaSegmentId();
@@ -30,11 +48,15 @@ const expectSegment = async (iterator, parserContext) => {
30
48
  iterator.counter.decrement(iterator.counter.getOffset() - offset);
31
49
  return {
32
50
  status: 'incomplete',
33
- segments: [],
34
51
  continueParsing: () => {
35
- return Promise.resolve((0, exports.expectSegment)(iterator, parserContext));
52
+ return (0, parse_children_1.expectAndProcessSegment)({
53
+ iterator,
54
+ parserContext,
55
+ offset,
56
+ children,
57
+ });
36
58
  },
37
- skipTo: null,
59
+ segment: null,
38
60
  };
39
61
  }
40
62
  const offsetBeforeVInt = iterator.counter.getOffset();
@@ -44,43 +66,43 @@ const expectSegment = async (iterator, parserContext) => {
44
66
  iterator.counter.decrement(iterator.counter.getOffset() - offset);
45
67
  return {
46
68
  status: 'incomplete',
47
- segments: [],
48
69
  continueParsing: () => {
49
- return Promise.resolve((0, exports.expectSegment)(iterator, parserContext));
70
+ return (0, exports.expectSegment)({ iterator, parserContext, offset, children });
50
71
  },
51
- skipTo: null,
72
+ segment: null,
52
73
  };
53
74
  }
54
75
  const bytesRemainingNow = iterator.byteLength() - iterator.counter.getOffset();
55
76
  if (segmentId === '0x18538067' || segmentId === '0x1f43b675') {
77
+ const newSegment = {
78
+ type: segmentId === '0x18538067' ? 'Segment' : 'Cluster',
79
+ minVintWidth: offsetAfterVInt - offsetBeforeVInt,
80
+ value: [],
81
+ };
56
82
  const main = await (0, parse_children_1.expectChildren)({
57
83
  iterator,
58
84
  length,
59
- initialChildren: [],
60
- wrap: segmentId === '0x18538067'
61
- ? (s) => ({
62
- type: 'Segment',
63
- value: s,
64
- minVintWidth: offsetAfterVInt - offsetBeforeVInt,
65
- })
66
- : (s) => ({
67
- type: 'Cluster',
68
- value: s,
69
- minVintWidth: offsetAfterVInt - offsetBeforeVInt,
70
- }),
85
+ children: newSegment.value,
71
86
  parserContext,
87
+ startOffset: iterator.counter.getOffset(),
72
88
  });
73
89
  if (main.status === 'incomplete') {
74
90
  return {
75
91
  status: 'incomplete',
76
- segments: main.segments,
77
- skipTo: null,
78
- continueParsing: main.continueParsing,
92
+ continueParsing: () => {
93
+ return continueAfterMatroskaParseResult({
94
+ iterator,
95
+ parserContext,
96
+ result: main,
97
+ segment: newSegment,
98
+ });
99
+ },
100
+ segment: newSegment,
79
101
  };
80
102
  }
81
103
  return {
82
104
  status: 'done',
83
- segments: main.segments,
105
+ segment: newSegment,
84
106
  };
85
107
  }
86
108
  if (bytesRemainingNow < length) {
@@ -88,11 +110,10 @@ const expectSegment = async (iterator, parserContext) => {
88
110
  iterator.counter.decrement(bytesRead);
89
111
  return {
90
112
  status: 'incomplete',
91
- segments: [],
113
+ segment: null,
92
114
  continueParsing: () => {
93
- return Promise.resolve((0, exports.expectSegment)(iterator, parserContext));
115
+ return (0, exports.expectSegment)({ iterator, parserContext, offset, children });
94
116
  },
95
- skipTo: null,
96
117
  };
97
118
  }
98
119
  const segment = await parseSegment({
@@ -104,7 +125,17 @@ const expectSegment = async (iterator, parserContext) => {
104
125
  });
105
126
  return {
106
127
  status: 'done',
107
- segments: [segment],
128
+ segment,
108
129
  };
109
130
  };
110
131
  exports.expectSegment = expectSegment;
132
+ const parseSegment = async ({ segmentId, iterator, length, parserContext, headerReadSoFar, }) => {
133
+ if (length < 0) {
134
+ throw new Error(`Expected length of ${segmentId} to be greater or equal 0`);
135
+ }
136
+ iterator.counter.decrement(headerReadSoFar);
137
+ const offset = iterator.counter.getOffset();
138
+ const ebml = await (0, parse_ebml_1.parseEbml)(iterator, parserContext);
139
+ const remapped = await (0, parse_ebml_1.postprocessEbml)({ offset, ebml, parserContext });
140
+ return remapped;
141
+ };
@@ -26,7 +26,7 @@ export declare const getArrayBufferIterator: (initialData: Uint8Array, maxBytes:
26
26
  isWebm: () => boolean;
27
27
  discard: (length: number) => void;
28
28
  getEightByteNumber: (littleEndian?: boolean) => number;
29
- getFourByteNumber: (littleEndian?: boolean) => number;
29
+ getFourByteNumber: () => number;
30
30
  getSlice: (amount: number) => Uint8Array;
31
31
  getAtom: () => string;
32
32
  isRiff: () => boolean;
@@ -132,14 +132,7 @@ const getArrayBufferIterator = (initialData, maxBytes) => {
132
132
  ]);
133
133
  return Number(bigInt);
134
134
  };
135
- const getFourByteNumber = (littleEndian = false) => {
136
- if (littleEndian) {
137
- const one = getUint8();
138
- const two = getUint8();
139
- const three = getUint8();
140
- const four = getUint8();
141
- return (four << 24) | (three << 16) | (two << 8) | one;
142
- }
135
+ const getFourByteNumber = () => {
143
136
  return ((getUint8() << 24) | (getUint8() << 16) | (getUint8() << 8) | getUint8());
144
137
  };
145
138
  const getPaddedFourByteNumber = () => {
@@ -0,0 +1,2 @@
1
+ import type { Avc1Data } from './create-codec-specific-data';
2
+ export declare const createAvc1Data: ({ avccBox, pasp, width, height, horizontalResolution, verticalResolution, compressorName, depth, }: Avc1Data) => Uint8Array;
@@ -0,0 +1,48 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.createAvc1Data = void 0;
4
+ const make_header_1 = require("../../../boxes/webm/make-header");
5
+ const primitives_1 = require("../primitives");
6
+ const createAvc1Data = ({ avccBox, pasp, width, height, horizontalResolution, verticalResolution, compressorName, depth, }) => {
7
+ return (0, primitives_1.addSize)((0, make_header_1.combineUint8Arrays)([
8
+ // type
9
+ (0, primitives_1.stringsToUint8Array)('avc1'),
10
+ // reserved
11
+ new Uint8Array([0, 0, 0, 0, 0, 0]),
12
+ // data_reference_index
13
+ new Uint8Array([0, 1]),
14
+ // version
15
+ new Uint8Array([0, 0]),
16
+ // revisionLevel
17
+ new Uint8Array([0, 0]),
18
+ // vendor
19
+ new Uint8Array([0, 0, 0, 0]),
20
+ // temporalQuality
21
+ new Uint8Array([0, 0, 0, 0]),
22
+ // spatialQuality
23
+ new Uint8Array([0, 0, 0, 0]),
24
+ // width
25
+ (0, primitives_1.numberTo16BitUIntOrInt)(width),
26
+ // height
27
+ (0, primitives_1.numberTo16BitUIntOrInt)(height),
28
+ // horizontalResolution
29
+ (0, primitives_1.setFixedPointSignedOrUnsigned1616Number)(horizontalResolution),
30
+ // verticalResolution
31
+ (0, primitives_1.setFixedPointSignedOrUnsigned1616Number)(verticalResolution),
32
+ // dataSize
33
+ new Uint8Array([0, 0, 0, 0]),
34
+ // frame count per sample
35
+ (0, primitives_1.numberTo16BitUIntOrInt)(1),
36
+ // compressor name
37
+ (0, primitives_1.stringToPascalString)(compressorName),
38
+ // depth
39
+ (0, primitives_1.numberTo16BitUIntOrInt)(depth),
40
+ // colorTableId
41
+ (0, primitives_1.numberTo16BitUIntOrInt)(-1),
42
+ // avcc box
43
+ avccBox,
44
+ // pasp
45
+ pasp,
46
+ ]));
47
+ };
48
+ exports.createAvc1Data = createAvc1Data;
@@ -0,0 +1,22 @@
1
+ import type { MakeTrackAudio, MakeTrackVideo } from '../../make-track-info';
2
+ export type Avc1Data = {
3
+ pasp: Uint8Array;
4
+ avccBox: Uint8Array;
5
+ width: number;
6
+ height: number;
7
+ horizontalResolution: number;
8
+ verticalResolution: number;
9
+ compressorName: string;
10
+ depth: number;
11
+ type: 'avc1-data';
12
+ };
13
+ export type Mp4aData = {
14
+ type: 'mp4a-data';
15
+ sampleRate: number;
16
+ channelCount: number;
17
+ maxBitrate: number;
18
+ avgBitrate: number;
19
+ codecPrivate: Uint8Array | null;
20
+ };
21
+ export type CodecSpecificData = Avc1Data | Mp4aData;
22
+ export declare const createCodecSpecificData: (track: MakeTrackAudio | MakeTrackVideo) => Uint8Array;
@@ -0,0 +1,36 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.createCodecSpecificData = void 0;
4
+ const create_avcc_1 = require("../trak/mdia/minf/stbl/stsd/create-avcc");
5
+ const create_pasp_1 = require("../trak/mdia/minf/stbl/stsd/create-pasp");
6
+ const avc1_1 = require("./avc1");
7
+ const mp4a_1 = require("./mp4a");
8
+ const createCodecSpecificData = (track) => {
9
+ if (track.type === 'video') {
10
+ return (0, avc1_1.createAvc1Data)({
11
+ avccBox: (0, create_avcc_1.createAvccBox)(track.codecPrivate),
12
+ compressorName: 'WebCodecs',
13
+ depth: 24,
14
+ horizontalResolution: 72,
15
+ verticalResolution: 72,
16
+ height: track.height,
17
+ width: track.width,
18
+ pasp: (0, create_pasp_1.createPasp)(1, 1),
19
+ type: 'avc1-data',
20
+ });
21
+ }
22
+ if (track.type === 'audio') {
23
+ return (0, mp4a_1.createMp4a)({
24
+ type: 'mp4a-data',
25
+ // TODO: Put in values based on real data,
26
+ // this seems to work though
27
+ avgBitrate: 128 * 1024,
28
+ maxBitrate: 128 * 1024,
29
+ channelCount: track.numberOfChannels,
30
+ sampleRate: track.sampleRate,
31
+ codecPrivate: track.codecPrivate,
32
+ });
33
+ }
34
+ throw new Error('Unsupported codec specific data ' + track);
35
+ };
36
+ exports.createCodecSpecificData = createCodecSpecificData;
@@ -0,0 +1,2 @@
1
+ import type { Mp4aData } from './create-codec-specific-data';
2
+ export declare const createMp4a: ({ sampleRate, channelCount, avgBitrate, maxBitrate, codecPrivate, }: Mp4aData) => Uint8Array;
@@ -0,0 +1,90 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.createMp4a = void 0;
4
+ const make_header_1 = require("../../../boxes/webm/make-header");
5
+ const primitives_1 = require("../primitives");
6
+ const createMp4a = ({ sampleRate, channelCount, avgBitrate, maxBitrate, codecPrivate, }) => {
7
+ if (!codecPrivate) {
8
+ throw new Error('Need codecPrivate for mp4a');
9
+ }
10
+ const esdsAtom = (0, primitives_1.addSize)((0, make_header_1.combineUint8Arrays)([
11
+ // type
12
+ (0, primitives_1.stringsToUint8Array)('esds'),
13
+ // version
14
+ new Uint8Array([0]),
15
+ // flags
16
+ new Uint8Array([0, 0, 0]),
17
+ // tag = 'ES_DescrTag'
18
+ new Uint8Array([3]),
19
+ (0, primitives_1.addLeading128Size)((0, make_header_1.combineUint8Arrays)([
20
+ // ES_ID
21
+ (0, primitives_1.numberTo16BitUIntOrInt)(2),
22
+ // streamDependenceFlag, URL_Flag, OCRstreamFlag
23
+ new Uint8Array([0]),
24
+ // DecoderConfigDescrTag
25
+ new Uint8Array([4]),
26
+ (0, primitives_1.addLeading128Size)((0, make_header_1.combineUint8Arrays)([
27
+ // objectTypeIndication
28
+ new Uint8Array([0x40]),
29
+ // streamType, upStream
30
+ new Uint8Array([21]),
31
+ // reserved
32
+ new Uint8Array([0, 0, 0]),
33
+ // maxBitrate
34
+ (0, primitives_1.numberTo32BitUIntOrInt)(maxBitrate),
35
+ // avgBitrate
36
+ (0, primitives_1.numberTo32BitUIntOrInt)(avgBitrate),
37
+ // DecoderSpecificInfoTag
38
+ new Uint8Array([5]),
39
+ // codec private, for example [17, 144]
40
+ // audioObjectType = 2 = 'AAC LC'
41
+ // samplingFrequencyIndex = 3 = '48000 Hz'
42
+ // channelConfiguration = 2 = '2 channels'
43
+ /**
44
+ * Byte 1 (17): 0001 0001
45
+ ^^^^^ ^^^^
46
+ | |
47
+ | +-- Start of samplingFrequencyIndex (3)
48
+ +-- audioConfigType (2)
49
+
50
+ Byte 2 (144): 1001 0000
51
+ ^^^^ ^^^^
52
+ | |
53
+ | +-- Remaining bits/padding
54
+ +-- channelConfiguration (2)
55
+ */
56
+ (0, primitives_1.addLeading128Size)(codecPrivate),
57
+ ])),
58
+ // SLConfigDescrTag
59
+ new Uint8Array([6]),
60
+ (0, primitives_1.addLeading128Size)(new Uint8Array([2])),
61
+ ])),
62
+ ]));
63
+ return (0, primitives_1.addSize)((0, make_header_1.combineUint8Arrays)([
64
+ // type
65
+ (0, primitives_1.stringsToUint8Array)('mp4a'),
66
+ // reserved
67
+ new Uint8Array([0, 0, 0, 0, 0, 0]),
68
+ // data_reference_index
69
+ (0, primitives_1.numberTo16BitUIntOrInt)(1),
70
+ // version
71
+ (0, primitives_1.numberTo16BitUIntOrInt)(0),
72
+ // revision level
73
+ (0, primitives_1.numberTo16BitUIntOrInt)(0),
74
+ // vendor
75
+ new Uint8Array([0, 0, 0, 0]),
76
+ // channelCount
77
+ (0, primitives_1.numberTo16BitUIntOrInt)(channelCount),
78
+ // sampleSize
79
+ (0, primitives_1.numberTo16BitUIntOrInt)(16),
80
+ // compressionId
81
+ (0, primitives_1.numberTo16BitUIntOrInt)(0),
82
+ // packet size
83
+ (0, primitives_1.numberTo16BitUIntOrInt)(0),
84
+ // sample rate
85
+ (0, primitives_1.setFixedPointSignedOrUnsigned1616Number)(sampleRate),
86
+ // esds atom
87
+ esdsAtom,
88
+ ]));
89
+ };
90
+ exports.createMp4a = createMp4a;
@@ -0,0 +1,6 @@
1
+ export declare const createColr: ({ fullRange, matrixIndex, primaries, transferFunction, }: {
2
+ fullRange: boolean;
3
+ matrixIndex: number;
4
+ primaries: number;
5
+ transferFunction: number;
6
+ }) => Uint8Array;
@@ -0,0 +1,26 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.createColr = void 0;
4
+ const make_header_1 = require("../../boxes/webm/make-header");
5
+ const primitives_1 = require("./primitives");
6
+ // TODO: Not used in creation of MP4 yet
7
+ const createColr = ({ fullRange, matrixIndex, primaries, transferFunction, }) => {
8
+ return (0, primitives_1.addSize)((0, make_header_1.combineUint8Arrays)([
9
+ // type
10
+ (0, primitives_1.stringsToUint8Array)('colr'),
11
+ // colour_type
12
+ (0, primitives_1.stringsToUint8Array)('nclx'),
13
+ // primaries
14
+ // 1 = 'ITU-R BT.7090
15
+ new Uint8Array([0, primaries]),
16
+ // transfer_function
17
+ // 1 = 'ITU-R BT.7090
18
+ new Uint8Array([0, transferFunction]),
19
+ // matrix_index
20
+ // 1 = 'ITU-R BT.7090
21
+ new Uint8Array([0, matrixIndex]),
22
+ // full_range_flag
23
+ new Uint8Array([fullRange ? 1 : 0]),
24
+ ]));
25
+ };
26
+ exports.createColr = createColr;
@@ -0,0 +1,10 @@
1
+ export declare const createFtyp: ({ majorBrand, minorBrand, compatibleBrands, }: {
2
+ majorBrand: string;
3
+ minorBrand: number;
4
+ compatibleBrands: string[];
5
+ }) => Uint8Array;
6
+ export declare const createIsoBaseMediaFtyp: ({ majorBrand, minorBrand, compatibleBrands, }: {
7
+ majorBrand: string;
8
+ minorBrand: number;
9
+ compatibleBrands: string[];
10
+ }) => Uint8Array;
@@ -0,0 +1,22 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.createIsoBaseMediaFtyp = exports.createFtyp = void 0;
4
+ const make_header_1 = require("../../boxes/webm/make-header");
5
+ const primitives_1 = require("./primitives");
6
+ const createFtyp = ({ majorBrand, minorBrand, compatibleBrands, }) => {
7
+ const type = (0, primitives_1.stringsToUint8Array)('ftyp');
8
+ const majorBrandArr = (0, primitives_1.stringsToUint8Array)(majorBrand);
9
+ const minorBrandArr = (0, primitives_1.numberTo32BitUIntOrInt)(minorBrand);
10
+ const compatibleBrandsArr = (0, make_header_1.combineUint8Arrays)(compatibleBrands.map((b) => (0, primitives_1.stringsToUint8Array)(b)));
11
+ return (0, primitives_1.addSize)((0, make_header_1.combineUint8Arrays)([
12
+ type,
13
+ majorBrandArr,
14
+ minorBrandArr,
15
+ compatibleBrandsArr,
16
+ ]));
17
+ };
18
+ exports.createFtyp = createFtyp;
19
+ const createIsoBaseMediaFtyp = ({ majorBrand, minorBrand, compatibleBrands, }) => {
20
+ return (0, exports.createFtyp)({ compatibleBrands, majorBrand, minorBrand });
21
+ };
22
+ exports.createIsoBaseMediaFtyp = createIsoBaseMediaFtyp;
@@ -0,0 +1 @@
1
+ export declare const createIlst: (items: Uint8Array[]) => Uint8Array;
@@ -0,0 +1,14 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.createIlst = void 0;
4
+ const make_header_1 = require("../../boxes/webm/make-header");
5
+ const primitives_1 = require("./primitives");
6
+ const createIlst = (items) => {
7
+ return (0, primitives_1.addSize)((0, make_header_1.combineUint8Arrays)([
8
+ // name
9
+ (0, primitives_1.stringsToUint8Array)('ilst'),
10
+ // items
11
+ ...items,
12
+ ]));
13
+ };
14
+ exports.createIlst = createIlst;
@@ -0,0 +1,2 @@
1
+ import type { MediaFn, MediaFnGeneratorInput } from '../media-fn';
2
+ export declare const createIsoBaseMedia: ({ writer, onBytesProgress, onMillisecondsProgress, logLevel, filename, }: MediaFnGeneratorInput) => Promise<MediaFn>;
@@ -0,0 +1,167 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.createIsoBaseMedia = void 0;
4
+ const make_header_1 = require("../../boxes/webm/make-header");
5
+ const log_1 = require("../../log");
6
+ const create_ftyp_1 = require("./create-ftyp");
7
+ const mp4_header_1 = require("./mp4-header");
8
+ const primitives_1 = require("./primitives");
9
+ const createIsoBaseMedia = async ({ writer, onBytesProgress, onMillisecondsProgress, logLevel, filename, }) => {
10
+ const header = (0, create_ftyp_1.createIsoBaseMediaFtyp)({
11
+ compatibleBrands: ['isom', 'iso2', 'avc1', 'mp42'],
12
+ majorBrand: 'isom',
13
+ minorBrand: 512,
14
+ });
15
+ const w = await writer.createContent({ filename, mimeType: 'video/mp4' });
16
+ await w.write(header);
17
+ let durationInUnits = 0;
18
+ const currentTracks = [];
19
+ const samplePositions = [];
20
+ const sampleChunkIndices = [];
21
+ const moovOffset = w.getWrittenByteCount();
22
+ const getPaddedMoovAtom = () => {
23
+ return (0, mp4_header_1.createPaddedMoovAtom)({
24
+ durationInUnits,
25
+ trackInfo: currentTracks.map((track) => {
26
+ var _a;
27
+ return {
28
+ track,
29
+ durationInUnits,
30
+ samplePositions: (_a = samplePositions[track.trackNumber]) !== null && _a !== void 0 ? _a : [],
31
+ timescale: track.timescale,
32
+ };
33
+ }),
34
+ timescale: 1000,
35
+ });
36
+ };
37
+ await w.write(getPaddedMoovAtom());
38
+ let mdatSize = 8;
39
+ const mdatSizeOffset = w.getWrittenByteCount();
40
+ await w.write((0, make_header_1.combineUint8Arrays)([
41
+ // size
42
+ (0, primitives_1.numberTo32BitUIntOrInt)(mdatSize),
43
+ // type
44
+ (0, primitives_1.stringsToUint8Array)('mdat'),
45
+ ]));
46
+ const updateMdatSize = async () => {
47
+ await w.updateDataAt(mdatSizeOffset, (0, primitives_1.numberTo32BitUIntOrInt)(mdatSize));
48
+ onBytesProgress(w.getWrittenByteCount());
49
+ };
50
+ const operationProm = { current: Promise.resolve() };
51
+ const updateMoov = async () => {
52
+ await w.updateDataAt(moovOffset, getPaddedMoovAtom());
53
+ onBytesProgress(w.getWrittenByteCount());
54
+ };
55
+ const updateDuration = (newDuration) => {
56
+ durationInUnits = newDuration;
57
+ onMillisecondsProgress(newDuration);
58
+ };
59
+ const addCodecPrivateToTrack = ({ trackNumber, codecPrivate, }) => {
60
+ currentTracks.forEach((track) => {
61
+ if (track.trackNumber === trackNumber) {
62
+ track.codecPrivate = codecPrivate;
63
+ }
64
+ });
65
+ };
66
+ let lastChunkWasVideo = false;
67
+ const addSample = async ({ chunk, trackNumber, isVideo, timescale, codecPrivate, }) => {
68
+ var _a, _b;
69
+ const position = w.getWrittenByteCount();
70
+ await w.write(chunk.data);
71
+ mdatSize += chunk.data.length;
72
+ onBytesProgress(w.getWrittenByteCount());
73
+ if (codecPrivate) {
74
+ addCodecPrivateToTrack({ trackNumber, codecPrivate });
75
+ }
76
+ const newDuration = Math.round((chunk.timestamp + ((_a = chunk.duration) !== null && _a !== void 0 ? _a : 0)) / 1000);
77
+ updateDuration(newDuration);
78
+ if (!samplePositions[trackNumber]) {
79
+ samplePositions[trackNumber] = [];
80
+ }
81
+ if (typeof sampleChunkIndices[trackNumber] === 'undefined') {
82
+ sampleChunkIndices[trackNumber] = 0;
83
+ }
84
+ // For video, make a new chunk if it's a keyframe
85
+ if (isVideo && chunk.type === 'key') {
86
+ sampleChunkIndices[trackNumber]++;
87
+ } // For audio, make a new chunk every 22 samples, that's how bbb.mp4 is encoded
88
+ else if (!isVideo && samplePositions[trackNumber].length % 22 === 0) {
89
+ sampleChunkIndices[trackNumber]++;
90
+ }
91
+ // Need to create a new chunk if the last chunk was a different type
92
+ else if (lastChunkWasVideo !== isVideo) {
93
+ sampleChunkIndices[trackNumber]++;
94
+ }
95
+ // media parser and EncodedVideoChunk returns timestamps in microseconds
96
+ // need to normalize the timestamps to milliseconds
97
+ const samplePositionToAdd = {
98
+ isKeyframe: chunk.type === 'key',
99
+ offset: position,
100
+ chunk: sampleChunkIndices[trackNumber],
101
+ cts: Math.round(chunk.cts / (1000000 / timescale)),
102
+ dts: Math.round(chunk.dts / (1000000 / timescale)),
103
+ duration: Math.round(((_b = chunk.duration) !== null && _b !== void 0 ? _b : 0) / (1000000 / timescale)),
104
+ size: chunk.data.length,
105
+ };
106
+ lastChunkWasVideo = isVideo;
107
+ samplePositions[trackNumber].push(samplePositionToAdd);
108
+ };
109
+ const addTrack = (track) => {
110
+ const trackNumber = currentTracks.length + 1;
111
+ currentTracks.push({ ...track, trackNumber });
112
+ return Promise.resolve({ trackNumber });
113
+ };
114
+ const waitForFinishPromises = [];
115
+ return {
116
+ save: () => {
117
+ return w.save();
118
+ },
119
+ remove: async () => {
120
+ await w.remove();
121
+ },
122
+ addSample: ({ chunk, trackNumber, isVideo, timescale, codecPrivate }) => {
123
+ operationProm.current = operationProm.current.then(() => {
124
+ return addSample({
125
+ chunk,
126
+ trackNumber,
127
+ isVideo,
128
+ timescale,
129
+ codecPrivate,
130
+ });
131
+ });
132
+ return operationProm.current;
133
+ },
134
+ addTrack: (track) => {
135
+ operationProm.current = operationProm.current.then(() => addTrack(track));
136
+ return operationProm.current;
137
+ },
138
+ updateTrackSampleRate: ({ sampleRate, trackNumber }) => {
139
+ currentTracks.forEach((track) => {
140
+ if (track.trackNumber === trackNumber) {
141
+ if (track.type !== 'audio') {
142
+ throw new Error(`Tried to update sample rate of track ${trackNumber}, but it's not an audio track`);
143
+ }
144
+ track.sampleRate = sampleRate;
145
+ }
146
+ });
147
+ },
148
+ addWaitForFinishPromise: (promise) => {
149
+ waitForFinishPromises.push(promise);
150
+ },
151
+ async waitForFinish() {
152
+ log_1.Log.verbose(logLevel, 'All write operations queued. Waiting for finish...');
153
+ await Promise.all(waitForFinishPromises.map((p) => p()));
154
+ log_1.Log.verbose(logLevel, 'Cleanup tasks executed');
155
+ await operationProm.current;
156
+ await updateMoov();
157
+ await updateMdatSize();
158
+ log_1.Log.verbose(logLevel, 'All write operations done. Waiting for finish...');
159
+ await w.waitForFinish();
160
+ },
161
+ updateDuration: (duration) => {
162
+ operationProm.current = operationProm.current.then(() => updateDuration(duration));
163
+ return operationProm.current;
164
+ },
165
+ };
166
+ };
167
+ exports.createIsoBaseMedia = createIsoBaseMedia;