Куб в opengl python

Работа с 3-х мерными объектами в Python с использованием OpenGL

В данной программе будет представлен пример, как работать с объёмными фигурами в
OpenGL на языке Python. В итоге будет представлен куб в 3-ёх мерном виде.

Среда разработки: PyCharm Community Edition 2020.1.2

Для начала работы потребуется наличие следующих инструментов или пакетов: Python, PyOpenGL, PyGame.

Как установить Python можно посмотреть на официальном сайте, ссылка на него: https://www.python.org/

Далее рассмотрим установку пакетов на Python.

Для того, чтобы загрузить PyOpenGL и PyGame, воспользуемся PyPi. В терминале IDE вводим команды:

pip install pygame pip install PyOpenGL
import pygame import OpenGL

Если эти выражения не вызовут ошибок, значит вы готовы к дальнейшей работе. Если возникнут ошибки, значит при установке пакетов произошла ошибка, либо текущие версии пакетов несовместимы с Вашей версией Python. Более детальную информацию можно узнать в документации к используемым пакетам Python’a: PyGame и PyOpenGL.

Отлично, теперь перейдем непосредственно к коду! Если у вас еще сохранился код импорта, который мы только что запускали, сотрите его: мы начнем полностью с чистого листа.

Для начала произведем импорт необходимых библиотек:

import pygame from pygame.locals import * from OpenGL.GL import * from OpenGL.GLU import *

Мы импортируем все из PyGame, а затем все из PyGame.locals. Это вполне стандартный код для PyGame.Затем мы импортируем OpenGL.GL и OpenGL.GLU. OpenGL.GL содержит в себе самые обычные функции библиотеки OpenGL, а вот OpenGL.GLU — более сложных объектов.

Изначально создадим функцию main() для удобства:

vertices= ( (1.0, -1.0, -1.0), (1.0, 1.0, -1.0), (-1.0, 1.0, -1.0), (-1.0, -1.0, -1.0), (1.0, - 1.0, 1.0), (1.0, 1.0, 1.0), (-1.0, -1.0, 1.0), (-1.0, 1.0, 1.0) )

Здесь мы определили координаты (x, y, z) каждой нашей вершины. Думаю, лучше всего представить это в относительных единицах.

Далее нам надо задать ребра:

edges = ( (0,1), (0,3), (0,4), (2,1), (2,3), (2,7), (6,3), (6,4), (6,7), (5,1), (5,4), (5,7) )

Каждое ребро представлено кортежем, состоящим из двух чисел. Эти числа соответствуют номерам вершин, а ребро их соединяет. Как принято в Python, да и во многих других языках программирования, нумерация начинается с 0. Соответственно, 0 обозначает вершину (1, -1, -1), и так далее.

Теперь, когда у нас все это есть, давайте поработаем над необходимым кодом для работы с OpenGL, чтобы фактически создать сам куб (описывать функцию Cube() мы будем вне функции main()):

def Cube(vertices, edges): glBegin(GL_LINES) for edge in edges: for vertex in edge: glVertex3fv(vertices[vertex]) glEnd()

Как обычно, мы начинаем с задания функции. Поскольку это просто функция, которая будет содержать код OpenGL, мы начинаем этот код со следующего выражения: glBegin (GL_LINES). Это уведомляет OpenGL сначала о том, что мы собираемся бросить в нее какой-то код, а затем — о том, как надо обрабатывать этот код (это указывает аргумент GL_LINES). В данном случае этот код будет рассматриваться как код для рисования линий.

Читайте также:  Вывод тегов на странице

Далее, мы итерируем по всем нашим ребрам (список edges), а затем каждой вершине в ребре (их там две) мы ставим в соответствие вершину из нашего списка вершин vertices (при помощи функции glVertex3fv).

glVertex3fv((1, -1, -1)) glVertex3fv((1, 1, -1))

После прохождения всех ребер работа функции заканчивается и мы вызываем glEnd(), чтобы сообщить об этом OpenGL. Подобные открывающие и закрывающие команды используются в OpenGL постоянно.

Это все, что касается нашей функции. Она создает куб, но теперь мы хотим его отобразить и указать его перспективу в нашем окружении, для этого возвращаемся в функцию main() и пишем следующее:

pygame.init() display = (800,600) pygame.display.set_mode(display, DOUBLEBUF|OPENGL)

Это тоже очень типичный для Pygame код. Единственное существенное отличие здесь в том, что после параметра display в функции pygame.display.set_mode мы добавляем еще один параметр. На самом деле это константы, уведомляющие PyGame о том, что мы будем использовать код OpenGL. Константа DOUBLEBUF расшифровывается как двойной буфер. Она обозначает тип буфферизации, в котором есть два буфера для соответствия кадровой частоте монитора. Обратите внимание, что для разделения констант используется символ «|». Мы еще столкнемся с ним в дальнейшем.

