示例#1
0
    def active_uniforms(self):
        """Query OpenGL for a list of active uniforms.

        This is needed, because we are only allowed to set and query the
        values of active uniforms.

        """
        # Query number of active uniforms
        nr_uniforms = gl.GLint()
        gl.glGetProgramiv(self.handle, gl.GL_ACTIVE_UNIFORMS,
                          byref(nr_uniforms))
        nr_uniforms = nr_uniforms.value

        length = gl.GLsizei()
        size = gl.GLsizei()
        enum = gl.GLenum()
        name = create_string_buffer(self._ACTIVE_UNIFORM_MAX_LENGTH)

        uniforms = []
        for i in range(nr_uniforms):
            gl.glGetActiveUniform(self.handle, i, 20, byref(length), byref(size),
                                  byref(enum), name)
            uniforms.append(name.value)

        return uniforms
示例#2
0
def check_program(program):
    """check_program(program)

    Raises a RuntimeError if the program hasn't linked correctly."""

    # See if the program linkd correctly
    link_ok = gl.GLint(0)

    gl.glGetProgramiv(program, gl.GL_LINK_STATUS,
                      c.pointer(link_ok))

    # If linking fails, get the error description from OpenGL and raise
    # it
    if not link_ok:
        log_len = gl.GLint(0)

        gl.glGetProgramiv(program, gl.GL_INFO_LOG_LENGTH,
                          c.pointer(log_len))

        log_buf = c.create_string_buffer(log_len.value)

        gl.glGetProgramInfoLog(program, log_len, None, log_buf)

        raise RuntimeError(
            "Program %d could not link: %s" % (
                program, log_buf.value))
示例#3
0
    def __init__(self, *shaders: Shader):
        self.name = gl.glCreateProgram()
        for shader in shaders:
            gl.glAttachShader(self.name, shader.name)

        gl.glLinkProgram(self.name)
        success = gl.GLint(0)
        gl.glGetProgramiv(self.name, gl.GL_LINK_STATUS, byref(success))

        if not success:
            log_length = gl.GLint(0)
            gl.glGetProgramiv(self.name, gl.GL_INFO_LOG_LENGTH,
                              byref(log_length))
            log_buffer = create_string_buffer(log_length.value)
            gl.glGetProgramInfoLog(self.name, log_length.value, None,
                                   log_buffer)
            self.logger.error("Error linking program %s, error # %d",
                              self.name, success.value)
            self.logger.error("---Message---")
            for line in log_buffer.value.decode("ascii").splitlines():
                self.logger.error("Program: " + line)
            self.logger.error("------")
            raise RuntimeError("Linking program failed.")

        # free resources
        for shader in shaders:
            gl.glDeleteShader(shader.name)
示例#4
0
def get_uniform_data(program):
    """
    Args:
        program:

    Returns:

    """
    uniforms = {}

    count = pointer(GLint())
    buffer_size = GLsizei(32)
    length = GLsizei()
    size = GLint()
    data_type = GLenum()
    uniform_name = c_string('', size=buffer_size.value)

    glGetProgramiv(program, GL_ACTIVE_UNIFORMS, count)

    for i in range(count.contents.value):
        glGetActiveUniform(program, GLuint(i), buffer_size, length, size,
                           data_type, uniform_name)
        uniform_name_ = uniform_name.value.decode('utf-8')
        data_type_string = temp[data_type.value]
        uniforms[uniform_name_] = {
            'dtype': table[data_type_string]['dtype'],
            'index': i,
            'size': size.value,
            'value': None,
            'location': glGetUniformLocation(program, uniform_name),
            'function': table[data_type_string]['function'],
        }
        print(uniform_name_, uniforms[uniform_name_])
    return uniforms
示例#5
0
    def get_num_active(self, variable_type: gl.GLenum) -> int:
        """Get the number of active variables of the passed GL type.

        variable_type can be GL_ACTIVE_ATTRIBUTES, GL_ACTIVE_UNIFORMS, etc.
        """
        num_active = gl.GLint(0)
        gl.glGetProgramiv(self.prog_id, variable_type, byref(num_active))
        return num_active.value
示例#6
0
 def _get(self, paramId):
     outvalue = c_int(0)
     gl.glGetProgramiv(self.id, paramId, byref(outvalue))
     value = outvalue.value
     if value in shader_errors.keys():
         msg = '%s from glGetProgram(%s, %s, &value)'
         raise ValueError(msg % (shader_errors[value], self.id, paramId))
     return value
