Когда-то очень давно, во времена DOS, CGA и винчестеров с объёмом 20Мб, написав собственный попиксельный графический редактор и столкнувшись с размером сохраняемых файлов, я "придумал" следующий алгоритм их сохранения в обычный текстовый файл - записываем координаты первого пикселя, его атрибуты, координаты следующих пикселей с такими же атрибутами пропускаем и записываем координаты первого отличающегося от них пикселя. И так далее. В какой-то степени, описанная процедура верна для существующих кодеков межкадрового сжатия - только в роли пикселей выступают участки кадров с фиксированными размерами.
Наиболее значимыми в мире MS Windows являются кодек Windows Media, девятая версия которого и будет рассмотрена в данной статье, а также выросший из MS MPEG4 кодек DivX - будет рассмотрена версия 5.1...
Несколько сведений о MPEG
Появившееся в рассматриваемой версии DivX окно Feedback, запускаемое при кодировании в сторонних программах (и "съедающее", по личным наблюдениям, до 20% их производительности) наглядно показывает сам процесс кодирования в общем случае. Рассмотрим получаемую при его работе картинку. (Для её получения пришлось задействовать ресурсы оппонента в виде Windows Media Encoder 9 :))
Для любого стандарта MPEG (и любых других кодеков межкадрового сжатия) есть общая черта - это наличие трёх основных типов кадров:
I-фреймы (от Intra - вступление), или опорные кадры - это кадры, закодированные как неподвижные изображения - без ссылок на последующие или предыдущие. Они используются как стартовые или ключевые.
P-фреймы (от Predicted - предсказанный) - это кадры, предсказаные из предыдущих I- или P-кадров. Каждый макроблок в P-фрейме строится в зависимости от соответвующего блока последнего раскодированного I- или P-кадра, или может быть закодирован в I-кадр, если соответствующего блока не нашлось. Механизм построения блоков прост. Кадр обычно разбивается на блоки по 8х8, 16х8 или 16х16 пикселей. Конкретная величина выбирается в зависимости от параметров качества и производительности настройки кодека. Как видно из окна Feedback, кодировщик сравнивает содержимое каждого блока кадра, и если это - не I-кадр, то кодирует только существенно отличающиеся, что зависит от настроек кодека. В окне Feedback эти кодируемые участки окрашены серым, а вся остальная информация берётся из предыдущих кадров.
И, наконец, B-фреймы (от Bidirectional - двунаправленный), которые предсказаны из двух ближайших I- или P-фреймов, одного предыдущего и другого - последующего. Соответствующие блоки ищутся в этих кадрах, и из них выбирается лучший. Ищется прямой вектор, затем обратный и вычисляется среднее между соответствующими макроблоками в прошлом и будущем. Если это не работает, то блок может быть закодирован как в I-фрейме.
Последовательность раскодированных кадров обычно выглядит как
I B B P B B P B B P B B I B B P B B P B ...
Здесь от I до I фрейма - 12 кадров. Это основано на требовании произвольного доступа, согласно которому начальная точка должна повторяться каждые 0.4 секунды. Соотношение P и B - основано на опыте.
Чтобы декодер мог работать, необходимо, чтобы первый P-фрейм в потоке встретился до первого B, поэтому сжатый поток выглядит так:
0 x x 3 1 2 6 4 5 ...
где числа - это номера кадров. х x может не быть ничем, если это начало последовательности, или B-фреймы с индексами -2 и -1, если это - фрагмент из середины потока.
Сначала необходимо раскодировать I-фрейм, затем P, затем, имея их оба в памяти, раскодировать B. Во время декодирования P показывается I-фрейм, B показываются сразу, а раскодированный P показывается во время декодирования следующего.
В каждом конкретном случае отношение типов кадров может быть разным. Например, в случае на скриншоте, количество P- и B-кадров равно, а I-кадром является приблизительно каждый 90 кадр.
Так как, в принципе, все кодеки межкадрового сжатия строятся на этих "трёх китах", трудно ожидать, что результат их работы будет существенно разным с точки зрения качества. Я долго думал о возможности объективного подхода к сравнению получаемого результата, но после того, как в разных программах при использовании кодека с одинаковыми настройками получал существенно разные результаты, отказался от объективного сравнения, в частности, от хронометража. Я также не буду приводить данные о загрузке системы. По-моему, это не существенный факт, тем более что, как оказалось, и приведённый скриншот тому доказательство, и кодирование в DivX, и создание wmv-файла могут проходить параллельно (я даже до закрытия Feedback думал, что запись экрана не проходит, так незначительно было падение производительности). Кроме того, при использовании разных программ косвенные методы измерения загрузки системы показали, что, опять же, многое зависит от конкретной программы, использующей кодек. (Этим косвенным методом было время пробега короткой бегущей строки в несколько символов на чёрном фоне в режиме Заставка/Screensaver.)
Методика сравнения
Вначале о конфигурации системы, в которой происходил процесс сравнения -
Chaintech Apogee 7VJL (KT333/8235)
Athlon XP T-bred B 2200+ (1800MHz), 512Mb DDR 2100 (133MHz)
ASUS V8420S
HDD Seagate 7200.7 ST3120022A
MS Windows XP Pro SP1, Direct X 9b, MS Windows Media Encoder 9 (b.2926)
DivX Pro 5.1, Dr.DivX 1.0.3
Об остальных использовавшихся программах и устройствах упоминание будет там, где они использовались.
Исходный материал в виде avi-, mpeg-, vob- файлов сначала кодировался в кодеке WMV9, затем при использовании настроек, дающих в результате битрейт, близкий к полученному битрейту видеоряда wmv-файла, кодировался в кодеке DivX Pro 5.1. При полученных качественных отличиях в одну из сторон, пробовалось менять настройку времени кодирования в одном из кодеков, и полученный результат вновь сравнивался - сначала чисто визуально при полноэкранном воспроизведении (или при формате исходного файла), затем делались скриншоты наиболее интересных мест с помощью HyperSnap-DX 5 (
http://www.hypersnap.com).
Так как Windows Media Encoder не имеет софтового декодера MPEG-2, то файлы данного типа либо перекодировались в avi-формат, либо использовались сторонние программы, корректно поддерживающие оба сравниваемые кодека. В основном использовалась программа DVD2AVI v.1.77.3 (разработчик Loli J.,
http://arbor.ee.ntu.edu.tw/~jackei/dvd2avi/) с полной поддержкой дополнительных инструкций процессора AthlonXP.
В качестве исходного материала использовались эпизоды с DVD-дисков с фильмами "Sweet Home Alabama" и "Titanic".
Сравнение
Обычно о преимуществах того или иного кодека судят по настройкам по умолчанию. С этого я и начал, назначив в кодеке WMV9 только битрейт видеопотока в 1Mb/s VBR (переменный битрейт). Остальные параметры не изменялись. Отрывок из фильма "Sweet Home Alabama" кодировался прямо с DVD-диска с помощью программы DVD2AVI. Затем с полученным битрейтом таким же образом тот же отрывок кодировался кодеком DivX Pro 5.1. В обоих случаях процесс кодирования был за один проход, частота смены кадров оригинальная (29 Гц). После просмотра полученного материала меня заинтересовали три места.
В этом эпизоде у кодека DivX прослеживается менее отчётливая прорисовка отдельных нитей фаты, в некоторых местах они попросту исчезают.
Тот же самый эффект размываемости границ прослеживается и в следующем фрагменте
Естественно, оба фрагмента далеки от оригинала. Вы можете сказать, что, мол, кто будет рассматривать такую мелочь. Но третий эпизод просто не смотрелся в DivX, так было искажено изображение.
Кадр ещё терпим. Но вот что видим в DivX - на экране вместо листьев деревьев в левом углу при просмотре было какое-то оранжево-фиолетовое пятно, левая половина лица отца героини фильма так и осталась размыта во время просмотра всего эпизода.
Этот эпизод заставил меня экспериментировать сначала с настройками DivX, но даже самая качественная (и медленная) настройка кодека не дала картинку, которая бы просто смотрелась. При этом более быстрые настройки кодека WMV давали возможность более качественного просмотра эпизода, чем в кодеке DivX. Лишь кодирование под Dr.DivX со снижением частоты кадров до 25Гц дало возможность нормального воспроизведения эпизода. Но что будет, если оригинал фильма будет иметь частоту кадров в 25Гц? Таким фильмом оказался "Titanic". Просто посмотрите на скриншоты. Отмечу, что эпизод кодировался за два прохода в обоих случаях.
Видим, что там, где нет возможности повышения качества за счёт снижения частоты кадров, кодек DivX явно проигрывает в качестве кодеку MS WMV9. При этом, в зависимости от сюжета, возможно снизить время кодирования в WMV 9 до сравнимых с DivX (и даже более быстрых).
Выводы
Почему же, несмотря на лучшую картинку, кодек от Microsoft не имеет такой популярности среди домашних пользователей, как DivX? На мой взгляд, есть несколько причин - во-первых, крайне мало программ, которые бы полностью поддерживали возможности и WMV, и WMA - требуется либо устанавливать дополнительные MPEG-2 декодеры, либо кодировать MPEG-2 в какой-нибудь поддерживаемый Windows Media Encoder формат. Крайне мало, если они вообще существуют, звуковых редакторов, поддерживающих многоканальное аудио - с одной стороны, WMA обеспечивает сжатие аудиопотока 5.1, с другой стороны - чем его редактировать (по крайней мере, на домашнем компьютере), и чем связать оба этих потока?
Во-вторых, при использовании сторонних программ для кодека можно выбрать только дискретный ряд битрейтов без возможности плавной регулировки. Причём, в большинстве случаев требуется сшивка видео- и аудиофайлов.
В то же время, установка Dr.DivX позволяет "на лету" преобразовать vob-файл на DVD-диске в avi-файл, целиком умещающийся на CD и не требующий дополнительного редактирования.
При кодировании же отличных от MPEG-2 файлов, на мой взгляд, стоит отдать предпочтение Windows Media Encoder 9 в случае файлов в высоком разрешении, в малых разрешениях качественная разница визуально не ощутима и выбор кодека носит характер личной привязанности к той или иной программе...