config.py (6755B)
1 from PyQt6.QtCore import QUrl 2 from qutebrowser.api import interceptor 3 from qutebrowser.browser import commands 4 import subprocess 5 6 # import <str> can mean import ./<str>.py apparently. 7 # Great, transparent, design. 8 import search 9 import stylesheets 10 11 # Qutebrowser requires me to tell it this or else it 12 # gives an annoying message each time it opens. 13 config.load_autoconfig(False) 14 15 # Save tabs + urls 16 c.auto_save.session = True 17 18 # Didn't ask. 19 c.changelog_after_upgrade = 'never' 20 21 # Don't annoy me. 22 c.new_instance_open_target = 'tab-bg-silent' 23 24 white = '#cccccc' 25 normfg = '#cccccc' 26 normbg = '#050a10' 27 selbg = '#1b364b' 28 29 # Selected tabs 30 c.colors.tabs.selected.even.bg = '#1b364b' 31 c.colors.tabs.selected.odd.bg = '#1b364b' 32 c.colors.tabs.selected.even.fg = white 33 c.colors.tabs.selected.odd.fg = white 34 c.colors.tabs.even.bg = '#050a10' 35 c.colors.tabs.odd.bg = '#050a10' 36 c.colors.tabs.even.fg = white 37 c.colors.tabs.odd.fg = white 38 39 # Unselected tabs 40 c.colors.webpage.darkmode.enabled = False 41 c.colors.webpage.darkmode.enabled = False 42 43 # Statusbar 44 c.colors.statusbar.url.hover.fg = 'aqua' 45 c.colors.statusbar.progress.bg = selbg 46 c.colors.statusbar.command.private.fg = '#005f87' 47 c.colors.statusbar.command.private.bg = selbg 48 c.colors.statusbar.passthrough.fg = '#bb5540' 49 c.colors.statusbar.passthrough.bg = normbg 50 c.colors.statusbar.normal.fg = normfg 51 c.colors.statusbar.normal.bg = 'black' 52 c.colors.statusbar.command.fg = '#005f87' 53 c.colors.statusbar.command.bg = 'black' 54 55 # Completion 56 # c.colors.completion.category.border.bottom = 'black' 57 # c.colors.completion.category.border.top = 'black' 58 # c.colors.completion.category.fg = 'white' 59 # c.colors.completion.even.bg = '#333333' 60 # c.colors.completion.fg = [white, white, 'white'] 61 # c.colors.completion.odd.bg = '#444444' 62 # c.colors.completion.odd.bg = '#444444' 63 # c.colors.completion.category.fg = cyan 64 # c.colors.completion.category.bg = normbg 65 # c.colors.completion.category.border.bottom = normbg 66 # c.colors.completion.category.border.top = normbg 67 # c.colors.completion.item.selected.bg = '#e8c000' 68 # c.colors.completion.item.selected.border.bottom = '#bbbb00' 69 # c.colors.completion.item.selected.border.top = '#bbbb00' 70 # c.colors.completion.item.selected.fg = 'black' 71 # c.colors.completion.item.selected.match.fg = '#ff4444' 72 # c.colors.completion.match.fg = '#ff4444' 73 # c.completion.scrollbar.width = 0 74 # c.completion.scrollbar.padding = 0 75 # c.colors.completion.scrollbar.bg = normbg 76 # c.colors.completion.scrollbar.fg = normbg 77 78 # Tabbed muscle memory 79 config.bind('<Alt-q>', 'tab-close') 80 config.bind('<Alt-h>', 'tab-prev') 81 config.bind('<Alt-l>', 'tab-next') 82 config.bind('<Alt-Shift-h>', 'tab-prev') 83 config.bind('<Alt-Shift-l>', 'tab-next') 84 85 # Darkmode 86 c.colors.webpage.bg = '#050a10' 87 c.colors.webpage.darkmode.algorithm = 'lightness-cielab' 88 c.colors.webpage.darkmode.enabled = True 89 c.colors.webpage.darkmode.policy.images = 'never' 90 c.colors.webpage.darkmode.policy.page = 'always' 91 c.colors.webpage.preferred_color_scheme = 'dark' 92 93 # Configuration 94 ## cd to qutebrowser dir before editing to get quick access to other files 95 c.editor.command = ['rc', '-c', 'cd `$nl{dirname \'{file}\'}; st -e vim `$nl{basename \'{file}\'}'] 96 config.bind('R', 'config-source') 97 config.bind('e', 'config-edit') 98 99 # Shady 100 c.aliases = {'tor': 'set content.proxy socks://localhost:9050 ;; set content.javascript.enabled false ;; open -t check.torproject.org', 101 'i2p': 'set content.proxy http://localhost:4444 ;; set content.javascript.enabled false ;; open -t localhost:7070', 102 'unproxy': 'set content.proxy none ;; set content.javascript.enabled true', 103 'jon': 'set content.javascript.enabled true', 104 'joff': 'set content.javascript.enabled false'} 105 106 # I need to plumb 107 config.bind('d', 'hint all download') 108 c.downloads.location.directory = "~/downloads/" 109 110 # Warp the mouse as seen by qtwebengine 111 config.bind('a', 'hint all hover') 112 113 # Alphabet soup 114 config.bind('A', 'spawn --userscript randomagent') 115 c.content.headers.user_agent = 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/110.0.0.0 Safari/537.36' 116 117 # Stylesheets 118 c.content.user_stylesheets = stylesheets.list 119 120 # Home/default page 121 c.url.default_page = 'about:blank' 122 config.bind('~', 'open file:///home/hayden/.config/qutebrowser/home.html') 123 124 # Hint characters. 125 # Same as the default, but with f placed last. It seems that qutebrowser will 126 # construct multichar hints by going right to left to select the first char. 127 # Since f is the default hint binding I think this will make hints quicker to 128 # type as my finger should already be on f when it is generating hints such as 129 # 'fa', 'fb', 'fc'... 130 c.hints.chars = 'asdlghjkf' 131 132 # Search (search.py) 133 c.url.open_base_url = True 134 c.url.searchengines = search.list 135 136 # Security 137 ## Uh-oh gmail might break with this option! Oh no! 138 c.content.cookies.accept = 'no-3rdparty' 139 ## DNT does nothing but provide a more unique fingerprint 140 c.content.headers.do_not_track = None 141 ## I know, I know, but I don't care. 142 c.downloads.prevent_mixed_content = False 143 144 # Redirects 145 def domainredir(info: interceptor.Request): 146 host = info.request_url.host() 147 target = QUrl(info.request_url) 148 149 # Fuck python. Why can't I split these out on to multiple lines and indent 150 # them? Why can't you give me a switch statement? I would love for 151 # string-capable switch statements to exist in more languages. 152 if (host == 'twitter.com' or host == 'www.twitter.com' or host == 'mobile.twitter.com'): 153 target.setHost('nitter.io.lol'); 154 elif (host == 'reddit.com' or host == 'www.reddit.com' or host == 'teddit.net'): 155 target.setHost('old.reddit.com'); 156 elif (host == 'en.m.wikipedia.org'): 157 target.setHost('en.wikipedia.org'); 158 else: 159 return 160 161 try: 162 info.redirect(target) 163 except interceptor.interceptors.RedirectException: 164 pass 165 interceptor.register(domainredir) 166 167 # Clipboard (use primary for everything) 168 config.unbind('Pp') 169 config.unbind('PP') 170 config.unbind('pp') 171 config.unbind('pP') 172 config.unbind('yD') 173 config.unbind('yM') 174 config.unbind('yP') 175 config.unbind('yT') 176 config.unbind('yY') 177 config.bind('P', 'open -t -- {primary}') 178 config.bind('p', 'open -- {primary}') 179 config.bind('yd', 'yank domain -s') 180 config.bind('ym', 'yank inline [{title}]({url}) -s') 181 config.bind('yp', 'yank pretty-url -s') 182 config.bind('yt', 'yank title -s') 183 config.bind('yy', 'yank -s') 184 config.bind('yh', 'hint all yank-primary') 185 186 # Keeps getting in the way 187 config.unbind('q') 188 189 # Bookmarks 190 config.bind('m', 'bookmark-add') 191 config.bind('b', 'set-cmd-text -s :bookmark-load') 192 config.bind('B', 'set-cmd-text -s :bookmark-load -t') 193 config.bind('M', 'set-cmd-text -s :bookmark-del') 194 195 # Notifications 196 c.content.notifications.presenter = 'herbe'