Search in sources :

Example 16 with BufferInfo

use of android.media.MediaCodec.BufferInfo in project android_packages_apps_Gallery2 by LineageOS.

the class VideoUtils method genVideoUsingMuxer.

/**
 * @param srcPath the path of source video file.
 * @param dstPath the path of destination video file.
 * @param startMs starting time in milliseconds for trimming. Set to
 *            negative if starting from beginning.
 * @param endMs end time for trimming in milliseconds. Set to negative if
 *            no trimming at the end.
 * @param useAudio true if keep the audio track from the source.
 * @param useVideo true if keep the video track from the source.
 * @throws IOException
 */
private static void genVideoUsingMuxer(String srcPath, String dstPath, int startMs, int endMs, boolean useAudio, boolean useVideo) throws IOException {
    // Set up MediaExtractor to read from the source.
    MediaExtractor extractor = new MediaExtractor();
    extractor.setDataSource(srcPath);
    int trackCount = extractor.getTrackCount();
    // Set up MediaMuxer for the destination.
    MediaMuxer muxer;
    muxer = new MediaMuxer(dstPath, MediaMuxer.OutputFormat.MUXER_OUTPUT_MPEG_4);
    // Set up the tracks and retrieve the max buffer size for selected
    // tracks.
    HashMap<Integer, Integer> indexMap = new HashMap<Integer, Integer>(trackCount);
    int bufferSize = -1;
    for (int i = 0; i < trackCount; i++) {
        MediaFormat format = extractor.getTrackFormat(i);
        String mime = format.getString(MediaFormat.KEY_MIME);
        boolean selectCurrentTrack = false;
        if (mime.startsWith("audio/") && useAudio) {
            selectCurrentTrack = true;
        } else if (mime.startsWith("video/") && useVideo) {
            selectCurrentTrack = true;
        }
        if (selectCurrentTrack) {
            extractor.selectTrack(i);
            try {
                int dstIndex = muxer.addTrack(format);
                indexMap.put(i, dstIndex);
                if (format.containsKey(MediaFormat.KEY_MAX_INPUT_SIZE)) {
                    int newSize = format.getInteger(MediaFormat.KEY_MAX_INPUT_SIZE);
                    bufferSize = newSize > bufferSize ? newSize : bufferSize;
                }
            } catch (IllegalArgumentException e) {
                Log.e(LOGTAG, "Unsupported format '" + mime + "'");
                throw new IOException("Muxer does not support " + mime);
            }
        }
    }
    if (bufferSize < 0) {
        bufferSize = DEFAULT_BUFFER_SIZE;
    }
    // Set up the orientation and starting time for extractor.
    MediaMetadataRetriever retrieverSrc = new MediaMetadataRetriever();
    retrieverSrc.setDataSource(srcPath);
    String degreesString = retrieverSrc.extractMetadata(MediaMetadataRetriever.METADATA_KEY_VIDEO_ROTATION);
    if (degreesString != null) {
        int degrees = Integer.parseInt(degreesString);
        if (degrees >= 0) {
            muxer.setOrientationHint(degrees);
        }
    }
    if (startMs > 0) {
        extractor.seekTo(startMs * 1000, MediaExtractor.SEEK_TO_CLOSEST_SYNC);
    }
    // Copy the samples from MediaExtractor to MediaMuxer. We will loop
    // for copying each sample and stop when we get to the end of the source
    // file or exceed the end time of the trimming.
    int offset = 0;
    int trackIndex = -1;
    ByteBuffer dstBuf = ByteBuffer.allocate(bufferSize);
    BufferInfo bufferInfo = new BufferInfo();
    try {
        muxer.start();
        while (true) {
            bufferInfo.offset = offset;
            bufferInfo.size = extractor.readSampleData(dstBuf, offset);
            if (bufferInfo.size < 0) {
                Log.d(LOGTAG, "Saw input EOS.");
                bufferInfo.size = 0;
                break;
            } else {
                bufferInfo.presentationTimeUs = extractor.getSampleTime();
                if (endMs > 0 && bufferInfo.presentationTimeUs > (endMs * 1000)) {
                    Log.d(LOGTAG, "The current sample is over the trim end time.");
                    break;
                } else {
                    bufferInfo.flags = extractor.getSampleFlags();
                    trackIndex = extractor.getSampleTrackIndex();
                    muxer.writeSampleData(indexMap.get(trackIndex), dstBuf, bufferInfo);
                    extractor.advance();
                }
            }
        }
        muxer.stop();
    } catch (IllegalStateException e) {
        // Swallow the exception due to malformed source.
        Log.w(LOGTAG, "The source video file is malformed");
        File f = new File(dstPath);
        if (f.exists()) {
            f.delete();
        }
        throw e;
    } finally {
        muxer.release();
    }
    return;
}
Also used : MediaFormat(android.media.MediaFormat) BufferInfo(android.media.MediaCodec.BufferInfo) HashMap(java.util.HashMap) IOException(java.io.IOException) MediaExtractor(android.media.MediaExtractor) MediaMuxer(android.media.MediaMuxer) ByteBuffer(java.nio.ByteBuffer) MediaMetadataRetriever(android.media.MediaMetadataRetriever) RandomAccessFile(java.io.RandomAccessFile) IsoFile(com.coremedia.iso.IsoFile) File(java.io.File)

Example 17 with BufferInfo

use of android.media.MediaCodec.BufferInfo in project AndroidRoad by yeungeek.

the class VideoDeviceOutputImpl method decodeConsumeOutput.

