Вот мой код:
Код: Выделить всё
using Android.Media;
using Android.Util;
using Java.IO;
using Java.Nio;
using System;
using System.IO;
using static Android.Media.MediaCodec;
namespace Record.Droid
{
public class VideoRecorder
{
private const string TAG = "VideoRecorder";
private const string MIMETYPE = "video/avc";
private const int WAITTIME = 10000; // Adjust as needed
private MediaCodec codec;
private DataOutputStream dos;
public bool SetupEncoder(int width, int height, string outputPath)
{
try
{
try
{
FileStream fileStream = new FileStream(outputPath, FileMode.Create);
dos = new DataOutputStream(fileStream);
}
catch (System.IO.IOException e)
{
Log.Error(TAG, "Failed to open output file: " + e.Message);
return false;
}
MediaFormat mediaFormat = MediaFormat.CreateVideoFormat(MIMETYPE, width, height);
mediaFormat.SetInteger(MediaFormat.KeyBitRate, 700000);
mediaFormat.SetInteger(MediaFormat.KeyFrameRate, 30);
mediaFormat.SetInteger(MediaFormat.KeyColorFormat, (int)MediaCodecCapabilities.Formatyuv420planar);
mediaFormat.SetInteger(MediaFormat.KeyIFrameInterval, 5);
codec = MediaCodec.CreateEncoderByType(MIMETYPE);
codec.Configure(mediaFormat, null, null, MediaCodecConfigFlags.Encode);
codec.Start();
return true;
}
catch (System.IO.IOException e)
{
Log.Error(TAG, "Failed to set up encoder: " + e.Message);
ReleaseEncoder();
return false;
}
}
public void EncodeFrame(byte[] data, long presentationTimeUs)
{
try
{
ByteBuffer[] inputBuffers = codec.GetInputBuffers();
ByteBuffer[] outputBuffers = codec.GetOutputBuffers();
bool sawInputEOS = false;
int inputBufferIndex = -1, outputBufferIndex = -1;
BufferInfo info = new BufferInfo();
inputBufferIndex = codec.DequeueInputBuffer(WAITTIME);
if (inputBufferIndex >= 0)
{
ByteBuffer inputBuffer = inputBuffers[inputBufferIndex];
inputBuffer.Clear();
inputBuffer.Put(data);
codec.QueueInputBuffer(inputBufferIndex, 0, data.Length, presentationTimeUs, 0);
}
outputBufferIndex = codec.DequeueOutputBuffer(info, WAITTIME);
if (outputBufferIndex >= 0)
{
ByteBuffer outputBuffer = codec.GetOutputBuffer(outputBufferIndex).Duplicate();
outputBuffer.Position(info.Offset);
outputBuffer.Limit(info.Offset + info.Size);
byte[] array = new byte[info.Size];
outputBuffer.Get(array);
dos.Write(array);
codec.ReleaseOutputBuffer(outputBufferIndex, false);
if ((info.Flags & MediaCodecBufferFlags.EndOfStream) != 0)
{
ReleaseEncoder();
}
}
}
catch (System.IO.IOException e)
{
Log.Error(TAG, "Error encoding frame: " + e.Message);
}
}
public void ReleaseEncoder()
{
try
{
if (dos != null)
{
dos.Flush();
dos.Close();
}
}
catch (System.IO.IOException e)
{
Log.Error(TAG, "Failed to release encoder: " + e.Message);
}
if (codec != null)
{
codec.Stop();
codec.Release();
codec = null;
}
}
}
}
[img]https: //i.sstatic.net/Fypmn4qV.png[/img]
Шаги по воспроизведению:
Настройте кодировщик с помощью метода SetupEncoder с указанную ширину, высоту и путь вывода.
Передайте кадры в кодировщик с помощью метода EncodeFrame.
Просмотрите сохраненный видеофайл.
Вопросы:
Почему выходное видео разбито на плитки?
Какие изменения необходимы в моем коде, чтобы исправить эту проблему и создать нормальное видео?
Будем очень признательны за любую помощь или предложения. Спасибо!
Подробнее здесь: https://stackoverflow.com/questions/787 ... deo-output
Мобильная версия