技术问询:如何从图片列表制作视频?开发选3张图库图生成视频存SD卡的应用
Hey there! Let's split this into two clear sections: first, the core technical ways to turn a list of images into a video, then a step-by-step guide to build that specific app you're asking for.
FFmpeg (Cross-Platform Workhorse)
FFmpeg is the go-to tool for most multimedia tasks, including image-to-video conversion. It works by encoding a sequence of images into a video stream, supporting nearly all video formats. A basic command to create a video from sequentially named images (like image1.jpg, image2.jpg, image3.jpg) would look like this:
ffmpeg -framerate 1 -i image%d.jpg -c:v libx264 -r 30 -pix_fmt yuv420p output.mp4
Quick breakdown of key parameters:
-framerate 1: Displays 1 image per second (adjust this to control how long each image stays on screen)-i image%d.jpg: Specifies the input image sequence (the%dmatches sequential numbering)-c:v libx264: Uses the widely supported H.264 video codec-r 30: Sets the output video's frame rate to 30 FPS-pix_fmt yuv420p: Ensures compatibility with most media players
Native Platform APIs (For Mobile/Desktop Apps)
If you're building a native app (Android/iOS), using platform-specific APIs avoids relying on third-party libraries and offers better performance:
- Android: Use
MediaCodecfor video encoding andMediaMuxerto package encoded frames into a video file. This gives you full control over the process. - iOS: Use the
AVFoundationframework—specificallyAVAssetWriterandAVAssetWriterInputto write image frames into a video asset.
High-Level Frameworks (Rapid Prototyping)
For quick testing or non-performance-critical projects, high-level libraries simplify the process:
- Python/OpenCV: Use
cv2.VideoWriterto write images directly to a video file. Super easy for scripts, but not ideal for mobile apps. - JavaScript: Libraries like
ffmpeg.jslet you run FFmpeg in the browser for web-based image-to-video tools.
Since you mentioned saving to an SD card, I'll focus on Android here—this logic can be adapted for iOS with similar core steps.
1. Request Required Permissions
First, you need permissions to access the user's gallery and save files:
- For Android 13+: Add
READ_MEDIA_IMAGESto yourAndroidManifest.xmlfor gallery access. UseMediaStoreto save videos to public directories (no extra permission needed) or requestMANAGE_EXTERNAL_STORAGEfor direct SD card access. - For older Android versions: Add
READ_EXTERNAL_STORAGEandWRITE_EXTERNAL_STORAGEto the manifest, and request these permissions at runtime.
2. Let Users Select 3 Images
Use an Intent to open the system gallery with multi-selection enabled:
Intent intent = new Intent(Intent.ACTION_PICK, MediaStore.Images.Media.EXTERNAL_CONTENT_URI); intent.putExtra(Intent.EXTRA_ALLOW_MULTIPLE, true); intent.setType("image/*"); startActivityForResult(intent, REQUEST_CODE_PICK_IMAGES);
In your onActivityResult (or ActivityResultCallback for newer Android versions), collect the selected image URIs and convert them to Bitmap objects for processing.
3. Generate the Video from 3 Images
Use MediaCodec and MediaMuxer to encode the images into an MP4 video. Here's a simplified code snippet:
// Configure video settings using the first image's resolution int width = firstBitmap.getWidth(); int height = firstBitmap.getHeight(); String outputPath = getExternalStoragePublicDirectory(Environment.DIRECTORY_MOVIES) + "/3_image_video.mp4"; MediaMuxer muxer = new MediaMuxer(outputPath, MediaMuxer.OutputFormat.MUXER_OUTPUT_MPEG_4); MediaCodec codec = MediaCodec.createEncoderByType("video/avc"); // Set up video format parameters MediaFormat format = MediaFormat.createVideoFormat("video/avc", width, height); format.setInteger(MediaFormat.KEY_BIT_RATE, 1000000); format.setInteger(MediaFormat.KEY_FRAME_RATE, 1); // 1 image per second format.setInteger(MediaFormat.KEY_I_FRAME_INTERVAL, 3); format.setInteger(MediaFormat.KEY_COLOR_FORMAT, MediaCodecInfo.CodecCapabilities.COLOR_FormatYUV420Flexible); codec.configure(format, null, null, MediaCodec.CONFIGURE_FLAG_ENCODE); codec.start(); // Add each image as a video frame List<Bitmap> images = Arrays.asList(firstBitmap, secondBitmap, thirdBitmap); for (Bitmap bmp : images) { // Get input buffer from codec int inputBufferIndex = codec.dequeueInputBuffer(-1); ByteBuffer inputBuffer = codec.getInputBuffer(inputBufferIndex); // Convert Bitmap to YUV format (required by MediaCodec) fillInputBufferWithYUV(inputBuffer, bmp, width, height); // Queue the input buffer for encoding codec.queueInputBuffer(inputBufferIndex, 0, inputBuffer.limit(), System.nanoTime() / 1000, 0); // Write encoded output to muxer MediaCodec.BufferInfo bufferInfo = new MediaCodec.BufferInfo(); int outputBufferIndex = codec.dequeueOutputBuffer(bufferInfo, -1); while (outputBufferIndex >= 0) { ByteBuffer outputBuffer = codec.getOutputBuffer(outputBufferIndex); muxer.writeSampleData(videoTrackIndex, outputBuffer, bufferInfo); codec.releaseOutputBuffer(outputBufferIndex, false); outputBufferIndex = codec.dequeueOutputBuffer(bufferInfo, -1); } } // Clean up resources codec.stop(); codec.release(); muxer.stop(); muxer.release();
Note: You'll need to implement fillInputBufferWithYUV to convert Bitmap to YUV format—standard utility functions for this are widely available, or you can use Android's YuvImage class.
4. Save the Video to SD Card
To save directly to an SD card (not internal storage), use Context.getExternalFilesDirs() (Android 5+) to access the SD card's root path. Always check if the SD card is mounted and writable before saving.
Key Tips
- Image Resolution: Resize all 3 images to the same resolution before encoding to avoid video artifacts.
- Frame Duration: Adjust the
KEY_FRAME_RATEvalue to control how long each image stays on screen (e.g., 0.5 FPS means each image shows for 2 seconds). - Error Handling: Add try-catch blocks for file operations, codec errors, and permission checks to make the app robust.
内容的提问来源于stack exchange,提问作者Mehedi Hasan

