Получить данные из OpenGL glReadPixels (используя Pyglet) - PullRequest
0 голосов
/ 15 декабря 2008

Я использую Pyglet (и OpenGL) в Python для приложения, я пытаюсь использовать glReadPixels, чтобы получить значения RGBA для набора пикселей. Насколько я понимаю, OpenGL возвращает данные в виде упакованных целых чисел, поскольку они хранятся на оборудовании. Однако по понятным причинам я хотел бы привести его в нормальный формат для работы с. Основываясь на некотором прочтении, я придумал следующее: http://dpaste.com/99206/, однако это не удается с помощью IndexError. Как бы я поступил так?

Ответы [ 5 ]

4 голосов
/ 08 февраля 2009

Сначала необходимо создать массив правильного типа, а затем передать его в glReadPixels:

a = (GLuint * 1)(0)
glReadPixels(x, y, 1, 1, GL_RGB, GL_UNSIGNED_INT, a)

Чтобы проверить это, вставьте в пример "opengl.py" Pyglet следующее:

@window.event
def on_mouse_press(x, y, button, modifiers):
    a = (GLuint * 1)(0)
    glReadPixels(x, y, 1, 1, GL_RGB, GL_UNSIGNED_INT, a)
    print a[0]

Теперь вы должны видеть цветовой код для пикселя под курсором мыши всякий раз, когда вы щелкаете где-то в окне приложения.

1 голос
/ 08 ноября 2010

Я смог получить весь буфер кадра, используя glReadPixels(...), затем использовал PIL для записи в файл:

# Capture image from the OpenGL buffer
buffer = ( GLubyte * (3*window.width*window.height) )(0)
glReadPixels(0, 0, window.width, window.height, GL_RGB, GL_UNSIGNED_BYTE, buffer)

# Use PIL to convert raw RGB buffer and flip the right way up
image = Image.fromstring(mode="RGB", size=(window.width, window.height), data=buffer)     
image = image.transpose(Image.FLIP_TOP_BOTTOM)

# Save image to disk
image.save('jpap.png')

Меня не интересовала альфа, но я уверен, что вы могли бы легко добавить ее.

Я был вынужден использовать glReadPixels(...) вместо кода Пиглета

pyglet.image.get_buffer_manager().get_color_buffer().save('jpap.png')

потому что вывод с использованием save(...) не был идентичен тому, что я видел в Окне. (Буферы мультисэмплинга пропущены?)

1 голос
/ 15 декабря 2008

Вы можете использовать библиотеку PIL, вот фрагмент кода, который я использую для захвата такого изображения:

    buffer = gl.glReadPixels(0, 0, width, height, gl.GL_RGB, 
                             gl.GL_UNSIGNED_BYTE)
    image = Image.fromstring(mode="RGB", size=(width, height), 
                             data=buffer)
    image = image.transpose(Image.FLIP_TOP_BOTTOM)

Я полагаю, что включение альфа-канала должно быть довольно простым (возможно, просто заменить RGB на RGBA, но я этого не пробовал).

Редактировать: я не знал, что API-интерфейс pyglet OpenGL отличается от API-интерфейса PyOpenGL. Я полагаю, что нужно изменить приведенный выше код, чтобы использовать буфер в качестве седьмого аргумента (в соответствии с менее питоническим стилем пиглета).

0 голосов
/ 15 декабря 2008

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

0 голосов
/ 15 декабря 2008

Если вы прочитаете фрагмент, на который вы ссылаетесь, вы поймете, что самый простой и удобный способ получить "нормальные" значения - это просто получить доступ к массиву в правильном порядке.
Этот фрагмент выглядит так, как будто он должен делать эту работу. Если это не так, отладьте его и посмотрите, в чем проблема.

...