示例#7
0
 def _get(self, paramId):
     outvalue = c_int(0)
     gl.glGetProgramiv(self.id, paramId, byref(outvalue))
     value = outvalue.value
     if value in shader_errors.keys():
         msg = '%s from glGetProgram(%s, %s, &value)'
         raise ValueError(msg % (shader_errors[value], self.id, paramId))
     return value
示例#8
0
 def was_link_successful(self):
     status = c_int(0)
     glGetProgramiv(self.handle, GL_LINK_STATUS, byref(status))
     if not status:
         glGetProgramiv(self.handle, GL_INFO_LOG_LENGTH, byref(status))
         buffer = create_string_buffer(status.value)
         glGetProgramInfoLog(self.handle, status, None, buffer)
         self.log.error(f"{buffer.value}")
     return status
示例#9
0
def link_program(program):
    gl.glLinkProgram(program)

    length = gl.GLint(0)
    gl.glGetProgramiv(program, gl.GL_INFO_LOG_LENGTH, ctypes.byref(length))
    log_buffer = ctypes.create_string_buffer(length.value)
    gl.glGetProgramInfoLog(program, length, None, log_buffer)

    for line in log_buffer.value[:length.value].decode('ascii').splitlines():
        print('GLSL: ' + line)
示例#10
0
    def _introspect_uniform_blocks(self):
        active_uniform_blocks = gl.GLint(0)
        gl.glGetProgramiv(self._glo, gl.GL_ACTIVE_UNIFORM_BLOCKS,
                          byref(active_uniform_blocks))
        # print('GL_ACTIVE_UNIFORM_BLOCKS', active_uniform_blocks)

        for loc in range(active_uniform_blocks.value):
            index, size, name = self._query_uniform_block(loc)
            block = UniformBlock(self._glo, index, size, name)
            self._uniforms[name] = block
示例#11
0
def link_program(program):
    ''' link a glsl program and print error messages.'''
    gl.glLinkProgram(program)

    length = gl.GLint(0)
    gl.glGetProgramiv(program, gl.GL_INFO_LOG_LENGTH, ctypes.byref(length))
    log_buffer = ctypes.create_string_buffer(length.value)
    gl.glGetProgramInfoLog(program, length, None, log_buffer)

    for line in log_buffer.value[:length.value].decode('ascii').splitlines():
        print('GLSL: ' + line)
示例#12
0
    def link(self):
        """link the program"""
        gl.glLinkProgram(self.id)

        # Check if linking was successful.  If not, print the log.
        link_status = c_int(0)
        gl.glGetProgramiv(self.id, gl.GL_LINK_STATUS, byref(link_status))
        if not link_status:
            gl.glGetProgramiv(self.id, gl.GL_INFO_LOG_LENGTH, byref(link_status))  # retrieve the log length
            buffer = create_string_buffer(link_status.value)  # create a buffer for the log
            gl.glGetProgramInfoLog(self.id, link_status, None, buffer)  # retrieve the log text
            print(buffer.value)  # print the log to the console
示例#13
0
    def print_error(message):
        nonlocal error
        error = True

        status = GLint()
        glGetProgramiv(program, GL_INFO_LOG_LENGTH, byref(
            status))  # Getting the number of char in info log to 'status'

        output = create_string_buffer(status.value)  # status.value)
        glGetProgramInfoLog(program, status, None, output)

        print(message, output.value.decode('utf-8'), file=sys.stderr)
示例#14
0
 def link(glo):
     """Link a shader program"""
     gl.glLinkProgram(glo)
     status = c_int()
     gl.glGetProgramiv(glo, gl.GL_LINK_STATUS, status)
     if not status.value:
         length = c_int()
         gl.glGetProgramiv(glo, gl.GL_INFO_LOG_LENGTH, length)
         log = c_buffer(length.value)
         gl.glGetProgramInfoLog(glo, len(log), None, log)
         raise ShaderException("Program link error: {}".format(
             log.value.decode()))
