Форум программистов, компьютерный форум, киберфорум
C (Си)
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.83/6: Рейтинг темы: голосов - 6, средняя оценка - 4.83
 Аватар для Dizark
25 / 25 / 16
Регистрация: 12.04.2013
Сообщений: 85

Перекодирование видео

29.05.2023, 15:43. Показов 1255. Ответов 3
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Есть задача - получать данные с IP камеры и отправлять видео в виде отдельных кадров как JPG картинки.

для этих целей использую libAV


В цикле я
1. Считываю кадр из потока в пакет (av_read_frame)
2. Проверяю, тот ли номер стрима, который я открывал
3. Отправляю пакет в декодер (avcodec_send_packet)
4. Дальше в цикле считываю кадры из декодера (avcodec_receive_frame)
5. Полученный кадр отправляю к кодер MJPEG (avcodec_send_frame)
6. Принимаю пакет из кодера, и уже данные из packet->data отправляю потребителю.

В целом все работает, но есть два Но.

1. Картинку мне нужно уменьшить
2. Постоянно теряется опорный кадр и в программе получателе (при движении камеры) в основном не видео, а ... разностная картинка)

Может кто подсказать, в какую сторону лучше думать?
0
IT_Exp
Эксперт
34794 / 4073 / 2104
Регистрация: 17.06.2006
Сообщений: 32,602
Блог
29.05.2023, 15:43
Ответы с готовыми решениями:

Перекодирование из с -> с++
Здравствуйте , нужна помощь , у меня есть блок программы написанный на языке си , а я изучаю с++, так вот мне нужно перекомпилировать с си...

Перекодирование информации
Нужно создать программу на QT, где будет перекодировка информации из 8 бит в формат 7 бит для использования в определенных каналах связи....

Перекодирование файла
Всем привет! Файл csv может иметь различную кодировку. Обычно она UTF-16 LE. Нужно для Qt преобразовать её в UTF-8. Как это сделать? В...

3
35 / 24 / 11
Регистрация: 18.02.2021
Сообщений: 100
29.05.2023, 17:59
Я этим не занимался и с libAV не знаком
Цитата Сообщение от Dizark Посмотреть сообщение
1. Картинку мне нужно уменьшить
После получения кадра и его отправки в кодер MJPEG avcodec_send_frame() можно ли задать параметры кодирования (такие как например разрешение, степень сжатия и прочие)? Если да, то скорее всего можно при вызове функции дать параметры для уменьшения разрешения кадра.
Цитата Сообщение от Dizark Посмотреть сообщение
2. Постоянно теряется опорный кадр и в программе получателе (при движении камеры) в основном не видео, а ... разностная картинка)
Что такое опорный кадр?
0
 Аватар для Dizark
25 / 25 / 16
Регистрация: 12.04.2013
Сообщений: 85
29.05.2023, 23:33  [ТС]
с кадрами вроде разобрался, остался вопрос с размером изображения

с камеры идет размер 1920х1080. Мне надо это ужать в 640х360

Если я просто присваиваю для выходного context объекта параметры width и height -- то делается просто кроп с исходного изображения.

Пробую делать через swscale:
C
1
2
3
4
5
6
            struct SwsContext *resize;
            resize = sws_getContext(pCodecContext->width, pCodecContext->height, AV_PIX_FMT_YUV420P,
                                    jpegContext->width, jpegContext->height, AV_PIX_FMT_RGB24, SWS_BICUBIC, NULL, NULL, NULL);
 
            AVFrame* frame2 = av_frame_alloc();
            sws_scale(resize, pFrame->data, pFrame->linesize, 0, pCodecContext->height, frame2->data, frame2->linesize);
то при попытке отправить этот frame2 в кодер mjpeg выводится следующее:

[swscaler @ 0x5583036530] bad dst image pointers
[mjpeg @ 0x55826e53f0] AVFrame.format is not set
[mjpeg @ 0x55826e53f0] AVFrame.width or height is not set

ну и программа отваливается
0
 Аватар для Наталья8
