Compare commits

..

19 commits

Author SHA1 Message Date
a9d7f96ad2
nvim: Update plugins 2023-08-25 16:32:51 +02:00
c781693c26
qutebrowser: Change qute-gemini to open tab related
Using the userscript qute-gemini to open any tabs
(if invoked as qute-gemini-tab) to be related to
the current tab.
2023-08-25 16:32:22 +02:00
8bf61fc582
papistui: Add page scroll and info window
Added info window displaying abstracts or citation information.
Added quick page scrolling with <c-f> <c-u> mimicking vim.
2023-08-25 16:31:09 +02:00
0e12325730
papis: Change papis-reload to work on current lib
Papis reload will now only rebuild the cache of the currently
active library by default. To rebuild the cache of all libraries
papis knows, simply supply the `--all` switch.
2023-08-25 16:27:42 +02:00
6122077124
papis: Add papis-tag tag-listing command
Command takes a query and lists all the tags contained in
all documents of the query sorted alphabetically.
2023-08-25 16:26:43 +02:00
bda8a3d6f6
papis: Extend papis-show to use rich output
Papis show can now show output styled by python-rich if it
is in the environment. Otherwise falls back to normal
console printing.
Added more information to output (journal, volume, issue,
type, doi) but also added `-s` switch which returns to
old single-line behavior for copying to other programs.
2023-08-25 16:25:54 +02:00
4994e9782d
qutebrowser: Remove gemini shortcut from main link
Main linking buttons (f/F) *can* be used for this but the resulting
userscript has to account for many more different scenarios than
opening a page.

If it does not, we can not 'click' on text entry fields, dropdowns,
sliders etc with the f-buttons anymore.

This commit switches the qute-gemini script to be invoked via ,g or ,G
thus with the local leader mapping instead.
2023-08-25 16:24:25 +02:00
ae58c1c4ef
qutebrowser: Slightly refactor translate & codegrab
Code grabbing has been slightly refactored to always check for the
existence of the qutebrowser fifo before sending anything.

Translate has been fixed up a little to use lingva for selection
translations, only falling back to google translate for complete page
translations since I do not think any other services support this for
now.
2023-08-08 17:12:53 +02:00
f7304b8941
qutebrowser: Refactor gemini userscript
Now possibly a little less clunky (though still using soon-to-be
deprecated modules), and able to correctly surf gemini/non-gemini pages
as a userscript or as a stand-alone script (simply calling it from
command line).

Works as before for tabbed pages (the clunky rename/symlink way).

Can now also be used as the default way to surf to links so I switched
out my qutebrowser f/F link hinting for this script. Will simply open
links if staying on http but open gemini version as local file if moving
on to gemini.