示例#15
0
 def link(self):
     if self._shaders_empty:
         raise RuntimeError("No shaders attached to program")
     gl.glLinkProgram(self.gl_id)
     rc = gl.GLint(0)
     gl.glGetProgramiv(self.gl_id, gl.GL_LINK_STATUS, ctypes.byref(rc))
     if not rc:
         gl.glGetProgramiv(self.gl_id, gl.GL_INFO_LOG_LENGTH,
                           ctypes.byref(rc))
         buffer = ctypes.create_string_buffer(rc.value)
         gl.glGetProgramInfoLog(self.gl_id, rc, None, buffer)
         raise GLObjectException(buffer.value.decode())
     else:
         self._done_link = True
示例#16
0
    def link(self):
        gl.glLinkProgram(self.__value)

        err_status = ct.c_int()
        gl.glGetProgramiv(self.__value, gl.GL_LINK_STATUS, ct.byref(err_status))
        if err_status.value != gl.GL_TRUE:
            log_length = ct.c_int()
            gl.glGetProgramiv(self.__value, gl.GL_INFO_LOG_LENGTH, ct.byref(log_length))

            log_buf = (ct.c_char * (log_length.value))()
            log_buf_ptr = ct.cast(ct.pointer(log_buf), ct.c_char_p)
            gl.glGetProgramInfoLog(self.__value, log_length.value, None, log_buf_ptr)

            raise GLException("Program failed to link:\n%s" % log_buf.value)
示例#17
0
    def link(self):
        """link the program"""
        gl.glLinkProgram(self.id)

        # Check if linking was successful.  If not, print the log.
        link_status = c_int(0)
        gl.glGetProgramiv(self.id, gl.GL_LINK_STATUS, byref(link_status))
        if not link_status:
            gl.glGetProgramiv(self.id, gl.GL_INFO_LOG_LENGTH,
                              byref(link_status))  # retrieve the log length
            buffer = create_string_buffer(
                link_status.value)  # create a buffer for the log
            gl.glGetProgramInfoLog(self.id, link_status, None,
                                   buffer)  # retrieve the log text
            print(buffer.value)  # print the log to the console
示例#18
0
    def link(self):
        gl.glLinkProgram(self.handle)

        # Retrieve the link status
        status = c_int(0)
        gl.glGetProgramiv(self.handle, gl.GL_LINK_STATUS, byref(status))

        # If linking failed, get log and abort.
        if not status:
            #Retrieve the log and pass it up with an exception.
            gl.glGetProgramiv(self.handle, gl.GL_INFO_LOG_LENGTH,
                              byref(status))
            log = create_string_buffer(status.value)
            gl.glGetProgramInfoLog(self.handle, status, None, log)

            raise Exception("Linking shaders failed {0}".format(log.value))
        else:
            self.linked = True
示例#19
0
 def link(self):
     # link the program
     glLinkProgram(self.handle)
     temp = c_int(0)
     # retrieve the link status
     glGetProgramiv(self.handle, GL_LINK_STATUS, byref(temp))
     # if linking failed, print the log
     if not temp:
         # retrieve the log length
         glGetProgramiv(self.handle, GL_INFO_LOG_LENGTH, byref(temp))
         # create a buffer for the log
         buffer = create_string_buffer(temp.value)
         # retrieve the log text
         glGetProgramInfoLog(self.handle, temp, None, buffer)
         # print the log to the console
         self.log.error(f"{buffer.value}")
     else:
         # all is well, so we are linked
         self.linked = True
示例#20
0
def program_status(program: GLuint, status_type: int) -> int:
    """

    Args:
        program:      The handle to the program.
        status_type:  GL_DELETE_STATUS, GL_LINK_STATUS, GL_VALIDATE_STATUS, GL_INFO_LOG_LENGTH, GL_ATTACHED_SHADERS,
                      GL_ACTIVE_ATOMIC_COUNTER_BUFFERS, GL_ACTIVE_ATTRIBUTES, GL_ACTIVE_ATTRIBUTE_MAX_LENGTH,
                      GL_ACTIVE_UNIFORMS, GL_ACTIVE_UNIFORM_BLOCKS, GL_ACTIVE_UNIFORM_BLOCK_MAX_NAME_LENGTH,
                      GL_ACTIVE_UNIFORM_MAX_LENGTH, GL_COMPUTE_WORK_GROUP_SIZE GL_PROGRAM_BINARY_LENGTH,
                      GL_TRANSFORM_FEEDBACK_BUFFER_MODE, GL_TRANSFORM_FEEDBACK_VARYINGS,
                      GL_TRANSFORM_FEEDBACK_VARYING_MAX_LENGTH, GL_GEOMETRY_VERTICES_OUT, GL_GEOMETRY_INPUT_TYPE,
                      GL_GEOMETRY_OUTPUT_TYPE.

    Returns:
        Status code.
    """
    status = GLint()
    glGetProgramiv(program, status_type, byref(status))
    return status.value
