Извлечение размеров видеопотока H264 - PullRequest
22 голосов
/ 18 июня 2011

Я пытаюсь получить размеры (высоту и ширину) из потока H264.Я знаю, что для извлечения тех же деталей из потока mpeg2 вам нужно взглянуть на четыре байта, следующих за начальным кодом заголовка последовательности ((01B3)).Будет ли такая же логика работать на H264?Буду признателен за любую помощь, которую я получу ..

Ответы [ 4 ]

46 голосов
/ 25 июня 2011

НЕТ !!!

Вы должны запустить сложную функцию, чтобы извлечь размеры видео из наборов параметров последовательности.Как это сделать?Ну, во-первых, вы должны написать свой собственный декодер Exp-Golomb или найти его в сети ... в исходном коде live555, где-то есть его, например ...

Затем вы должны получить один кадр SPS.Он имеет NAL=0x67 (NAL - первый байт в кадре H.264), и вы можете найти его как строку в кодировке Base64 в SDP в sprop-parameter-sets это первая строка Base64 перед первой запятой.Другими строками, разделенными запятыми, являются наборы параметров изображения ... Это один SPS из SDP Z0KAKYiLQDIBL0IAAB1MAAK/IAg=, вам необходимо декодировать что-то подобное из Base64 в байтовый массив.

Затем необходимо извлечь RAW BYTEПОСЛЕДОВАТЕЛЬНАЯ ЗАГРУЗКА , за которой следует NAL UNIT HEADER в этом байтовом массиве !!!Обычно это один байт, но читайте дальше, чтобы быть уверенным ... RBSP содержит байты, необходимые для запуска функции seq_parameter_set_data( ).Поэтому вам нужно сначала удалить заголовок NAL UNIT (один или несколько байтов).

Вот эта функция извлекает байты RBSP из NAL UNIT SPS:

NAL UNIT

Затем, когда у вас есть SPS (байты RBSP), вам нужно выполнить функцию, которая анализирует биты в этом байтовом массиве.Вот функция со всеми проанализированными там параметрами (весь документ можно найти здесь: http://www.itu.int/rec/T-REC-H.264-201003-I/en и его бесплатно): How to decode SPS

Там вы можете увидеть некоторые странные вещи ... во-первых, вашРазмеры видео рассчитываются следующим образом:

Width = ((pic_width_in_mbs_minus1 +1)*16) - frame_crop_right_offset*2 - frame_crop_left_offset*2;
Height = ((2 - frame_mbs_only_flag)* (pic_height_in_map_units_minus1 +1) * 16) - (frame_crop_top_offset * 2) - (frame_crop_bottom_offset * 2);

Во-вторых, и самое важное, в столбце DESCRIPTOR этой кодовой таблицы указано, что вы должны сделать, чтобы прочитать параметр жирного текста в первом столбце.Вот что означают значения:

  • u (N) - Считать число без знака длиной N бит
  • s (N) - Считать число со знаком, длина которого N битов
  • ue (v) - Считать число без знака Exp-Golomb (v для переменной длины, поэтому оно равно ue())
  • se (v) - Считать подписанный номер Exp-Golomb

Здесь вам пригодится ваш Exp-Golomb декодер ...

Итак, реализуйте эту функцию, проанализируйте SPS, и вы получите свои ширину и высоту.Наслаждайтесь ...:)

21 голосов
/ 06 июля 2012

К сожалению, вычисления размера неверны и должны быть:

width = ((pic_width_in_mbs_minus1 +1)*16) - frame_crop_left_offset*2 - frame_crop_right_offset*2;
height= ((2 - frame_mbs_only_flag)* (pic_height_in_map_units_minus1 +1) * 16) - (frame_crop_top_offset * 2) - (frame_crop_bottom_offset * 2);
5 голосов
/ 29 августа 2012

На самом деле параметры обрезки следует использовать только в том случае, если в SPS включен параметр [frame_cropping_flag].Наслаждайтесь H.264!

2 голосов
/ 13 июля 2016

Что касается расчета размера кадра, приведенная выше формула неверна.

Когда присутствует chroma_format_idc, мы должны извлечь его из SPS.Если chroma_format_idc отсутствует, то оно должно быть равно 1 (формат цветности 4: 2: 0).В этом случае separate_color_plane_flag не установлен.Это означает, что chromaArrayType = chroma_format_idc и subWidthC и subHeightC равны 2.

Переменные cropUnitX и cropUnitY выводятся следующим образом:

  • Если chromaArrayType равно 0, cropUnitX и cropUnitY получаются как:

    cropUnitX = 1
    cropUnitY = 2 - frame_mbs_only_flag
    
  • В противном случае (chromaArrayType равно 1, 2 или 3), cropUnitX и cropUnitY выводятся как:

    cropUnitX = subWidthC
    cropUnitY = subHeightC * ( 2 - frame_mbs_only_flag )
    

Теперь вы можете использовать cropUnitX и cropUnitY в приведенной выше формулечтобы получить правильные значения для размера кадра.

...