private boolean decodeConsumeOutput() {
    if (!isDecodeInit) {
        return false;
    }
    BufferInfo decodeBufferInfo = new BufferInfo();
    int decodeOutputBufferIndex = decodeRecvOutputBuffer(decodeBufferInfo);
    if (decodeOutputBufferIndex < 0) {
        return false;
    }
    if (mVideoDeviceCb != null) {
        mVideoDeviceCb.onFrameOut(decodeBufferInfo.presentationTimeUs, 0);
    }
    /*DecodeTag tag = decodeRemoveTag(decodeBufferInfo.presentationTimeUs);
        if (tag != null) {
          if (PROFILE_VIDEO) {
              Log.i("VideoProfile", "Frame decoded, timestamp = " + tag.timeFrame
                + ", system time = " + tag.timeOut
                + ", decode duration = " + (tag.timeOut - tag.timeIn));
          }
        }*/
    decodeDisplayOutput(decodeOutputBufferIndex);
    if (mVideoDeviceCb != null) {
        mVideoDeviceCb.onFrameConsumed(decodeBufferInfo.presentationTimeUs);
    }
    return true;
}
Also used : BufferInfo(android.media.MediaCodec.BufferInfo)

Example 18 with BufferInfo

use of android.media.MediaCodec.BufferInfo in project robolectric by robolectric.

the class ShadowMediaCodec method __constructor__.

// Member methods.
@Implementation
protected void __constructor__(String name, boolean nameIsType, boolean encoder) {
    invokeConstructor(MediaCodec.class, realCodec, ClassParameter.from(String.class, name), ClassParameter.from(boolean.class, nameIsType), ClassParameter.from(boolean.class, encoder));
    CodecConfig codecConfig = encoder ? encoders.getOrDefault(name, DEFAULT_CODEC) : decoders.getOrDefault(name, DEFAULT_CODEC);
    fakeCodec = codecConfig.codec;
    for (int i = 0; i < BUFFER_COUNT; i++) {
        inputBuffers[i] = ByteBuffer.allocateDirect(codecConfig.inputBufferSize).order(ByteOrder.LITTLE_ENDIAN);
        outputBuffers[i] = ByteBuffer.allocateDirect(codecConfig.outputBufferSize).order(ByteOrder.LITTLE_ENDIAN);
        outputBufferInfos[i] = new BufferInfo();
    }
}
Also used : BufferInfo(android.media.MediaCodec.BufferInfo) Implementation(org.robolectric.annotation.Implementation)

Example 19 with BufferInfo

use of android.media.MediaCodec.BufferInfo in project robolectric by robolectric.

the class ShadowMediaCodecTest method passesEndOfStreamFlagWithFinalOutputBuffer.

@Test
public void passesEndOfStreamFlagWithFinalOutputBuffer() throws IOException {
    MediaCodec codec = createAsyncEncoder();
    ArgumentCaptor<Integer> indexCaptor = ArgumentCaptor.forClass(Integer.class);
    verify(callback).onInputBufferAvailable(same(codec), indexCaptor.capture());
    ByteBuffer buffer = codec.getInputBuffer(indexCaptor.getValue());
    int start = buffer.position();
    // "Write" to the buffer.
    buffer.position(buffer.limit());
    codec.queueInputBuffer(indexCaptor.getValue(), /* offset= */
    start, /* size= */
    buffer.position() - start, /* presentationTimeUs= */
    0, /* flags= */
    MediaCodec.BUFFER_FLAG_END_OF_STREAM);
    ArgumentCaptor<BufferInfo> infoCaptor = ArgumentCaptor.forClass(BufferInfo.class);
    asyncVerify(callback).onOutputBufferAvailable(same(codec), indexCaptor.capture(), infoCaptor.capture());
    assertThat(infoCaptor.getValue().flags & MediaCodec.BUFFER_FLAG_END_OF_STREAM).isNotEqualTo(0);
}
Also used : BufferInfo(android.media.MediaCodec.BufferInfo) MediaCodec(android.media.MediaCodec) ByteBuffer(java.nio.ByteBuffer) Test(org.junit.Test)

Example 20 with BufferInfo

use of android.media.MediaCodec.BufferInfo in project robolectric by robolectric.

the class ShadowMediaCodecTest method dequeueOutputBuffer_inASyncMode_throws.

@Test
public void dequeueOutputBuffer_inASyncMode_throws() throws IOException {
    MediaCodec codec = createAsyncEncoder();
    try {
        codec.dequeueOutputBuffer(new BufferInfo(), /* timeoutUs= */
        0);
        fail();
    } catch (IllegalStateException expected) {
    }
}
Also used : BufferInfo(android.media.MediaCodec.BufferInfo) MediaCodec(android.media.MediaCodec) Test(org.junit.Test)

Aggregations

BufferInfo (android.media.MediaCodec.BufferInfo)27 ByteBuffer (java.nio.ByteBuffer)10 MediaCodec (android.media.MediaCodec)8 MediaFormat (android.media.MediaFormat)8 Test (org.junit.Test)7 IOException (java.io.IOException)6 SuppressLint (android.annotation.SuppressLint)5 Rect (android.graphics.Rect)4 Surface (android.view.Surface)4 MediaExtractor (android.media.MediaExtractor)2 Implementation (org.robolectric.annotation.Implementation)2 MediaMetadataRetriever (android.media.MediaMetadataRetriever)1 MediaMuxer (android.media.MediaMuxer)1 ParcelFileDescriptor (android.os.ParcelFileDescriptor)1 IsoFile (com.coremedia.iso.IsoFile)1 File (java.io.File)1 RandomAccessFile (java.io.RandomAccessFile)1 Buffer (java.nio.Buffer)1 HashMap (java.util.HashMap)1 CalledByNative (org.chromium.base.CalledByNative)1