示例#21
0
    def _introspect_attributes(self):
        """Introspect and store detailed info about an attribute"""
        # TODO: Ensure gl_* attributes are ignored
        num_attrs = gl.GLint()
        gl.glGetProgramiv(self._glo, gl.GL_ACTIVE_ATTRIBUTES, num_attrs)
        num_varyings = gl.GLint()
        gl.glGetProgramiv(self._glo, gl.GL_TRANSFORM_FEEDBACK_VARYINGS,
                          num_varyings)
        # print(f"attrs {num_attrs.value} varyings={num_varyings.value}")

        for i in range(num_attrs.value):
            c_name = create_string_buffer(256)
            c_size = gl.GLint()
            c_type = gl.GLenum()
            gl.glGetActiveAttrib(
                self._glo,  # program to query
                i,  # index (not the same as location)
                256,  # max attr name size
                None,  # c_length,  # length of name
                c_size,  # size of attribute (array or not)
                c_type,  # attribute type (enum)
                c_name,  # name buffer
            )

            # Get the actual location. Do not trust the original order
            location = gl.glGetAttribLocation(self._glo, c_name)

            # print(c_name.value, c_size, c_type)
            type_info = GLTypes.get(c_type.value)
            # print(type_info)
            self._attributes.append(
                AttribFormat(
                    c_name.value.decode(),
                    type_info.gl_type,
                    type_info.components,
                    type_info.gl_size,
                    location=location,
                ))

        # The attribute key is used to cache VertexArrays
        self.attribute_key = ":".join(
            f"{attr.name}[{attr.gl_type}/{attr.components}]"
            for attr in self._attributes)
示例#22
0
    def link(self):
        """Main steps to link the program:
        1. glLinkProgram:
                linke the shaders in the program to create an executable
        2. glGetProgramiv:
                retrieve the link status
        3. glGetProgramInfoLog:
                print the error log if link failed
        """
        gl.glLinkProgram(self.program)

        link_status = gl.GLint(0)
        gl.glGetProgramiv(self.program, gl.GL_LINK_STATUS, ct.byref(link_status))

        if not link_status:
            info_length = gl.GLint(0)
            gl.glGetProgramiv(self.program, gl.GL_INFO_LOG_LENGTH, ct.byref(info_length))
            error_info = ct.create_string_buffer(info_length.value)
            gl.glGetProgramInfoLog(self.program, info_length, None, error_info)
            print(error_info.value)
示例#23
0
    def link(self):
        """link the program, making it the active shader.

        .. note:: Shader.bind() is preferred here, because link() Requires the Shader to be compiled already.
        """
        gl.glLinkProgram(self.id)

        # Check if linking was successful.  If not, print the log.
        link_status = c_int(0)
        gl.glGetProgramiv(self.id, gl.GL_LINK_STATUS, byref(link_status))
        if not link_status:
            gl.glGetProgramiv(self.id, gl.GL_INFO_LOG_LENGTH,
                              byref(link_status))  # retrieve the log length
            buffer = create_string_buffer(
                link_status.value)  # create a buffer for the log
            gl.glGetProgramInfoLog(self.id, link_status, None,
                                   buffer)  # retrieve the log text
            print(buffer.value)  # print the log to the console

        self.is_linked = True
示例#24
0
def link_program(program_name):
    '''
    link a glsl program and print error messages.
    '''
    gl.glLinkProgram(program_name)

    success = gl.GLint(0)
    gl.glGetProgramiv(program_name, gl.GL_LINK_STATUS, ctypes.byref(success))

    length = gl.GLint(0)
    gl.glGetProgramiv(program_name, gl.GL_INFO_LOG_LENGTH,
                      ctypes.byref(length))
    log_buffer = ctypes.create_string_buffer(length.value)
    gl.glGetProgramInfoLog(program_name, length, None, log_buffer)

    log_message = log_buffer.value[:length.value].decode('ascii').strip()
    if log_message:
        sys.stderr.write(log_message + '\n')

    if not success:
        raise ValueError('Linking of the shader program failed.')