617 / 375 / 67
Регистрация: 09.03.2016
Сообщений: 4,048
01.06.2023, 01:54
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
 
 
// Это структура. Указатель на неё бросаеться из функции в функцию....
// ========= Для аудио и видео отдельно
typedef struct In_Out_Struct {
    int64_t next_pts;//< ---- Видеокадры перещёлкивать (rescale_video_frame)
               int64_t aud_smp_count;// < ---- Для звука (load_encode_and_write)
            int width, height;
              double Fr_ps;
         AVStream *stream;
    struct SwsContext *sws_ctx;// <=== Видео
    /* Контекст libswresample. В отличие от libavcodec и libavformat, эта структура непрозрачная*/
    struct SwrContext *swr_ctx;// <===  Аудио ресамплер
AVCodecContext *dec_ctx = NULL;// input  Context
AVCodecContext *enc_ctx = NULL;// output  Context;
} In_Out_Struct;
// =========================== Структура прямо под инкладами нарисована
 
 
 
 
// Здесь на входе, фрейм уже раскодированный
// А это часть функции... Вызываеться для каждого кадра
 
if (!ost->sws_ctx) {
                 /* Выделите и верните SwsContext.Это нужно для выполнения (  == Выполняеться один раз == )
                 операции масштабирования/преобразования с использованием sws_scale(). // AV_PIX_FMT_YUV420P --- > pix_fmt */
                 //---------------------------  Исходный размер    исходный         Размер target      target
                 ost->sws_ctx = sws_getContext(ost->dec_ctx->width,
        ost->dec_ctx->height, ost->dec_ctx->pix_fmt, c->width, c->height, c->pix_fmt, SWS_FAST_BILINEAR, NULL, NULL, NULL);
                 //---------------------------------------------------------------------------  
        if (!ost->sws_ctx) { printf(" (decode_video_packet) Could not initialize the conversion context\n"); return; }
             }
           else { // Создать  фрейм выделить под него память преобразовать в него картинку вызывать запись и освободить память
                AVFrame *frame;
                 frame = av_frame_alloc();
                 frame->format = c->pix_fmt;
                 frame->width = c->width;
                 frame->height = c->height;
                 /* allocate the buffers for the frame data */
                 ret = av_frame_get_buffer(frame, 32);
                 if (ret < 0) {
                     fprintf(stderr, " (decode_video_packet) Could not allocate frame data.\n"); return;
                 }
            sws_scale(ost->sws_ctx, _frame->data, _frame->linesize,// исходное
                     0, ost->dec_ctx->height, frame->data, frame->linesize); // ПРЕОБР. КАРТИНКИ  целевое
             //------------------------------- void open_video ( там выделение фрейма ost->frame... задан размер)
             /* encode the image */
            if (ext)frame->pts = fgh;
            else frame->pts = ost->next_pts++;
            if (one)
                 encode_write_frame(frame, ost, ext);
             av_frame_free(&frame);
             one = true;
         }
Добавлено через 6 минут
Это циклично всё видео преобразовывает размер кадров....
А вообще в вашем случае учить материал надо. Лазить по гитхабу, читать исходники.
ffmpeg - это чё libAV?

Добавлено через 22 минуты
Раскодировал пакет. Взял фрейм. Преобразовал в нём размер кадра.
И кодируй его куда надо....

Добавлено через 10 минут
ost - переменная структуры (для понятия)

Добавлено через 1 час 30 минут
=========== На всякий случай из личных запасов

C++
1
2
3
4
5
6
7
8
9
10
// -------------------------------        Исходный размер кадра
    img_convert_ctx = sws_getContext(m_Video_CodecCtx->width, m_Video_CodecCtx->height, m_Video_CodecCtx->pix_fmt,
                                                   m_Video_CodecCtx->width / size_divider
                                                , m_Video_CodecCtx->height / size_divider
                                                            // < ---- (целевой размер... делю на два)
                                                     ,AV_PIX_FMT_RGBA, SWS_FAST_BILINEAR
                                                     ,NULL, NULL, NULL);
                                                m_Texture.create(GetWidth() / size_divider
                                                               ,GetHeight() / size_divider
                                                );// ===== Делю на два (создание текстуры sfml)==========
