def _set_points(self, points, kind, tris): """Set fill and line points.""" if points is None: self._counts[kind] = 0 points = np.asarray(points, dtype=np.float32, order='C') assert points.ndim == 2 and points.shape[1] == 2 array_count = points.size // 2 if kind == 'line' else points.size if kind == 'fill': assert tris is not None tris = np.asarray(tris, dtype=np.uint32, order='C') assert tris.ndim == 1 and tris.size % 3 == 0 tris.shape = (-1, 3) assert (tris < len(points)).all() self._tris[kind] = tris del tris self._points[kind] = points del points gl.glUseProgram(self._program) gl.glBindBuffer(gl.GL_ARRAY_BUFFER, self._buffers[kind]['array']) gl.glBufferData(gl.GL_ARRAY_BUFFER, self._points[kind].size * 4, self._points[kind].tobytes(), gl.GL_STATIC_DRAW) if kind == 'line': self._counts[kind] = array_count if kind == 'fill': self._counts[kind] = self._tris[kind].size gl.glBindBuffer(gl.GL_ELEMENT_ARRAY_BUFFER, self._buffers[kind]['index']) gl.glBufferData(gl.GL_ELEMENT_ARRAY_BUFFER, self._tris[kind].size * 4, self._tris[kind].tobytes(), gl.GL_STATIC_DRAW) gl.glBindBuffer(gl.GL_ELEMENT_ARRAY_BUFFER, 0) gl.glBindBuffer(gl.GL_ARRAY_BUFFER, 0) gl.glUseProgram(0)
def draw(self): """Draw the object to the display buffer.""" gl.glUseProgram(self._program) for kind in ('fill', 'line'): if self._counts[kind] > 0: if kind == 'line': if self._line_width <= 0.0: continue gl.glLineWidth(self._line_width) if self._line_loop: mode = gl.GL_LINE_LOOP else: mode = gl.GL_LINE_STRIP cmd = partial(gl.glDrawArrays, mode, 0, self._counts[kind]) else: gl.glBindBuffer(gl.GL_ELEMENT_ARRAY_BUFFER, self._buffers[kind]['index']) cmd = partial(gl.glDrawElements, gl.GL_TRIANGLES, self._counts[kind], gl.GL_UNSIGNED_INT, 0) gl.glBindBuffer(gl.GL_ARRAY_BUFFER, self._buffers[kind]['array']) loc_pos = gl.glGetAttribLocation(self._program, b'a_position') gl.glEnableVertexAttribArray(loc_pos) gl.glVertexAttribPointer(loc_pos, 2, gl.GL_FLOAT, gl.GL_FALSE, 0, 0) loc_col = gl.glGetUniformLocation(self._program, b'u_color') gl.glUniform4f(loc_col, *self._colors[kind]) cmd() # cleanup gl.glDisableVertexAttribArray(loc_pos) if kind != 'line': gl.glBindBuffer(gl.GL_ELEMENT_ARRAY_BUFFER, 0) gl.glBindBuffer(gl.GL_ARRAY_BUFFER, 0) gl.glUseProgram(0)
def _create_program(ec, vert, frag): program = gl.glCreateProgram() vertex = gl.glCreateShader(gl.GL_VERTEX_SHADER) buf = create_string_buffer(vert.encode('ASCII')) ptr = cast(pointer(pointer(buf)), POINTER(POINTER(c_char))) gl.glShaderSource(vertex, 1, ptr, None) gl.glCompileShader(vertex) _check_log(vertex, gl.glGetShaderInfoLog) fragment = gl.glCreateShader(gl.GL_FRAGMENT_SHADER) buf = create_string_buffer(frag.encode('ASCII')) ptr = cast(pointer(pointer(buf)), POINTER(POINTER(c_char))) gl.glShaderSource(fragment, 1, ptr, None) gl.glCompileShader(fragment) _check_log(fragment, gl.glGetShaderInfoLog) gl.glAttachShader(program, vertex) gl.glAttachShader(program, fragment) gl.glLinkProgram(program) _check_log(program, gl.glGetProgramInfoLog) gl.glDetachShader(program, vertex) gl.glDetachShader(program, fragment) # Set the view matrix gl.glUseProgram(program) loc = gl.glGetUniformLocation(program, b'u_view') view = ec.window_size_pix view = np.diag([2. / view[0], 2. / view[1], 1., 1.]) view[-1, :2] = -1 view = view.astype(np.float32).ravel() gl.glUniformMatrix4fv(loc, 1, False, (c_float * 16)(*view)) gl.glUseProgram(0) return program
def __init__(self, ec, fill_color, line_color, line_width, line_loop): self._ec = ec self._line_width = line_width self._line_loop = line_loop # whether or not lines drawn are looped # initialize program and shaders self._program = _create_program(ec, tri_vert, tri_frag) gl.glUseProgram(self._program) self._counts = dict() self._colors = dict() self._buffers = dict() self._points = dict() self._tris = dict() for kind in ('line', 'fill'): self._counts[kind] = 0 self._colors[kind] = (0., 0., 0., 0.) self._buffers[kind] = dict(array=gl.GLuint()) gl.glGenBuffers(1, pointer(self._buffers[kind]['array'])) self._buffers['fill']['index'] = gl.GLuint() gl.glGenBuffers(1, pointer(self._buffers['fill']['index'])) gl.glUseProgram(0) self.set_fill_color(fill_color) self.set_line_color(line_color)
def draw(self): """Draw the object to the display buffer""" gl.glUseProgram(self._program) for kind in ('fill', 'line'): if self._counts[kind] > 0: if kind == 'line': if self._line_width <= 0.0: continue gl.glLineWidth(self._line_width) if self._line_loop: mode = gl.GL_LINE_LOOP else: mode = gl.GL_LINE_STRIP cmd = partial(gl.glDrawArrays, mode, 0, self._counts[kind]) else: gl.glBindBuffer(gl.GL_ELEMENT_ARRAY_BUFFER, self._buffers[kind]['index']) cmd = partial(gl.glDrawElements, gl.GL_TRIANGLES, self._counts[kind], gl.GL_UNSIGNED_INT, 0) gl.glBindBuffer(gl.GL_ARRAY_BUFFER, self._buffers[kind]['array']) loc_pos = gl.glGetAttribLocation(self._program, b'a_position') gl.glEnableVertexAttribArray(loc_pos) gl.glVertexAttribPointer(loc_pos, 2, gl.GL_FLOAT, gl.GL_FALSE, 0, 0) loc_col = gl.glGetUniformLocation(self._program, b'u_color') gl.glUniform4f(loc_col, *self._colors[kind]) cmd() # The following line is probably only necessary because # Pyglet makes some assumptions about the GL state that # it perhaps shouldn't. Without it, Text might not # render properly (see #252) gl.glDisableVertexAttribArray(loc_pos) gl.glUseProgram(0)
def _draw(self): tex = self._player.get_texture() gl.glUseProgram(self._program) gl.glActiveTexture(gl.GL_TEXTURE0) gl.glBindTexture(tex.target, tex.id) gl.glBindVertexArray(0) x, y = self._actual_pos w = self.source_width * self._scale h = self.source_height * self._scale pos = np.array([(x, y), (x + w, y), (x + w, y + h), (x, y + h)], np.float32) gl.glBindBuffer(gl.GL_ARRAY_BUFFER, self._buffers['position']) gl.glBufferData(gl.GL_ARRAY_BUFFER, pos.nbytes, pos.tobytes(), gl.GL_DYNAMIC_DRAW) loc_pos = gl.glGetAttribLocation(self._program, b'a_position') gl.glEnableVertexAttribArray(loc_pos) gl.glVertexAttribPointer(loc_pos, 2, gl.GL_FLOAT, gl.GL_FALSE, 0, 0) gl.glBindBuffer(gl.GL_ARRAY_BUFFER, self._buffers['texcoord']) loc_tex = gl.glGetAttribLocation(self._program, b'a_texcoord') gl.glEnableVertexAttribArray(loc_tex) gl.glVertexAttribPointer(loc_tex, 2, gl.GL_FLOAT, gl.GL_FALSE, 0, 0) gl.glBindBuffer(gl.GL_ARRAY_BUFFER, 0) gl.glDrawArrays(gl.GL_QUADS, 0, 4) gl.glDisableVertexAttribArray(loc_pos) gl.glDisableVertexAttribArray(loc_tex) gl.glUseProgram(0) gl.glBindTexture(tex.target, 0)
def _set_points(self, points, kind, tris): """Set fill and line points.""" if points is None: self._counts[kind] = 0 points = np.asarray(points, dtype=np.float32, order='C') assert points.ndim == 2 and points.shape[1] == 2 array_count = points.size // 2 if kind == 'line' else points.size if kind == 'fill': assert tris is not None tris = np.asarray(tris, dtype=np.uint32, order='C') assert tris.ndim == 1 and tris.size % 3 == 0 tris.shape = (-1, 3) assert (tris < len(points)).all() self._tris[kind] = tris del tris self._points[kind] = points del points gl.glUseProgram(self._program) gl.glBindBuffer(gl.GL_ARRAY_BUFFER, self._buffers[kind]['array']) gl.glBufferData(gl.GL_ARRAY_BUFFER, self._points[kind].size * 4, self._points[kind].tostring(), gl.GL_STATIC_DRAW) if kind == 'line': self._counts[kind] = array_count if kind == 'fill': self._counts[kind] = self._tris[kind].size gl.glBindBuffer(gl.GL_ELEMENT_ARRAY_BUFFER, self._buffers[kind]['index']) gl.glBufferData(gl.GL_ELEMENT_ARRAY_BUFFER, self._tris[kind].size * 4, self._tris[kind].tostring(), gl.GL_STATIC_DRAW) gl.glUseProgram(0)
def __init__(self, ec, fill_color, line_color, line_width, line_loop): self._ec = ec self._line_width = line_width self._line_loop = line_loop # whether or not lines drawn are looped # initialize program and shaders self._program = gl.glCreateProgram() vertex = gl.glCreateShader(gl.GL_VERTEX_SHADER) buf = create_string_buffer(tri_vert.encode('ASCII')) ptr = cast(pointer(pointer(buf)), POINTER(POINTER(c_char))) gl.glShaderSource(vertex, 1, ptr, None) gl.glCompileShader(vertex) _check_log(vertex, gl.glGetShaderInfoLog) fragment = gl.glCreateShader(gl.GL_FRAGMENT_SHADER) buf = create_string_buffer(tri_frag.encode('ASCII')) ptr = cast(pointer(pointer(buf)), POINTER(POINTER(c_char))) gl.glShaderSource(fragment, 1, ptr, None) gl.glCompileShader(fragment) _check_log(fragment, gl.glGetShaderInfoLog) gl.glAttachShader(self._program, vertex) gl.glAttachShader(self._program, fragment) gl.glLinkProgram(self._program) _check_log(self._program, gl.glGetProgramInfoLog) gl.glDetachShader(self._program, vertex) gl.glDetachShader(self._program, fragment) gl.glUseProgram(self._program) # Prepare buffers and bind attributes loc = gl.glGetUniformLocation(self._program, b'u_view') view = ec.window_size_pix view = np.diag([2. / view[0], 2. / view[1], 1., 1.]) view[-1, :2] = -1 view = view.astype(np.float32).ravel() gl.glUniformMatrix4fv(loc, 1, False, (c_float * 16)(*view)) self._counts = dict() self._colors = dict() self._buffers = dict() self._points = dict() self._tris = dict() for kind in ('line', 'fill'): self._counts[kind] = 0 self._colors[kind] = (0., 0., 0., 0.) self._buffers[kind] = dict(array=gl.GLuint()) gl.glGenBuffers(1, pointer(self._buffers[kind]['array'])) self._buffers['fill']['index'] = gl.GLuint() gl.glGenBuffers(1, pointer(self._buffers['fill']['index'])) gl.glUseProgram(0) self.set_fill_color(fill_color) self.set_line_color(line_color)
def __init__(self, ec, file_name, pos=(0, 0), units='norm', scale=1., center=True, visible=True): from pyglet.media import load, Player self._ec = ec # On Windows, the default is unaccelerated WMF, which is terribly slow. decoder = None if _new_pyglet(): try: from pyglet.media.codecs.ffmpeg import FFmpegDecoder decoder = FFmpegDecoder() except Exception as exc: warnings.warn( 'FFmpeg decoder could not be instantiated, decoding ' f'performance could be compromised:\n{exc}') self._source = load(file_name, decoder=decoder) self._player = Player() with warnings.catch_warnings(record=True): # deprecated eos_action self._player.queue(self._source) self._player._audio_player = None frame_rate = self.frame_rate if frame_rate is None: logger.warning('Frame rate could not be determined') frame_rate = 60. self._dt = 1. / frame_rate self._playing = False self._finished = False self._pos = pos self._units = units self._center = center self.set_scale(scale) # also calls set_pos self._visible = visible self._eos_fun = self._eos_new if _new_pyglet() else self._eos_old self._program = _create_program(ec, tex_vert, tex_frag) gl.glUseProgram(self._program) self._buffers = dict() for key in ('position', 'texcoord'): self._buffers[key] = gl.GLuint(0) gl.glGenBuffers(1, pointer(self._buffers[key])) w, h = self.source_width, self.source_height tex = np.array([(0, h), (w, h), (w, 0), (0, 0)], np.float32) gl.glBindBuffer(gl.GL_ARRAY_BUFFER, self._buffers['texcoord']) gl.glBufferData(gl.GL_ARRAY_BUFFER, tex.nbytes, tex.tobytes(), gl.GL_DYNAMIC_DRAW) gl.glBindBuffer(gl.GL_ARRAY_BUFFER, 0) gl.glUseProgram(0)