示例#25
0
    def link(self):
        # link the program
        glLinkProgram(self.handle)

        temp = c_int(0)
        # retrieve the link status
        glGetProgramiv(self.handle, GL_LINK_STATUS, byref(temp))

        # if linking failed, print the log
        if not temp:
            # retrieve the log length
            glGetProgramiv(self.handle, GL_INFO_LOG_LENGTH, byref(temp))
            # create a buffer for the log
            buffer = create_string_buffer(temp.value)
            # retrieve the log text
            glGetProgramInfoLog(self.handle, temp, None, buffer)
            # print the log to the console
            print(buffer.value)
        else:
            # all is well, so we are linked
            self.linked = True
示例#26
0
    def link(self):
        """
        Main steps to link the program:
        1. glLinkProgram:
                linke the shaders in the program to create an executable
        2. glGetProgramiv:
                retrieve the link status
        3. glGetProgramInfoLog:
                print the error log if link failed
        """
        gl.glLinkProgram(self.program)

        link_status = gl.GLint(0)
        gl.glGetProgramiv(self.program, gl.GL_LINK_STATUS, ct.byref(link_status))

        if not link_status:
            info_length = gl.GLint(0)
            gl.glGetProgramiv(self.program, gl.GL_INFO_LOG_LENGTH, ct.byref(info_length))
            error_info = ct.create_string_buffer(info_length.value)
            gl.glGetProgramInfoLog(self.program, info_length, None, error_info)
            print(error_info.value)
示例#27
0
    def _link(self):
        for shader in self:
            gl.glAttachShader(self.handle, shader.handle);

        # link the program
        gl.glLinkProgram(self.handle)

        temp = c_int(0)
        # retrieve the link status
        gl.glGetProgramiv(self.handle, gl.GL_LINK_STATUS, byref(temp))

        # if linking failed, print the log
        if not temp:
            #       retrieve the log length
            gl.glGetProgramiv(self.handle, gl.GL_INFO_LOG_LENGTH, byref(temp))
            # create a buffer for the log
            buffer = create_string_buffer(temp.value)
            # retrieve the log text
            gl.glGetProgramInfoLog(self.handle, temp, None, buffer)
            # print the log to the console
            raise GLSLError(buffer.value)

        # Query maximum uniform name length
        AUL = gl.GLint()
        gl.glGetProgramiv(self.handle, gl.GL_ACTIVE_UNIFORM_MAX_LENGTH,
                          byref(AUL))
        self._ACTIVE_UNIFORM_MAX_LENGTH = AUL.value

        self._update_uniform_types()
示例#28
0
    def _introspect_uniforms(self):
        """Figure out what uniforms are available and build an internal map"""
        # Number of active uniforms in the program
        active_uniforms = gl.GLint(0)
        gl.glGetProgramiv(self._glo, gl.GL_ACTIVE_UNIFORMS,
                          byref(active_uniforms))

        # Loop all the active uniforms
        for index in range(active_uniforms.value):
            # Query uniform information like name, type, size etc.
            u_name, u_type, u_size = self._query_uniform(index)
            u_location = gl.glGetUniformLocation(self._glo, u_name.encode())

            # Skip uniforms that may be in Uniform Blocks
            # TODO: We should handle all uniforms
            if u_location == -1:
                # print(f"Uniform {u_location} {u_name} {u_size} {u_type} skipped")
                continue

            u_name = u_name.replace("[0]", "")  # Remove array suffix
            self._uniforms[u_name] = Uniform(self._glo, u_location, u_name,
                                             u_type, u_size)
示例#29
0
    def __init__(self, *shaders):
        pid = False
        try:
            pid = glCreateProgramObjectARB()
        except GLException:
            raise ShaderError("Can't create program object!")

        for s in shaders:
            glAttachObjectARB(pid, s.sid)

        glLinkProgram(pid)

        v = GLint(0)
        glGetProgramiv(pid, GL_LINK_STATUS, byref(v))
        if not v:
            log = _get_infolog(pid)
            e = ShaderError("Error linking program!")
            e.infolog = log
            raise e

        self.pid = pid

        self.uniform = _UniformAccesser(self)
        self.attrib = _AttributeAccesser(self)