Идем дальше. В теле главной функции находится следующий код:

gluPerspective(45, (display[0]/display[1]), 0.1, 50.0)

Функция gluPerspective определяет перспективу, о чем, впрочем, несложно догадаться из ее названия. Ее первый параметр определяет угол поля зрения и выражается в градусах. Второй параметр — это соотношение сторон дисплея, ширина, деленная на высоту. Следующие два параметра — znear и zfar, которые представляют собой ближнюю и дальнюю плоскости отсечения.

Идем дальше. У нас есть следующая функция:

glTranslatef(0.0, -1.0, -10) glRotatef(20, 10, 0, 0)

Теперь напишем наш типичный цикл для отслеживания событий в PyGame:

while True: for event in pygame.event.get(): if event.type == pygame.QUIT: pygame.quit() quit()

Это простой цикл отслеживания событий в PyGame, который определяет возможность выхода. Иными словами, он отслеживает нажатие клавиши «x». Далее, под оператором while продолжаем наш код:

glRotatef(1, 0, 1, 0) glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT) Cube() pygame.display.flip() pygame.time.wait(10)

Функция glRotatef умножает текущую матрицу на матрицу вращения. Ее параметрами являются угол вращения и координаты x, y, и z.

Затем у нас есть функция glClear, работающая, как любая другая функция очистки. Мы указываем в ее параметрах пару констант, которые сообщают OpenGL, что именно мы очищаем.

Читайте также:  Найти все простые делители числа питон

Как только мы очистим «экран», мы опять вызовем нашу функцию Cube ().
После этого мы вызываем функцию pygame.display.flip (), которая обновляет наш экран.
И наконец, мы вставляем небольшую задержку при помощи функции pygame.time.wait (10).

И в завершении в самой программе просто вызываем функцию main().

import pygame from pygame.locals import * from OpenGL.GL import * from OpenGL.GLU import * def Cube(vertices, edges): glBegin(GL_LINES) for edge in edges: for vertex in edge: glVertex3fv(vertices[vertex]) glEnd()  def main(): vertices = ( (1.0, -1.0, -1.0), (1.0, 1.0, -1.0), (-1.0, 1.0, -1.0), (-1.0, -1.0, -1.0), (1.0, - 1.0, 1.0), (1.0, 1.0, 1.0), (-1.0, -1.0, 1.0), (-1.0, 1.0, 1.0) ) edges = ( (0, 1), (0, 3), (0, 4), (2, 1), (2, 3), (2, 7), (6, 3), (6, 4), (6, 7), (5, 1), (5, 4), (5, 7) ) pygame.init() display = (800, 600) pygame.display.set_mode(display, DOUBLEBUF|OPENGL) gluPerspective(45, (display[0]/display[1]), 0.1, 50.0) glTranslatef(0.0, -1.0, -10) glRotatef(20, 10, 0, 0) while True: for event in pygame.event.get(): if event.type == pygame.QUIT: pygame.quit() quit() glRotatef(1, 0, 1, 0) glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT) Cube(vertices, edges) pygame.display.flip() pygame.time.wait(10) main()
Прикрепленный файл Размер
main.rar 573 байта

Источник

How to make an OpenGL/Glut Cube in Python

The OpenGL Utility Toolkit (GLUT) is a library of utilities for OpenGL programs, which primarily perform system-level I/O with the host operating system. Functions performed include window definition, window control, and monitoring of keyboard and mouse input. Routines for drawing a number of geometric primitives (both in solid and wireframe mode) are also provided, including cubes, spheres and the Utah teapot. GLUT also has some limited support for creating pop-up menus.

Installation

Install PyOpenGL using the command:

The Code

We assume you have previous programming experience; Simply copy the code displayed below into a text editor.
Save the file as example.py

