Установка отдельных пикселей кадра RGB для кодирования ffmpeg

Я пытаюсь изменить тестовый шаблон стримера ffmpeg, Проблемы с синхронизацией libavformat / ffmpeg с x264 и RTP , в знакомый формат RGB. Моя более широкая цель — вычислять кадры потокового видео на лету.

Поэтому я заменил его AV_PIX_FMT_MONOWHITE с AV_PIX_FMT_RGB24«RGB 8: 8: 8, 24bpp, RGBRGB …» в соответствии с http://libav.org/doxygen/master/pixfmt_8h.html .

Заполнить его массив пикселей под названием dataЯ перепробовал много вариантов

for (int y=0; y<HEIGHT; ++y) {
for (int x=0; x<WIDTH; ++x) {
uint8_t* rgb = data + ((y*WIDTH + x) *3);
const double i = x/double(WIDTH);
//  const double j = y/double(HEIGHT);
rgb[0] = 255*i;
rgb[1] = 0;
rgb[2] = 255*(1-i);
}
}

В HEIGHTИксWIDTH= 80×60, эта версия дает
скриншот красно-синих полос, когда я ожидаю один сине-красный горизонтальный градиент.

640×480 дает тот же шаблон с 4 столбцами, но с гораздо большим количеством горизонтальных полос.

640×640, 160×160 и т. Д., Выход три столбцы, цианистый / пурпурный / желтоватый, с таким же типом горизонтальной полосатости.

Вертикальные градиенты ведут себя еще более странно.

Внешний вид не был затронут AV_PIX_FMT_RGBA попытка (4 не 3 байта на пиксель, альфа = 255). Также не зависит от порта от C до C ++.

Аргумент srcStrides перешел к sws_scale() массив длины 1, содержащий один int HEIGHT,

Доступ к каждому пикселю AVFrame задает тот же вопрос менее подробно, пока без ответа.

Стример издает одно предупреждение, которое, я сомневаюсь, влияет на внешний вид:

[rtp @ 0x269c0a0] Encoder did not produce proper pts, making some up.

Так. Как установить значение RGB пикселя в кадре для отправки в sws_scale () (а затем в x264_encoder_encode () и av_interleaved_write_frame ())?

0

Решение

использование avpicture_fill() как описано в Кодирование скриншота в видео с использованием FFMPEG .

Вместо прохождения data прямо к sws_scale(), сделай это:

AVFrame* pic = avcodec_alloc_frame();
avpicture_fill((AVPicture *)pic, data, AV_PIX_FMT_RGB24, WIDTH, HEIGHT);

а затем заменить 2-й и 3-й аргументы sws_scale() с

pic->data, pic->linesize,

Тогда указанные выше градиенты работают правильно при многих разрешениях.

2

Другие решения

Аргумент srcStrides, переданный в sws_scale (), является массивом длины 1, содержащим один int HEIGHT.

Страйд (АКА linesize) — расстояние в байтах между двумя строками. По разным причинам, связанным главным образом с оптимизацией, она часто больше, чем просто ширина в байтах, поэтому в конце каждой строки есть отступы.

В вашем случае, без каких-либо отступов, шаг должен быть шириной * 3.

1

По вопросам рекламы [email protected]