示例#30
0
    def __init__(self, *shaders):
        pid = False
        try:
            pid = glCreateProgramObjectARB()
        except GLException:
            raise ShaderError("Can't create program object!")

        for s in shaders:
            glAttachObjectARB(pid, s.sid)

        glLinkProgram(pid)

        v = GLint(0)
        glGetProgramiv(pid, GL_LINK_STATUS, byref(v))
        if not v:
            log = _get_infolog(pid)
            e = ShaderError("Error linking program!")
            e.infolog = log
            raise e

        self.pid = pid

        self.uniform = _UniformAccesser(self)
        self.attrib = _AttributeAccesser(self)
示例#31
0
    def __init__(
        self,
        ctx: "Context",
        *,
        vertex_shader: str,
        fragment_shader: str = None,
        geometry_shader: str = None,
        tess_control_shader: str = None,
        tess_evaluation_shader: str = None,
        out_attributes: List[str] = None,
    ):
        """Create a Program.

        :param Context ctx: The context this program belongs to
        :param str vertex_shader: vertex shader source
        :param str fragment_shader: fragment shader source
        :param str geometry_shader: geometry shader source
        :param str tess_control_shader: tessellation control shader source
        :param str tess_evaluation_shader: tessellation evaluation shader source
        :param List[str] out_attributes: List of out attributes used in transform feedback.
        """
        self._ctx = ctx
        self._glo = glo = gl.glCreateProgram()
        self._out_attributes = out_attributes or []
        self._geometry_info = (0, 0, 0)
        self._attributes = []  # type: List[AttribFormat]
        #: Internal cache key used with vertex arrays
        self.attribute_key = "INVALID"  # type: str
        self._uniforms: Dict[str, Uniform] = {}

        shaders = [(vertex_shader, gl.GL_VERTEX_SHADER)]
        if fragment_shader:
            shaders.append((fragment_shader, gl.GL_FRAGMENT_SHADER))
        if geometry_shader:
            shaders.append((geometry_shader, gl.GL_GEOMETRY_SHADER))
        if tess_control_shader:
            shaders.append((tess_control_shader, gl.GL_TESS_CONTROL_SHADER))
        if tess_evaluation_shader:
            shaders.append(
                (tess_evaluation_shader, gl.GL_TESS_EVALUATION_SHADER))

        shaders_id = []
        for shader_code, shader_type in shaders:
            shader = Program.compile_shader(shader_code, shader_type)
            gl.glAttachShader(self._glo, shader)
            shaders_id.append(shader)

        # For now we assume varyings can be set up if no fragment shader
        if not fragment_shader:
            self._setup_out_attributes()

        Program.link(self._glo)
        if geometry_shader:
            geometry_in = gl.GLint()
            geometry_out = gl.GLint()
            geometry_vertices = gl.GLint()
            gl.glGetProgramiv(self._glo, gl.GL_GEOMETRY_INPUT_TYPE,
                              geometry_in)
            gl.glGetProgramiv(self._glo, gl.GL_GEOMETRY_OUTPUT_TYPE,
                              geometry_out)
            gl.glGetProgramiv(self._glo, gl.GL_GEOMETRY_VERTICES_OUT,
                              geometry_vertices)
            self._geometry_info = (
                geometry_in.value,
                geometry_out.value,
                geometry_vertices.value,
            )

        # Flag shaders for deletion. Will only be deleted once detached from program.
        for shader in shaders_id:
            gl.glDeleteShader(shader)

        # Handle uniforms
        self._introspect_attributes()
        self._introspect_uniforms()
        self._introspect_uniform_blocks()

        self.ctx.stats.incr("program")
        weakref.finalize(self, Program._delete, self.ctx, shaders_id, glo)
示例#32
0
文件: shader.py 项目: Knio/miru
 def validate(self):
     gl.glValidateProgram(self.program_no)
     self.validation_status = gl.GLint()
     gl.glGetProgramiv(self.program_no, gl.GL_VALIDATE_STATUS, self.validation_status)
     if not self.validation_status:
         raise gl.GLSLException(_infolog(self.program_no, log_type="program"))