from OpenGL.GL import * from OpenGL.GLUT import * from OpenGL.GLU import * import serial import os import threading ESCAPE = '\033' window = 0 #rotation X_AXIS = 0.0 Y_AXIS = 0.0 Z_AXIS = 0.0 DIRECTION = 1 def InitGL(Width, Height): glClearColor(0.0, 0.0, 0.0, 0.0) glClearDepth(1.0) glDepthFunc(GL_LESS) glEnable(GL_DEPTH_TEST) glShadeModel(GL_SMOOTH) glMatrixMode(GL_PROJECTION) glLoadIdentity() gluPerspective(45.0, float(Width)/float(Height), 0.1, 100.0) glMatrixMode(GL_MODELVIEW) def keyPressed(*args): if args[0] == ESCAPE: sys.exit() def DrawGLScene(): global X_AXIS,Y_AXIS,Z_AXIS global DIRECTION glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT) glLoadIdentity() glTranslatef(0.0,0.0,-6.0) glRotatef(X_AXIS,1.0,0.0,0.0) glRotatef(Y_AXIS,0.0,1.0,0.0) glRotatef(Z_AXIS,0.0,0.0,1.0) # Draw Cube (multiple quads) glBegin(GL_QUADS) glColor3f(0.0,1.0,0.0) glVertex3f( 1.0, 1.0,-1.0) glVertex3f(-1.0, 1.0,-1.0) glVertex3f(-1.0, 1.0, 1.0) glVertex3f( 1.0, 1.0, 1.0) glColor3f(1.0,0.0,0.0) glVertex3f( 1.0,-1.0, 1.0) glVertex3f(-1.0,-1.0, 1.0) glVertex3f(-1.0,-1.0,-1.0) glVertex3f( 1.0,-1.0,-1.0) glColor3f(0.0,1.0,0.0) glVertex3f( 1.0, 1.0, 1.0) glVertex3f(-1.0, 1.0, 1.0) glVertex3f(-1.0,-1.0, 1.0) glVertex3f( 1.0,-1.0, 1.0) glColor3f(1.0,1.0,0.0) glVertex3f( 1.0,-1.0,-1.0) glVertex3f(-1.0,-1.0,-1.0) glVertex3f(-1.0, 1.0,-1.0) glVertex3f( 1.0, 1.0,-1.0) glColor3f(0.0,0.0,1.0) glVertex3f(-1.0, 1.0, 1.0) glVertex3f(-1.0, 1.0,-1.0) glVertex3f(-1.0,-1.0,-1.0) glVertex3f(-1.0,-1.0, 1.0) glColor3f(1.0,0.0,1.0) glVertex3f( 1.0, 1.0,-1.0) glVertex3f( 1.0, 1.0, 1.0) glVertex3f( 1.0,-1.0, 1.0) glVertex3f( 1.0,-1.0,-1.0) glEnd() X_AXIS = X_AXIS - 0.30 Z_AXIS = Z_AXIS - 0.30 glutSwapBuffers() def main(): global window glutInit(sys.argv) glutInitDisplayMode(GLUT_RGBA | GLUT_DOUBLE | GLUT_DEPTH) glutInitWindowSize(640,480) glutInitWindowPosition(200,200) window = glutCreateWindow('OpenGL Python Cube') glutDisplayFunc(DrawGLScene) glutIdleFunc(DrawGLScene) glutKeyboardFunc(keyPressed) InitGL(640, 480) glutMainLoop() if __name__ == "__main__": main() 

The part below defines the cube:

glBegin(GL_QUADS) glColor3f(0.0,1.0,0.0) glVertex3f( 1.0, 1.0,-1.0) glVertex3f(-1.0, 1.0,-1.0) glVertex3f(-1.0, 1.0, 1.0) glVertex3f( 1.0, 1.0, 1.0) glColor3f(1.0,0.0,0.0) glVertex3f( 1.0,-1.0, 1.0) glVertex3f(-1.0,-1.0, 1.0) glVertex3f(-1.0,-1.0,-1.0) glVertex3f( 1.0,-1.0,-1.0) glColor3f(0.0,1.0,0.0) glVertex3f( 1.0, 1.0, 1.0) glVertex3f(-1.0, 1.0, 1.0) glVertex3f(-1.0,-1.0, 1.0) glVertex3f( 1.0,-1.0, 1.0) glColor3f(1.0,1.0,0.0) glVertex3f( 1.0,-1.0,-1.0) glVertex3f(-1.0,-1.0,-1.0) glVertex3f(-1.0, 1.0,-1.0) glVertex3f( 1.0, 1.0,-1.0) glColor3f(0.0,0.0,1.0) glVertex3f(-1.0, 1.0, 1.0) glVertex3f(-1.0, 1.0,-1.0) glVertex3f(-1.0,-1.0,-1.0) glVertex3f(-1.0,-1.0, 1.0) glColor3f(1.0,0.0,1.0) glVertex3f( 1.0, 1.0,-1.0) glVertex3f( 1.0, 1.0, 1.0) glVertex3f( 1.0,-1.0, 1.0) glVertex3f( 1.0,-1.0,-1.0) glEnd() 

A cube consists of a set of six quads. Thats why we start with the statement glBegin(GL_QUADS);
The glVertex3f statement defines a point of the cube. Every quad has four points, where every single point is defined by its 3d coordinate (x,y,z)
The glColor3f statement defines the color of the quad.

Читайте также:  Mysql boolean and php

Источник

Оцените статью