Add ModeManager
This commit is contained in:
parent
53a5460c11
commit
8b5daad367
@ -53,6 +53,7 @@ import qutebrowser.config.style as style
|
|||||||
import qutebrowser.config.config as config
|
import qutebrowser.config.config as config
|
||||||
import qutebrowser.network.qutescheme as qutescheme
|
import qutebrowser.network.qutescheme as qutescheme
|
||||||
import qutebrowser.utils.message as message
|
import qutebrowser.utils.message as message
|
||||||
|
import qutebrowser.utils.modemanager as modemanager
|
||||||
from qutebrowser.widgets.mainwindow import MainWindow
|
from qutebrowser.widgets.mainwindow import MainWindow
|
||||||
from qutebrowser.widgets.crash import CrashDialog
|
from qutebrowser.widgets.crash import CrashDialog
|
||||||
from qutebrowser.commands.keys import CommandKeyParser
|
from qutebrowser.commands.keys import CommandKeyParser
|
||||||
@ -83,7 +84,6 @@ class QuteBrowser(QApplication):
|
|||||||
_timers: List of used QTimers so they don't get GCed.
|
_timers: List of used QTimers so they don't get GCed.
|
||||||
_shutting_down: True if we're currently shutting down.
|
_shutting_down: True if we're currently shutting down.
|
||||||
_quit_status: The current quitting status.
|
_quit_status: The current quitting status.
|
||||||
_mode: The mode we're currently in.
|
|
||||||
_opened_urls: List of opened URLs.
|
_opened_urls: List of opened URLs.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
@ -93,7 +93,6 @@ class QuteBrowser(QApplication):
|
|||||||
self._timers = []
|
self._timers = []
|
||||||
self._opened_urls = []
|
self._opened_urls = []
|
||||||
self._shutting_down = False
|
self._shutting_down = False
|
||||||
self._mode = None
|
|
||||||
|
|
||||||
sys.excepthook = self._exception_hook
|
sys.excepthook = self._exception_hook
|
||||||
|
|
||||||
@ -130,10 +129,11 @@ class QuteBrowser(QApplication):
|
|||||||
}
|
}
|
||||||
self._init_cmds()
|
self._init_cmds()
|
||||||
self.mainwindow = MainWindow()
|
self.mainwindow = MainWindow()
|
||||||
|
modemanager.init(self.mainwindow.tabs.keypress, self._keyparsers, self)
|
||||||
self.setQuitOnLastWindowClosed(False)
|
self.setQuitOnLastWindowClosed(False)
|
||||||
|
|
||||||
self._connect_signals()
|
self._connect_signals()
|
||||||
self.set_mode("normal")
|
modemanager.enter("normal")
|
||||||
|
|
||||||
self.mainwindow.show()
|
self.mainwindow.show()
|
||||||
self._python_hacks()
|
self._python_hacks()
|
||||||
@ -246,7 +246,6 @@ class QuteBrowser(QApplication):
|
|||||||
# misc
|
# misc
|
||||||
self.lastWindowClosed.connect(self.shutdown)
|
self.lastWindowClosed.connect(self.shutdown)
|
||||||
tabs.quit.connect(self.shutdown)
|
tabs.quit.connect(self.shutdown)
|
||||||
tabs.set_mode.connect(self.set_mode)
|
|
||||||
tabs.currentChanged.connect(self.mainwindow.update_inspector)
|
tabs.currentChanged.connect(self.mainwindow.update_inspector)
|
||||||
|
|
||||||
# status bar
|
# status bar
|
||||||
@ -401,20 +400,6 @@ class QuteBrowser(QApplication):
|
|||||||
logging.debug("maybe_quit quitting.")
|
logging.debug("maybe_quit quitting.")
|
||||||
self.quit()
|
self.quit()
|
||||||
|
|
||||||
@pyqtSlot(str)
|
|
||||||
def set_mode(self, mode):
|
|
||||||
"""Set a key input mode.
|
|
||||||
|
|
||||||
Args:
|
|
||||||
mode: The new mode to set, as an index for self._keyparsers.
|
|
||||||
"""
|
|
||||||
if self._mode is not None:
|
|
||||||
oldhandler = self._keyparsers[self._mode]
|
|
||||||
self.mainwindow.tabs.keypress.disconnect(oldhandler.handle)
|
|
||||||
handler = self._keyparsers[mode]
|
|
||||||
self.mainwindow.tabs.keypress.connect(handler.handle)
|
|
||||||
self._mode = mode
|
|
||||||
|
|
||||||
@cmdutils.register(instance='', maxsplit=0)
|
@cmdutils.register(instance='', maxsplit=0)
|
||||||
def pyeval(self, s):
|
def pyeval(self, s):
|
||||||
"""Evaluate a python string and display the results as a webpage.
|
"""Evaluate a python string and display the results as a webpage.
|
||||||
|
@ -28,6 +28,7 @@ from PyQt5.QtWidgets import QApplication
|
|||||||
import qutebrowser.config.config as config
|
import qutebrowser.config.config as config
|
||||||
import qutebrowser.utils.message as message
|
import qutebrowser.utils.message as message
|
||||||
import qutebrowser.utils.url as urlutils
|
import qutebrowser.utils.url as urlutils
|
||||||
|
import qutebrowser.utils.modemanager as modemanager
|
||||||
from qutebrowser.utils.keyparser import KeyParser
|
from qutebrowser.utils.keyparser import KeyParser
|
||||||
|
|
||||||
|
|
||||||
@ -104,8 +105,6 @@ class HintManager(QObject):
|
|||||||
Signals:
|
Signals:
|
||||||
hint_strings_updated: Emitted when the possible hint strings changed.
|
hint_strings_updated: Emitted when the possible hint strings changed.
|
||||||
arg: A list of hint strings.
|
arg: A list of hint strings.
|
||||||
set_mode: Emitted when the input mode should be changed.
|
|
||||||
arg: The new mode, as a string.
|
|
||||||
mouse_event: Mouse event to be posted in the web view.
|
mouse_event: Mouse event to be posted in the web view.
|
||||||
arg: A QMouseEvent
|
arg: A QMouseEvent
|
||||||
openurl: Open a new url
|
openurl: Open a new url
|
||||||
@ -146,7 +145,6 @@ class HintManager(QObject):
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
hint_strings_updated = pyqtSignal(list)
|
hint_strings_updated = pyqtSignal(list)
|
||||||
set_mode = pyqtSignal(str)
|
|
||||||
mouse_event = pyqtSignal('QMouseEvent')
|
mouse_event = pyqtSignal('QMouseEvent')
|
||||||
set_open_target = pyqtSignal(str)
|
set_open_target = pyqtSignal(str)
|
||||||
set_cmd_text = pyqtSignal(str)
|
set_cmd_text = pyqtSignal(str)
|
||||||
@ -353,7 +351,6 @@ class HintManager(QObject):
|
|||||||
|
|
||||||
Emit:
|
Emit:
|
||||||
hint_strings_updated: Emitted to update keypraser.
|
hint_strings_updated: Emitted to update keypraser.
|
||||||
set_mode: Emitted to enter hinting mode
|
|
||||||
"""
|
"""
|
||||||
self._target = target
|
self._target = target
|
||||||
self._baseurl = baseurl
|
self._baseurl = baseurl
|
||||||
@ -395,14 +392,10 @@ class HintManager(QObject):
|
|||||||
self._elems[string] = ElemTuple(e, label)
|
self._elems[string] = ElemTuple(e, label)
|
||||||
frame.contentsSizeChanged.connect(self.on_contents_size_changed)
|
frame.contentsSizeChanged.connect(self.on_contents_size_changed)
|
||||||
self.hint_strings_updated.emit(strings)
|
self.hint_strings_updated.emit(strings)
|
||||||
self.set_mode.emit("hint")
|
modemanager.enter("hint")
|
||||||
|
|
||||||
def stop(self):
|
def stop(self):
|
||||||
"""Stop hinting.
|
"""Stop hinting."""
|
||||||
|
|
||||||
Emit:
|
|
||||||
set_mode: Emitted to leave hinting mode.
|
|
||||||
"""
|
|
||||||
for elem in self._elems.values():
|
for elem in self._elems.values():
|
||||||
elem.label.removeFromDocument()
|
elem.label.removeFromDocument()
|
||||||
self._frame.contentsSizeChanged.disconnect(
|
self._frame.contentsSizeChanged.disconnect(
|
||||||
@ -410,7 +403,7 @@ class HintManager(QObject):
|
|||||||
self._elems = {}
|
self._elems = {}
|
||||||
self._target = None
|
self._target = None
|
||||||
self._frame = None
|
self._frame = None
|
||||||
self.set_mode.emit("normal")
|
modemanager.enter("normal")
|
||||||
message.clear()
|
message.clear()
|
||||||
|
|
||||||
def handle_partial_key(self, keystr):
|
def handle_partial_key(self, keystr):
|
||||||
|
106
qutebrowser/utils/modemanager.py
Normal file
106
qutebrowser/utils/modemanager.py
Normal file
@ -0,0 +1,106 @@
|
|||||||
|
# Copyright 2014 Florian Bruhin (The Compiler) <mail@qutebrowser.org>
|
||||||
|
#
|
||||||
|
# This file is part of qutebrowser.
|
||||||
|
#
|
||||||
|
# qutebrowser is free software: you can redistribute it and/or modify
|
||||||
|
# it under the terms of the GNU General Public License as published by
|
||||||
|
# the Free Software Foundation, either version 3 of the License, or
|
||||||
|
# (at your option) any later version.
|
||||||
|
#
|
||||||
|
# qutebrowser is distributed in the hope that it will be useful,
|
||||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
# GNU General Public License for more details.
|
||||||
|
#
|
||||||
|
# You should have received a copy of the GNU General Public License
|
||||||
|
# along with qutebrowser. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
"""Mode manager singleton which handles the current keyboard mode.
|
||||||
|
|
||||||
|
Module attributes:
|
||||||
|
manager: The ModeManager instance.
|
||||||
|
"""
|
||||||
|
|
||||||
|
import logging
|
||||||
|
|
||||||
|
from PyQt5.QtCore import QObject
|
||||||
|
|
||||||
|
|
||||||
|
manager = None
|
||||||
|
|
||||||
|
|
||||||
|
def init(source, parsers=None, parent=None):
|
||||||
|
"""Initialize the global ModeManager.
|
||||||
|
|
||||||
|
This needs to be done by hand because the import time is before Qt is ready
|
||||||
|
for everything.
|
||||||
|
|
||||||
|
Args:
|
||||||
|
source: The keypress source signal.
|
||||||
|
parsers: A dict of KeyParsers to register.
|
||||||
|
parent: Parent to use for ModeManager.
|
||||||
|
"""
|
||||||
|
global manager
|
||||||
|
manager = ModeManager(source, parsers, parent)
|
||||||
|
|
||||||
|
|
||||||
|
def enter(mode):
|
||||||
|
"""Enter the mode 'mode'."""
|
||||||
|
manager.enter(mode)
|
||||||
|
|
||||||
|
|
||||||
|
def register(mode, handler):
|
||||||
|
"""Register a new mode.
|
||||||
|
|
||||||
|
Args:
|
||||||
|
mode: The name of the mode.
|
||||||
|
handler: Handler for keyPressEvents.
|
||||||
|
"""
|
||||||
|
manager.register(mode, handler)
|
||||||
|
|
||||||
|
|
||||||
|
class ModeManager(QObject):
|
||||||
|
|
||||||
|
"""Manager for keyboard modes.
|
||||||
|
|
||||||
|
Attributes:
|
||||||
|
_source: The keypress source signal.
|
||||||
|
_handlers: A dictionary of modes and their handlers.
|
||||||
|
mode: The current mode.
|
||||||
|
"""
|
||||||
|
|
||||||
|
def __init__(self, sourcesig, parsers=None, parent=None):
|
||||||
|
"""Constructor.
|
||||||
|
|
||||||
|
Args:
|
||||||
|
sourcesig: The signal which gets emitted on a keypress.
|
||||||
|
parsers: A list of parsers to register.
|
||||||
|
"""
|
||||||
|
super().__init__(parent)
|
||||||
|
self._source = sourcesig
|
||||||
|
self._handlers = {}
|
||||||
|
self.mode = None
|
||||||
|
if parsers is not None:
|
||||||
|
for name, parser in parsers.items():
|
||||||
|
self._handlers[name] = parser.handle
|
||||||
|
|
||||||
|
def register(self, mode, handler):
|
||||||
|
"""Register a new mode.
|
||||||
|
|
||||||
|
Args:
|
||||||
|
mode: The name of the mode.
|
||||||
|
handler: Handler for keyPressEvents.
|
||||||
|
"""
|
||||||
|
self._handlers[mode] = handler
|
||||||
|
|
||||||
|
def enter(self, mode):
|
||||||
|
"""Enter a new mode."""
|
||||||
|
oldmode = self.mode
|
||||||
|
logging.debug("Switching mode: {} -> {}".format(oldmode, mode))
|
||||||
|
if oldmode is not None:
|
||||||
|
try:
|
||||||
|
self._source.disconnect(self._handlers[oldmode])
|
||||||
|
except TypeError:
|
||||||
|
logging.debug("Could not disconnect mode {}".format(oldmode))
|
||||||
|
self._source.connect(self._handlers[mode])
|
||||||
|
self.mode = mode
|
@ -69,8 +69,6 @@ class TabbedBrowser(TabWidget):
|
|||||||
arg 2: y-position in %.
|
arg 2: y-position in %.
|
||||||
hint_strings_updated: Hint strings were updated.
|
hint_strings_updated: Hint strings were updated.
|
||||||
arg: A list of hint strings.
|
arg: A list of hint strings.
|
||||||
set_mode: The input mode should be changed.
|
|
||||||
arg: The new mode as a string.
|
|
||||||
keypress: A key was pressed.
|
keypress: A key was pressed.
|
||||||
arg: The QKeyEvent leading to the keypress.
|
arg: The QKeyEvent leading to the keypress.
|
||||||
shutdown_complete: The shuttdown is completed.
|
shutdown_complete: The shuttdown is completed.
|
||||||
@ -89,7 +87,6 @@ class TabbedBrowser(TabWidget):
|
|||||||
cur_scroll_perc_changed = pyqtSignal(int, int)
|
cur_scroll_perc_changed = pyqtSignal(int, int)
|
||||||
hint_strings_updated = pyqtSignal(list)
|
hint_strings_updated = pyqtSignal(list)
|
||||||
set_cmd_text = pyqtSignal(str)
|
set_cmd_text = pyqtSignal(str)
|
||||||
set_mode = pyqtSignal(str)
|
|
||||||
keypress = pyqtSignal('QKeyEvent')
|
keypress = pyqtSignal('QKeyEvent')
|
||||||
shutdown_complete = pyqtSignal()
|
shutdown_complete = pyqtSignal()
|
||||||
quit = pyqtSignal()
|
quit = pyqtSignal()
|
||||||
@ -143,7 +140,6 @@ class TabbedBrowser(TabWidget):
|
|||||||
tab.urlChanged.connect(self._filter.create(self.cur_url_changed))
|
tab.urlChanged.connect(self._filter.create(self.cur_url_changed))
|
||||||
# hintmanager
|
# hintmanager
|
||||||
tab.hintmanager.hint_strings_updated.connect(self.hint_strings_updated)
|
tab.hintmanager.hint_strings_updated.connect(self.hint_strings_updated)
|
||||||
tab.hintmanager.set_mode.connect(self.set_mode)
|
|
||||||
tab.hintmanager.set_cmd_text.connect(self.set_cmd_text)
|
tab.hintmanager.set_cmd_text.connect(self.set_cmd_text)
|
||||||
# misc
|
# misc
|
||||||
tab.titleChanged.connect(self.on_title_changed)
|
tab.titleChanged.connect(self.on_title_changed)
|
||||||
|
Loading…
Reference in New Issue
Block a user