示例#33
0
    def create(cls, vertex_source, fragment_source, attributes, uniforms):
        number_of_string = 1

        # Create vertex shader.
        vertex_handle = glCreateShader(GL_VERTEX_SHADER)
        glShaderSource(vertex_handle, number_of_string,
                       c_pointer_to_char_pointers(vertex_source), None)
        glCompileShader(vertex_handle)

        # Create fragment shader.
        fragment_handle = glCreateShader(GL_FRAGMENT_SHADER)
        glShaderSource(fragment_handle, number_of_string,
                       c_pointer_to_char_pointers(fragment_source), None)
        glCompileShader(fragment_handle)

        # Create attributes.
        attribute_mapping = []
        for attribute in attributes:
            attribute_mapping.append(c_string(attribute))

        try:
            # Create program.
            program_handle = glCreateProgram()

            glAttachShader(program_handle, vertex_handle)
            glAttachShader(program_handle, fragment_handle)

            for index, name in enumerate(attribute_mapping):
                glBindAttribLocation(program_handle, index, name)

            glLinkProgram(program_handle)
            glValidateProgram(program_handle)
            glUseProgram(program_handle)

        except GLException as error:
            # Print vertex shader errors.
            status = GLint()
            glGetShaderiv(vertex_handle, GL_INFO_LOG_LENGTH, byref(status))
            output = create_string_buffer(status.value)
            glGetShaderInfoLog(vertex_handle, status, None, output)
            print(output.value.decode('utf-8'))

            # Print fragment shader errors.
            status = GLint()
            glGetShaderiv(fragment_handle, GL_INFO_LOG_LENGTH, byref(status))
            output = create_string_buffer(status.value)
            glGetShaderInfoLog(fragment_handle, status, None, output)
            print(output.value.decode('utf-8'))

            # Print program errors.
            status = GLint()
            glGetProgramiv(program_handle, GL_INFO_LOG_LENGTH, byref(
                status))  # Getting the number of char in info log to 'status'
            output = create_string_buffer(status.value)  # status.value)
            glGetProgramInfoLog(program_handle, status, None, output)
            print(output.value.decode('utf-8'))

            raise error

        # Get uniform location.
        uniform_mapping = {}
        for uniform in uniforms:
            name = c_string(uniform)
            location = glGetUniformLocation(
                program_handle, cast(pointer(name), POINTER(c_char)))
            uniform_mapping[uniform] = location

        return cls(program_handle, uniform_mapping)
示例#34
0
文件: shader.py 项目: Knio/miru
 def link(self):
     gl.glLinkProgram(self.program_no)
     gl.glGetProgramiv(self.program_no, gl.GL_LINK_STATUS, self.link_status)
     if not self.link_status:
         raise gl.GLSLException(_infolog(self.program_no, log_type="program"))
示例#35
0
    def __init__(self, shaders, attributes, uniforms):
        # Create vertex shader.
        vertex_shader = shaders[0]
        vertex_handle = glCreateShader(GL_VERTEX_SHADER)
        glShaderSource(vertex_handle, 1, c_string_array(vertex_shader), None)
        glCompileShader(vertex_handle)

        # Create fragment shader.
        fragment_shader = shaders[1]
        fragment_handle = glCreateShader(GL_FRAGMENT_SHADER)
        glShaderSource(fragment_handle, 1, c_string_array(fragment_shader),
                       None)
        glCompileShader(fragment_handle)

        try:
            # Create program.
            program_handle = glCreateProgram()

            # Attach shaders
            glAttachShader(program_handle, vertex_handle)
            glAttachShader(program_handle, fragment_handle)

            # Bind attributes.
            for index, name in enumerate(attributes):
                glBindAttribLocation(program_handle, index, c_string(name))

            # Link, validate and use.
            glLinkProgram(program_handle)
            glValidateProgram(program_handle)
            glUseProgram(program_handle)

        except GLException:
            # Print errors.
            status = GLint()
            glGetShaderiv(vertex_handle, GL_INFO_LOG_LENGTH, byref(status))
            output = create_string_buffer(status.value)
            glGetShaderInfoLog(vertex_handle, status, None, output)
            print(output.value.decode('utf-8'))

            status = GLint()
            glGetShaderiv(fragment_handle, GL_INFO_LOG_LENGTH, byref(status))
            output = create_string_buffer(status.value)
            glGetShaderInfoLog(fragment_handle, status, None, output)
            print(output.value.decode('utf-8'))

            status = GLint()
            glGetProgramiv(program_handle, GL_INFO_LOG_LENGTH, byref(
                status))  # Getting the number of char in info log to 'status'
            output = create_string_buffer(status.value)  # status.value)
            glGetProgramInfoLog(program_handle, status, None, output)
            print(output.value.decode('utf-8'))

        # Query uniform data.
        active_uniforms = GLint()
        glGetProgramiv(program_handle, GL_ACTIVE_UNIFORMS, active_uniforms)

        buffer_size = GLsizei(255)
        data_type = GLenum(0)

        string_buffer = create_string_buffer(buffer_size.value)
        name = c_char_p(addressof(string_buffer))

        uniform_mapping = {}
        for index in range(active_uniforms.value):
            glGetActiveUniform(program_handle, index, buffer_size, None, None,
                               byref(data_type), name)
            if name.value in uniforms:
                location = glGetUniformLocation(
                    program_handle, cast(pointer(name), POINTER(GLchar)))
                uniform = Uniform(name.value, location, data_type.value)
                uniform_mapping[name.value] = uniform

        self.id = GLuint(program_handle)
        self.uniforms = uniform_mapping
        self.attributes = attributes
