SDL 1.3: как сделать видео без его отображения? - PullRequest
2 голосов
/ 18 июня 2011

Итак, что мне нужно, это просто: представьте, что у нас вообще нет графического интерфейса - ssh-доступ к некоторому Linux, где мы собираемся создавать и размещать наше приложение. Это приложение будет генерировать видео поток. У нас есть приложение SDL с шейдером OpenGL. Все, что мы хотим, это получить рендеринг (как обычно мы делаем в окне SDL) в виде char * (с размером W * H * 3). Как это сделать? Как сделать так, чтобы SDL рендерил вещи не в окно графического интерфейса, а в какой-то заменяемый указатель?

Ответы [ 2 ]

3 голосов
/ 18 июня 2011

Чтобы быть полезным, OpenGL должен быть аппаратно ускорен, поэтому сначала проверьте, есть ли на вашем сервере графический процессор, отвечающий вашим требованиям.Если вы используете арендованный виртуальный сервер или какой-либо стандартный корневой сервер, то, скорее всего, у вас нет графического процессора.

Если у вас есть графический процессор, есть два возможных способа:


Метод 1 - простой

Вам (к сожалению) придется настроить и запустить для него X-сервер и этот X-сервер должентакже быть текущим виртуальным терминалом (то есть он должен быть активным на графической карте).Затем вы даете пользователю, который будет запускать этот видеогенератор, доступ к этому X-дисплею (прочитайте man xauth и на что он ссылается)

Следующий шаг не зависит от SDL, это OpenGL-идея: создать кадровый буферОбъект, на котором отображается желаемая графика;PBuffer также будет работать, и на самом деле я бы предпочел его в этой ситуации, однако я обнаружил, что объекты Framebuffer более надежны, чем PBuffers в текущем Linux и его драйверах.

Затем выполните рендеринг в этот объект Framebuffer или PBuffer какобычно и извлекают контент, используя glReadPixels


Метод 2 - гибкий

На низком уровне это очень похоже на метод 1, новсе становится для вас отвлеченным: получите VirtualGL http://www.virtualgl.org/ для выполнения фактического рендеринга OpenGL на GPU.Вместо запуска приложения на вторичном X-сервере вы напрямую используете сервер VirtualGL при условии отправки потока GLX и получения потока изображений JPEG обратно.Вы также можете использовать дополнительный X-сервер, на котором запущен виртуальный кадровый буфер, и постоянно снимать этот экран.Или, возможно, самый элегантный: напишите свой собственный видеодрайвер X.Org, который напрямую передает видео на видеопоток.


2 голосов
/ 18 июня 2011

Вы не можете напрямую рендериться в байтовый массив в OpenGL.

Есть два способа работы с этим. Первый способ является самым простым и не требует уловок контекста, а второй -.

Итак, во-первых, простой способ.

Чтобы OpenGL работал, у вас должно быть окно. Это не означает, что окно должно быть видимым , но вам нужно создать его, чтобы получить действительный контекст OpenGL. Поэтому Шаг 1. Создайте окно и сверните его.

Теперь, чтобы получить корректный рендеринг, пиксели в кадровом буфере должны пройти «тест владения пикселями». При рендеринге в кадровый буфер, который содержит сам экран, пиксели окна, которые фактически не видны на экране, не проходят тест владения пикселями. Поэтому значения этих пикселей не определены, если вы используете glReadPixels.

Однако это относится только к кадровому буферу по умолчанию, связанному с окном. Объекты кадрового буфера всегда проходят проверку владения пикселями. Следовательно, Шаг 2. Создайте объект кадрового буфера и связанные с ним средства визуализации для ваших нужд.

Оттуда все довольно просто. Просто сделайте рендеринг как обычно и сделайте glReadPixels, когда вы хотите получить данные. Объекты пиксельных буферов могут использоваться для асинхронной передачи данных пикселей, если производительность является проблемой. Шаг 3. Визуализация и использование glReadPixels для получения данных.


Второй способ более широкодоступен (для FBO требуется поддержка расширений или OpenGL 3.0), но в большей степени зависит от платформы.

Вместо создания FBO на шаге 2 у вас вместо этого есть Шаг 2: используйте glXCreatePbuffer для создания pbuffer. pbuffer - это объект закадрового рендера, который действует как кадровый буфер по умолчанию. Вы glXMakeContextCurrent говорите OpenGL отображать в pbuffer вместо стандартного кадрового буфера.

Шаги 1 и 3 такие же, как указано выше.

...