Could probably be rewritten as an actual plugin to interject itself in
link opening to be a little more elegant (similar to the redirect code I
have running to move to open source web frontends).
2023-08-08 15:52:12 +02:00
f09a75820e
qutebrowser: Improve shaarli/wallabag bookmarkers
Both bookmarkers can now either send the current page ("s for sending to
shaarli; "w to send to wallabag) or send any link on the current page
(;s for shaarli, ;w for wallabag).

Both have been adapted to the same format, both can be sent a link as an
argument as well (./wallabag_add.sh 'myawesome.blog/entry').
2023-08-08 12:05:41 +02:00
b58bd2767d
qutebrowser: Make recently downloaded executable
Moved the qutebrowser userscript to open recently downloaded files
to be accessible as a normal shell script as well
(`recently-downloaded`).

Mapped this to Super+Shift+D in riverwm to be easily able to open
the most recent downloads from anywhere.

Double the default lines shown to 20.
2023-08-08 11:38:25 +02:00
7662c5b776
qutebrowser: Remove blocked hosts from repo
Blocked hosts reside in a single (giant) plaintext file, which we
now remove from the repository.

Especially with the new blocking sources we grew from around 700k
(which was already a lot at ~35000 lines) to around 5MB which is
just stupid to keep in the git repo if we don't have to.
Since qutebrowser automatically re-creates the file for us on
running `:adblock-update` there's no reason to waste space here.
2023-08-08 11:24:41 +02:00
84eed308e1
nvim: Update plugins and dictionaries 2023-08-08 09:55:38 +02:00
90fe61e2f2
bootstrap: Update stable packages
Micro is out, I have actually never used the editor after first install.
Tectonic is in, a wonderful platform to process LaTeX files with.
Beets gets the plugins I am using injected through pipx.
Vale is out, if we need it on a system we install with nvim mason.
Pipewire-roc is in, wonderful way to stream audio in local networks.
2023-08-07 12:31:54 +02:00
5caf254c44
nvim: Add D language server to auto config
Automatically install D lsp with mason.
2023-08-07 12:17:20 +02:00
0a3ca9f2b1
nvim: Add git conflict resolution mappings
Added simple merge conflict highlighting and resolution through
git-conflict.nvim plugin.

Allows moving to the next/prev conflict with ]x or [x respectively,
then resolving the conflict currently hovered by using ours/theirs/
both/or neither of the offered options (with `ho/hO/hm/hM`
respectively).
2023-08-07 11:30:09 +02:00
596962c4d1
nvim: Add more bracket movement options
Enabled bracketed module of mini.nvim plugin, which enables many
(many!) more bracket jumping options. Some examples are moving
through the bufferlist, comments, files, jumplist, etc with [
and ]. Integrated into whichkey through pre-defined 'desc'
options for each mapping.
2023-08-07 11:27:52 +02:00
9934c2e8f0
nvim: Disable automatic formatting on save
Default the option to disable on formatting on save, but add new
key mapping to toggle it on (`<leader>sa`) and off. Still
the remaining issue of files always being 'unsaved' state when
using formatting on save, but this allows quicker toggling for
now.
2023-08-07 11:26:17 +02:00
112d6d8fa9
sh: Remove auto-creation of xdg directories
Removed the test-if-it-exists create-if-not cycle of manual xdg
intervention on every shell startup since it created mostly nothing but
problems so far.

It especially gets in the way of creating network filesystem mappings in
the home folder with hangups, freezes, and blocking automounts whenever
a new shell session is opened.
2023-08-07 10:48:52 +02:00
27 changed files with 399 additions and 35710 deletions

2
.gitignore vendored
View file

@ -27,6 +27,8 @@ sponsorblock.txt
/qutebrowser/.config/qutebrowser/stylesheets
# ignore the generated readability file for webpages
readability.html
# ignore the adblock file generated by qutebrowser
blocked-hosts
# ignore vifm & ueberzug utility files
vifm-help.txt

View file

@ -17,6 +17,7 @@ aspell-de German dictionary for aspell R
aspell-en English dictionary for aspell R
atool A script for managing file archives of various types R
aubio A tool for extracting annotations from audio signals R
autofs A kernel-based automounter for Linux A
barrier Open-source KVM software based on Synergy (GUI) R
base Minimal package set to define a basic Arch Linux installation R
base-devel Basic tools to build Arch Linux packages R
@ -27,7 +28,7 @@ bat Cat clone with syntax highlighting and git integration R
bc An arbitrary precision calculator language R
beancount A personal double entry accounting and budgeting software P git+https://github.com/bratekarate/beancount-categorizer.git,beancount-dkb,fava,python-magic,smart-importer
bearssl Implementation of the SSL/TLS protocol (RFC 5246) written in C R
beets Organize your music collection from the command line P beetcamp
beets Organize your music collection from the command line P beetcamp,deets-describe,beets-ydl,pyacoustid,pylast
bemoji-git Emoji picker that remembers your favorites. A
bibclean BibTeX and Scribe bibliography prettyprinter and syntax checker A
biber A Unicode-capable BibTeX replacement for biblatex users R
@ -158,7 +159,6 @@ masterpdfeditor-free A complete solution for creation and editing PDF files - Fr
mbsync-git free (GPL) mailbox synchronization program A
mediainfo Supplies technical and tag information about a video or audio file (CLI interface) R
mermaid-cli Generation of diagram and flowchart from text in a similar manner as markdown (CLI) A
micro Modern and intuitive terminal-based text editor R
mimeo Open files by MIME-type or file name using regular expressions. A
minidlna A DLNA/UPnP-AV Media server (aka ReadyDLNA) R
minio-client Replacement for ls, cp, mkdir, diff and rsync commands for filesystems and object storage R
@ -219,6 +219,7 @@ perl-authen-sasl Perl/CPAN Module Authen::SASL : SASL authentication framework R
piavpn-bin Private Internet Access client A
pigz Parallel implementation of the gzip file compressor R
pipewire-alsa Low-latency audio/video router and processor - ALSA configuration R
pipewire-roc Low-latency audio/video router and processor - ROC streaming support R
playerctl mpris media player controller and lib for spotify, vlc, audacious, bmp, xmms2, and others. R
podman Tool and library for running OCI-based containers in pods R
powertop A tool to diagnose issues with power consumption and power management R
@ -290,6 +291,7 @@ task-spooler Queue up tasks from the shell for batch execution A
taskopen Script for taking notes and open urls with taskwarrior A
tasksh A shell command that wraps Taskwarrior commands A
tea A command line tool to interact with Gitea servers R
tectonic Modernized, complete, self-contained TeX/LaTeX engine, powered by XeTeX and TeXLive R
tex-gyre-fonts Substitute PostScript fonts in OpenType format R
texlab A cross-platform implementation of the Language Server Protocol for LaTeX. R
thermald The Linux Thermal Daemon program from 01.org R
@ -319,7 +321,6 @@ urlview-xdg-git A curses URL parser for text files. Git version, adds support fo
usql A universal command-line interface for SQL databases A
v4l2loopback-dkms v4l2-loopback device module sources R
vagrant Build and distribute virtualized development environments R
vale-bin A customizable, syntax-aware linter for prose A
vdirsyncer Synchronize CalDAV and CardDAV. R
viddy A modern watch command A
vifm A file manager with curses interface, which provides Vi[m]-like environment R

Can't render this file because it has a wrong number of fields in line 29.

View file

@ -79,6 +79,9 @@ riverctl map normal $mod+Shift P spawn "pass-pick"
# File upload
riverctl map normal $mod+Shift U spawn "$term -e --class float sharefile | xargs notify-send"
# Open recent downloads
riverctl map normal $mod+Shift D spawn "recently-downloaded"
# # Screenshot
riverctl map normal None Print spawn "screenshot"
riverctl map normal Shift Print spawn "screenshot | sharefile -"

View file

@ -0,0 +1,3 @@
-- help out mini.comment since the treesitter implementation does not have
-- comment functionality so far afaik
vim.bo.commentstring = "// %s"

View file

@ -22,47 +22,48 @@
"cmp_luasnip": { "branch": "master", "commit": "18095520391186d634a0045dacaa346291096566" },
"completion-vcard": { "branch": "master", "commit": "2220fd517a985ececed1adcf0e5be8f2815564c7" },
"dial.nvim": { "branch": "master", "commit": "54b503f906bc9e5ab85288414840a1b86d40769f" },
"dressing.nvim": { "branch": "master", "commit": "e6eff7a5a950a853c3903d906dbcea03f778db5f" },
"dressing.nvim": { "branch": "master", "commit": "c0b67f3e2950adc07b555d3e73e38275b4a585ce" },
"easyread.nvim": { "branch": "main", "commit": "0b07e315a4cd7d700c4a794bdddbec79fdc2628b" },
"fidget.nvim": { "branch": "main", "commit": "0ba1e16d07627532b6cae915cc992ecac249fb97" },
"friendly-snippets": { "branch": "main", "commit": "ea84a710262cb2c286d439070bad37d36fd3db25" },
"friendly-snippets": { "branch": "main", "commit": "377d45475b49e37460a902d6d569d2093d4037d0" },
"fwatch.nvim": { "branch": "main", "commit": "a691f7349dc66285cd75a1a698dd28bca45f2bf8" },
"git-conflict.nvim": { "branch": "main", "commit": "8d962d83cae924a314965f738ed1e05a4000d682" },
"gitsigns.nvim": { "branch": "main", "commit": "bb808fc7376ed7bac0fbe8f47b83d4bf01738167" },
"headlines.nvim": { "branch": "master", "commit": "ddef41b2664f0ce25fe76520d708e2dc9dfebd70" },
"headlines.nvim": { "branch": "master", "commit": "74a083a3c32a08be24f7dfcc6f448ecf47857f46" },
"jupyter-kernel.nvim": { "branch": "main", "commit": "5b409598033884a3d819e2a3bcd1fe340bc8d783" },
"lazy.nvim": { "branch": "main", "commit": "b7303a68309296fb4809c51ce0bf66722e5dc4f7" },
"lazy.nvim": { "branch": "main", "commit": "3ad55ae678876516156cca2f361c51f7952a924b" },
"lightspeed.nvim": { "branch": "main", "commit": "299eefa6a9e2d881f1194587c573dad619fdb96f" },
"lsp-setup.nvim": { "branch": "main", "commit": "64542fb0da06414cdfaa0c5236b743679bb7ba7f" },
"lsp_signature.nvim": { "branch": "master", "commit": "4665921ff8e30601c7c1328625b3abc1427a6143" },
"lualine.nvim": { "branch": "master", "commit": "05d78e9fd0cdfb4545974a5aa14b1be95a86e9c9" },
"lualine.nvim": { "branch": "master", "commit": "45e27ca739c7be6c49e5496d14fcf45a303c3a63" },
"magma-nvim-goose": { "branch": "main", "commit": "9a626aab63361d027541d023707f82e28d7f872c" },
"markdown-preview.nvim": { "branch": "master", "commit": "9becceee5740b7db6914da87358a183ad11b2049" },
"mason-lspconfig.nvim": { "branch": "main", "commit": "e86a4c84ff35240639643ffed56ee1c4d55f538e" },
"mason-null-ls.nvim": { "branch": "main", "commit": "ae0c5fa57468ac65617f1bf821ba0c3a1e251f0c" },
"mason.nvim": { "branch": "main", "commit": "3f6b544c75c01549f7a2a9e395e0f1cea42b25dd" },
"mason.nvim": { "branch": "main", "commit": "74eac861b013786bf231b204b4ba9a7d380f4bd9" },
"mini.nvim": { "branch": "main", "commit": "296ebbbd3e5ba5e43f5125efe18ad76fe3b632cc" },
"null-ls.nvim": { "branch": "main", "commit": "db09b6c691def0038c456551e4e2772186449f35" },
"nvim-base16": { "branch": "master", "commit": "4f3aa29f49b38edb6db1c52cea57e64ce3de2373" },
"nvim-cmp": { "branch": "main", "commit": "c4e491a87eeacf0408902c32f031d802c7eafce8" },
"null-ls.nvim": { "branch": "main", "commit": "0010ea927ab7c09ef0ce9bf28c2b573fc302f5a7" },
"nvim-base16": { "branch": "master", "commit": "6247ca9aa9f34644dfa290a6df3f6feefb73eb97" },
"nvim-cmp": { "branch": "main", "commit": "51f1e11a89ec701221877532ee1a23557d291dd5" },
"nvim-colorizer.lua": { "branch": "master", "commit": "dde3084106a70b9a79d48f426f6d6fec6fd203f7" },
"nvim-lspconfig": { "branch": "master", "commit": "dd11ba7b3c8f82d51b6d4dd7d68fce2d78bf78a0" },
"nvim-lspconfig": { "branch": "master", "commit": "0d29cad8de3b2c654315203fc1fe12fde722a18a" },
"nvim-notify": { "branch": "master", "commit": "ea9c8ce7a37f2238f934e087c255758659948e0f" },
"nvim-surround": { "branch": "main", "commit": "211eaad7c6d01ef4ac02cba9052b3082ec232101" },
"nvim-surround": { "branch": "main", "commit": "0d6882635817a2677749a330127d12ac30a4f3c8" },
"nvim-toggleterm.lua": { "branch": "main", "commit": "b90a1381e9b5b8596f49070ee86c71db267ac868" },
"nvim-tree.lua": { "branch": "master", "commit": "3b62c6bf2c3f2973036aed609d02fd0ca9c3af35" },
"nvim-treesitter": { "branch": "master", "commit": "cc360a9beb1b30d172438f640e2c3450358c4086" },
"nvim-treesitter-context": { "branch": "master", "commit": "6f8f788738b968f24a108ee599c5be0031f94f06" },
"nvim-treesitter-textsubjects": { "branch": "master", "commit": "b913508f503527ff540f7fe2dcf1bf1d1f259887" },
"nvim-tree.lua": { "branch": "master", "commit": "18c7a3119839adc4599d838726deae662859c8b2" },
"nvim-treesitter": { "branch": "master", "commit": "63260da18bf273c76b8e2ea0db84eb901cab49ce" },
"nvim-treesitter-context": { "branch": "master", "commit": "d8fd71428e02190d8f75ff915b6cca9e3063992c" },
"nvim-treesitter-textsubjects": { "branch": "master", "commit": "df75fcec548014f158cda6498ac38c4622c221e1" },
"nvim-ts-autotag": { "branch": "main", "commit": "6be1192965df35f94b8ea6d323354f7dc7a557e4" },
"nvim-ts-context-commentstring": { "branch": "main", "commit": "7f625207f225eea97ef7a6abe7611e556c396d2f" },
"nvim-ts-context-commentstring": { "branch": "main", "commit": "e9062e2dfb9854e6a927370f2d720de354c88524" },
"nvim-ts-rainbow2": { "branch": "master", "commit": "b3120cd5ae9ca524af9cb602f41e12e301fa985f" },
"nvim-web-devicons": { "branch": "master", "commit": "efbfed0567ef4bfac3ce630524a0f6c8451c5534" },
"otter.nvim": { "branch": "main", "commit": "0a32dbdd75730361a0a2d9746c48d9bdfcdf2cad" },
"nvim-web-devicons": { "branch": "master", "commit": "ab899311f8ae00a47eae8e0879506cead8eb1561" },
"otter.nvim": { "branch": "main", "commit": "dda3359750a2f9c0d6ae073d967296f57fe99d8b" },
"playground": { "branch": "master", "commit": "2b81a018a49f8e476341dfcb228b7b808baba68b" },
"plenary.nvim": { "branch": "master", "commit": "253d34830709d690f013daf2853a9d21ad7accab" },
"popup.nvim": { "branch": "master", "commit": "b7404d35d5d3548a82149238289fa71f7f6de4ac" },
"quarto-nvim": { "branch": "main", "commit": "35f86035e7b3846dbf168267ffe0021c3d312259" },
"smartcolumn.nvim": { "branch": "main", "commit": "0c572e3eae48874f25b74394a486f38cadb5c958" },
"smartcolumn.nvim": { "branch": "main", "commit": "c2441d4490b7485844ac9ff2d44d882ff7536979" },
"telescope-fzf-native.nvim": { "branch": "main", "commit": "9bc8237565ded606e6c366a71c64c0af25cd7a50" },
"telescope.nvim": { "branch": "master", "commit": "776b509f80dd49d8205b9b0d94485568236d1192" },
"twilight.nvim": { "branch": "main", "commit": "8bb7fa7b918baab1ca81b977102ddb54afa63512" },

View file

@ -290,6 +290,8 @@ map(
{ silent = true, desc = "colorize background" }
)
map("n", "<leader>sa", "<cmd>FormatOnSave<cr>", { silent = true, desc = "toggle format on save" })
-- PLUGIN: undotree
if is_available("undotree") then
map("n", "<leader>su", function()

View file

@ -84,7 +84,7 @@ local globals = {
maplocalleader = ",",
tex_flavor = "latex",
format_on_save = true, -- from personal toggle function
format_on_save = false, -- from personal toggle function
}
for o, v in pairs(globals) do

View file

@ -32,6 +32,7 @@ local servers = {
marksman = {},
pyright = {},
ruff_lsp = {},
serve_d = {},
tailwindcss = {},
taplo = {},
texlab = {},

View file

@ -36,3 +36,22 @@ starter.setup({
})
vim.api.nvim_set_hl(0, "MiniCursorword", { bold = true })
require("mini.bracketed").setup({
{
buffer = { suffix = "b", options = {} },
comment = { suffix = "c", options = {} },
conflict = { suffix = "", options = {} },
diagnostic = { suffix = "d", options = {} },
file = { suffix = "f", options = {} },
indent = { suffix = "", options = {} }, -- disable since we use indentscope above
jump = { suffix = "j", options = {} },
location = { suffix = "l", options = {} },
oldfile = { suffix = "o", options = {} },
quickfix = { suffix = "q", options = {} },
treesitter = { suffix = "t", options = {} },
undo = { suffix = "", options = {} }, -- disable since I don't need it
window = { suffix = "w", options = {} },
yank = { suffix = "y", options = {} },
},
})

View file

@ -1,4 +1,21 @@
return {
{
"akinsho/git-conflict.nvim",
event = "VeryLazy",
config = function()
require("git-conflict").setup({
default_mappings = false,
disable_diagnostics = true,
})
vim.keymap.set("n", "<localleader>ho", "<Plug>(git-conflict-ours)", { desc = "Conflict use ours" })
vim.keymap.set("n", "<localleader>hO", "<Plug>(git-conflict-theirs)", { desc = "Conflict use theirs" })
vim.keymap.set("n", "<localleader>hm", "<Plug>(git-conflict-both)", { desc = "Conflict use both" })
vim.keymap.set("n", "<localleader>hM", "<Plug>(git-conflict-none)", { desc = "Conflict use none" })
vim.keymap.set("n", "[x", "<Plug>(git-conflict-prev-conflict)", { desc = "Prev git conflict" })
vim.keymap.set("n", "]x", "<Plug>(git-conflict-next-conflict)", { desc = "Next git conflict" })
end,
lazy = false, -- TODO needs to be force refreshed in lazy loaded mode unfortunately
},
{
"lewis6991/gitsigns.nvim", -- show vcs changes on left-hand gutter
event = "VeryLazy",
@ -24,7 +41,7 @@ return {
gs.next_hunk()
end)
return "<Ignore>"
end, { expr = true })
end, { expr = true, desc = "Next git hunk" })
map("n", "[h", function()
if vim.wo.diff then
@ -34,7 +51,7 @@ return {
gs.prev_hunk()
end)
return "<Ignore>"
end, { expr = true })
end, { expr = true, desc = "Previous git hunk" })
-- Actions
require("which-key").register({ ["<localleader>h"] = { name = "+git" } })

View file

@ -183,3 +183,5 @@ endogeneity
outliers
GitLab
Gitea
caramelization
Maillard

View file

@ -1,4 +1,4 @@
c.aliases["gem"] = "hint links userscript qute-gemini"
c.aliases["gem"] = "spawn --userscript qute-gemini "
# Use q for quitting a tab (mimicks vim buffer) - qa is used for exiting
c.aliases["q"] = "tab-close"
@ -38,4 +38,4 @@ c.aliases["taskadd"] = "spawn --userscript taskadd"
c.aliases["cookie-block"] = "spawn --userscript qute-cookie-block"
# open last downloads in dmenu-like
c.aliases["recent-downloads"] = "spawn --userscript open_download"
c.aliases["recent-downloads"] = "spawn --userscript recently-downloaded"

View file

@ -1,15 +1,12 @@
c.content.blocking.enabled = True
c.content.blocking.method = "both"
c.content.blocking.adblock.lists = [
"https://www.malwaredomainlist.com/hostslist/hosts.txt",
"https://easylist.to/easylist/easylist.txt",
"https://easylist.to/easylist/easyprivacy.txt",
"https://someonewhocares.org/hosts/hosts",
"https://pgl.yoyo.org/adservers/serverlist.php?hostformat=hosts&mimetype=plaintext",
"https://secure.fanboy.co.nz/fanboy-cookiemonster.txt",
]
c.content.blocking.hosts.lists = [
"https://winhelp2002.mvps.org/hosts.zip",
"https://malwaredomains.lehigh.edu/files/justdomains.zip",
]
c.content.blocking.whitelist = ["piwik.org"]
c.content.autoplay = False
c.content.prefers_reduced_motion = True

View file

@ -6,6 +6,7 @@ lleader = ","
## CHANGED DEFAULTS
# rebind moving tabs to free for download
config.bind("gG", "tab-give")
# switch binds for scroll-marks and quick-/book-marks
@ -53,6 +54,11 @@ config.bind(lleader + "I", "spawn uoeia -v imv {url}")
config.bind(lleader + "i", "hint links spawn uoeia -v imv {hint-url}")
config.bind(lleader + "<Ctrl-i>", "hint images spawn uoeia -v imv {hint-url}")
# [G]emini shortcuts
# the full power of qutebrowser at your fingertips for any gemini page!
config.bind(f"{lleader}g", "hint all userscript qute-gemini")
config.bind(f"{lleader}G", "hint all userscript qute-gemini-tab")
# bind youtube-dl to download the current page/links
config.bind(lleader + "dM", "spawn vidl {url}")
config.bind(
@ -67,13 +73,14 @@ config.bind(lleader + "dp", "save-to-pdf", mode="normal")
config.bind("gD", "recent-downloads", mode="normal")
config.bind('"w', "add-wallabag", mode="normal") # add current page to wallabag
config.bind(";w", "hint links run add-wallabag") # add link to wallabag
config.bind(';w', "hint links userscript wallabag_add.sh") # add link to wallabag
config.bind('"s', "add-shaarli", mode="normal")
config.bind(';s', "hint links userscript shaarli_add.sh")
config.bind('"a', "send-to-archive", mode="normal")
config.bind('"t', "translate-page-google", mode="normal")
config.bind('"T', "translate-selection-google", mode="normal")
config.bind('"t', "translate-selection-google", mode="caret")
config.bind('"q', "show-qr")

View file

@ -42,7 +42,7 @@ elif command -v rofi >/dev/null 2>&1; then
)}
elif command -v bemenu >/dev/null 2>&1; then
ROFI_CMD="bemenu"
ROFI_ARGS="${ROFI_ARGS:--il 10}"
ROFI_ARGS="${ROFI_ARGS:--il 20}"
fi
msg() {

File diff suppressed because it is too large Load diff

View file

@ -14,15 +14,16 @@ else:
PYPERCLIP = True
def parse_text_content(element):
def parse_text_content(element) -> str:
root = ET.fromstring(element)
text = ET.tostring(root, encoding="unicode", method="text")
text = html.unescape(text)
return text
def send_command_to_qute(command):
with open(os.environ.get("QUTE_FIFO"), "w") as f:
def send_command_to_qute(command) -> None:
if fifo := os.environ.get("QUTE_FIFO"):
with open(fifo, "w") as f:
f.write(command)
@ -32,7 +33,7 @@ def main():
# https://github.com/qutebrowser/qutebrowser/blob/master/doc/userscripts.asciidoc
element = os.environ.get("QUTE_SELECTED_HTML")
code_text = parse_text_content(element)
if PYPERCLIP:
if pyperclip and PYPERCLIP:
pyperclip.copy(code_text)
send_command_to_qute(
"message-info 'copied to clipboard: {info}{suffix}'".format(

View file

@ -6,6 +6,20 @@
# SPDX-FileCopyrightText: 2020 petedussin
# SPDX-FileCopyrightText: 2020-2021 Sotiris Papatheodorou
# SPDX-License-Identifier: GPL-3.0-or-later
# 2022-2023 Marty Oehme (added stand-alone script capability)
# Use it as a qutebrowser userscript to open gemini pages:
# Put this file in qutebrowser userscript folder and call command
# `:spawn --userscript qute-gemini "gemini://my-gemini-url.org"`
# or
# `:hint links userscript qute-gemini` to open from selected link
# Rename file to `qute-gemini-tab` (or create symlink) to open
# any gemini url as a new tab.
# Since the script also opens normal URLs you can even replace your
# normal link hint mapping with it (usually f or F for tabbed) and
# continue surfing like normal, only that you can now also access
# any gemini pages as if they were part of the normal http protocol.
import cgi
import html
@ -41,7 +55,8 @@ CSS
_status_code_desc = {
"1": "Gemini status code 1 Input. This is not implemented in qute-gemini.",
"10": "Gemini status code 10 Input. This is not implemented in qute-gemini.",
"11": "Gemini status code 11 Sensitive Input. This is not implemented in qute-gemini.",
"11": """Gemini status code 11 Sensitive Input. This is not implemented
in qute-gemini.""",
"3": "Gemini status code 3 Redirect. Stopped after "
+ str(_max_redirects)
+ " redirects.",
@ -53,28 +68,41 @@ _status_code_desc = {
+ " redirects.",
"4": "Gemini status code 4 Temporary Failure. Server message: META",
"40": "Gemini status code 40 Temporary Failure. Server message: META",
"41": "Gemini status code 41 Server Unavailable. The server is unavailable due to overload or maintenance. Server message: META",
"42": "Gemini status code 42 CGI Error. A CGI process, or similar system for generating dynamic content, died unexpectedly or timed out. Server message: META",
"43": "Gemini status code 43 Proxy Error. A proxy request failed because the server was unable to successfully complete a transaction with the remote host. Server message: META",
"44": "Gemini status code 44 Slow Down. Rate limiting is in effect. Please wait META seconds before making another request to this server.",
"41": """Gemini status code 41 Server Unavailable.
The server is unavailable due to overload or maintenance. Server message: META""",
"42": """Gemini status code 42 CGI Error.
A CGI process, or similar system for generating dynamic content,
died unexpectedly or timed out. Server message: META""",
"43": """Gemini status code 43 Proxy Error.
A proxy request failed because the server was unable to successfully
complete a transaction with the remote host. Server message: META""",
"44": """Gemini status code 44 Slow Down. Rate limiting is in effect.
Please wait META seconds before making another request to this server.""",
"5": "Gemini status code 5 Permanent Failure. Server message: META",
"50": "Gemini status code 50 Permanent Failure. Server message: META",
"51": "Gemini status code 51 Not Found. he requested resource could not be found but may be available in the future. Server message: META",
"52": "Gemini status code 52 Gone. The resource requested is no longer available and will not be available again. Server message: META",
"53": "Gemini status code 53 Proxy Request Refused. The request was for a resource at a domain not served by the server and the server does not accept proxy requests. Server message: META",
"59": "Gemini status code 59 Bad Request. The server was unable to parse the client's request, presumably due to a malformed request. Server message: META",
"6": "Gemini status code 6 Client Certificate Required. This is not implemented in qute-gemini.",
"51": """Gemini status code 51 Not Found. The requested resource could
not be found but may be available in the future. Server message: META""",
"52": """Gemini status code 52 Gone. The resource requested is no longer
available and will not be available again. Server message: META""",
"53": """Gemini status code 53 Proxy Request Refused. The request was for
a resource at a domain not served by the server and the server does
not accept proxy requests. Server message: META""",
"59": """Gemini status code 59 Bad Request. The server was unable to
parse the client's request, presumably due to a malformed request.
Server message: META""",
"6": """Gemini status code 6 Client Certificate Required.
This is not implemented in qute-gemini.""",
}
def qute_url() -> str:
"""Get the URL passed to the script by qutebrowser."""
return os.environ["QUTE_URL"]
return os.environ.get("QUTE_URL", "")
def qute_fifo() -> str:
"""Get the FIFO or file to write qutebrowser commands to."""
return os.environ["QUTE_FIFO"]
return os.environ.get("QUTE_FIFO", "")
def html_href(url: str, description: str) -> str:
@ -118,7 +146,7 @@ def gemini_fetch_url(url: str) -> Tuple[str, str, str, str, str]:
url = "gemini://" + url
parsed_url = urllib.parse.urlparse(url)
if parsed_url.scheme != "gemini":
return "", "Received non-gemini:// URL: " + url
return "", "Received non-gemini:// URL: " + url, "59", "", "Non-gemini URL"
if parsed_url.port is not None:
useport = parsed_url.port
else:
@ -214,15 +242,15 @@ def gemtext_to_html(
pass
# Link
elif line.startswith("=>"):
l = line[2:].split(None, 1)
ln = line[2:].split(None, 1)
# Use the URL itself as the description if there is none
if len(l) == 1:
l.append(l[0])
if len(ln) == 1:
ln.append(ln[0])
# Encode the link description
l[1] = html.escape(l[1])
ln[1] = html.escape(ln[1])
# Resolve relative URLs
l[0] = gemini_absolutise_url(url, l[0])
lines.append("\t\t<p>" + html_href(l[0], l[1]) + "</p>")
ln[0] = gemini_absolutise_url(url, ln[0])
lines.append("\t\t<p>" + html_href(ln[0], ln[1]) + "</p>")
# Preformated toggle
elif line.startswith("```"):
if in_pre:
@ -316,7 +344,7 @@ def qute_error_page(url: str, description: str) -> str:
return "data:text/html;charset=UTF-8," + urllib.parse.quote(html_page)
def open_gemini(url: str, open_args: str) -> None:
def open_gemini(url: str) -> str:
"""Open Gemini URL in qutebrowser."""
# Get the Gemini content
content, content_url, status, meta, error_msg = gemini_fetch_url(url)
@ -328,30 +356,43 @@ def open_gemini(url: str, open_args: str) -> None:
tmpf = tempfile.NamedTemporaryFile("w", suffix=".html", delete=False)
tmp_filename = tmpf.name
tmpf.close()
if not tmp_filename:
return ""
with open(tmp_filename, "w") as f:
f.write(gemtext_to_html(content, content_url, url, status, meta))
open_url = " file://" + tmp_filename
# Open the HTML file in qutebrowser
with open(qute_fifo(), "w") as qfifo:
qfifo.write("open " + open_args + open_url)
return open_url
def open_other(url: str, open_args: str) -> None:
"""Open non-Gemini URL in qutebrowser."""
with open(qute_fifo(), "w") as qfifo:
qfifo.write("open " + open_args + " " + url)
def open_url(url: str, open_args: str) -> None:
parsed_url = urllib.parse.urlparse(url)
if parsed_url.scheme == "gemini":
to_open = open_gemini(url)
else:
to_open = url
if not to_open:
return
fifo = qute_fifo()
if fifo and fifo != "":
with open(fifo, "w") as qfifo:
qfifo.write(f"open {open_args} {to_open}")
return
os.system(f"xdg-open {to_open}")
if __name__ == "__main__":
# Open in the current or a new tab depending on the script name
if sys.argv[0].endswith("-tab"):
open_args = "-t"
open_args = "-b -r"
else:
open_args = ""
# Select how to open the URL depending on its scheme
url = qute_url()
parsed_url = urllib.parse.urlparse(url)
if parsed_url.scheme == "gemini":
open_gemini(url, open_args)
# Take url to open as argument or from qutebrowser url
if len(sys.argv) > 1:
url = sys.argv[1]
else:
open_other(url, open_args)
url = qute_url()
# Select how to open the URL depending on its scheme
open_url(url, open_args)

View file

@ -0,0 +1 @@
../../../bin/recently-downloaded

View file

@ -1,4 +1,27 @@
#! /usr/bin/bash
#! /usr/bin/env bash
#
# Send current page/link to a shaarli instance.
#
# Can be used for sending the current page via:
# :spawn --userscript shaarli_add.sh
# for sending an arbitrary page passed as argument:
# :spawn --userscript shaarli_add.sh https://myinterestingpage.com
# or for sending a hinted link:
# :hint links userscript shaarli_add.sh
#
# Configure your shaarli instance with this:
SHAARLI_INSTANCE="https://links.martyoeh.me"
# send page to shaarli instance and open the 'post' page to edit it
if [ "$#" -gt 0 ]; then
BM="$SHAARLI_INSTANCE/?post=$*"
else
BM="$SHAARLI_INSTANCE/?post=$QUTE_URL"
fi
if [ -n "$QUTE_FIFO" ]; then
echo "open -t -r $BM" >>"$QUTE_FIFO"
else
xdg-open "$BM"
fi
# send current page to my personal shaarli instance and open the 'post' page to edit it
echo "open https://links.martyoeh.me/?post=$QUTE_URL" >>"$QUTE_FIFO"

View file

@ -3,6 +3,7 @@
# Translate the page, or if `--text` argument is given the current selection, with google translate.
#
# Adapted code from https://github.com/AckslD/Qute-Translate, with much gratitude.
PAGE="https://lingva.garudalinux.org/SOURCELANGUAGE/TARGETLANGUAGE/TRANSLATETEXT"
while [ $# -gt 0 ]; do
case $1 in
@ -38,14 +39,13 @@ fi
if [ "$QUTE_TRANS_URL" = "false" ]; then
# Translate selected text
PAGE="https://translate.google.com/#view=home&op=translate&"
CONT_KEY="text"
CONTENT=$QUTE_SELECTED_TEXT
PAGE=$(echo "$PAGE" | sed -e "s/SOURCELANGUAGE/$QUTE_TRANS_SOURCE/" -e "s/TARGETLANGUAGE/$QUTE_TRANS_TARGET/" -e "s/TRANSLATETEXT/$QUTE_SELECTED_TEXT/")
echo "open -t ${PAGE}" >>"$QUTE_FIFO"
else
# Default translate URL
PAGE="https://translate.google.com/translate?"
CONT_KEY="u"
CONTENT=$QUTE_URL
CONTENT="$QUTE_URL"
echo "open -t ${PAGE}sl=${QUTE_TRANS_SOURCE}&tl=${QUTE_TRANS_TARGET}&${CONT_KEY}=\"${CONTENT}\"" >>"$QUTE_FIFO"
fi
echo "open -t ${PAGE}sl=$QUTE_TRANS_SOURCE&tl=$QUTE_TRANS_TARGET&$CONT_KEY=$CONTENT" >>"$QUTE_FIFO"

View file

@ -1,4 +1,4 @@
#! /usr/bin/bash
#! /usr/bin/env bash
#
# Send current page/link to a wallabag instance.
#
@ -14,7 +14,13 @@ WALLABAG_INSTANCE="https://read.martyoeh.me"
# only works for wallabag v2.*
if [ "$#" -gt 0 ]; then
echo "open -b -r $WALLABAG_INSTANCE/bookmarklet?url=$*" >>"$QUTE_FIFO"
BM="$WALLABAG_INSTANCE/bookmarklet?url=$*"
else
echo "open -b -r $WALLABAG_INSTANCE/bookmarklet?url=$QUTE_URL" >>"$QUTE_FIFO"
BM="$WALLABAG_INSTANCE/bookmarklet?url=$QUTE_URL"
fi
if [ -n "$QUTE_FIFO" ]; then
echo "open -b -r $BM" >>"$QUTE_FIFO"
else
xdg-open "$BM"
fi

View file

@ -37,41 +37,6 @@ test "$XDG_BIN_HOME" || export XDG_BIN_HOME="$HOME/.local/bin"
# anything on BIN_HOME should be executable form anywhere
export PATH="$PATH:$XDG_BIN_HOME"
xdg_isThere() {
if [ -e "$1" ] || [ -h "$1" ]; then
true
else
false
fi
}
xdg_makeForUser() {
mkdir -p "$1"
chmod 0700 "$1"
}
if [ -h "$XDG_MEDIA_DIR" ] && [ ! -e "$XDG_MEDIA_DIR" ]; then
rm "$XDG_MEDIA_DIR"
xdg_makeForUser "$XDG_MEDIA_DIR"
fi
## ensure directories exist
xdg_isThere "$XDG_BIN_HOME" || xdg_makeForUser "$XDG_BIN_HOME"
xdg_isThere "$XDG_CACHE_HOME" || xdg_makeForUser "$XDG_CACHE_HOME"
xdg_isThere "$XDG_CONFIG_HOME" || xdg_makeForUser "$XDG_CONFIG_HOME"
xdg_isThere "$XDG_DATA_HOME" || xdg_makeForUser "$XDG_DATA_HOME"
# create xdg-user-dirs if necessary
xdg_isThere "$XDG_DESKTOP_DIR" || xdg_makeForUser "$XDG_DESKTOP_DIR"
xdg_isThere "$XDG_DOCUMENTS_DIR" || xdg_makeForUser "$XDG_DOCUMENTS_DIR"
xdg_isThere "$XDG_DOWNLOAD_DIR" || xdg_makeForUser "$XDG_DOWNLOAD_DIR"
xdg_isThere "$XDG_MUSIC_DIR" || xdg_makeForUser "$XDG_MUSIC_DIR"
xdg_isThere "$XDG_PICTURES_DIR" || xdg_makeForUser "$XDG_PICTURES_DIR"
xdg_isThere "$XDG_VIDEOS_DIR" || xdg_makeForUser "$XDG_VIDEOS_DIR"
xdg_isThere "$XDG_PROJECTS_DIR" || xdg_makeForUser "$XDG_PROJECTS_DIR"
unset -f xdg_isThere xdg_makeForUser
## Applications that can be set through environment variables
export ANDROID_HOME="$XDG_DATA_HOME/android"
export ATOM_HOME="$XDG_DATA_HOME/atom"

View file

@ -25,18 +25,37 @@ documentlist:
rowstyle: white_bg
separator: " \u2502 "
keymappings:
' ': mark_selected
' ': mark_down
/: search_mode
<key_down>: scroll_down
<key_up>: scroll_up
<ctrl-f>: page_down
<ctrl-b>: page_up
'?': help
G: jump_to_bottom
e: edit
gg: jump_to_top
j: scroll_down
k: scroll_up
o: open
e: edit
n: papis edit -n papis_id:{doc['papis_id']}
q: quit
t: tag
ii:
- info_toggle
- "Toggle info window"
ij:
- info_cycle
- "Cycle info windows"
infowindow:
default_on: False
views:
apa:
content: "{format_reference(doc)}"
abstract:
content: "{doc['abstract']}"
linewrap: True
height: 8
statusbar:
left:
default: <black_white> {info["mode_upper"]} <black_white>

View file

@ -3,13 +3,25 @@
#
# This tiny script updates all libraries by rebuilding their caches.
# Useful to invoke after manual edits in one of your library folders
# so you don't have to think about which library you changed stuff in
# if you have many 'sub-libraries' (one library location with sub-
# directories).
# You don't have to think about which library you changed stuff in
# and just get everything updated. Might take a little time but
# should generally be a quick process (even with 1000s of entries).
# should generally be a quick process ().
import papis.api
from argparse import ArgumentParser
libs = papis.api.get_libraries()
parser = ArgumentParser()
parser.add_argument(
"--all", "-a", help="reload all libraries not just current", action="store_true"
)
args = parser.parse_args()
if args.all:
libs = papis.api.get_libraries()
else:
libs = [papis.api.get_lib_name()]
for lib in libs:
papis.api.clear_lib_cache(lib)

View file

@ -1,6 +1,116 @@
#!/usr/bin/env bash
#!/usr/bin/env python
# papis-short-help: Display pretty human-readable document overview
#
# TODO strip {} from bibtex entries to really pretty print
# Takes a query and displays the metadata of the results. Uses
# python-rich to display pretty panels if it exists in the environment,
# otherwise displays regular text.
# Can be invoked with -s to display single-line results better for
# pasting into other documents.
papis -l "${PAPIS_LIB}" list --format "{doc[author]} ({doc[year]}). {doc[title]}." "$@"
import argparse
from importlib.util import find_spec
from papis import database
from papis.database.base import Database
from papis.document import Document
from dataclasses import dataclass, field
parser = argparse.ArgumentParser()
parser.add_argument(
"--short", "-s", help="only display single-line quick info", action="store_true"
)
parser.add_argument(
"--url",
dest="identifier",
help="display identifier (doi, isbn, url) or not",
action=argparse.BooleanOptionalAction,
default=True,
)
parser.add_argument("query", nargs="*", help="the query to search for")
args = parser.parse_args()
@dataclass
class DocInfo:
author: str = ""
title: str = ""
year: str = ""
journal: str = ""
volume: str = ""
issue: str = ""
pages: str = ""
publisher: str = ""
tags: list = field(default_factory=lambda: [])
dtype: str = ""
identifier: str = ""
doi: str = ""
@staticmethod
def from_Document(doc: Document):
t: list[str] | str = doc.get("tags", "")
tags = (
t.replace(";", ",").replace(" ", "").split(",") if isinstance(t, str) else t
)
return DocInfo(
author=doc.get("author", ""),
title=doc.get("title", ""),
year=doc.get("year", ""),
journal=doc.get("journal", ""),
volume=doc.get("volume", ""),
issue=doc.get("issue", ""),
pages=doc.get("pages", ""),
publisher=doc.get("publisher", ""),
tags=tags,
dtype=doc.get("type", ""),
identifier=doc.get("doi", doc.get("isbn", doc.get("url", ""))),
)
def main(db: Database, args) -> None:
query = " ".join(args.query)
docs: list[Document] = db.query(query)
for doc in docs:
info = DocInfo.from_Document(doc)
if args.short:
print_short(info, with_identifier=args.identifier)
else:
print_info(info, with_identifier=args.identifier)
def print_short(doc: DocInfo, with_identifier: bool = True) -> None:
print(
f"{doc.author} ({doc.year}). {doc.title}. "
f"{doc.identifier if with_identifier else ''}\n"
)
def print_info(doc: DocInfo, with_identifier: bool = True) -> None:
if find_spec("rich"):
from rich import print as richprint
from rich.panel import Panel
info: str = (
f"[red]{doc.author}[/red] ({doc.year}) "
f"[steel_blue]\\[{doc.dtype}][/steel_blue]\n"
f"[bold]{doc.title}[/bold]\n"
f"{doc.journal} ({doc.volume}/{doc.issue}){doc.pages} - {doc.publisher}\n"
f"[grey69]{[tag for tag in doc.tags]} "
)
if with_identifier:
info += f"[link={doc.identifier}]{doc.identifier}[/link][/grey69]"
richprint(Panel(info, expand=False))
else:
info: str = (
f"{doc.author} ({doc.year}) "
f"[{doc.dtype}]\n"
f"{doc.title}\n"
f"{doc.journal} ({doc.volume}/{doc.issue}){doc.pages} - {doc.publisher}\n"
f"{[tag for tag in doc.tags]} "
f"{doc.identifier}"
if with_identifier
else ""
)
print(f"{info}\n---")
if __name__ == "__main__":
main(database.get(), args)

View file

@ -0,0 +1,39 @@
#!/usr/bin/env python
# papis-short-help: List all tags occuring in query items
#
# Takes a query and spits out a sorted list of all tags contained therein,
# nothing more.
# Can be very useful for things like picking a tag or two and listing all
# items that contain it:
# $ papis tags "*" | fzf | xargs papis show "tags:{}"
import argparse
from papis import database
from papis.database.base import Database
from papis.document import Document
parser = argparse.ArgumentParser()
parser.add_argument("query", nargs="*", help="the query to search for")
args = parser.parse_args()
def main(db: Database, args) -> None:
query = " ".join(args.query)
docs: list[Document] = db.query(query)
all_tags: set[str] = set()
for doc in docs:
t: list[str] | str = doc.get("tags", "")
tags = (
t.replace(";", ",").replace(" ", "").split(",") if isinstance(t, str) else t
)
for tag in tags:
all_tags.add(tag)
for tag in sorted(all_tags):
print(tag)
if __name__ == "__main__":
main(database.get(), args)