示例#36
0
 def __get__(self, instance, cls):
     glGetProgramiv(instance.pid, self.pname, byref(self.buffer))
     return self.buffer.value
示例#37
0
 def linked(self):
     temp = c_int(0)
     # retrieve the link status
     gl.glGetProgramiv(self.handle, gl.GL_LINK_STATUS, byref(temp))
     return bool(temp)
示例#38
0
    def __init__(self, shaders, attributes, uniforms):
        vertex_shader = shaders[0]
        fragment_shader = shaders[1]

        vertex_handle = glCreateShader(GL_VERTEX_SHADER)
        glShaderSource(
            vertex_handle, 1,
            cast(pointer(pointer(create_string_buffer(vertex_shader))),
                 POINTER(POINTER(GLchar))), None)
        glCompileShader(vertex_handle)

        fragment_handle = glCreateShader(GL_FRAGMENT_SHADER)
        glShaderSource(
            fragment_handle, 1,
            cast(pointer(pointer(create_string_buffer(fragment_shader))),
                 POINTER(POINTER(GLchar))), None)
        glCompileShader(fragment_handle)

        # Create attributes.
        attribute_mapping = []
        for attribute in attributes:
            attribute_mapping.append(create_string_buffer(attribute))

        try:
            # Create program.
            program_handle = glCreateProgram()

            glAttachShader(program_handle, vertex_handle)
            glAttachShader(program_handle, fragment_handle)

            for index, name in enumerate(attributes):  # CHANGED
                glBindAttribLocation(program_handle, index, name)

            glLinkProgram(program_handle)
            glValidateProgram(program_handle)
            glUseProgram(program_handle)

        except GLException:
            # Print errors.
            status = GLint()
            glGetShaderiv(vertex_handle, GL_INFO_LOG_LENGTH, byref(status))
            output = create_string_buffer(status.value)
            glGetShaderInfoLog(vertex_handle, status, None, output)
            print(output.value.decode('utf-8'))

            status = GLint()
            glGetShaderiv(fragment_handle, GL_INFO_LOG_LENGTH, byref(status))
            output = create_string_buffer(status.value)
            glGetShaderInfoLog(fragment_handle, status, None, output)
            print(output.value.decode('utf-8'))

            status = GLint()
            glGetProgramiv(program_handle, GL_INFO_LOG_LENGTH, byref(
                status))  # Getting the number of char in info log to 'status'
            output = create_string_buffer(status.value)  # status.value)
            glGetProgramInfoLog(program_handle, status, None, output)
            print(output.value.decode('utf-8'))

        # # Get uniform location.
        # uniform_mapping = {}
        # for uniform in uniforms:
        #     name = create_string_buffer(uniform)
        #     location = glGetUniformLocation(program_handle, cast(pointer(name), POINTER(GLchar)))
        #     uniform_mapping[uniform] = location

        active_shaders = GLint()
        glGetProgramiv(program_handle, GL_ACTIVE_UNIFORMS, active_shaders)

        buffer_size = GLsizei(255)
        data_type = GLenum(0)

        string_buffer = create_string_buffer(buffer_size.value)
        name = c_char_p(addressof(string_buffer))

        uniform_mapping = {}
        for index in range(active_shaders.value):
            glGetActiveUniform(program_handle, index, buffer_size, None, None,
                               byref(data_type), name)
            if name.value in uniforms:
                location = glGetUniformLocation(
                    program_handle, cast(pointer(name), POINTER(GLchar)))
                uniform = Uniform(name.value, location, data_type.value)
                uniform_mapping[name.value] = uniform

        super().__init__(program_handle)
        self.uniforms = uniform_mapping
        self.attributes = attribute_mapping