node-av 1.0.3 → 1.2.0

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 (162) hide show
  1. package/README.md +56 -41
  2. package/dist/api/bitstream-filter.d.ts +180 -123
  3. package/dist/api/bitstream-filter.js +182 -126
  4. package/dist/api/bitstream-filter.js.map +1 -1
  5. package/dist/api/decoder.d.ts +286 -130
  6. package/dist/api/decoder.js +321 -159
  7. package/dist/api/decoder.js.map +1 -1
  8. package/dist/api/encoder.d.ts +254 -158
  9. package/dist/api/encoder.js +326 -298
  10. package/dist/api/encoder.js.map +1 -1
  11. package/dist/api/filter-presets.d.ts +912 -0
  12. package/dist/api/filter-presets.js +1407 -0
  13. package/dist/api/filter-presets.js.map +1 -0
  14. package/dist/api/filter.d.ts +280 -284
  15. package/dist/api/filter.js +435 -509
  16. package/dist/api/filter.js.map +1 -1
  17. package/dist/api/hardware.d.ts +226 -159
  18. package/dist/api/hardware.js +405 -287
  19. package/dist/api/hardware.js.map +1 -1
  20. package/dist/api/index.d.ts +3 -2
  21. package/dist/api/index.js +1 -0
  22. package/dist/api/index.js.map +1 -1
  23. package/dist/api/io-stream.d.ts +65 -61
  24. package/dist/api/io-stream.js +45 -47
  25. package/dist/api/io-stream.js.map +1 -1
  26. package/dist/api/media-input.d.ts +244 -141
  27. package/dist/api/media-input.js +207 -104
  28. package/dist/api/media-input.js.map +1 -1
  29. package/dist/api/media-output.d.ts +206 -128
  30. package/dist/api/media-output.js +212 -129
  31. package/dist/api/media-output.js.map +1 -1
  32. package/dist/api/pipeline.d.ts +168 -38
  33. package/dist/api/pipeline.js +238 -14
  34. package/dist/api/pipeline.js.map +1 -1
  35. package/dist/api/types.d.ts +22 -182
  36. package/dist/api/utilities/audio-sample.d.ts +1 -1
  37. package/dist/api/utilities/image.d.ts +1 -1
  38. package/dist/api/utilities/media-type.d.ts +1 -1
  39. package/dist/api/utilities/pixel-format.d.ts +1 -1
  40. package/dist/api/utilities/sample-format.d.ts +1 -1
  41. package/dist/api/utilities/timestamp.d.ts +1 -1
  42. package/dist/api/utils.d.ts +1 -2
  43. package/dist/api/utils.js +9 -0
  44. package/dist/api/utils.js.map +1 -1
  45. package/dist/{lib → constants}/channel-layouts.d.ts +1 -1
  46. package/dist/constants/channel-layouts.js.map +1 -0
  47. package/dist/{lib → constants}/constants.d.ts +19 -4
  48. package/dist/{lib → constants}/constants.js +15 -1
  49. package/dist/constants/constants.js.map +1 -0
  50. package/dist/constants/decoders.d.ts +609 -0
  51. package/dist/constants/decoders.js +617 -0
  52. package/dist/constants/decoders.js.map +1 -0
  53. package/dist/constants/encoders.d.ts +285 -0
  54. package/dist/constants/encoders.js +298 -0
  55. package/dist/constants/encoders.js.map +1 -0
  56. package/dist/constants/index.d.ts +4 -0
  57. package/dist/constants/index.js +5 -0
  58. package/dist/constants/index.js.map +1 -0
  59. package/dist/index.d.ts +1 -0
  60. package/dist/index.js +2 -0
  61. package/dist/index.js.map +1 -1
  62. package/dist/lib/audio-fifo.d.ts +128 -171
  63. package/dist/lib/audio-fifo.js +130 -173
  64. package/dist/lib/audio-fifo.js.map +1 -1
  65. package/dist/lib/binding.d.ts +7 -5
  66. package/dist/lib/binding.js +5 -0
  67. package/dist/lib/binding.js.map +1 -1
  68. package/dist/lib/bitstream-filter-context.d.ts +139 -184
  69. package/dist/lib/bitstream-filter-context.js +139 -188
  70. package/dist/lib/bitstream-filter-context.js.map +1 -1
  71. package/dist/lib/bitstream-filter.d.ts +69 -55
  72. package/dist/lib/bitstream-filter.js +68 -54
  73. package/dist/lib/bitstream-filter.js.map +1 -1
  74. package/dist/lib/codec-context.d.ts +317 -381
  75. package/dist/lib/codec-context.js +316 -381
  76. package/dist/lib/codec-context.js.map +1 -1
  77. package/dist/lib/codec-parameters.d.ts +161 -171
  78. package/dist/lib/codec-parameters.js +162 -172
  79. package/dist/lib/codec-parameters.js.map +1 -1
  80. package/dist/lib/codec-parser.d.ts +92 -105
  81. package/dist/lib/codec-parser.js +92 -103
  82. package/dist/lib/codec-parser.js.map +1 -1
  83. package/dist/lib/codec.d.ts +328 -217
  84. package/dist/lib/codec.js +392 -218
  85. package/dist/lib/codec.js.map +1 -1
  86. package/dist/lib/dictionary.d.ts +150 -204
  87. package/dist/lib/dictionary.js +159 -213
  88. package/dist/lib/dictionary.js.map +1 -1
  89. package/dist/lib/error.d.ts +97 -131
  90. package/dist/lib/error.js +98 -128
  91. package/dist/lib/error.js.map +1 -1
  92. package/dist/lib/filter-context.d.ts +317 -194
  93. package/dist/lib/filter-context.js +335 -200
  94. package/dist/lib/filter-context.js.map +1 -1
  95. package/dist/lib/filter-graph.d.ts +252 -293
  96. package/dist/lib/filter-graph.js +253 -294
  97. package/dist/lib/filter-graph.js.map +1 -1
  98. package/dist/lib/filter-inout.d.ts +87 -95
  99. package/dist/lib/filter-inout.js +87 -95
  100. package/dist/lib/filter-inout.js.map +1 -1
  101. package/dist/lib/filter.d.ts +93 -111
  102. package/dist/lib/filter.js +94 -112
  103. package/dist/lib/filter.js.map +1 -1
  104. package/dist/lib/format-context.d.ts +321 -429
  105. package/dist/lib/format-context.js +314 -386
  106. package/dist/lib/format-context.js.map +1 -1
  107. package/dist/lib/frame.d.ts +263 -406
  108. package/dist/lib/frame.js +263 -408
  109. package/dist/lib/frame.js.map +1 -1
  110. package/dist/lib/hardware-device-context.d.ts +150 -204
  111. package/dist/lib/hardware-device-context.js +149 -203
  112. package/dist/lib/hardware-device-context.js.map +1 -1
  113. package/dist/lib/hardware-frames-context.d.ts +171 -181
  114. package/dist/lib/hardware-frames-context.js +171 -181
  115. package/dist/lib/hardware-frames-context.js.map +1 -1
  116. package/dist/lib/index.d.ts +2 -3
  117. package/dist/lib/index.js +2 -5
  118. package/dist/lib/index.js.map +1 -1
  119. package/dist/lib/input-format.d.ts +90 -118
  120. package/dist/lib/input-format.js +89 -117
  121. package/dist/lib/input-format.js.map +1 -1
  122. package/dist/lib/io-context.d.ts +210 -242
  123. package/dist/lib/io-context.js +221 -253
  124. package/dist/lib/io-context.js.map +1 -1
  125. package/dist/lib/log.d.ts +86 -120
  126. package/dist/lib/log.js +85 -122
  127. package/dist/lib/log.js.map +1 -1
  128. package/dist/lib/native-types.d.ts +127 -112
  129. package/dist/lib/native-types.js +9 -0
  130. package/dist/lib/native-types.js.map +1 -1
  131. package/dist/lib/option.d.ts +285 -242
  132. package/dist/lib/option.js +310 -250
  133. package/dist/lib/option.js.map +1 -1
  134. package/dist/lib/output-format.d.ts +78 -102
  135. package/dist/lib/output-format.js +77 -101
  136. package/dist/lib/output-format.js.map +1 -1
  137. package/dist/lib/packet.d.ts +173 -241
  138. package/dist/lib/packet.js +172 -241
  139. package/dist/lib/packet.js.map +1 -1
  140. package/dist/lib/rational.d.ts +0 -2
  141. package/dist/lib/rational.js +0 -2
  142. package/dist/lib/rational.js.map +1 -1
  143. package/dist/lib/software-resample-context.d.ts +242 -326
  144. package/dist/lib/software-resample-context.js +242 -326
  145. package/dist/lib/software-resample-context.js.map +1 -1
  146. package/dist/lib/software-scale-context.d.ts +130 -174
  147. package/dist/lib/software-scale-context.js +132 -176
  148. package/dist/lib/software-scale-context.js.map +1 -1
  149. package/dist/lib/stream.d.ts +88 -198
  150. package/dist/lib/stream.js +87 -197
  151. package/dist/lib/stream.js.map +1 -1
  152. package/dist/lib/types.d.ts +1 -1
  153. package/dist/lib/utilities.d.ts +372 -181
  154. package/dist/lib/utilities.js +373 -182
  155. package/dist/lib/utilities.js.map +1 -1
  156. package/install/check.js +0 -1
  157. package/package.json +32 -24
  158. package/release_notes.md +43 -13
  159. package/CHANGELOG.md +0 -8
  160. package/dist/lib/channel-layouts.js.map +0 -1
  161. package/dist/lib/constants.js.map +0 -1
  162. /package/dist/{lib → constants}/channel-layouts.js +0 -0
