def __setitem__(self, key, value): if not isinstance(key, int) and not isinstance(key, slice): raise KeyError('Key must be an integer or a slice, got {}'.format( type(key).__qualname__)) if self.mapinfo is not None: return self.__setitem_mapped(self, key, value) self.bind() blen = len(self) if isinstance(key, int): key = eval_index(key, blen) buf = self.format.pack((value, )) buf_size = sizeof(buf) glBufferSubData(self.target, key * buf_size, buf_size, byref(buf)) else: if key.step is not None and key.step not in (1, -1): raise NotImplementedError( 'Unmapped buffer write do not support steps different than 1.' ) if key.step == -1: value = list(reversed(value)) start, stop, step = eval_slice(key, blen) if stop - start != len(value): raise ValueError("Buffer do not support resizing") buf = self.format.pack(value) buf_size = sizeof(self.format.struct) * (stop - start) buf_offset = start * sizeof(self.format.struct) glBufferSubData(self.target, buf_offset, buf_size, byref(buf))
def data(self, buffer_type, data, offset): if buffer_type != "texture": gl.glBindBuffer(gl.GL_ARRAY_BUFFER, self.buffers[buffer_type]) if buffer_type == "color": offset *= 16 else: offset *= 12 gl_data = to_gl_float(data) length = len(data) * 4 gl.glBufferSubData(gl.GL_ARRAY_BUFFER, offset, length, gl_data) if buffer_type == "vertex": self.vertex_count += int(len(data) / 3) else: self.buffers["texture"] = gl.GLuint(0) gl.glGenTextures(1, self.buffers["texture"]) gl.glBindTexture(data.target, data.id) gl.glTexParameterf(gl.GL_TEXTURE_2D, gl.GL_TEXTURE_MAG_FILTER, gl.GL_NEAREST) gl.glTexParameterf(gl.GL_TEXTURE_2D, gl.GL_TEXTURE_MIN_FILTER, gl.GL_NEAREST) gl.glTexImage2D(gl.GL_TEXTURE_2D, 0, gl.GL_RGB, texture.width, texture.height, 0, gl.GL_RGB, gl.GL_UNSIGNED_BYTE, texture_data)
def __setitem__(self, key, value): with self.bound: sz = len(self) if isinstance(key, slice): start = int(key.start) if key.start is not None else 0 stop = int(key.stop) if key.stop is not None else start + value.size else: start = int(key) stop = start + 1 if start < 0 or stop < 0 or start >= stop: raise IndexError if stop > sz: newsz = max(sz * 2, stop) a = numpy.empty((newsz,), dtype=self.dtype) # intel dies when querying an empty buffer :[ if sz > 0: gl.glGetBufferSubData(gl.GL_ARRAY_BUFFER, 0, sz * self.dtype.itemsize, a.ctypes.data) b = numpy.asarray(value).reshape(-1) a[start:stop] = b gl.glBufferData(gl.GL_ARRAY_BUFFER, newsz * self.dtype.itemsize, a.ctypes.data, self.usage) else: a = numpy.ascontiguousarray(value, self.dtype).reshape(-1) sz = min((stop - start), len(a)) gl.glBufferSubData(gl.GL_ARRAY_BUFFER, start * self.dtype.itemsize, sz * self.dtype.itemsize, a.ctypes.data)
def __setitem__(self, key, value): if not isinstance(key, int) and not isinstance(key, slice): raise KeyError('Key must be an integer or a slice, got {}'.format(type(key).__qualname__)) if self.mapinfo is not None: return self.__setitem_mapped(self, key, value) self.bind() blen = len(self) if isinstance(key, int): key = eval_index(key, blen) buf = self.format.pack((value,)) buf_size = sizeof(buf) glBufferSubData(self.target, key*buf_size, buf_size, byref(buf)) else: if key.step is not None and key.step not in (1, -1): raise NotImplementedError('Unmapped buffer write do not support steps different than 1.') if key.step == -1: value = list(reversed(value)) start, stop, step = eval_slice(key, blen) if stop-start != len(value): raise ValueError("Buffer do not support resizing") buf = self.format.pack(value) buf_size = sizeof(self.format.struct) * (stop-start) buf_offset = start * sizeof(self.format.struct) glBufferSubData(self.target, buf_offset, buf_size, byref(buf))
def write(self, data: Any, offset: int = 0): """Write byte data to the buffer. :param bytes data: The byte data to write. This can be bytes or any object supporting the buffer protocol. :param int offset: The byte offset """ gl.glBindBuffer(gl.GL_ARRAY_BUFFER, self._glo) size, data = data_to_ctypes(data) gl.glBufferSubData(gl.GL_ARRAY_BUFFER, gl.GLintptr(offset), size, data)
def update(self, visible: ChunkList): chunks = self.edge_chunks * self.edge_chunks num_chunks = len(visible) gl.glBindBuffer(gl.GL_ARRAY_BUFFER, self.offsets) if num_chunks > chunks: self.edge_chunks += 1 print(f"Growing the chunk buffer to {self.edge_chunks}") chunks = self.edge_chunks * self.edge_chunks gl.glBufferData(gl.GL_ARRAY_BUFFER, 2 * chunks * sizeof(gl.GLfloat), None, gl.GL_DYNAMIC_DRAW) chunk_offsets = (gl.GLfloat * (chunks * 2))() for i, chunk in enumerate(visible): chunk_offsets[i * 2:i * 2 + 2] = chunk.x, chunk.y self.stored_chunks.append(chunk.id) gl.glBufferSubData(gl.GL_ARRAY_BUFFER, 0, sizeof(chunk_offsets), chunk_offsets) self.instances = num_chunks
def send_mesh_data_to_gpu(self): # pass mesh data to gpu if not self.mesh_quad_count: return gl.glBindVertexArray(self.vao) gl.glBindBuffer(gl.GL_ARRAY_BUFFER, self.vbo) gl.glBufferData(gl.GL_ARRAY_BUFFER, # Orphaning ctypes.sizeof(gl.GLfloat * CHUNK_WIDTH * CHUNK_HEIGHT * CHUNK_LENGTH * 7), None, gl.GL_DYNAMIC_DRAW ) gl.glBufferSubData( gl.GL_ARRAY_BUFFER, 0, ctypes.sizeof(gl.GLfloat * len(self.mesh)), (gl.GLfloat * len(self.mesh)) (*self.mesh) ) gl.glBufferSubData( gl.GL_ARRAY_BUFFER, ctypes.sizeof(gl.GLfloat * len(self.mesh)), ctypes.sizeof(gl.GLfloat * len(self.translucent_mesh)), (gl.GLfloat * len(self.translucent_mesh)) (*self.translucent_mesh) ) if not self.world.options.INDIRECT_RENDERING: return self.draw_commands = [ # Index Count Instance Count Base Index Base Vertex Base Instance self.mesh_quad_count * 6, 1, 0, 0, 0, # Opaque mesh commands self.translucent_quad_count * 6, 1, 0, self.mesh_quad_count * 4, 0 # Translucent mesh commands ] gl.glBindBuffer(gl.GL_DRAW_INDIRECT_BUFFER, self.indirect_command_buffer) gl.glBufferSubData( gl.GL_DRAW_INDIRECT_BUFFER, 0, ctypes.sizeof(gl.GLuint * len(self.draw_commands)), (gl.GLuint * len(self.draw_commands)) (*self.draw_commands) )
def write(self, data: bytes, offset: int = 0): gl.glBindBuffer(gl.GL_ARRAY_BUFFER, self.buffer_id) gl.glBufferSubData(gl.GL_ARRAY_BUFFER, gl.GLintptr(offset), len(data), data)
def _buffer_subdata(self): with self: gl.glBufferSubData(self.target, 0, 4 * self.data.size, vec(self.data.ravel()))