Как преобразовать сырой файл h.264 в mp4 - PullRequest
0 голосов
/ 22 февраля 2019

Я видел, как конвертировать видео в mp4 с помощью MediaCodec.В этих примерах использовался Surface.

Тогда я думаю, что h.264 => decode => Surface => encode (file), это ненужный процесс кодирования / декодирования.

Возможно ли этосделать необработанные файлы формата h.264 mp4 без кодирования / декодирования с помощью Android MediaCodec / MediaMuxer?

Обновление

Я реализовал ссылку для обновления кода (https://developer.android.com/reference/android/media/MediaMuxer)комментария.

        while(!finished) {
            // getInputBuffer() will fill the inputBuffer with one frame of encoded
            // sample from either MediaCodec or MediaExtractor, set isAudioSample to
            // true when the sample is audio data, set up all the fields of bufferInfo,
            // and return true if there are no more samples.
            byte[] tempBuffer = new byte[1000000];
            try {
                inputBuffer.clear();
                int bytesRead = videoFis.read(tempBuffer, 0, inputBuffer.limit());
                if(bytesRead <= -1) {
                    break;
                }
                else {
                    inputBuffer.put(tempBuffer, 0, bytesRead);
                    int currentTrackIndex = videoTrackIndex; // isAudioSample ? audioTrackIndex : videoTrackIndex;
                    muxer.writeSampleData(currentTrackIndex, inputBuffer, bufferInfo);

                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }

приведенный выше код не работает. Я не получаю закодированный один кадр.

// getInputBuffer() will fill the inputBuffer with one frame of encoded
// sample from either MediaCodec or MediaExtractor

Для получения закодированного одного кадра из необработанного h.264, я должениспользовать MediaCodec?

Update2

                bb.mark();
        // read all
        while(true) {
            try {
                int bb2 = videoFis.read(tempBuffer, 0, tempBuffer.length);
                if(bb2 != -1) {
                    bb.put(tempBuffer, 0, bb2);
                }
                else {
                    break;
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        bb.reset();

        int mata[][] = new int[5][256];
        mata[0][0] = 1;
        mata[1][0] = 2;
        mata[2][0] = 3;
        mata[3][1] = 4;
        int step = 0;
        // find first key frame.
        while(bb.hasRemaining()) {
            step = mata[step][(bb.get() & 0xFF)];
            if(step < 4) {
                step = mata[step][(bb.get() & 0xFF)];
            }
            else if(step == 4) {
                byte g = bb.get();
                if((g & 0x1f) == 5) {
                    bb.position(bb.position() - 5);
                    break;
                }
            }
        }
        step = 0;
        while(!finished) {
            int nextPosition = -1;
            int offset = bb.position();
            bb.get(); bb.get(); bb.get(); bb.get();
            byte nalUnit = bb.get();
            while(bb.hasRemaining()) {
                if(step < 4) {
                    step = mata[step][(bb.get() & 0xFF)];
                }
                else if(step == 4) {
                    byte g = bb.get();
                    if((g & 0x60) != 0) {
                        nextPosition = bb.position() - 5;
                        break;
                    }
                }
            }
            step = 0;
            bufferInfo.flags = (nalUnit & 0x1f) == 5 ? MediaCodec.BUFFER_FLAG_KEY_FRAME : 0;
            bufferInfo.offset = offset;
            bufferInfo.size = nextPosition - offset;
            bufferInfo.presentationTimeUs += 1000 * 1000 / 15;
            Log.d(",,", "offset: " + bufferInfo.offset + "..." + "size: " + bufferInfo.size + "..." + "pts: " + bufferInfo.presentationTimeUs);
            muxer.writeSampleData(videoTrackIndex, inputBuffer, bufferInfo);
            bb.position(nextPosition);
            if(bufferInfo.presentationTimeUs >= 666660)
            {
                bufferInfo.size = 0;
                break;
            }
        }
        muxer.stop();
        muxer.release();

Как и в приведенной выше реализации, я нахожу 0x00 0x00 0x00 0x01 с именем NAL, я заполнил bufferInfo со смещением, размером, pts. Но яполучил сообщения

...
02-23 17:59:25.131 7597-7738/com.example.ksoo.ballbotpkg I/MPEG4Writer: setStartTimestampUs: 66666
    Earliest track starting time: 66666
02-23 17:59:25.131 7597-7597/com.example.ksoo.ballbotpkg D/,,: offset: 284939...size: 10531...pts: 133332
02-23 17:59:25.132 7597-7597/com.example.ksoo.ballbotpkg D/,,: offset: 295470...size: 15908...pts: 199998
    offset: 311378...size: 20194...pts: 266664
02-23 17:59:25.133 7597-7597/com.example.ksoo.ballbotpkg D/,,: offset: 331572...size: 20628...pts: 333330
    offset: 352200...size: 21346...pts: 399996
02-23 17:59:25.134 7597-7597/com.example.ksoo.ballbotpkg D/,,: offset: 373546...size: 21407...pts: 466662
02-23 17:59:25.134 7597-7597/com.example.ksoo.ballbotpkg D/,,: offset: 394953...size: 22494...pts: 533328
02-23 17:59:25.135 7597-7597/com.example.ksoo.ballbotpkg D/,,: offset: 417447...size: 23230...pts: 599994
02-23 17:59:25.135 7597-7597/com.example.ksoo.ballbotpkg D/,,: offset: 440677...size: 23820...pts: 666660
02-23 17:59:25.136 7597-7597/com.example.ksoo.ballbotpkg I/MPEG4Writer: Normal stop process
02-23 17:59:25.136 7597-7597/com.example.ksoo.ballbotpkg D/MPEG4Writer: Video track stopping. Stop source
    Video track source stopping
    Video track source stopped
02-23 17:59:25.136 7597-7738/com.example.ksoo.ballbotpkg I/MPEG4Writer: Received total/0-length (10/0) buffers and encoded 10 frames. - Video
02-23 17:59:25.136 7597-7597/com.example.ksoo.ballbotpkg D/MPEG4Writer: Video track stopped. Stop source
    Stopping writer thread
02-23 17:59:25.137 7597-7737/com.example.ksoo.ballbotpkg D/MPEG4Writer: 0 chunks are written in the last batch
02-23 17:59:25.137 7597-7597/com.example.ksoo.ballbotpkg D/MPEG4Writer: Writer thread stopped
02-23 17:59:25.138 7597-7597/com.example.ksoo.ballbotpkg I/MPEG4Writer: The mp4 file will not be streamable.
02-23 17:59:25.138 7597-7597/com.example.ksoo.ballbotpkg D/MPEG4Writer: Video track stopping. Stop source

Я сделал ошибку?

...