Can global variables be used in a glfw callback function to modify global state?

Advertisements

I am trying to use a global variable named mouse_button_was_pressed to track whether I should check for intersections with a button object (yet to be implemented) and am running into an issue where the global variable is not being modified by the glfw button callback function I set up. I can tell the callback is being called when I click, because the print statement works, but the main function does not see the update to the global variable.

callbacks.py

import glfw

def mouse_button_callback(window, button, action, mod):

    global mouse_button_was_pressed
    
    if (button == glfw.MOUSE_BUTTON_LEFT and action == glfw.PRESS):
        
        #print("PRESSED!")
        
        mouse_button_was_pressed = True

main.py

# -----------------------------------------------------------------------------
# Package imports
# -----------------------------------------------------------------------------

from OpenGL import GL as gl
import glfw
import numpy as np

# -----------------------------------------------------------------------------
# Local imports
# -----------------------------------------------------------------------------

import window_setup
import framerate_counter
import shaders
import Button
import pixels_to_screen_coords
import callbacks

# -----------------------------------------------------------------------------
# Main function
# -----------------------------------------------------------------------------

def main():
    
    # -------------------------------------------------------------------------
    # Window setup / callback functions
    # -------------------------------------------------------------------------
    
    window = window_setup.setup()
    gl.glEnable(gl.GL_DEPTH_TEST)
    
    global mouse_button_was_pressed
    mouse_button_was_pressed = False
    glfw.set_mouse_button_callback(window, callbacks.mouse_button_callback)
    
    # -------------------------------------------------------------------------
    # Frame counter
    # -------------------------------------------------------------------------
    
    frame_counter = framerate_counter.FrameCounter()
    
    # -------------------------------------------------------------------------
    # Shader setup/activation
    # -------------------------------------------------------------------------
    
    shader_program = shaders.compile_shader_program()
    gl.glUseProgram(shader_program)
    
    # -------------------------------------------------------------------------
    # Buffer Objects setup
    # -------------------------------------------------------------------------
    
    button = Button.Button(-1, 1, 1, 1)
    
    vao = gl.glGenVertexArrays(1)
    gl.glBindVertexArray(vao)
    
    vbo = gl.glGenBuffers(1)
    gl.glBindBuffer(gl.GL_ARRAY_BUFFER, vbo)
    gl.glBufferData(
        gl.GL_ARRAY_BUFFER, 
        len(button.vertices)*4, 
        np.array(button.vertices, dtype=np.float32), 
        gl.GL_STATIC_DRAW
    )
    gl.glVertexAttribPointer(
        0,              # Attribute location
        3,              # Number of elements in attribute (number of verts, etc.)
        gl.GL_FLOAT,    # Data type
        False,          # Normalize?
        0,              # Stride
        None            # Offset pointer
    )
    gl.glEnableVertexAttribArray(0)
    
    # -------------------------------------------------------------------------
    # Main loop
    # -------------------------------------------------------------------------
    
    while not glfw.window_should_close(window):
        
        gl.glClear(gl.GL_COLOR_BUFFER_BIT | gl.GL_DEPTH_BUFFER_BIT)

        # Draw
        gl.glDrawArrays(gl.GL_TRIANGLES, 0, int(len(button.vertices)/3))
        
        glfw.swap_buffers(window)
        glfw.poll_events()
        
        if (mouse_button_was_pressed is True):
            print("from main: PRESSED!")
            mouse_button_was_pressed = False

        frame_counter.update()
    
    glfw.terminate()

# -----------------------------------------------------------------------------
# Prevent code from running on import
# -----------------------------------------------------------------------------

if __name__ == "__main__":
    main()

>Solution :

A global variable is global in file scope. mouse_button_was_pressed from callbacks.py is not the same as mouse_button_was_pressed from main.py. Init mouse_button_was_pressed in callbacks.py:

callbacks.py:

mouse_button_was_pressed = False

def mouse_button_callback(window, button, action, mod):
    global mouse_button_was_pressed
    if (button == glfw.MOUSE_BUTTON_LEFT and action == glfw.PRESS):
        mouse_button_was_pressed = True

Access it with callbacks.mouse_button_was_pressed in main.py:

main.py:

import callbacks
if callbacks.mouse_button_was_pressed:
    print("from main: PRESSED!")
    callbacks.mouse_button_was_pressed = False

Leave a ReplyCancel reply