======================================== =================

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
AVPacket m_Packet;
         do {// Считать именно видеокадр
                init_packet(&m_Packet);// Вызов функции инициализировать пакет
    if (av_read_frame(m_pFormatCtx, &m_Packet) < 0){ av_free_packet(&m_Packet); return 0; }// return ???
            } while (m_Packet.stream_index != m_iVideoSt_indx);
            frameFinished = 0;
            avcodec_decode_video2(m_Video_CodecCtx, m_pFrame, &frameFinished, &m_Packet);
            if (frameFinished) {
sws_scale(img_convert_ctx, m_pFrame->data, m_pFrame->linesize,
                    0, m_Video_CodecCtx->height, m_pFrameRGB->data, m_pFrameRGB->linesize);
            
m_Texture.update(m_pBuffer);// ЗДЕСЬ ДЕЛАЕТ УПДАТЕ
 
if (size_divider == 1){// Выбросить файл - картинку
        
    string temp_patch(m_sFilename);
temp_patch = temp_patch.substr(0, temp_patch.rfind('.') + 1);// <<===== отрезать расширение
 
temp_patch += "png";// Привинтить .png
        // бросить картинку в рабочий фолдер
    m_Texture.copyToImage().saveToFile(temp_patch);
    Beep(4000,5);
       }
Добавлено через 10 минут
Только боюсь, вас метода не устроит...
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
BasicMan
Эксперт
29316 / 5623 / 2384
Регистрация: 17.02.2009
Сообщений: 30,364
Блог
01.06.2023, 01:54
Помогаю со студенческими работами здесь

Перекодирование аудио ffmpeg
Здравствуйте! Подскажите пожалуйста кто-нибудь, как можно перекодировать аудио из 711 кодека (файл .PCMA) в 722 кодек (файл .G722) с...

Обработка видео с камеры видео наблюдения (для экспертов)
Обработка видео с камеры видео наблюдения (для экспертов) Имеются несколько каналов видео с камер видео наблюдения и за полследние время...

<vfw.h> winApi. несколько лет пытаюсь микшировать PCM звук в AVI видео. Микшируеться 1час 16 минут. и видео портиться
// Открываю --- продолжительность видео определяет правильно. HRESULT hr; PAVISTREAM pavi;// Дескриптор для открытия потока ...

Qt creator, работа с видео, видео кодеки
Прив. Вы шел из ридонли потому что не знаю как решить проблему в общем: как в qt происходит работа с кодеками и потоковым видео? и...

Перекодирование строк
получаю от сервера строку в utf-8 header('Content-type: text/html; charset=utf-8'); $str = '&lt;?xml version=&quot;1.0&quot;...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
4
Ответ Создать тему
Новые блоги и статьи
Программный отбор значения справочника
Maks 21.03.2026
Процедура ВодителиНачалоВыбора(Элемент, ДанныеВыбора, ВыборДобавлением, СтандартнаяОбработка) / / Отключаем стандартную обработку (стандартное открытие формы выбора без фильтров) . . .
Переходник USB-CAN-GPIO
Eddy_Em 20.03.2026
Достаточно давно на работе возникла необходимость в переходнике CAN-USB с гальваноразвязкой, оный и был разработан. Однако, все меня терзала совесть, что аж 48-ногий МК используется так тупо: просто. . .
Оттенки серого
Argus19 18.03.2026
Оттенки серого Нашёл в интернете 3 прекрасных модуля: Модуль класса открытия диалога открытия/ сохранения файла на Win32 API; Модуль класса быстрого перекодирования цветного изображения в оттенки. . .
SDL3 для Desktop (MinGW): Рисуем цветные прямоугольники с помощью рисовальщика SDL3 на Си и C++
8Observer8 17.03.2026
Содержание блога Финальные проекты на Си и на C++: finish-rectangles-sdl3-c. zip finish-rectangles-sdl3-cpp. zip
Символические и жёсткие ссылки в Linux.
algri14 15.03.2026
Существует два типа ссылок — символические и жёсткие. Ссылка в Linux — это запись в каталоге, которая может указывать либо на inode «файла-ИСТОЧНИКА», тогда это будет «жёсткая ссылка» (hard link),. . .
[Owen Logic] Поддержание уровня воды в резервуаре количеством включённых насосов: моделирование и выбор регулятора
ФедосеевПавел 14.03.2026
Поддержание уровня воды в резервуаре количеством включённых насосов: моделирование и выбор регулятора ВВЕДЕНИЕ Выполняя задание на управление насосной группой заполнения резервуара,. . .
делаю науч статью по влиянию грибов на сукцессию
anaschu 13.03.2026
прикрепляю статью
SDL3 для Desktop (MinGW): Создаём пустое окно с нуля для 2D-графики на SDL3, Си и C++
8Observer8 10.03.2026
Содержание блога Финальные проекты на Си и на C++: hello-sdl3-c. zip hello-sdl3-cpp. zip Результат:
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru