def 新建窗口(尺寸, 标题, 图标路径=None, 内置按键回调=True): glfw.window_hint(glfw.TRANSPARENT_FRAMEBUFFER, True) glfw.window_hint(glfw.RESIZABLE, False) glfw.window_hint(glfw.FLOATING, True) window = glfw.create_window(*尺寸, 标题, None, None) if 图标路径: glfw.set_window_icon(window, 1, 图标(图标路径)) if 内置按键回调: def key_callback(_, key, __, 方向, ___): if 方向 != 1: return d = { 'D': glfw.DECORATED, 'F': glfw.FLOATING, } if chr(key) in d: flag = d[chr(key)] t = glfw.get_window_attrib(window, flag) glfw.set_window_attrib(window, flag, not t) # esc if key == 256: glfw.set_window_should_close(window, True) window.key_callback = key_callback glfw.set_key_callback(window, key_callback) return window
def create(): glfw.default_window_hints() glfw.window_hint(glfw.RESIZABLE, 0) # 0 = false Window.window = glfw.create_window(Config.values["window"]["width"], Config.values["window"]["height"], "Moteur jeu en python", None, None) if not Window.window: glfw.terminate() sys.exit(2) glfw.make_context_current(Window.window) glfw.set_window_icon(Window.window, 1, Image.open("game/resources/icon.png")) if Config.values["window"]["limFrameRate"]: glfw.swap_interval(1) # max frame rate of the monitor else: glfw.swap_interval(0) # No frame limit # Hints for OpenGL gl.glViewport(0, 0, Config.values["window"]["width"], Config.values["window"]["height"]) gl.glEnable(gl.GL_TEXTURE_2D) gl.glActiveTexture(gl.GL_TEXTURE0) gl.glEnable(gl.GL_BLEND) gl.glBlendFunc(gl.GL_SRC_ALPHA, gl.GL_ONE_MINUS_SRC_ALPHA)
def __init__(self, win, *args, **kwargs): """Set up the backend window according the params of the PsychoPy win Before PsychoPy 1.90.0 this code was executed in Window._setupPygame() :param win: a PsychoPy Window (usually not fully created yet) :param share: a PsychoPy Window to share a context with :param bpc: list-like, bits per color (R, G, B) :param refreshHz: int, refresh rate :param depthBits: int, framebuffer depth bits :param stencilBits: int, framebuffer stencil bits :param swapInterval: int, screen updates before swapping buffers :param winTitle: str, optional window title """ BaseBackend.__init__(self, win) # window to share a context with share_win = kwargs.get('share', None) if share_win is not None: if share_win.winType == 'glfw': share_context = share_win.winHandle else: logging.warning( 'Cannot share a context with a non-GLFW window. Disabling.' ) share_context = None else: share_context = None if sys.platform == 'darwin' and not win.useRetina and pyglet.version >= "1.3": raise ValueError("As of PsychoPy 1.85.3 OSX windows should all be " "set to useRetina=True (or remove the argument). " "Pyglet 1.3 appears to be forcing " "us to use retina on any retina-capable screen " "so setting to False has no effect.") # window framebuffer configuration win.bpc = kwargs.get('bpc', (8, 8, 8)) # nearly all displays use 8 bpc win.refreshHz = int(kwargs.get('refreshHz', 60)) win.depthBits = int(kwargs.get('depthBits', 8)) win.stencilBits = int(kwargs.get('stencilBits', 8)) # TODO - make waitBlanking set this too, independent right now win.swapInterval = int(kwargs.get('swapInterval', 1)) # vsync ON if 1 # get monitors, with GLFW the primary display is ALWAYS at index 0 allScrs = glfw.get_monitors() if len(allScrs) < int(win.screen) + 1: logging.warn("Requested an unavailable screen number - " "using first available.") win.screen = 0 this_screen = allScrs[win.screen] if win.autoLog: logging.info('configured GLFW screen %i' % win.screen) # find a matching video mode (can we even support this configuration?) vidmode_is_supported = False for vidmode in glfw.get_video_modes(this_screen): _size, _bpc, _hz = vidmode if win._isFullScr: # size and refresh rate are ignored if windowed has_size = _size == tuple(win.size) has_hz = _hz == win.refreshHz else: has_size = has_hz = True has_bpc = _bpc == tuple(win.bpc) if has_size and has_bpc and has_hz: vidmode_is_supported = True break _size, _bpc, _hz = glfw.get_video_mode(this_screen) if not vidmode_is_supported: # the requested video mode is not supported, use current logging.warning( ("The specified video mode is not supported by this display, " "using native mode ...")) logging.warning( ("Overriding user video settings: size {} -> {}, bpc {} -> " "{}, refreshHz {} -> {}".format(tuple(win.size), _size, tuple(win.bpc), _bpc, win.refreshHz, _hz))) # change the window settings win.bpc = _bpc win.refreshHz = _hz win.size = _size if win._isFullScr: use_display = this_screen else: use_display = None # configure stereo use_stereo = 0 if win.stereo: # provide warning if stereo buffers are requested but unavailable if not glfw.extension_supported('GL_STEREO'): logging.warning( 'A stereo window was requested but the graphics ' 'card does not appear to support GL_STEREO') win.stereo = False else: use_stereo = 1 # setup multisampling # This enables multisampling on the window backbuffer, not on other # framebuffers. msaa_samples = 0 if win.multiSample: max_samples = (GL.GLint)() GL.glGetIntegerv(GL.GL_MAX_SAMPLES, max_samples) if (win.numSamples & (win.numSamples - 1)) != 0: # power of two? logging.warning( 'Invalid number of MSAA samples provided, must be ' 'power of two. Disabling.') elif 0 > win.numSamples > max_samples.value: # check if within range logging.warning( 'Invalid number of MSAA samples provided, outside of valid ' 'range. Disabling.') else: msaa_samples = win.numSamples win.multiSample = msaa_samples > 0 # disable stencil buffer if win.allowStencil: win.stencilBits = 0 # set buffer configuration hints glfw.window_hint(glfw.RED_BITS, win.bpc[0]) glfw.window_hint(glfw.GREEN_BITS, win.bpc[1]) glfw.window_hint(glfw.BLUE_BITS, win.bpc[2]) glfw.window_hint(glfw.REFRESH_RATE, win.refreshHz) glfw.window_hint(glfw.STEREO, use_stereo) glfw.window_hint(glfw.SAMPLES, msaa_samples) glfw.window_hint(glfw.STENCIL_BITS, win.stencilBits) glfw.window_hint(glfw.DEPTH_BITS, win.depthBits) # window appearance and behaviour hints if not win.allowGUI: glfw.window_hint(glfw.DECORATED, 0) glfw.window_hint(glfw.AUTO_ICONIFY, 0) # window title title_text = str(kwargs.get('winTitle', "PsychoPy (GLFW)")) # create the window self.winHandle = glfw.create_window(width=win.size[0], height=win.size[1], title=title_text, monitor=use_display, share=share_context) # set the window icon glfw.set_window_icon(self.winHandle, 1, _WINDOW_ICON_) # The window's user pointer maps the Python Window object to its GLFW # representation. glfw.set_window_user_pointer(self.winHandle, win) glfw.make_context_current(self.winHandle) # ready to use # set the window size to the framebuffer size win.size = np.array(glfw.get_framebuffer_size(self.winHandle)) if win.useFBO: # check for necessary extensions if not glfw.extension_supported('GL_EXT_framebuffer_object'): msg = ("Trying to use a framebuffer object but " "GL_EXT_framebuffer_object is not supported. Disabled") logging.warn(msg) win.useFBO = False if not glfw.extension_supported('GL_ARB_texture_float'): msg = ("Trying to use a framebuffer object but " "GL_ARB_texture_float is not supported. Disabling") logging.warn(msg) win.useFBO = False # Assign event callbacks, these are dispatched when 'poll_events' is # called. glfw.set_mouse_button_callback(self.winHandle, event._onGLFWMouseButton) glfw.set_scroll_callback(self.winHandle, event._onGLFWMouseScroll) glfw.set_key_callback(self.winHandle, event._onGLFWKey) glfw.set_char_mods_callback(self.winHandle, event._onGLFWText) # enable vsync, GLFW has additional setting for this that might be # useful. glfw.swap_interval(win.swapInterval) # give the window class GLFW specific methods win.setMouseType = self.setMouseType if not win.allowGUI: self.setMouseVisibility(False) #glfw.set_window_size_callback(self.winHandle, _onResize) #self.winHandle.on_resize = _onResize # avoid circular reference # TODO - handle window resizing # Set the position of the window if not fullscreen. if not win.pos: # work out where the centre should be win.pos = [(_size[0] - win.size[0]) / 2.0, (_size[1] - win.size[1]) / 2.0] if not win._isFullScr: # get the virtual position of the monitor, apply offset to pos _px, _py = glfw.get_monitor_pos(this_screen) glfw.set_window_pos(self.winHandle, int(win.pos[0] + _px), int(win.pos[1] + _py))
def __init__( self, module, width, height, caption, scale, palette, fps, border_width, border_color, ): if glfw.get_version() < tuple(map(int, GLFW_VERSION.split("."))): raise RuntimeError( "glfw version is lower than {}".format(GLFW_VERSION)) if width > APP_SCREEN_MAX_SIZE or height > APP_SCREEN_MAX_SIZE: raise ValueError("screen size is larger than {}x{}".format( APP_SCREEN_MAX_SIZE, APP_SCREEN_MAX_SIZE)) self._module = module self._palette = palette[:] self._pil_palette = self._get_pil_palette(palette) self._fps = fps self._border_width = border_width self._border_color = border_color self._next_update_time = 0 self._one_frame_time = 1 / fps self._key_state = {} self._update = None self._draw = None self._capture_start = 0 self._capture_index = 0 self._capture_images = [None] * APP_GIF_CAPTURE_COUNT self._perf_monitor_is_enabled = False self._perf_fps_count = 0 self._perf_fps_start_time = 0 self._perf_fps = 0 self._perf_update_count = 0 self._perf_update_total_time = 0 self._perf_update_time = 0 self._perf_draw_count = 0 self._perf_draw_total_time = 0 self._perf_draw_time = 0 module.width = width module.height = height module.mouse_x = 0 module.mouse_y = 0 module.frame_count = 0 # initialize window if not glfw.init(): exit() monitor = glfw.get_primary_monitor() display_width, display_height = glfw.get_video_mode(monitor)[0] if scale == 0: scale = max( min( (display_width // width) - APP_SCREEN_SCALE_CUTDOWN, (display_height // height) - APP_SCREEN_SCALE_CUTDOWN, ), APP_SCREEN_SCALE_MINIMUM, ) window_width = width * scale + border_width window_height = height * scale + border_width self._window = glfw.create_window(window_width, window_height, caption, None, None) if not self._window: glfw.terminate() exit() glfw.set_window_pos( self._window, (display_width - window_width) // 2, (display_height - window_height) // 2, ) glfw.make_context_current(self._window) glfw.set_window_size_limits(self._window, width, height, glfw.DONT_CARE, glfw.DONT_CARE) self._hidpi_scale = (glfw.get_framebuffer_size(self._window)[0] / glfw.get_window_size(self._window)[0]) self._update_viewport() glfw.set_key_callback(self._window, self._key_callback) glfw.set_cursor_pos_callback(self._window, self._cursor_pos_callback) glfw.set_mouse_button_callback(self._window, self._mouse_button_callback) glfw.set_window_icon(self._window, 1, [self._get_icon_image()]) # initialize renderer self._renderer = Renderer(width, height) # initialize audio player self._audio_player = AudioPlayer() # export module functions module.btn = self.btn module.btnp = self.btnp module.btnr = self.btnr module.run = self.run module.run_with_profiler = self.run_with_profiler module.quit = self.quit module.save = self.save module.load = self.load module.image = self._renderer.image module.tilemap = self._renderer.tilemap module.clip = self._renderer.draw_command.clip module.pal = self._renderer.draw_command.pal module.cls = self._renderer.draw_command.cls module.pix = self._renderer.draw_command.pix module.line = self._renderer.draw_command.line module.rect = self._renderer.draw_command.rect module.rectb = self._renderer.draw_command.rectb module.circ = self._renderer.draw_command.circ module.circb = self._renderer.draw_command.circb module.blt = self._renderer.draw_command.blt module.bltm = self._renderer.draw_command.bltm module.text = self._renderer.draw_command.text module.sound = self._audio_player.sound module.play = self._audio_player.play # module.playm = self._audio_player.playm module.stop = self._audio_player.stop
def __init__(self, module, width, height, caption, scale, palette, fps, border_width, border_color): self._module = module self._palette = palette[:] self._pil_palette = self._get_pil_palette(palette) self._fps = fps self._border_width = border_width self._border_color = border_color self._next_update_time = 0 self._one_frame_time = 1 / fps self._key_state = {} self._update = None self._draw = None self._capture_start = 0 self._capture_index = 0 self._capture_images = [None] * APP_SCREEN_CAPTURE_COUNT self._perf_monitor_is_enabled = False self._perf_fps_count = 0 self._perf_fps_start_time = 0 self._perf_fps = 0 self._perf_update_count = 0 self._perf_update_total_time = 0 self._perf_update_time = 0 self._perf_draw_count = 0 self._perf_draw_total_time = 0 self._perf_draw_time = 0 module.width = width module.height = height module.mouse_x = 0 module.mouse_y = 0 module.frame_count = 0 # initialize window if not glfw.init(): exit() window_width = width * scale + border_width window_height = height * scale + border_width self._window = glfw.create_window(window_width, window_height, caption, None, None) if not self._window: glfw.terminate() exit() glfw.make_context_current(self._window) glfw.set_window_size_limits(self._window, width, height, glfw.DONT_CARE, glfw.DONT_CARE) self._hidpi_scale = (glfw.get_framebuffer_size(self._window)[0] / glfw.get_window_size(self._window)[0]) self._update_viewport() glfw.set_key_callback(self._window, self._key_callback) glfw.set_cursor_pos_callback(self._window, self._cursor_pos_callback) glfw.set_mouse_button_callback(self._window, self._mouse_button_callback) glfw.set_window_icon(self._window, 1, [self._get_icon_image()]) # initialize renderer self._renderer = Renderer(width, height) # initialize audio player self._audio_player = AudioPlayer() # export module functions module.btn = self.btn module.btnp = self.btnp module.btnr = self.btnr module.run = self.run module.quit = self.quit module.image = self._renderer.image module.clip = self._renderer.draw_command.clip module.pal = self._renderer.draw_command.pal module.cls = self._renderer.draw_command.cls module.pix = self._renderer.draw_command.pix module.line = self._renderer.draw_command.line module.rect = self._renderer.draw_command.rect module.rectb = self._renderer.draw_command.rectb module.circ = self._renderer.draw_command.circ module.circb = self._renderer.draw_command.circb module.blt = self._renderer.draw_command.blt module.text = self._renderer.draw_command.text module.sound = self._audio_player.sound module.play = self._audio_player.play module.stop = self._audio_player.stop
def __init__(self, address, camera, space, width, height, lock): # Create GLFW window if not glfw.init(): raise RuntimeError('Failed to initialize GLFW!') glfw.window_hint(glfw.CONTEXT_VERSION_MAJOR, 3) glfw.window_hint(glfw.CONTEXT_VERSION_MINOR, 3) glfw.window_hint(glfw.OPENGL_PROFILE, glfw.OPENGL_CORE_PROFILE) glfw.window_hint(glfw.OPENGL_FORWARD_COMPAT, True) self.window = glfw.create_window(width, height, 'Axuy', None, None) if not self.window: glfw.terminate() raise RuntimeError('Failed to create GLFW window!') self.camera = camera self.picos = {address: camera} self.colors = {address: choice(COLOR_NAMES)} self.last_time = glfw.get_time() self.lock = lock # Window's rendering and event-handling configuration glfw.set_window_icon(self.window, 1, Image.open(abspath('icon.png'))) glfw.make_context_current(self.window) glfw.swap_interval(1) glfw.set_input_mode(self.window, glfw.CURSOR, glfw.CURSOR_DISABLED) glfw.set_input_mode(self.window, glfw.STICKY_KEYS, True) glfw.set_cursor_pos_callback(self.window, self.camera.look) self.fov = FOV_INIT glfw.set_scroll_callback(self.window, self.zoom) glfw.set_mouse_button_callback(self.window, self.shoot) # Create OpenGL context self.context = context = moderngl.create_context() context.enable(moderngl.BLEND) context.enable(moderngl.DEPTH_TEST) self.space, vertices = space, [] for (x, y, z), occupied in np.ndenumerate(self.space): if self.space[x][y][z - 1] ^ occupied: vertices.extend(i + j for i, j in product(neighbors(x, y, z), OXY)) if self.space[x - 1][y][z] ^ occupied: vertices.extend(i + j for i, j in product(neighbors(x, y, z), OYZ)) if self.space[x][y - 1][z] ^ occupied: vertices.extend(i + j for i, j in product(neighbors(x, y, z), OZX)) self.maprog = context.program(vertex_shader=MAP_VERTEX, fragment_shader=MAP_FRAGMENT) self.maprog['bg'].write(color('Background').tobytes()) self.maprog['color'].write(color('Aluminium').tobytes()) mapvb = context.buffer(np.stack(vertices).astype(np.float32).tobytes()) self.mapva = context.simple_vertex_array(self.maprog, mapvb, 'in_vert') self.prog = context.program(vertex_shader=PICO_VERTEX, fragment_shader=PICO_FRAGMENT) pvb = [(context.buffer(TETRAVERTICES.tobytes()), '3f', 'in_vert')] pib = context.buffer(TETRAINDECIES.tobytes()) self.pva = context.vertex_array(self.prog, pvb, pib) svb = [(context.buffer(OCTOVERTICES.tobytes()), '3f', 'in_vert')] sib = context.buffer(OCTOINDECIES.tobytes()) self.sva = context.vertex_array(self.prog, svb, sib)
def __init__(self, win, *args, **kwargs): """Set up the backend window according the params of the PsychoPy win Before PsychoPy 1.90.0 this code was executed in Window._setupPygame() Parameters ---------- win : psychopy.visual.Window instance PsychoPy Window (usually not fully created yet). share : psychopy.visual.Window instance PsychoPy Window to share a context with bpc : array_like Bits per color (R, G, B). refreshHz : int Refresh rate in Hertz. depthBits : int, Framebuffer (back buffer) depth bits. swapInterval : int Swap interval for the current OpenGL context. stencilBits : int Framebuffer (back buffer) stencil bits. winTitle : str Optional window title string. *args Additional position arguments. **kwargs Additional keyword arguments. """ BaseBackend.__init__(self, win) # window to share a context with shareWin = kwargs.get('share', None) if shareWin is not None: if shareWin.winType == 'glfw': shareContext = shareWin.winHandle else: logging.warning( 'Cannot share a context with a non-GLFW window. Disabling.') shareContext = None else: shareContext = None if sys.platform=='darwin' and not win.useRetina and pyglet.version >= "1.3": raise ValueError("As of PsychoPy 1.85.3 OSX windows should all be " "set to useRetina=True (or remove the argument). " "Pyglet 1.3 appears to be forcing " "us to use retina on any retina-capable screen " "so setting to False has no effect.") # window framebuffer configuration win.bpc = kwargs.get('bpc', (8, 8, 8)) # nearly all displays use 8 bpc win.refreshHz = int(kwargs.get('refreshHz', 60)) win.depthBits = int(kwargs.get('depthBits', 8)) win.stencilBits = int(kwargs.get('stencilBits', 8)) # win.swapInterval = int(kwargs.get('swapInterval', 1)) # vsync ON if 1 # get monitors, with GLFW the primary display is ALWAYS at index 0 allScrs = glfw.get_monitors() if len(allScrs) < int(win.screen) + 1: logging.warn("Requested an unavailable screen number - " "using first available.") win.screen = 0 thisScreen = allScrs[win.screen] if win.autoLog: logging.info('configured GLFW screen %i' % win.screen) # find a matching video mode (can we even support this configuration?) isVidmodeSupported = False for vidmode in glfw.get_video_modes(thisScreen): size, bpc, hz = vidmode if win._isFullScr: # size and refresh rate are ignored if windowed hasSize = size == tuple(win.size) hasHz = hz == win.refreshHz else: hasSize = hasHz = True hasBpc = bpc == tuple(win.bpc) if hasSize and hasBpc and hasHz: isVidmodeSupported = True break nativeVidmode = glfw.get_video_mode(thisScreen) if not isVidmodeSupported: # the requested video mode is not supported, use current logging.warning( ("The specified video mode is not supported by this display, " "using native mode ...")) logging.warning( ("Overriding user video settings: size {} -> {}, bpc {} -> " "{}, refreshHz {} -> {}".format( tuple(win.size), nativeVidmode[0], tuple(win.bpc), nativeVidmode[1], win.refreshHz, nativeVidmode[2]))) # change the window settings win.size, win.bpc, win.refreshHz = nativeVidmode if win._isFullScr: useDisplay = thisScreen else: useDisplay = None # configure stereo useStereo = 0 if win.stereo: # provide warning if stereo buffers are requested but unavailable if not glfw.extension_supported('GL_STEREO'): logging.warning( 'A stereo window was requested but the graphics ' 'card does not appear to support GL_STEREO') win.stereo = False else: useStereo = 1 # setup multisampling # This enables multisampling on the window backbuffer, not on other # framebuffers. msaaSamples = 0 if win.multiSample: maxSamples = (GL.GLint)() GL.glGetIntegerv(GL.GL_MAX_SAMPLES, maxSamples) if (win.numSamples & (win.numSamples - 1)) != 0: # power of two? logging.warning( 'Invalid number of MSAA samples provided, must be ' 'power of two. Disabling.') elif 0 > win.numSamples > maxSamples.value: # check if within range logging.warning( 'Invalid number of MSAA samples provided, outside of valid ' 'range. Disabling.') else: msaaSamples = win.numSamples win.multiSample = msaaSamples > 0 # disable stencil buffer if not win.allowStencil: win.stencilBits = 0 # set buffer configuration hints glfw.window_hint(glfw.RED_BITS, win.bpc[0]) glfw.window_hint(glfw.GREEN_BITS, win.bpc[1]) glfw.window_hint(glfw.BLUE_BITS, win.bpc[2]) glfw.window_hint(glfw.REFRESH_RATE, win.refreshHz) glfw.window_hint(glfw.STEREO, useStereo) glfw.window_hint(glfw.SAMPLES, msaaSamples) glfw.window_hint(glfw.STENCIL_BITS, win.stencilBits) glfw.window_hint(glfw.DEPTH_BITS, win.depthBits) glfw.window_hint(glfw.AUTO_ICONIFY, 0) # window appearance and behaviour hints if not win.allowGUI: glfw.window_hint(glfw.DECORATED, 0) # create the window self.winHandle = glfw.create_window( width=win.size[0], height=win.size[1], title=str(kwargs.get('winTitle', "PsychoPy (GLFW)")), monitor=useDisplay, share=shareContext) # The window's user pointer maps the Python Window object to its GLFW # representation. glfw.set_window_user_pointer(self.winHandle, win) glfw.make_context_current(self.winHandle) # ready to use # set the position of the window if not fullscreen if not win._isFullScr: # if no window position is specified, centre it on-screen if win.pos is None: size, bpc, hz = nativeVidmode win.pos = [(size[0] - win.size[0]) / 2.0, (size[1] - win.size[1]) / 2.0] # get the virtual position of the monitor, apply offset to the # window position px, py = glfw.get_monitor_pos(thisScreen) glfw.set_window_pos(self.winHandle, int(win.pos[0] + px), int(win.pos[1] + py)) elif win._isFullScr and win.pos is not None: logging.warn("Ignoring window 'pos' in fullscreen mode.") # set the window icon glfw.set_window_icon(self.winHandle, 1, _WINDOW_ICON_) # set the window size to the framebuffer size win.size = np.array(glfw.get_framebuffer_size(self.winHandle)) if win.useFBO: # check for necessary extensions if not glfw.extension_supported('GL_EXT_framebuffer_object'): msg = ("Trying to use a framebuffer object but " "GL_EXT_framebuffer_object is not supported. Disabled") logging.warn(msg) win.useFBO = False if not glfw.extension_supported('GL_ARB_texture_float'): msg = ("Trying to use a framebuffer object but " "GL_ARB_texture_float is not supported. Disabling") logging.warn(msg) win.useFBO = False # Assign event callbacks, these are dispatched when 'poll_events' is # called. glfw.set_mouse_button_callback(self.winHandle, event._onGLFWMouseButton) glfw.set_scroll_callback(self.winHandle, event._onGLFWMouseScroll) glfw.set_key_callback(self.winHandle, event._onGLFWKey) glfw.set_char_mods_callback(self.winHandle, event._onGLFWText) # set swap interval to manual setting, independent of waitBlanking self.setSwapInterval(int(kwargs.get('swapInterval', 1))) # give the window class GLFW specific methods win.setMouseType = self.setMouseType if not win.allowGUI: self.setMouseVisibility(False)
def __init__( self, module, width, height, caption, scale, palette, fps, border_width, border_color, ): if glfw.get_version() < tuple(map(int, GLFW_VERSION.split("."))): raise RuntimeError( "glfw version is lower than {}".format(GLFW_VERSION)) if width > APP_SCREEN_MAX_SIZE or height > APP_SCREEN_MAX_SIZE: raise ValueError("screen size is larger than {}x{}".format( APP_SCREEN_MAX_SIZE, APP_SCREEN_MAX_SIZE)) global pyxel pyxel = module self._palette = palette[:] self._fps = fps self._border_width = border_width self._border_color = border_color self._next_update_time = 0 self._one_frame_time = 1 / fps self._key_state = {} self._is_mouse_visible = False self._update = None self._draw = None self._capture_start = 0 self._capture_count = 0 self._capture_images = [None] * APP_GIF_CAPTURE_COUNT self._perf_monitor_is_enabled = False self._perf_fps_count = 0 self._perf_fps_start_time = 0 self._perf_fps = 0 self._perf_update_count = 0 self._perf_update_total_time = 0 self._perf_update_time = 0 self._perf_draw_count = 0 self._perf_draw_total_time = 0 self._perf_draw_time = 0 # exports variables pyxel._app = self pyxel.width = width pyxel.height = height pyxel.mouse_x = 0 pyxel.mouse_y = 0 pyxel.frame_count = 0 # initialize window if not glfw.init(): exit() monitor = glfw.get_primary_monitor() display_width, display_height = glfw.get_video_mode(monitor)[0] if scale == 0: scale = max( min( (display_width // width) - APP_SCREEN_SCALE_CUTDOWN, (display_height // height) - APP_SCREEN_SCALE_CUTDOWN, ), APP_SCREEN_SCALE_MINIMUM, ) window_width = width * scale + border_width window_height = height * scale + border_width self._window = glfw.create_window(window_width, window_height, caption, None, None) if not self._window: glfw.terminate() exit() glfw.set_window_pos( self._window, (display_width - window_width) // 2, (display_height - window_height) // 2, ) glfw.make_context_current(self._window) glfw.set_window_size_limits(self._window, width, height, glfw.DONT_CARE, glfw.DONT_CARE) self._hidpi_scale = (glfw.get_framebuffer_size(self._window)[0] / glfw.get_window_size(self._window)[0]) self._update_viewport() glfw.set_key_callback(self._window, self._key_callback) glfw.set_mouse_button_callback(self._window, self._mouse_button_callback) glfw.set_window_icon(self._window, 1, [utilities.get_icon_image()]) glfw.set_input_mode(self._window, glfw.CURSOR, glfw.CURSOR_HIDDEN) # initialize renderer self._renderer = Renderer(width, height) # initialize audio player self._audio_player = AudioPlayer() # export module functions pyxel.btn = self.btn pyxel.btnp = self.btnp pyxel.btnr = self.btnr pyxel.mouse = self.mouse pyxel.run = self.run pyxel.run_with_profiler = self.run_with_profiler pyxel.quit = self.quit pyxel.save = self.save pyxel.load = self.load pyxel.image = self._renderer.image pyxel.tilemap = self._renderer.tilemap pyxel.clip = self._renderer.draw_command.clip pyxel.pal = self._renderer.draw_command.pal pyxel.cls = self._renderer.draw_command.cls pyxel.pix = self._renderer.draw_command.pix pyxel.line = self._renderer.draw_command.line pyxel.rect = self._renderer.draw_command.rect pyxel.rectb = self._renderer.draw_command.rectb pyxel.circ = self._renderer.draw_command.circ pyxel.circb = self._renderer.draw_command.circb pyxel.blt = self._renderer.draw_command.blt pyxel.bltm = self._renderer.draw_command.bltm pyxel.text = self._renderer.draw_command.text pyxel.sound = self._audio_player.sound pyxel.music = self._audio_player.music pyxel.play = self._audio_player.play pyxel.playm = self._audio_player.playm pyxel.stop = self._audio_player.stop # initialize mouse cursor pyxel.image(3, system=True).set(MOUSE_CURSOR_IMAGE_X, MOUSE_CURSOR_IMAGE_Y, MOUSE_CURSOR_DATA)
def __init__(self, win, backendConf=None): """Set up the backend window according the params of the PsychoPy win Before PsychoPy 1.90.0 this code was executed in Window._setupPygame() Parameters ---------- win : `psychopy.visual.Window` instance PsychoPy Window (usually not fully created yet). backendConf : `dict` or `None` Backend configuration options. Options are specified as a dictionary where keys are option names and values are settings. For this backend the following options are available: * `share` (`psychopy.visual.Window instance`) PsychoPy Window to share a context with. * `refreshHz` (`int`) Refresh rate in Hertz. * `bpc` (`array_like`) Bits per color (R, G, B). * `swapInterval` (`int`) Swap interval for the current OpenGL context. * `depthBits` (`int`) Framebuffer (back buffer) depth bits. * `stencilBits` (`int`) Framebuffer (back buffer) stencil bits. * `winTitle` (`str`) Optional window title string. Examples -------- Create a window using the GLFW backend and specify custom options:: import psychopy.visual as visual options = {'bpc': (8, 8, 8), 'depthBits': 24, 'stencilBits': 8} win = visual.Window(winType='glfw', backendOptions=options) """ BaseBackend.__init__(self, win) # if `None`, change to `dict` to extract options backendConf = backendConf if backendConf is not None else {} if not isinstance(backendConf, dict): # type check on options raise TypeError( 'Object passed to `backendConf` must be type `dict`.') # window to share a context with shareWin = backendConf.get('share', None) if shareWin is not None: if shareWin.winType == 'glfw': shareContext = shareWin.winHandle else: logging.warning( 'Cannot share a context with a non-GLFW window. Disabling.') shareContext = None else: shareContext = None if sys.platform=='darwin' and not win.useRetina and pyglet.version >= "1.3": raise ValueError("As of PsychoPy 1.85.3 OSX windows should all be " "set to useRetina=True (or remove the argument). " "Pyglet 1.3 appears to be forcing " "us to use retina on any retina-capable screen " "so setting to False has no effect.") # window framebuffer configuration bpc = backendConf.get('bpc', (8, 8, 8)) if isinstance(bpc, int): win.bpc = (bpc, bpc, bpc) else: win.bpc = bpc win.refreshHz = int(backendConf.get('refreshHz', 60)) win.depthBits = int(backendConf.get('depthBits', 8)) win.stencilBits = int(backendConf.get('stencilBits', 8)) # win.swapInterval = int(backendConf.get('swapInterval', 1)) # vsync ON if 1 # get monitors, with GLFW the primary display is ALWAYS at index 0 allScrs = glfw.get_monitors() if len(allScrs) < int(win.screen) + 1: logging.warn("Requested an unavailable screen number - " "using first available.") win.screen = 0 thisScreen = allScrs[win.screen] if win.autoLog: logging.info('configured GLFW screen %i' % win.screen) # find a matching video mode (can we even support this configuration?) isVidmodeSupported = False for vidmode in glfw.get_video_modes(thisScreen): size, bpc, hz = vidmode if win._isFullScr: # size and refresh rate are ignored if windowed hasSize = size == tuple(win.size) hasHz = hz == win.refreshHz else: hasSize = hasHz = True hasBpc = bpc == tuple(win.bpc) if hasSize and hasBpc and hasHz: isVidmodeSupported = True break nativeVidmode = glfw.get_video_mode(thisScreen) if not isVidmodeSupported: # the requested video mode is not supported, use current logging.warning( ("The specified video mode is not supported by this display, " "using native mode ...")) actualWidth, actualHeight = nativeVidmode.size redBits, greenBits, blueBits = nativeVidmode.bits # change the window settings if win._isFullScr: logging.warning( ("Overriding user video settings: size {} -> {}, bpc {} -> " "{}, refreshHz {} -> {}".format( tuple(win.size), (actualWidth, actualHeight), tuple(win.bpc), (redBits, greenBits, blueBits), win.refreshHz, nativeVidmode.refresh_rate))) win.clientSize = np.array((actualWidth, actualHeight), int) else: logging.warning( ("Overriding user video settings: bpc {} -> " "{}, refreshHz {} -> {}".format( tuple(win.bpc), (redBits, greenBits, blueBits), win.refreshHz, nativeVidmode.refresh_rate))) win.bpc = (redBits, greenBits, blueBits) win.refreshHz = nativeVidmode.refresh_rate if win._isFullScr: useDisplay = thisScreen else: useDisplay = None # configure stereo useStereo = 0 if win.stereo: # provide warning if stereo buffers are requested but unavailable if not glfw.extension_supported('GL_STEREO'): logging.warning( 'A stereo window was requested but the graphics ' 'card does not appear to support GL_STEREO') win.stereo = False else: useStereo = 1 # setup multisampling # This enables multisampling on the window backbuffer, not on other # framebuffers. msaaSamples = 0 if win.multiSample: maxSamples = (GL.GLint)() GL.glGetIntegerv(GL.GL_MAX_SAMPLES, maxSamples) if (win.numSamples & (win.numSamples - 1)) != 0: # power of two? logging.warning( 'Invalid number of MSAA samples provided, must be ' 'power of two. Disabling.') elif 0 > win.numSamples > maxSamples.value: # check if within range logging.warning( 'Invalid number of MSAA samples provided, outside of valid ' 'range. Disabling.') else: msaaSamples = win.numSamples win.multiSample = msaaSamples > 0 # disable stencil buffer if not win.allowStencil: win.stencilBits = 0 # set buffer configuration hints glfw.window_hint(glfw.RED_BITS, win.bpc[0]) glfw.window_hint(glfw.GREEN_BITS, win.bpc[1]) glfw.window_hint(glfw.BLUE_BITS, win.bpc[2]) glfw.window_hint(glfw.REFRESH_RATE, win.refreshHz) glfw.window_hint(glfw.STEREO, useStereo) glfw.window_hint(glfw.SAMPLES, msaaSamples) glfw.window_hint(glfw.STENCIL_BITS, win.stencilBits) glfw.window_hint(glfw.DEPTH_BITS, win.depthBits) glfw.window_hint(glfw.AUTO_ICONIFY, 0) # window appearance and behaviour hints if not win.allowGUI: glfw.window_hint(glfw.DECORATED, 0) # create the window self.winHandle = glfw.create_window( width=win.clientSize[0], height=win.clientSize[1], title=str(backendConf.get('winTitle', "PsychoPy (GLFW)")), monitor=useDisplay, share=shareContext) # The window's user pointer maps the Python Window object to its GLFW # representation. glfw.set_window_user_pointer(self.winHandle, win) glfw.make_context_current(self.winHandle) # ready to use # set the position of the window if not fullscreen if not win._isFullScr: # if no window position is specified, centre it on-screen if win.pos is None: size, bpc, hz = nativeVidmode win.pos = [(size[0] - win.clientSize[0]) / 2.0, (size[1] - win.clientSize[1]) / 2.0] # get the virtual position of the monitor, apply offset to the # window position px, py = glfw.get_monitor_pos(thisScreen) glfw.set_window_pos(self.winHandle, int(win.pos[0] + px), int(win.pos[1] + py)) elif win._isFullScr and win.pos is not None: logging.warn("Ignoring window 'pos' in fullscreen mode.") # set the window icon if hasattr(glfw, 'set_window_icon'): glfw.set_window_icon(self.winHandle, 1, _WINDOW_ICON_) # set the window size to the framebuffer size self._frameBufferSize = np.array(glfw.get_framebuffer_size(self.winHandle)) if win.useFBO: # check for necessary extensions if not glfw.extension_supported('GL_EXT_framebuffer_object'): msg = ("Trying to use a framebuffer object but " "GL_EXT_framebuffer_object is not supported. Disabled") logging.warn(msg) win.useFBO = False if not glfw.extension_supported('GL_ARB_texture_float'): msg = ("Trying to use a framebuffer object but " "GL_ARB_texture_float is not supported. Disabling") logging.warn(msg) win.useFBO = False # Assign event callbacks, these are dispatched when 'poll_events' is # called. glfw.set_mouse_button_callback(self.winHandle, self.onMouseButton) glfw.set_cursor_pos_callback(self.winHandle, self.onMouseMove) glfw.set_cursor_enter_callback(self.winHandle, self.onMouseEnter) glfw.set_scroll_callback(self.winHandle, self.onMouseScroll) glfw.set_key_callback(self.winHandle, event._onGLFWKey) glfw.set_char_mods_callback(self.winHandle, event._onGLFWText) # set swap interval to manual setting, independent of waitBlanking self.setSwapInterval(int(backendConf.get('swapInterval', 1))) # give the window class GLFW specific methods win.setMouseType = self.setMouseType if not win.allowGUI: self.setMouseVisibility(False)
def __LoadIcon(self, filepath: str) -> None: img = Image.open(filepath) glfw.set_window_icon(self.__handle, 1, img) img.close()
def _set_icon(self, icon_path) -> None: image = Image.open(icon_path) glfw.set_window_icon(self._window, 1, image)
def __init__(self, config): # Create GLFW window if not glfw.init(): raise RuntimeError('Failed to initialize GLFW') glfw.window_hint(glfw.CLIENT_API, glfw.OPENGL_API) glfw.window_hint(glfw.CONTEXT_CREATION_API, glfw.NATIVE_CONTEXT_API) glfw.window_hint(glfw.CONTEXT_VERSION_MAJOR, 3) glfw.window_hint(glfw.CONTEXT_VERSION_MINOR, 3) glfw.window_hint(glfw.OPENGL_PROFILE, glfw.OPENGL_CORE_PROFILE) glfw.window_hint(glfw.OPENGL_FORWARD_COMPAT, True) Peer.__init__(self, config) self.camera, self.colors = self.pico, {self.addr: randint(0, 5)} width, height = config.size self.zmlvl = config.zmlvl self.window = glfw.create_window(width, height, 'axuy@{}:{}'.format(*self.addr), None, None) if not self.window: glfw.terminate() raise RuntimeError('Failed to create GLFW window') self.fpses = deque() # Window's rendering and event-handling configuration glfw.set_window_icon(self.window, 1, Image.open(abspath('icon.png'))) glfw.make_context_current(self.window) glfw.swap_interval(config.vsync) glfw.set_window_size_callback(self.window, self.resize) # Create OpenGL context self.context = context = moderngl.create_context() context.enable_only(moderngl.DEPTH_TEST) # GLSL program and vertex array for map rendering self.maprog = context.program(vertex_shader=MAP_VERTEX, fragment_shader=MAP_FRAGMENT) mapvb = context.buffer(mirror(self.space)) self.mapva = context.simple_vertex_array(self.maprog, mapvb, 'in_vert') # GLSL programs and vertex arrays for picos and shards rendering pvb = [(context.buffer(TETRAVERTICES), '3f', 'in_vert')] pib = context.buffer(TETRAINDECIES) svb = [(context.buffer(OCTOVERTICES), '3f', 'in_vert')] sib = context.buffer(OCTOINDECIES) self.prog = context.program(vertex_shader=PICO_VERTEX, geometry_shader=PICO_GEOMETRY, fragment_shader=PICO_FRAGMENT) self.pva = context.vertex_array(self.prog, pvb, pib) self.sva = context.vertex_array(self.prog, svb, sib) quad_buffer = context.buffer(QUAD) self.pfilter = context.simple_vertex_array( context.program(vertex_shader=TEX_VERTEX, fragment_shader=SAT_FRAGMENT), quad_buffer, 'in_vert') self.gaussh = context.program(vertex_shader=GAUSSH_VERTEX, fragment_shader=GAUSS_FRAGMENT) self.gaussh['width'].value = 256 self.gausshva = context.simple_vertex_array(self.gaussh, quad_buffer, 'in_vert') self.gaussv = context.program(vertex_shader=GAUSSV_VERTEX, fragment_shader=GAUSS_FRAGMENT) self.gaussv['height'].value = 256 * height / width self.gaussvva = context.simple_vertex_array(self.gaussv, quad_buffer, 'in_vert') self.edge = context.program(vertex_shader=TEX_VERTEX, fragment_shader=COMBINE_FRAGMENT) self.edge['la'].value = 0 self.edge['tex'].value = 1 self.combine = context.simple_vertex_array(self.edge, quad_buffer, 'in_vert') size, table = (width, height), (256, height * 256 // width) self.fb = context.framebuffer(context.texture(size, 4), context.depth_renderbuffer(size)) self.fb.color_attachments[0].use(1) self.ping = context.framebuffer(context.texture(table, 3)) self.pong = context.framebuffer(context.texture(table, 3))