使用android MediaCodec api压缩视频

使用android MediaCodec api压缩视频,android,compression,decode,encode,android-mediacodec,Android,Compression,Decode,Encode,Android Mediacodec,我想将本地保存的视频文件压缩为较小的大小,以便上传到服务器 自从我使用MediaCodec以来,我发现了一些压缩视频的技巧。以下是我遵循的步骤 1) 。使用MediaExrtactor提取媒体文件并对其进行解码。 2) . 使用所需的文件格式创建编码器 3) . 创建muxer以将文件保存在本地存储中。(不完整) 问题:但我不知道如何对已经解码的流进行编码,并使用MediaMuxer将流保存到本地存储中 public class CompressMedia { private stat

我想将本地保存的视频文件压缩为较小的大小,以便上传到服务器

自从我使用MediaCodec以来,我发现了一些压缩视频的技巧。以下是我遵循的步骤

1) 。使用MediaExrtactor提取媒体文件并对其进行解码。 2) . 使用所需的文件格式创建编码器 3) . 创建muxer以将文件保存在本地存储中。(不完整)

问题:但我不知道如何对已经解码的流进行编码,并使用MediaMuxer将流保存到本地存储中

public class CompressMedia {

    private static final String SAMPLE = Environment
            .getExternalStorageDirectory() + "/DCIM/Camera/20140506_174959.mp4";

    private static final String OUTPUT_PATH = Environment
            .getExternalStorageDirectory()
            + "/DCIM/Camera/20140506_174959_REC.mp4";

    private MediaExtractor extractor;
    private MediaCodec decoder;
    private MediaCodec encoder;
    String mime;

    private static final String MIME_TYPE = "video/avc";

    public void extractMediaFile() {

        // work plan
        // locate media file
        // extract media file using Media Extractor
        // retrieve decoded frames

        extractor = new MediaExtractor();
        try {
            extractor.setDataSource(SAMPLE);
        } catch (IOException e) {
            // TODO Auto-generated catch block
            // file not found
            e.printStackTrace();
        }

        // add decoded frames
        for (int i = 0; i < extractor.getTrackCount(); i++) {
            MediaFormat format = extractor.getTrackFormat(i);
            mime = format.getString(MediaFormat.KEY_MIME);
            if (mime.startsWith("video/")) {
                extractor.selectTrack(i);
                decoder = MediaCodec.createDecoderByType(mime);
                decoder.configure(format, null, null, 0);
                break;
            }
        }

        if (decoder == null) {
            Log.e("DecodeActivity", "Can't find video info!");
            return;
        }

        // - start decoder -
        decoder.start();
        extractor.selectTrack(0);

        // - decoded frames can obtain in here -

    }

    private void createsEncoder() {

        // creates media encoder to set formats
        encoder = MediaCodec.createDecoderByType(MIME_TYPE);

        // init media format
        MediaFormat mediaFormat = MediaFormat.createVideoFormat(MIME_TYPE, /* 640 */
                320, /* 480 */240);
        mediaFormat.setInteger(MediaFormat.KEY_BIT_RATE, 400000);
        mediaFormat.setInteger(MediaFormat.KEY_FRAME_RATE, 25);
        mediaFormat.setInteger(MediaFormat.KEY_COLOR_FORMAT,
                MediaCodecInfo.CodecCapabilities.COLOR_FormatYUV420SemiPlanar);
        mediaFormat.setInteger(MediaFormat.KEY_I_FRAME_INTERVAL, 5);
        encoder.configure(mediaFormat, null, null,
                MediaCodec.CONFIGURE_FLAG_ENCODE);
        encoder.start();

        // - encoded data format is avaiable in here

    }

    private void createMuxer() {

        // creates media muxer - media muxer will be used to write the final
        // strem in to a desired file :)

        try {
            MediaMuxer muxer = new MediaMuxer(OUTPUT_PATH,
                    OutputFormat.MUXER_OUTPUT_MPEG_4);

            int videoTrackIndex = muxer.addTrack(encoder.getOutputFormat());

            //muxer.writeSampleData(videoTrackIndex, inputBuffers, bufferInfo);
            muxer.start();

        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }

    }

}
公共类压缩媒体{
私有静态最终字符串SAMPLE=Environment
.getExternalStorageDirectory()+“/DCIM/Camera/20140506_174959.mp4”;
私有静态最终字符串输出\u路径=环境
.getExternalStorageDirectory()
+“/DCIM/Camera/20140506_174959_REC.mp4”;
专用媒体提取器;
专用媒体编解码器;
专用媒体编解码器;
字符串mime;
私有静态最终字符串MIME_TYPE=“video/avc”;
public-void-extractMediaFile(){
//工作计划
//找到媒体文件
//使用媒体提取器提取媒体文件
//检索解码帧
提取器=新的媒体提取器();
试一试{
提取器.setDataSource(示例);
}捕获(IOE异常){
//TODO自动生成的捕捉块
//找不到文件
e、 printStackTrace();
}
//添加解码帧
for(int i=0;i
以下是我遵循的链接 及

您可以尝试Intel INDE on和Media Pack for Android,这是INDE的一部分,是上的教程。它有一个示例,演示如何使用media pack对视频文件进行转码=重新压缩。您可以将较小的分辨率和\或比特率设置为输出,以获得较小的文件

在Composer TranscodeCoreActivity.java中

protected void setTranscodeParameters(MediaComposer mediaComposer) throws IOException {

    mediaComposer.addSourceFile(mediaUri1);
    mediaComposer.setTargetFile(dstMediaPath);

    configureVideoEncoder(mediaComposer, videoWidthOut, videoHeightOut);
    configureAudioEncoder(mediaComposer);
}

protected void transcode() throws Exception {

    factory = new AndroidMediaObjectFactory(getApplicationContext());
    mediaComposer = new MediaComposer(factory, progressListener);
    setTranscodeParameters(mediaComposer);
    mediaComposer.start();
}

嗨,G先生,我需要你的帮助。我想压缩视频。你能告诉我如何用MideaCodec压缩视频吗。或者显示一个压缩视频的示例?@NewDeveloper我使用intel transcode pack进行压缩,它从kit kat开始工作,还没有从mediacodec尝试过,我认为最简单的方法是使用ffmepg,你可以使用预编译的FFPEG libsThanks将ffmpeg支持发送到android studio以获得回复。。