@@ -1,51 +1,43 @@
1
- import { Frame, Stream } from '../lib/index.js';
2
- import type { AVFilterCmdFlag, AVMediaType, AVPixelFormat, AVSampleFormat, HardwareFramesContext, IRational } from '../lib/index.js';
1
+ import { Frame } from '../lib/index.js';
2
+ import type { AVFilterCmdFlag, AVMediaType } from '../constants/constants.js';
3
3
  import type { FilterOptions, StreamInfo } from './types.js';
4
- interface VideoFilterConfig {
5
- type: 'video';
6
- width: number;
7
- height: number;
8
- pixelFormat: AVPixelFormat;
9
- timeBase: IRational;
10
- frameRate?: IRational;
11
- sampleAspectRatio?: IRational;
12
- hwFramesCtx?: HardwareFramesContext | null;
13
- }
14
- interface AudioFilterConfig {
15
- type: 'audio';
16
- sampleRate: number;
17
- sampleFormat: AVSampleFormat;
18
- channelLayout: bigint;
19
- timeBase: IRational;
20
- }
21
- type FilterConfig = VideoFilterConfig | AudioFilterConfig;
22
4
  /**
23
- * High-level filter API for media processing.
5
+ * High-level filter API for audio and video processing.
24
6
  *
25
- * Provides a simplified interface for FFmpeg's filter system.
26
- * Supports both simple filter chains and complex filter graphs.
27
- * Handles automatic format negotiation and buffer management.
7
+ * Provides simplified interface for applying FFmpeg filters to frames.
8
+ * Handles filter graph construction, frame buffering, and command control.
9
+ * Supports both software and hardware-accelerated filtering operations.
10
+ * Essential component for effects, transformations, and format conversions.
28
11
  *
29
12
  * @example
30
13
  * ```typescript
31
- * import { FilterAPI, Frame } from 'node-av/api';
14
+ * import { FilterAPI } from 'node-av/api';
32
15
  *
33
- * // Create a simple video filter from a stream
34
- * const videoStream = media.video();
35
- * const filter = await FilterAPI.create('scale=1280:720,format=yuv420p', videoStream);
16
+ * // Create video filter
17
+ * const filter = await FilterAPI.create('scale=1280:720', videoInfo);
36
18
  *
37
- * // Process frames
38
- * const outputFrame = await filter.process(inputFrame);
19
+ * // Process frame
20
+ * const output = await filter.process(inputFrame);
21
+ * if (output) {
22
+ * console.log(`Filtered frame: ${output.width}x${output.height}`);
23
+ * output.free();
24
+ * }
39
25
  * ```
40
26
  *
41
27
  * @example
42
28
  * ```typescript
43
- * // Create filter with hardware acceleration
44
- * const hw = await HardwareContext.auto();
45
- * const filter = await FilterAPI.create('scale_vt=640:480', videoStream, {
46
- * hardware: hw
47
- * });
29
+ * // Hardware-accelerated filtering
30
+ * const hw = HardwareContext.auto();
31
+ * const filter = await FilterAPI.create(
32
+ * 'hwupload,scale_cuda=1920:1080,hwdownload',
33
+ * videoInfo,
34
+ * { hardware: hw }
35
+ * );
48
36
  * ```
37
+ *
38
+ * @see {@link FilterGraph} For low-level filter graph API
39
+ * @see {@link HardwareContext} For hardware acceleration
40
+ * @see {@link Frame} For frame operations
49
41
  */
50
42
  export declare class FilterAPI implements Disposable {
51
43
  private graph;
@@ -54,404 +46,408 @@ export declare class FilterAPI implements Disposable {
54
46
  private config;
55
47
  private mediaType;
56
48
  private initialized;
57
- private needsHardware;
58
49
  private hardware?;
59
- private pendingInit?;
50
+ private description;
51
+ private options;
60
52
  /**
61
- * Create a new Filter instance.
62
- *
63
- * The filter is uninitialized until setup with a filter description.
64
- * Use the static factory methods for easier creation.
65
- *
66
- * @param config - Filter configuration
67
- * @param hardware - Optional hardware context for late framesContext binding
53
+ * @param config - Stream configuration
54
+ * @param description - Filter description string
55
+ * @param options - Filter options
68
56
  * @internal
69
57
  */
70
58
  private constructor();
71
59
  /**
72
- * Create a filter from a filter description string.
73
- *
74
- * Accepts either a Stream (from MediaInput/Decoder) or StreamInfo (for raw data).
75
- * Automatically sets up buffer source and sink filters.
60
+ * Create a filter with specified description and configuration.
76
61
  *
77
- * Handles complex filter chains with multiple filters. Automatically detects if ANY
78
- * filter in the chain requires hardware acceleration (e.g., scale_vt in
79
- * "format=nv12,hwupload,scale_vt=640:480").
62
+ * Constructs filter graph from description string.
63
+ * Configures input/output buffers and threading.
64
+ * For video filters, uses lazy initialization to detect hardware frames.
80
65
  *
81
- * @param description - Filter graph description (e.g., "scale=1280:720" or complex chains)
82
- * @param input - Stream or StreamInfo describing the input
83
- * @param options - Optional filter options including hardware context
66
+ * Direct mapping to avfilter_graph_parse_ptr() and avfilter_graph_config().
84
67
  *
85
- * @returns Promise resolving to configured Filter instance
68
+ * @param description - Filter graph description
69
+ * @param input - Input stream configuration
70
+ * @param options - Filter options
71
+ * @returns Configured filter instance
86
72
  *
87
- * @throws {FFmpegError} If filter creation or configuration fails
73
+ * @throws {Error} If filter creation or configuration fails
74
+ * @throws {FFmpegError} If graph parsing or config fails
88
75
  *
89
76
  * @example
90
77
  * ```typescript
91
- * // Simple filter
92
- * const filter = await FilterAPI.create('scale=640:480', videoStream);
78
+ * // Simple video filter
79
+ * const filter = await FilterAPI.create('scale=640:480', videoInfo);
80
+ * ```
93
81
  *
94
- * // Complex filter chain with hardware
95
- * const hw = await HardwareContext.auto();
82
+ * @example
83
+ * ```typescript
84
+ * // Complex filter chain
96
85
  * const filter = await FilterAPI.create(
97
- * 'format=nv12,hwupload,scale_vt=640:480,hwdownload,format=yuv420p',
98
- * videoStream,
99
- * { hardware: hw }
86
+ * 'crop=640:480:0:0,rotate=PI/4',
87
+ * videoInfo
100
88
  * );
89
+ * ```
101
90
  *
102
- * // From StreamInfo (for raw data)
103
- * const filter = await FilterAPI.create('scale=640:480', {
104
- * type: 'video',
105
- * width: 1920,
106
- * height: 1080,
107
- * pixelFormat: AV_PIX_FMT_YUV420P,
108
- * timeBase: { num: 1, den: 30 }
109
- * });
91
+ * @example
92
+ * ```typescript
93
+ * // Audio filter
94
+ * const filter = await FilterAPI.create(
95
+ * 'volume=0.5,aecho=0.8:0.9:1000:0.3',
96
+ * audioInfo
97
+ * );
110
98
  * ```
99
+ *
100
+ * @see {@link process} For frame processing
101
+ * @see {@link FilterOptions} For configuration options
111
102
  */
112
- static create(description: string, input: Stream | StreamInfo, options?: FilterOptions): Promise<FilterAPI>;
103
+ static create(description: string, input: StreamInfo, options?: FilterOptions): Promise<FilterAPI>;
113
104
  /**
114
- * Process a single frame through the filter.
105
+ * Process a frame through the filter.
115
106
  *
116
- * Sends a frame through the filter graph and returns the filtered result.
117
- * May return null if the filter needs more input frames.
107
+ * Applies filter operations to input frame.
108
+ * May buffer frames internally before producing output.
109
+ * For video, performs lazy initialization on first frame.
118
110
  *
119
- * @param frame - Input frame to filter
111
+ * Direct mapping to av_buffersrc_add_frame() and av_buffersink_get_frame().
120
112
  *
121
- * @returns Promise resolving to filtered frame or null
113
+ * @param frame - Input frame to process
114
+ * @returns Filtered frame or null if buffered
122
115
  *
116
+ * @throws {Error} If filter not ready
123
117
  * @throws {FFmpegError} If processing fails
124
118
  *
125
119
  * @example
126
120
  * ```typescript
127
- * const outputFrame = await filter.process(inputFrame);
128
- * if (outputFrame) {
129
- * // Process the filtered frame
121
+ * const output = await filter.process(inputFrame);
122
+ * if (output) {
123
+ * console.log(`Got filtered frame: pts=${output.pts}`);
124
+ * output.free();
130
125
  * }
131
126
  * ```
127
+ *
128
+ * @example
129
+ * ```typescript
130
+ * // Process and drain
131
+ * const output = await filter.process(frame);
132
+ * if (output) yield output;
133
+ *
134
+ * // Drain buffered frames
135
+ * let buffered;
136
+ * while ((buffered = await filter.receive()) !== null) {
137
+ * yield buffered;
138
+ * }
139
+ * ```
140
+ *
141
+ * @see {@link receive} For draining buffered frames
142
+ * @see {@link frames} For stream processing
132
143
  */
133
144
  process(frame: Frame): Promise<Frame | null>;
134
145
  /**
135
- * Process multiple frames through the filter.
146
+ * Process multiple frames at once.
136
147
  *
137
- * Batch processing for better performance.
138
- * Returns all available output frames.
148
+ * Processes batch of frames and drains all output.
149
+ * Useful for filters that buffer multiple frames.
139
150
  *
140
151
  * @param frames - Array of input frames
152
+ * @returns Array of all output frames
141
153
  *
142
- * @returns Promise resolving to array of filtered frames
143
- *
154
+ * @throws {Error} If filter not ready
144
155
  * @throws {FFmpegError} If processing fails
145
156
  *
146
157
  * @example
147
158
  * ```typescript
148
- * const outputFrames = await filter.processMultiple(inputFrames);
159
+ * const outputs = await filter.processMultiple([frame1, frame2, frame3]);
160
+ * for (const output of outputs) {
161
+ * console.log(`Output frame: pts=${output.pts}`);
162
+ * output.free();
163
+ * }
149
164
  * ```
165
+ *
166
+ * @see {@link process} For single frame processing
150
167
  */
151
168
  processMultiple(frames: Frame[]): Promise<Frame[]>;
152
169
  /**
153
- * Receive a filtered frame without sending input.
170
+ * Receive buffered frame from filter.
171
+ *
172
+ * Drains frames buffered by the filter.
173
+ * Call repeatedly until null to get all buffered frames.
154
174
  *
155
- * Used to drain buffered frames from the filter.
156
- * Returns null when no more frames are available.
175
+ * Direct mapping to av_buffersink_get_frame().
157
176
  *
158
- * @returns Promise resolving to filtered frame or null
177
+ * @returns Buffered frame or null if none available
159
178
  *
160
- * @throws {FFmpegError} If receiving fails
179
+ * @throws {Error} If filter not ready
180
+ * @throws {FFmpegError} If receive fails
161
181
  *
162
182
  * @example
163
183
  * ```typescript
164
- * // Drain all buffered frames
165
- * while (true) {
166
- * const frame = await filter.receive();
167
- * if (!frame) break;
168
- * // Process frame
184
+ * // Drain buffered frames
185
+ * let frame;
186
+ * while ((frame = await filter.receive()) !== null) {
187
+ * console.log(`Buffered frame: pts=${frame.pts}`);
188
+ * frame.free();
169
189
  * }
170
190
  * ```
191
+ *
192
+ * @see {@link process} For input processing
193
+ * @see {@link flush} For end-of-stream
171
194
  */
172
195
  receive(): Promise<Frame | null>;
173
196
  /**
174
- * Flush the filter by sending null frame.
197
+ * Flush filter and signal end-of-stream.
175
198
  *
176
- * Signals end of stream to the filter.
177
- * Use receive() to get any remaining frames.
199
+ * Sends null frame to flush buffered data.
200
+ * Must call receive() to get flushed frames.
178
201
  *
179
- * @returns Promise resolving when flush is complete
202
+ * Direct mapping to av_buffersrc_add_frame(NULL).
180
203
  *
204
+ * @throws {Error} If filter not ready
181
205
  * @throws {FFmpegError} If flush fails
182
206
  *
183
207
  * @example
184
208
  * ```typescript
185
209
  * await filter.flush();
186
210
  * // Get remaining frames
187
- * while (true) {
188
- * const frame = await filter.receive();
189
- * if (!frame) break;
190
- * // Process final frames
211
+ * let frame;
212
+ * while ((frame = await filter.receive()) !== null) {
213
+ * frame.free();
191
214
  * }
192
215
  * ```
216
+ *
217
+ * @see {@link flushFrames} For async iteration
218
+ * @see {@link receive} For draining frames
193
219
  */
194
220
  flush(): Promise<void>;
195
221
  /**
196
- * Flush filter and yield all remaining frames as a generator.
222
+ * Flush filter and yield remaining frames.
197
223
  *
198
- * More convenient than calling flush() + receive() in a loop.
199
- * Automatically sends flush signal and yields all buffered frames.
224
+ * Convenient async generator for flushing.
225
+ * Combines flush and receive operations.
200
226
  *
201
- * @returns Async generator of remaining frames
202
- *
203
- * @throws {Error} If filter is not initialized
227
+ * @yields Remaining frames from filter
228
+ * @throws {Error} If filter not ready
229
+ * @throws {FFmpegError} If flush fails
204
230
  *
205
231
  * @example
206
232
  * ```typescript
207
- * // Process all remaining frames with generator
208
233
  * for await (const frame of filter.flushFrames()) {
209
- * // Process final frame
210
- * using _ = frame; // Auto cleanup
234
+ * console.log(`Flushed frame: pts=${frame.pts}`);
235
+ * frame.free();
211
236
  * }
212
237
  * ```
238
+ *
239
+ * @see {@link flush} For manual flush
240
+ * @see {@link frames} For complete pipeline
213
241
  */
214
242
  flushFrames(): AsyncGenerator<Frame>;
215
243
  /**
216
- * Process frames as an async generator.
217
- *
218
- * Provides a convenient iterator interface for filtering.
219
- * Automatically handles buffering and draining.
220
- * Input frames are automatically freed after processing.
221
- *
222
- * IMPORTANT: The yielded frames MUST be freed by the caller!
223
- * Input frames are automatically freed after processing.
244
+ * Process frame stream through filter.
224
245
  *
225
- * @param frames - Async generator of input frames (will be freed automatically)
246
+ * High-level async generator for filtering frame streams.
247
+ * Automatically handles buffering and flushing.
248
+ * Frees input frames after processing.
226
249
  *
227
- * @returns Async generator of filtered frames (ownership transferred to caller)
250
+ * @param frames - Async generator of input frames
251
+ * @yields Filtered frames
252
+ * @throws {Error} If filter not ready
253
+ * @throws {FFmpegError} If processing fails
228
254
  *
229
255
  * @example
230
256
  * ```typescript
231
- * for await (const filtered of filter.frames(decoder.frames())) {
232
- * // Process filtered frame
233
- * filtered.free(); // Must free output frame
257
+ * // Filter decoded frames
258
+ * for await (const frame of filter.frames(decoder.frames(packets))) {
259
+ * await encoder.encode(frame);
260
+ * frame.free();
234
261
  * }
235
262
  * ```
236
- */
237
- frames(frames: AsyncGenerator<Frame>): AsyncGenerator<Frame>;
238
- /**
239
- * Get the filter graph description.
240
- *
241
- * Returns a string representation of the filter graph in DOT format.
242
- * Useful for debugging and visualization.
243
- *
244
- * @returns Graph description or null if not initialized
245
263
  *
246
264
  * @example
247
265
  * ```typescript
248
- * const description = filter.getGraphDescription();
249
- * console.log(description);
266
+ * // Chain filters
267
+ * const filter1 = await FilterAPI.create('scale=640:480', info);
268
+ * const filter2 = await FilterAPI.create('rotate=PI/4', info);
269
+ *
270
+ * for await (const frame of filter2.frames(filter1.frames(input))) {
271
+ * // Process filtered frames
272
+ * frame.free();
273
+ * }
250
274
  * ```
251
- */
252
- getGraphDescription(): string | null;
253
- /**
254
- * Check if the filter is initialized and ready.
255
275
  *
256
- * @returns true if the filter is ready for processing
276
+ * @see {@link process} For single frame processing
277
+ * @see {@link flush} For end-of-stream handling
257
278
  */
258
- isReady(): boolean;
279
+ frames(frames: AsyncGenerator<Frame>): AsyncGenerator<Frame>;
259
280
  /**
260
- * Get the media type of this filter.
281
+ * Send command to filter.
261
282
  *
262
- * @returns The media type (video or audio)
263
- */
264
- getMediaType(): AVMediaType;
265
- /**
266
- * Get the filter configuration.
283
+ * Sends runtime command to specific filter in graph.
284
+ * Allows dynamic parameter adjustment.
267
285
  *
268
- * @returns The filter configuration used to create this instance
269
- */
270
- getConfig(): FilterConfig;
271
- /**
272
- * Free all filter resources.
286
+ * Direct mapping to avfilter_graph_send_command().
273
287
  *
274
- * Releases the filter graph and all associated filters.
275
- * The filter instance cannot be used after calling this.
288
+ * @param target - Target filter name
289
+ * @param cmd - Command name
290
+ * @param arg - Command argument
291
+ * @param flags - Command flags
292
+ * @returns Response string from filter
293
+ *
294
+ * @throws {Error} If filter not ready
295
+ * @throws {FFmpegError} If command fails
276
296
  *
277
297
  * @example
278
298
  * ```typescript
279
- * filter.free();
280
- * // filter is now invalid
299
+ * // Change volume at runtime
300
+ * const response = filter.sendCommand('volume', 'volume', '0.5');
301
+ * console.log(`Volume changed: ${response}`);
281
302
  * ```
303
+ *
304
+ * @see {@link queueCommand} For delayed commands
282
305
  */
283
- free(): void;
306
+ sendCommand(target: string, cmd: string, arg: string, flags?: AVFilterCmdFlag): string;
284
307
  /**
285
- * Initialize the filter graph.
308
+ * Queue command for later execution.
286
309
  *
287
- * Sets up buffer source, buffer sink, and parses the filter description.
288
- * Configures the graph for processing.
310
+ * Schedules command to execute at specific timestamp.
311
+ * Useful for synchronized parameter changes.
289
312
  *
290
- * @internal
291
- */
292
- private initialize;
293
- /**
294
- * Create and configure the buffer source filter.
313
+ * Direct mapping to avfilter_graph_queue_command().
295
314
  *
296
- * @internal
297
- */
298
- private createBufferSource;
299
- /**
300
- * Create and configure the buffer sink filter.
315
+ * @param target - Target filter name
316
+ * @param cmd - Command name
317
+ * @param arg - Command argument
318
+ * @param ts - Timestamp for execution
319
+ * @param flags - Command flags
320
+ * @throws {Error} If filter not ready
321
+ * @throws {FFmpegError} If queue fails
301
322
  *
302
- * @internal
303
- */
304
- private createBufferSink;
305
- /**
306
- * Parse and connect the filter description.
323
+ * @example
324
+ * ```typescript
325
+ * // Queue volume change at 10 seconds
326
+ * filter.queueCommand('volume', 'volume', '0.8', 10.0);
327
+ * ```
307
328
  *
308
- * @internal
329
+ * @see {@link sendCommand} For immediate commands
309
330
  */
310
- private parseFilterDescription;
331
+ queueCommand(target: string, cmd: string, arg: string, ts: number, flags?: AVFilterCmdFlag): void;
311
332
  /**
312
- * Send a command to a filter in the graph.
313
- *
314
- * Allows runtime modification of filter parameters without recreating the graph.
315
- * Not all filters support commands - check filter documentation.
333
+ * Get filter graph description.
316
334
  *
317
- * @param target - Filter name or "all" to send to all filters
318
- * @param cmd - Command name (e.g., "volume", "hue", "brightness")
319
- * @param arg - Command argument value
320
- * @param flags - Optional command flags
335
+ * Returns human-readable graph structure.
336
+ * Useful for debugging filter chains.
321
337
  *
322
- * @returns Command response
338
+ * Direct mapping to avfilter_graph_dump().
323
339
  *
324
- * @example
325
- * ```typescript
326
- * // Change volume dynamically
327
- * const response = filter.sendCommand('volume', 'volume', '0.5');
328
- * if (response) {
329
- * console.log('Volume changed successfully');
330
- * }
331
- * ```
340
+ * @returns Graph description or null if not initialized
332
341
  *
333
342
  * @example
334
343
  * ```typescript
335
- * // Enable/disable all filters at runtime
336
- * filter.sendCommand('all', 'enable', 'expr=gte(t,10)');
344
+ * const description = filter.getGraphDescription();
345
+ * console.log('Filter graph:', description);
337
346
  * ```
338
347
  */
339
- sendCommand(target: string, cmd: string, arg: string, flags?: AVFilterCmdFlag): string;
348
+ getGraphDescription(): string | null;
340
349
  /**
341
- * Queue a command to be executed at a specific time.
350
+ * Check if filter is ready for processing.
342
351
  *
343
- * Commands are executed when processing frames with matching timestamps.
344
- * Useful for scripted filter changes synchronized with media playback.
345
- *
346
- * @param target - Filter name or "all" to send to all filters
347
- * @param cmd - Command name (e.g., "volume", "hue", "brightness")
348
- * @param arg - Command argument value
349
- * @param ts - Timestamp when command should execute (in seconds)
350
- * @param flags - Optional command flags
352
+ * @returns true if initialized and ready
351
353
  *
352
354
  * @example
353
355
  * ```typescript
354
- * // Schedule volume changes at specific times
355
- * filter.queueCommand('volume', 'volume', '0.5', 5.0); // At 5 seconds
356
- * filter.queueCommand('volume', 'volume', '0.8', 10.0); // At 10 seconds
357
- * filter.queueCommand('volume', 'volume', '0.2', 15.0); // At 15 seconds
356
+ * if (filter.isReady()) {
357
+ * const output = await filter.process(frame);
358
+ * }
358
359
  * ```
360
+ */
361
+ isReady(): boolean;
362
+ /**
363
+ * Get media type of filter.
364
+ *
365
+ * @returns AVMEDIA_TYPE_VIDEO or AVMEDIA_TYPE_AUDIO
359
366
  *
360
367
  * @example
361
368
  * ```typescript
362
- * // Fade effect at specific timestamp
363
- * filter.queueCommand('fade', 'alpha', '0.5', 30.0);
369
+ * if (filter.getMediaType() === AVMEDIA_TYPE_VIDEO) {
370
+ * console.log('Video filter');
371
+ * }
364
372
  * ```
365
373
  */
366
- queueCommand(target: string, cmd: string, arg: string, ts: number, flags?: AVFilterCmdFlag): void;
374
+ getMediaType(): AVMediaType;
367
375
  /**
368
- * Dispose of the filter.
376
+ * Free filter resources.
369
377
  *
370
- * Implements the Disposable interface for automatic cleanup.
371
- * Equivalent to calling free().
378
+ * Releases filter graph and contexts.
379
+ * Safe to call multiple times.
372
380
  *
373
381
  * @example
374
382
  * ```typescript
375
- * {
376
- * using filter = await Filter.create('scale=1280:720', config);
377
- * // ... use filter
378
- * } // Automatically freed when leaving scope
383
+ * filter.free();
379
384
  * ```
385
+ *
386
+ * @see {@link Symbol.dispose} For automatic cleanup
380
387
  */
381
- [Symbol.dispose](): void;
382
- }
383
- /**
384
- * Common filter presets for convenience.
385
- *
386
- * Provides pre-defined filter strings for common operations.
387
- * Can be used with Filter.create() for quick setup.
388
- *
389
- * @example
390
- * ```typescript
391
- * const filter = await Filter.create(
392
- * FilterPresets.scale(1280, 720),
393
- * config
394
- * );
395
- * ```
396
- */
397
- export declare class FilterPresets {
398
- /**
399
- * Scale video to specified dimensions.
400
- */
401
- static scale(width: number, height: number, flags?: string): string;
402
- /**
403
- * Crop video to specified dimensions.
404
- */
405
- static crop(width: number, height: number, x?: number, y?: number): string;
406
- /**
407
- * Change frame rate.
408
- */
409
- static fps(fps: number): string;
410
- /**
411
- * Convert pixel format.
412
- * Can accept either format name string or AVPixelFormat enum.
413
- */
414
- static format(pixelFormat: string | AVPixelFormat): string;
415
- /**
416
- * Rotate video by angle.
417
- */
418
- static rotate(angle: number): string;
419
- /**
420
- * Flip video horizontally.
421
- */
422
- static hflip(): string;
423
- /**
424
- * Flip video vertically.
425
- */
426
- static vflip(): string;
388
+ free(): void;
427
389
  /**
428
- * Apply fade effect.
390
+ * Initialize filter graph.
391
+ *
392
+ * Creates and configures filter graph components.
393
+ * For video, may use hardware frames context from first frame.
394
+ *
395
+ * @param firstFrame - First frame for hardware detection (video only)
396
+ * @throws {Error} If initialization fails
397
+ * @throws {FFmpegError} If configuration fails
429
398
  */
430
- static fade(type: 'in' | 'out', start: number, duration: number): string;
399
+ private initialize;
431
400
  /**
432
- * Overlay one video on another.
401
+ * Create buffer source with hardware frames context.
402
+ *
403
+ * @param frame - Frame with hw_frames_ctx
404
+ * @throws {Error} If creation fails
405
+ * @throws {FFmpegError} If configuration fails
433
406
  */
434
- static overlay(x?: number, y?: number): string;
407
+ private createBufferSourceWithHwFrames;
435
408
  /**
436
- * Adjust audio volume.
409
+ * Create standard buffer source.
410
+ *
411
+ * @throws {Error} If creation fails
437
412
  */
438
- static volume(factor: number): string;
413
+ private createBufferSource;
439
414
  /**
440
- * Convert audio sample format.
441
- * Can accept either format name string or AVSampleFormat enum.
415
+ * Create buffer sink.
416
+ *
417
+ * @throws {Error} If creation fails
442
418
  */
443
- static aformat(sampleFormat: string | AVSampleFormat, sampleRate?: number, channelLayout?: string): string;
419
+ private createBufferSink;
444
420
  /**
445
- * Change audio tempo without changing pitch.
421
+ * Parse filter description and build graph.
422
+ *
423
+ * @param description - Filter description string
424
+ * @throws {Error} If parsing fails
425
+ * @throws {FFmpegError} If graph construction fails
446
426
  */
447
- static atempo(factor: number): string;
427
+ private parseFilterDescription;
448
428
  /**
449
- * Apply audio fade.
429
+ * Check hardware requirements for filters.
430
+ *
431
+ * @param description - Filter description
432
+ * @param options - Filter options
433
+ * @throws {Error} If hardware requirements not met
450
434
  */
451
- static afade(type: 'in' | 'out', start: number, duration: number): string;
435
+ private checkHardwareRequirements;
452
436
  /**
453
- * Mix multiple audio streams.
437
+ * Dispose of filter.
438
+ *
439
+ * Implements Disposable interface for automatic cleanup.
440
+ * Equivalent to calling free().
441
+ *
442
+ * @example
443
+ * ```typescript
444
+ * {
445
+ * using filter = await FilterAPI.create('scale=640:480', info);
446
+ * // Use filter...
447
+ * } // Automatically freed
448
+ * ```
449
+ *
450
+ * @see {@link free} For manual cleanup
454
451
  */
455
- static amix(inputs?: number, duration?: 'first' | 'longest' | 'shortest'): string;
452
+ [Symbol.dispose](): void;
456
453
  }
457
- export {};