mirror of
https://github.com/RyanGreenup/cadmus.git
synced 2025-08-18 03:41:18 +02:00
Merge branch 'master' into feature/shorter-alternatives
This commit is contained in:
1
.gitignore
vendored
Normal file
1
.gitignore
vendored
Normal file
@@ -0,0 +1 @@
|
||||
config.json
|
285
README.md
285
README.md
@@ -3,98 +3,92 @@ Shell Scripts to Facilitate Effective Note Taking
|
||||
|
||||
## Introduction
|
||||
|
||||
Essentially I ~~used to~~ have a dozen shell scripts in `~/bin` that I use to capture notes,
|
||||
this is an attempt to wrap them into a single script and then have aliases to make them quick to access.
|
||||
This is a **self-contained** shell script that uses pre-existing tools (such as TMSU and recoll) to provide an interface for markdown notes.
|
||||
|
||||

|
||||
It's command based and prints out available subcommands for any given command, these means you can use a directory of markdown files like a personal wiki, much like OneNote/Evernote/Notable, for example:
|
||||
|
||||
The idea is that it is just a menu to dispatch different scripts so I could
|
||||
share those scripts with classmates.
|
||||
|
||||
## Design Philosophy
|
||||

|
||||
|
||||
- ****<span style="color:rgb(90,210,90);font-family:Courier New,Courier, monospace,serif;">cadmus</span>**** acts as a menu for scripts to acheive things
|
||||
- the script name ~~will~~ should always be printed to the terminal so the individual
|
||||
script can be repurposed with out fishing through code.
|
||||
- Subscripts ~~will~~ should take *only one* argument (or `STDIN`)
|
||||
- If the first argument is either `-h` or `--help` help will be printed and then `exit 0`
|
||||
- This might lead to some limitations but the simplicity is for sanity, modularity and extensibility.
|
||||
- Will always return absolute path.
|
||||
- I played around with relative path but it got confusing when calling the script from inside a function inside a script, so instead if you want a relative path you should do `scriptname './' | xargs realpath --relative-to='./'`
|
||||
- Be a Front end to tie together different scripts and tools
|
||||
- Don't replicate work other people have done.
|
||||
- Plain Text, Open Source.
|
||||
- Be Modular
|
||||
- Pipe in input, output goes to STDOUT
|
||||
- Leave Aliases and piping to the user
|
||||
- See [Recommended Aliases](#recommended-aliases)
|
||||
- ****<span style="color:rgb(90,210,90);font-family:Courier New,Courier, monospace,serif;">cadmus</span>**** will take the notes directory from the global variable `CADMUS_NOTES_DIR`
|
||||
- The Actual work will be done by subscripts denoted by `description.bash`
|
||||
- The subscripts will take the note directory as an argument so they are portable and modular
|
||||
- The Arguments will be shifted and then all passed down to subfunctions
|
||||
and an overview of what it looks like in the terminal
|
||||
|
||||

|
||||
|
||||
For example if you wanted to extract all the tags from your markdown notes (either `#tags` or from the YAML), cadmus has a tool for that:
|
||||
|
||||

|
||||
|
||||
|
||||
Ultimately the idea is it is to act a menu to dispatch different scripts I already had so I could
|
||||
more easily share those scripts with classmates.
|
||||
|
||||
The real heavy lifting is done by Pandoc, Recoll, ripgrep, skim/fzf, TMSU etc.
|
||||
|
||||
## Installation
|
||||
|
||||
To install:
|
||||
### Automatic
|
||||
|
||||
Copy this into your shell:
|
||||
|
||||
|
||||
``` bash
|
||||
cd $(mktemp -d)
|
||||
wget https://raw.githubusercontent.com/RyanGreenup/cadmus/master/install.sh
|
||||
bash install.sh
|
||||
```
|
||||
|
||||
|
||||
- Cadmus will work from within a self-contained directory and add a symlink to `~/.local/bin`
|
||||
- in this way it's zero lock-in, it does not modify your curr directory of Markdown files.
|
||||
- Installation will automatically create a config file in its directory (which is by default `~/.cadmus`
|
||||
- The script will list any [dependencies](#dependencies) that are not satisfied.
|
||||
|
||||
### Manual
|
||||
|
||||
To install manually:
|
||||
|
||||
1. satisfy [the dependencies](#Dependencies)
|
||||
2. [Set up Recoll](#Configuring-recoll)
|
||||
3. Download cadmus and put it in the `PATH`
|
||||
3. Download cadmus and put it into the `PATH`
|
||||
```bash
|
||||
mkdir ~/.cadmus && \
|
||||
git clone https://github.com/RyanGreenup/cadmus ~/.cadmus \
|
||||
|| echo "Delete ~/.cadmus first"
|
||||
ln -s ~/.cadmus/bin/cadmus $HOME/bin/
|
||||
|| echo "Delete $HOME/.cadmus first"
|
||||
mkdir -p $HOME/.local/bin
|
||||
ln -s "$HOME/.cadmus/bin/cadmus" "$HOME/.local/bin/"
|
||||
```
|
||||
3. If you haven't already add `$HOME/bin` to the `$PATH` variable, something like this should be fairly shell agnostic:
|
||||
3. According to the [*SystemD Standard*](https://www.freedesktop.org/software/systemd/man/file-hierarchy.html) `~/.local/bin` should be in `$PATH`, if you are using some other init implementation you can add this directory to `"$PATH"` it by doing something like this:
|
||||
|
||||
``` bash
|
||||
echo $PATH | grep "$HOME/bin" &> /dev/null && echo "$HOME/bin in path already" || ls "$HOME/bin" &> /dev/null && echo 'PATH="$PATH:$HOME/bin"' >> $HOME/.profile
|
||||
## Should work in bash/zsh/fish
|
||||
echo $PATH | grep "$HOME/.local/bin" &> /dev/null && echo "$HOME/.local/bin in path already" || ls "$HOME/.local/bin" &> /dev/null && echo 'PATH="$PATH:$HOME/.local/bin"' >> $HOME/.profile
|
||||
|
||||
```
|
||||
|
||||
4. You will probably need to change the directory to your notes in the script:
|
||||
> When first run, the script will prompt you to make a config file in the directory in which it is run.
|
||||
|
||||
```bash
|
||||
which cadmus | xargs xdg-open
|
||||
```
|
||||
|
||||
```
|
||||
readonly NOTES_DIR="$HOME/Notes/"
|
||||
readonly SERVER_DIR="/var/www/html/MD"
|
||||
readonly MKDOCS_YML="$HOME/Notes/mkdocs.yml"
|
||||
```
|
||||
### Assumptions
|
||||
|
||||
It is assumed that:
|
||||
|
||||
1. Notes are:
|
||||
1. *Markdown* files with a `.md` extension
|
||||
3. Recoll updates it's index on the fly
|
||||
* The notes directory will need to be indexed by *Recoll* in order for
|
||||
the results to show up when using `cadmus search`.
|
||||
3. SSD
|
||||
* I use an SSD and so I let some scripts be pretty inefficient (for example something like `grep | cut |
|
||||
xargs find` to avoid creating a variable), I don't know if HDD performance would be great.
|
||||
5. All Notes have Unique Names
|
||||
6. On *MacOS* you'll need to define `xdg-open` and have GNU coreutils, so do something like:
|
||||
```bash
|
||||
alias xdg-open='open &>/dev/null'
|
||||
alias realpath=grealpath &>/dev/null
|
||||
```
|
||||
[*nushell*]: https://github.com/nushell/nushell
|
||||
[*Fish*]: https://fishshell.com/
|
||||
[*OMF*]: https://github.com/oh-my-fish/oh-my-fish
|
||||
|
||||
|
||||
|
||||
<!---
|
||||
4. Copy the help files to `/usr/share/cadmus`
|
||||
|
||||
5. Copy in the scripts, with [*stow*] something like this should be sensible:
|
||||
|
||||
```bash
|
||||
exec bash
|
||||
cd ~/DotFiles
|
||||
|
||||
if [[ -d ".git" ]]; then
|
||||
echo "Adding Submodule";
|
||||
git submodule add https://github.com/RyanGreenup/cadmus
|
||||
else echo "Cloning Repository";
|
||||
git clone https://github.com/RyanGreenup/cadmus
|
||||
fi
|
||||
|
||||
stow -t $HOME -S cadmus
|
||||
```
|
||||
|
||||
|:warning: WARNING |
|
||||
| --- |
|
||||
| Stow is [currently broken][stowIssue] on Arch If you are using Stow 2.3.1-2 downgrade |
|
||||
> Downgrade with:
|
||||
> sudo pacman -U https://archive.archlinux.org/packages/s/stow/stow-2.2.2-5-any.pkg.tar.xz
|
||||
|
||||
[stowIssue]: https://github.com/aspiers/stow/issues/65 -->
|
||||
-->
|
||||
|
||||
|
||||
### Configuring recoll
|
||||
|
||||
Currently the search just uses the default recoll config, I intend to modify this to use `~/.cadmus` as a config directory so as to not interfere with the default config.
|
||||
@@ -116,47 +110,29 @@ then select *index configuration* and configure recoll to have `~/Notes/MD` as t
|
||||
| If you want to change the notes directory change the variable `NOTES_DIR` in ****<span style="color:rgb(90,210,90);font-family:Courier New,Courier, monospace,serif;">cadmus</span>**** |
|
||||
|
||||
-->
|
||||
## Usage
|
||||
|
||||
|
||||
It's all Menu driven so just follow the diagram to do what you need.
|
||||
|
||||

|
||||
## Design Philosophy
|
||||
|
||||
### Assumptions
|
||||
|
||||
It is assumed that:
|
||||
|
||||
1. Notes are:
|
||||
1. *Markdown* files with a `.md` extension
|
||||
2. Underneath `~/Notes` (you ma)
|
||||
3. Recoll updates it's index on the fly
|
||||
* `~/Notes` will need to be indexed by *Recoll* so the results will show up.
|
||||
3. SSD
|
||||
* I use an SSD and some scripts are pretty inefficient (like `grep | cut |
|
||||
xargs find` to avoid creating a variable), I don't know if things like
|
||||
would work on a HDD.
|
||||
5. All Notes have Unique Names
|
||||
6. On *MacOS* you'll need to define `xdg-open` so do something like:
|
||||
```bash
|
||||
alias xdg-open='open &>/dev/null'
|
||||
```
|
||||
<!---
|
||||
2. You're going to use [Kitty](https://sw.kovidgoyal.net/kitty/)
|
||||
* You could either change the source or use anoter terminal that supports
|
||||
calling functions with `--`, e.g. `kitty -- nvim`
|
||||
-->
|
||||
<!---
|
||||
5. I use [*Fish*] and *Oh My Fish* ([*OMF*]) as my default shell, this means `basename $SHELL` is `fish` for
|
||||
me and even though this is written in `bash` maybe that could cause issues.
|
||||
* Try [*Fish*] for a while, it's quite good, when you need to test something
|
||||
it's easy to temporarily jump back with `exec zsh`.
|
||||
* I wonder if this would work for [*nushell*]???
|
||||
-->
|
||||
|
||||
[*nushell*]: https://github.com/nushell/nushell
|
||||
[*Fish*]: https://fishshell.com/
|
||||
[*OMF*]: https://github.com/oh-my-fish/oh-my-fish
|
||||
- ****<span style="color:rgb(90,210,90);font-family:Courier New,Courier, monospace,serif;">cadmus</span>**** acts as a menu for scripts to acheive things
|
||||
- The Actual work will be done by subscripts denoted by `description.bash`
|
||||
- The subscripts will take the note directory as an argument so they are portable and modular
|
||||
- The Arguments will be shifted and then all passed down to subfunctions
|
||||
- the script name ~~will~~ should always be printed to the terminal so the individual
|
||||
script can be repurposed with out fishing through code.
|
||||
- Subscripts ~~will~~ should take *only one* argument (or `STDIN`)
|
||||
- If the first argument is either `-h` or `--help` help will be printed and then `exit 0`
|
||||
- This might lead to some limitations but the simplicity is for sanity, modularity and extensibility.
|
||||
- Will always return absolute path.
|
||||
- I played around with relative path but it got confusing when calling the script from inside a function inside a script, so instead if you want a relative path you should do `scriptname './' | xargs realpath --relative-to='./'`
|
||||
- Be a Front end to tie together different scripts and tools
|
||||
- Don't replicate work other people have done.
|
||||
- Plain Text, Free as in Speech and Beer.
|
||||
- try to make modular subscripts:
|
||||
- Pipe in input, output goes to STDOUT
|
||||
- Leave Aliases and piping to the user
|
||||
- See [Recommended Aliases](#recommended-aliases)
|
||||
|
||||
## Dependencies
|
||||
|
||||
@@ -164,55 +140,60 @@ It is assumed that:
|
||||
This was a dependency but I switched to java script
|
||||
- [R](https://en.wikipedia.org/wiki/R_(programming_language))
|
||||
-->
|
||||
- [highlight](https://www.archlinux.org/packages/community/x86_64/highlight/)
|
||||
- [recode](https://www.archlinux.org/packages/extra/x86_64/recode/)
|
||||
- [node](https://nodejs.org/en/)
|
||||
- [bat](https://github.com/sharkdp/bat)
|
||||
- [cut](https://www.gnu.org/software/coreutils/manual/html_node/The-cut-command.html)
|
||||
- [fd](https://github.com/sharkdp/fd)
|
||||
- [find](https://man7.org/linux/man-pages/man1/find.1.html)
|
||||
- [fzf](https://github.com/junegunn/fzf)
|
||||
- [skim](https://github.com/lotabout/skim)
|
||||
- [rg](https://www.google.com/search?client=firefox-b-d&q=ripgrep+github)
|
||||
- Make sure to include `pcre2`, this comes in *Arch*, if using `cargo`:
|
||||
```bash
|
||||
cargo install ripgrep --features 'pcre2'
|
||||
```
|
||||
- [GNU realpath](https://www.gnu.org/software/coreutils/manual/html_node/realpath-invocation.html#realpath-invocation)
|
||||
- [grep](https://www.gnu.org/software/grep/)
|
||||
- [highlight](https://www.archlinux.org/packages/community/x86_64/highlight/)
|
||||
- jq <sup> [Arch](https://www.archlinux.org/packages/community/x86_64/jq/) | [brew](https://formulae.brew.sh/formula/jq#default) | [ubuntu](https://packages.ubuntu.com/search?keywords=jq) </sup>
|
||||
- [mdcat](https://aur.archlinux.org/packages/mdcat/)<sup>AUR</sup>
|
||||
- [node](https://nodejs.org/en/)
|
||||
- [Pandoc](https://github.com/jgm/pandoc)
|
||||
- [perl](https://wiki.archlinux.org/index.php/Perl)
|
||||
- [python](https://www.python.org/download/releases/3.0/)
|
||||
- [tmsu](https://aur.archlinux.org/packages/tmsu/)<sup>AUR</sup>
|
||||
- [ranger](https://www.archlinux.org/packages/community/any/ranger/)
|
||||
- [mdcat](https://aur.archlinux.org/packages/mdcat/)<sup>AUR</sup>
|
||||
- [xclip](https://www.archlinux.org/packages/extra/x86_64/xclip/)
|
||||
- [sd](https://github.com/chmln/sd)
|
||||
- [fd](https://github.com/sharkdp/fd)
|
||||
- [sed](https://www.gnu.org/software/sed/)
|
||||
- [cut](https://www.gnu.org/software/coreutils/manual/html_node/The-cut-command.html)
|
||||
- [grep](https://www.gnu.org/software/grep/)
|
||||
- [find](https://man7.org/linux/man-pages/man1/find.1.html)
|
||||
- [GNU realpath](https://www.gnu.org/software/coreutils/manual/html_node/realpath-invocation.html#realpath-invocation)
|
||||
- [recode](https://www.archlinux.org/packages/extra/x86_64/recode/)
|
||||
- [Recoll](https://www.lesbonscomptes.com/recoll/)
|
||||
- [Pandoc](https://github.com/jgm/pandoc)
|
||||
- [bat](https://github.com/sharkdp/bat)
|
||||
- [rg](https://www.google.com/search?client=firefox-b-d&q=ripgrep+github)
|
||||
- Make sure to include `pcre2`, this comes in *Arch*, if using `cargo`:
|
||||
```bash
|
||||
cargo install ripgrep --features 'pcre2'
|
||||
```
|
||||
|
||||
- [sd](https://github.com/chmln/sd)
|
||||
- [sed](https://www.gnu.org/software/sed/)
|
||||
- [skim](https://github.com/lotabout/skim)
|
||||
- [tmsu](https://aur.archlinux.org/packages/tmsu/)<sup>AUR</sup>
|
||||
- [xclip](https://www.archlinux.org/packages/extra/x86_64/xclip/)
|
||||
|
||||
### Recommended for all Features
|
||||
|
||||
- [WeasyPrint](https://aur.archlinux.org/packages/python-weasyprint/)
|
||||
- [tectonic](https://tectonic-typesetting.github.io/en-US/)
|
||||
- [nvim](https://neovim.io/)
|
||||
- [ip](https://jlk.fjfi.cvut.cz/arch/manpages/man/ip.8)
|
||||
- if you're on mac [this stackExchange](https://superuser.com/a/898971) answer suggests [iproute2](https://formulae.brew.sh/formula/iproute2mac#default) may work
|
||||
- [Kitty](https://sw.kovidgoyal.net/kitty/)
|
||||
- I've also heard good things about [iterm2](https://www.iterm2.com/)
|
||||
- [MkDocs](https://pypi.org/project/mkdocs-material-extensions/)
|
||||
- [MkDocs Material Theme](https://github.com/squidfunk/mkdocs-material)
|
||||
- [MkDocs Material Extensions](https://pypi.org/project/mkdocs-material-extensions/)
|
||||
- [MkDocs Material Theme](https://github.com/squidfunk/mkdocs-material)
|
||||
- [nvim](https://neovim.io/)
|
||||
- [tectonic](https://tectonic-typesetting.github.io/en-US/)
|
||||
- [WeasyPrint](https://aur.archlinux.org/packages/python-weasyprint/)
|
||||
|
||||
### Interesting / Helpful / Recommended Generally (Not strictly necessary)
|
||||
|
||||
- [guake](http://guake-project.org/) or [yakuake](https://kde.org/applications/en/system/org.kde.yakuake)
|
||||
- [MarkText](https://github.com/marktext/marktext)
|
||||
- [VNote](https://github.com/tamlok/vnote)
|
||||
|
||||
### recommended / Interesting / Helpful packages not required
|
||||
|
||||
- [readability-cli](https://gitlab.com/gardenappl/readability-cli)
|
||||
- mdless
|
||||
- [readability-cli](https://gitlab.com/gardenappl/readability-cli)
|
||||
- [VNote](https://github.com/tamlok/vnote)
|
||||
- VSCode
|
||||
|
||||
### PATH
|
||||
|
||||
If installed with `pip` or `cargo` it will be necessary to add these directories to your `PATH`:
|
||||
If any dependencies are installed with `pip` or `cargo` it will be necessary to add these directories to your `PATH`:
|
||||
|
||||
``` bash
|
||||
## bash
|
||||
@@ -238,7 +219,29 @@ set PATH "$HOME/.cargo/bin $PATH
|
||||
|
||||
## Recommended Aliases
|
||||
|
||||
I wrote all this with aliases in mind, when I settle on some aliases i'll put up my `fish` functions. (I also wanted to do some autocomplete.)
|
||||
I wrote all this with aliases in mind, when I settle on some aliases i'll put up my `fish` functions. (I also wanted autocomplete)
|
||||
|
||||
|
||||
## Why / Comparison with other tools
|
||||
|
||||
So the boxes I needed ticked are, more or less:
|
||||
𐄞
|
||||
| | FOSS | Offline | Linux/BSD? | terminal? | RawFiles? | Markdown | AnyEditor? |
|
||||
|-----------|------|---------|------------|-----------|-----------|----------|------------|
|
||||
| OneNote | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ |
|
||||
| EverNote | ❌ | ? | ❌ | ❌ | ❌ | ❌ | ❌ |
|
||||
| Notable | ❌ | ✅ | ✅ | ❌ | ✅ | ✅ | ✅ |
|
||||
| Zim | ✅ | ✅ | ✅ | ❌ | ✅ | ✅ | ✅ |
|
||||
| Obsidian | ❌ | ✅ | ✅ | ❌ | ✅ | ✅ | ✅ |
|
||||
| dokuwiki | ✅ | ❌ | ✅ | ❌ | ✅ | ✅* | ✅ |
|
||||
| joplin | ✅ | ✅ | ✅ | ✅ | ❌ | ✅ | ❌ † |
|
||||
| mediawiki | ✅ | ❌ | ✅ | ❌ | ❌ | ❌ | ❌ ‡ |
|
||||
| Org-Mode | ✅ | ✅ | ✅ | ✅ | ✅ | ❌ | ❌ |
|
||||
| Cadmus | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ |
|
||||
|
||||
> † You can't open the files from vim with FZF so it gets a no. <br>
|
||||
> ‡ Unlike dokuwiki everything is in a database so it gets a no <br>
|
||||
> \* With a Plugin <br>
|
||||
|
||||
## Related
|
||||
|
||||
|
@@ -91,7 +91,7 @@ readFirstArgument () {
|
||||
SkimNotes () {
|
||||
|
||||
## Change directory if One was specified, exit if no directory exists
|
||||
|
||||
|
||||
cd "${1}"
|
||||
|
||||
FILE="$(SkimGrep)"
|
||||
|
83
bin/cadmus
83
bin/cadmus
@@ -1,8 +1,12 @@
|
||||
#! /usr/bin/env bash
|
||||
readonly NOTES_DIR="$HOME/Notes/MD/notes" ## TODO Global Variables are bad
|
||||
readonly SERVER_DIR="/srv/www/html/MD"
|
||||
readonly RECOLL_CONFIG_DIR="$HOME/.cadmus"
|
||||
readonly MKDOCS_YML="$HOME/Notes/mkdocs.yml" ## This may be above the notes directory, the
|
||||
IFS=$'\t\n' # Split on newlines and tabs (but not on spaces)
|
||||
readonly script_name=$(basename "${0}")
|
||||
script_dir=$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )
|
||||
readonly script_dir=$(realpath "${script_dir}""/""${script_name}" | xargs dirname)
|
||||
readonly CONFIG=$(realpath "${script_dir}/../config.json") # one directory above
|
||||
## readonly SERVER_DIR="/srv/www/html/MD"
|
||||
## readonly RECOLL_CONFIG_DIR="$HOME/.cadmus"
|
||||
## readonly MKDOCS_YML="$HOME/Notes/mkdocs.yml" ## This may be above the notes directory, the
|
||||
## notes directory may not contain all the
|
||||
## images for want of seperation and mkdocs is
|
||||
## fidally, so specify the path to mkdocs.yml.
|
||||
@@ -18,7 +22,7 @@ set -o pipefail
|
||||
# * Main Functions
|
||||
|
||||
main() {
|
||||
|
||||
checkConfig
|
||||
setvars
|
||||
[[ -z "${1:-}" ]] && mainHelp && exit 0
|
||||
arguments "${@:-}"
|
||||
@@ -26,12 +30,14 @@ main() {
|
||||
|
||||
function setvars() {
|
||||
|
||||
IFS=$'\t\n' # Split on newlines and tabs (but not on spaces)
|
||||
readonly script_name=$(basename "${0}")
|
||||
script_dir=$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )
|
||||
readonly script_dir=$(realpath "${script_dir}""/""${script_name}" | xargs dirname)
|
||||
readonly TERMINAL="kitty"
|
||||
readonly TERMINAL_EXEC='kitty -- '
|
||||
|
||||
|
||||
readonly NOTES_DIR="$(cat "${CONFIG}" | jq -r '.notesDir')"
|
||||
readonly SERVER_DIR="$(cat "${CONFIG}" | jq -r '.serverDir')"
|
||||
readonly RECOLL_CONFIG_DIR="$(cat "${CONFIG}" | jq -r '.recollConfigDir')"
|
||||
readonly MKDOCS_YML="$(cat "${CONFIG}" | jq -r '.mkdocsConfigDir')" ## This may be above the notes directory, the
|
||||
}
|
||||
|
||||
|
||||
@@ -55,7 +61,7 @@ function mainHelp() {
|
||||
echo -e " ⎋ \e[1;36m convert \e[0m \e[1;34m ┊┊┊ 📁\e[0m Convert Clipboard Contents to Different Formats "
|
||||
echo -e " 🧰 \e[1;37m misc \e[0m \e[1;34m ┊┊┊ 📁\e[0m Miscelanneous Tools nice to have on hand "
|
||||
echo -e " 🌏\e[1;92m publish\e[0m \e[1;34m ┊┊┊ 📁\e[0m Publish with \e[1;34m \e[4m\e[3mMkDocs\e[0m\e[0m🐍"
|
||||
echo -e " 🕮 \e[1;93m preview \e[0m \e[1;34m ┊┊┊ 🎆\e[0m Preview with \e[1;34m \e[4m\e[3mMarkServ\e[0m\e[0m (use chrome for this)"
|
||||
echo -e " 🕮 \e[1;93m preview \e[0m \e[1;34m ┊┊┊ 🎆\e[0m Preview with \e[1;34m \e[4m\e[3mMarkServ\e[0m\e[0m (use 'preview!' for global)"
|
||||
echo -e " 🕮 \e[1;94m help \e[0m \e[1;34m ┊┊┊ 🎆\e[0m Open help for correspoding functions "
|
||||
echo
|
||||
echo -e " \e[3m\e[1m• Legend\e[0m "
|
||||
@@ -66,6 +72,33 @@ function mainHelp() {
|
||||
}
|
||||
|
||||
# ** Main Arguments - Level 0
|
||||
# *** Config
|
||||
checkConfig () {
|
||||
if [[ -f "${CONFIG}" ]]; then
|
||||
echo "Config Detected"
|
||||
else
|
||||
echo -e "No config File detected at ${CONFIG}"
|
||||
echo -e "Would you like to generate a config?"
|
||||
echo
|
||||
echo -e "Press y to continue or any other key to exit."
|
||||
echo
|
||||
read -d '' -s -n1 choice
|
||||
if [[ "${choice}" == "y" ]]; then
|
||||
config_json=$("${script_dir}/makeConfig.bash")
|
||||
if [[ "${config_json}" != "" ]]; then
|
||||
echo "${config_json}" > "${CONFIG}"
|
||||
echo -e "This is the Config:\n"
|
||||
highlight "${CONFIG}"
|
||||
else
|
||||
echo "Config not Generated"
|
||||
exit 1
|
||||
fi
|
||||
else
|
||||
exit 0
|
||||
fi
|
||||
fi
|
||||
|
||||
}
|
||||
# *** Switch
|
||||
arguments () {
|
||||
|
||||
@@ -90,8 +123,14 @@ arguments () {
|
||||
;;
|
||||
publish|pub) shift; CadmusPublish "${@:-}"
|
||||
;;
|
||||
publish) shift; CadmusPublish "${@:-}"
|
||||
;;
|
||||
preview|p) shift; cd "${NOTES_DIR}" && markserv || echo -e " \n \e[1;34m maybe fix this with:\n\tsudo fuser 35729/tcp -k \n \tor\n\tkillall markserv \e[0m\n"
|
||||
;;
|
||||
preview!) shift; previewGlobal
|
||||
;;
|
||||
help) subHelp && exit 0
|
||||
;;
|
||||
--*) >&2 echo "bad option $1"
|
||||
;;
|
||||
*) >&2 echo -e "argument \e[1;35m${1}\e[0m has no definition."
|
||||
@@ -290,7 +329,7 @@ makeNewNote () {
|
||||
echo -e "Please Choose Relevant Tags (Use Tab for Multi Select)"
|
||||
echo -e "\n\t(Press any key to continue)"
|
||||
read -d '' -s -n1 choice
|
||||
|
||||
|
||||
## Choose Tags
|
||||
TAGS="$(node "${script_dir}"/tags/yaml-parse.js "${NOTES_DIR}" 2>/dev/null | sort -u| sk -m)"
|
||||
|
||||
@@ -522,6 +561,28 @@ CadmusConvert () {
|
||||
|
||||
}
|
||||
|
||||
# *** Preview Global
|
||||
previewGlobal() {
|
||||
MARKSERVPORT="28754"
|
||||
cd "${NOTES_DIR}"
|
||||
printQR
|
||||
markserv -p "${MARKSERVPORT}" -a 0.0.0.0 || echo -e " \n \e[1;34m maybe fix this with:\n\tsudo fuser 35729/tcp -k \n \tor\n\tkillall markserv \e[0m\n"
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
# **** Print QR
|
||||
printQR () {
|
||||
command -v qrencode >/dev/null 2>&1 || { echo -e >&2 "I require qrencode but it's not installed.\nNo QR Code can be printed."; return; }
|
||||
command -v ip >/dev/null 2>&1 || { echo -e >&2 "I requre ip but it's not installed.\nNo QR Code can be printed."; return; }
|
||||
|
||||
CURRENTIP="$(ip route get 1 | sed -n 's/^.*src \([0-9.]*\) .*$/\1/p')"
|
||||
qrencode -t UTF8 "http://${CURRENTIP}:${MARKSERVPORT}"
|
||||
|
||||
}
|
||||
|
||||
# **** Help
|
||||
function ConvertHelp () {
|
||||
|
||||
|
142
bin/makeConfig.bash
Executable file
142
bin/makeConfig.bash
Executable file
@@ -0,0 +1,142 @@
|
||||
#! /usr/bin/env bash
|
||||
#
|
||||
# Author: Ryan Greenup <ryan.greenup@protonmail.com>
|
||||
|
||||
# * Shell Settings
|
||||
set -o errexit # abort on nonzero exitstatus
|
||||
set -o nounset # abort on unbound variable
|
||||
set -o pipefail # don't hide errors within pipes
|
||||
|
||||
# * Main Function
|
||||
main() {
|
||||
|
||||
# Use STDERR so as to not clog STDIN
|
||||
# Is there a better way to do this?
|
||||
echoerr() { echo -e "$@" 1>&2; }
|
||||
|
||||
|
||||
check_for_dependencies
|
||||
setVars
|
||||
readFirstArgument "${@}"
|
||||
AskValues
|
||||
|
||||
if [ "${promptComplete}" != "Completed" ]; then
|
||||
exit 1
|
||||
fi
|
||||
|
||||
MakeConfig "${@}"
|
||||
|
||||
}
|
||||
|
||||
# ** Helper Functions
|
||||
# *** Check for Dependencies
|
||||
check_for_dependencies () {
|
||||
|
||||
for i in ${DependArray[@]}; do
|
||||
command -v "$i" >/dev/null 2>&1 || { echo >&2 "I require $i but it's not installed. Aborting."; exit 1; }
|
||||
done
|
||||
|
||||
|
||||
}
|
||||
|
||||
# **** List of Dependencies
|
||||
|
||||
declare -a DependArray=(
|
||||
"jq"
|
||||
"cat"
|
||||
"xclip"
|
||||
)
|
||||
|
||||
|
||||
# *** Set variables below main
|
||||
setVars () {
|
||||
readonly script_name=$(basename "${0}")
|
||||
readonly script_dir=$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )
|
||||
IFS=$'\t\n' # Split on newlines and tabs (but not on spaces)
|
||||
}
|
||||
|
||||
# **** Print Help
|
||||
Help () {
|
||||
|
||||
|
||||
echo
|
||||
echo -e " \e[3m\e[1mMakeConfig.sh \e[0m; Helpful Shell Scripts for Markdown Notes"
|
||||
echo -e " \e[1;31m--------------------------\e[0m "
|
||||
echo
|
||||
echo -e " \e[3m\e[1m• Usage \e[0m "
|
||||
echo
|
||||
echo -e " "${script_name}" [-h]"
|
||||
echo -e " "${script_name}" [--help]"
|
||||
echo
|
||||
echo -e " Fully Interactive, just follow the prompts"
|
||||
echo
|
||||
echo -e " \e[3m By Design: No Options; No Arguments\e[0m"
|
||||
echo
|
||||
echo -e " \e[3m\e[1m• Compatability \e[0m "
|
||||
echo
|
||||
echo -e " This prints everything to STDERR to that STDOUT only has"
|
||||
echo -e " The config file in it, I'm not sure if that's an issue "
|
||||
echo
|
||||
exit 0
|
||||
}
|
||||
|
||||
|
||||
# *** Read First Argument
|
||||
readFirstArgument () {
|
||||
|
||||
if [[ "${1:-}" == "-h" ]] || [[ "${1:-}" == "--help" ]]; then
|
||||
Help && exit 0
|
||||
fi
|
||||
|
||||
}
|
||||
|
||||
# ***
|
||||
AskValues () {
|
||||
echoerr "Please Enter the Directory of you Markdown Files"
|
||||
echoerr "\t (This directory should contain index.md or home.md)"
|
||||
read NOTES_DIR
|
||||
NOTES_DIR="$(echo "${NOTES_DIR/\~/$HOME}")"
|
||||
read -d '' -s -n1 choice
|
||||
# NOTES_DIR="$(cd /; sk --height 40% -i -c 'fd {}' )"
|
||||
[[ -d "${NOTES_DIR}" ]] || echoerr -e "\n \e[3m\e[1m \e[1;31m ⚠ WARNING: \e[0m No Such Directory!"
|
||||
|
||||
|
||||
echoerr "\nPlease Enter the Directory of the recoll config you want to use"
|
||||
echoerr "\t Leave it blank to use the default config"
|
||||
echoerr "\t This is not implemented so don't worry"
|
||||
read RECOLL_CONFIG_DIR
|
||||
RECOLL_CONFIG_DIR="$(echo "${RECOLL_CONFIG_DIR/\~/$HOME}")"
|
||||
[[ -d "${RECOLL_CONFIG_DIR}" ]] || echoerr "\n \e[3m\e[1m \e[1;31m ⚠ WARNING: \e[0m No Such Directory!"
|
||||
|
||||
echoerr "\nPlease Enter the location of your mkdocs yml"
|
||||
echoerr "\t (If you're not going to use this just leave it blank and press Enter)"
|
||||
read MKDOCS_YML
|
||||
MKDOCS_YML="$(echo "${MKDOCS_YML/\~/$HOME}")"
|
||||
[[ -f "${MKDOCS_YML}" ]] || echoerr -e "\n \e[3m\e[1m \e[1;31m ⚠ WARNING: \e[0m No Such File!"
|
||||
|
||||
echoerr "\nPlease Enter the Directory in which you want mkdocs to build your static site"
|
||||
echoerr "\t (If you're not going to use this just leave it blank and press Enter)"
|
||||
read SERVER_DIR
|
||||
SERVER_DIR="$(echo "${SERVER_DIR/\~/$HOME}")"
|
||||
[[ -d "${SERVER_DIR}" ]] || echoerr -e "\n \e[3m\e[1m \e[1;31m ⚠ WARNING: \e[0m No Such Directory!"
|
||||
|
||||
promptComplete="Completed"
|
||||
|
||||
}
|
||||
# *** Make Config
|
||||
MakeConfig () {
|
||||
|
||||
JSON_STRING=$( jq -n \
|
||||
--arg nd "$NOTES_DIR" \
|
||||
--arg sd "$SERVER_DIR" \
|
||||
--arg rc "$RECOLL_CONFIG_DIR" \
|
||||
--arg mk "$MKDOCS_YML" \
|
||||
'{notesDir: $nd, serverDir: $sd, recollConfigDir: $rc, mkdocsConfigDir: $mk}' )
|
||||
|
||||
echo "$JSON_STRING"
|
||||
|
||||
exit 0
|
||||
}
|
||||
|
||||
# * Call Main Function
|
||||
main "${@}"
|
124
cadmus
124
cadmus
@@ -1,124 +0,0 @@
|
||||
#! /usr/bin/env bash
|
||||
#
|
||||
# Author: Ryan Greenup <ryan.greenup@protonmail.com>
|
||||
# abort on nonzero exitstatus
|
||||
set -o errexit
|
||||
# abort on unbound variable
|
||||
set -o nounset
|
||||
# don't hide errors within pipes
|
||||
set -o pipefail
|
||||
|
||||
|
||||
## * Main Functions
|
||||
|
||||
main() {
|
||||
|
||||
setvars
|
||||
[[ -z "${1:-}" ]] && mainHelp
|
||||
arguments "${@:-}"
|
||||
}
|
||||
|
||||
function setvars() {
|
||||
|
||||
IFS=$'\t\n' # Split on newlines and tabs (but not on spaces)
|
||||
readonly script_name=$(basename "${0}")
|
||||
readonly script_dir=$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )
|
||||
readonly TERMINAL="kitty"
|
||||
readonly TERMINAL_EXEC='kitty -- '
|
||||
readonly NOTES_DIR="$HOME/Notes"
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
# * Sub-functions
|
||||
# ** Help
|
||||
|
||||
function mainHelp() {
|
||||
|
||||
echo
|
||||
echo -e " \e[3m\e[1m Cadmus\e[0m; Helpful Shell Scripts for Markdown Notes"
|
||||
echo -e " \e[1;31m -------------------------\e[0m "
|
||||
echo
|
||||
|
||||
echo -e " \e[1;91m \e[1m Command \e[0m\e[0m \e[1;34m┊┊┊ \e[0m Description "
|
||||
echo -e " ..............\e[1;34m┊┊┊\e[0m........................................... "
|
||||
echo -e " 🔍 \e[1;93m find \e[0m \e[1;34m ┊┊┊ \e[0m Find Notes based on FileName"
|
||||
echo -e " 🔎 \e[1;32m search \e[0m \e[1;34m ┊┊┊ \e[0m Search through Notes using Recoll"
|
||||
echo -e " 🏷 \e[1;33m tags \e[0m \e[1;34m ┊┊┊ \e[0m Use TMSU to work with tags"
|
||||
echo -e " 🔧 \e[1;34m tools \e[0m \e[1;34m ┊┊┊ \e[0m Tools for Editing"
|
||||
echo -e " 📝 \e[1;35m export \e[0m \e[1;34m ┊┊┊ \e[0m Export Notes to Different Formats "
|
||||
echo -e " ⎋ \e[1;36m convert \e[0m \e[1;34m ┊┊┊ \e[0m Convert Clipboard Contents to Different Formats "
|
||||
echo -e " 🧰 \e[1;37m misc \e[0m \e[1;34m ┊┊┊ \e[0m Miscelanneous Tools nice to have on hand "
|
||||
echo -e " 🌏\e[1;92m publish\e[0m \e[1;34m ┊┊┊ \e[0m Publish with \e[1;34m \e[4m\e[3mMkDocs\e[0m\e[0m🐍"
|
||||
echo -e " 🕮 \e[1;92m preview \e[0m \e[1;34m ┊┊┊ \e[0m Preview with \e[1;34m \e[4m\e[3mMarkServ\e[0m\e[0m "
|
||||
|
||||
echo
|
||||
}
|
||||
|
||||
# ** Main Arguments - Level 0
|
||||
#
|
||||
arguments () {
|
||||
|
||||
while test $# -gt 0
|
||||
do
|
||||
case "$1" in
|
||||
--help) Help
|
||||
;;
|
||||
-h) Help
|
||||
;;
|
||||
find) shift; NoteFind "${@:-}" ## Don't steal function name
|
||||
;;
|
||||
search) echo "begin note search"
|
||||
;;
|
||||
tags) echo "begin tags"
|
||||
;;
|
||||
tools) echo "begin tools"
|
||||
;;
|
||||
export) echo "begin export"
|
||||
;;
|
||||
convert) echo "begin convert"
|
||||
;;
|
||||
misc) echo "begin misc"
|
||||
;;
|
||||
publish) echo "begin publish"
|
||||
;;
|
||||
preview) echo "begin preview"
|
||||
;;
|
||||
--*) >&2 echo "bad option $1"
|
||||
;;
|
||||
*) >&2 echo -e "argument \e[1;35m${1}\e[0m has no definition."
|
||||
;;
|
||||
esac
|
||||
shift
|
||||
done
|
||||
}
|
||||
|
||||
# *** Find
|
||||
|
||||
function NoteFind() {
|
||||
|
||||
bash "NoteFind.sh "${@:-}""
|
||||
}
|
||||
|
||||
mytest() {
|
||||
echo "This is a test"
|
||||
exit 0
|
||||
}
|
||||
|
||||
Help () {
|
||||
# Display Help
|
||||
echo "Add description of the script functions here."
|
||||
echo
|
||||
echo "Syntax: scriptTemplate [-g|h|t|v|V]"
|
||||
echo "options:"
|
||||
echo "g Print the GPL license notification."
|
||||
echo "h Print this Help."
|
||||
echo "v Verbose mode."
|
||||
echo "V Print software version and exit."
|
||||
exit 0
|
||||
}
|
||||
|
||||
|
||||
main "${@}"
|
||||
|
127
install.sh
127
install.sh
@@ -1,4 +1,6 @@
|
||||
#!/usr/bin/env bash
|
||||
INSTALL_DIR="$HOME/.cadmus"
|
||||
BIN_DIR="$HOME/.local/bin/"
|
||||
|
||||
main () {
|
||||
me=`basename "$0"`
|
||||
@@ -6,16 +8,24 @@ main () {
|
||||
HelpStatement $1
|
||||
UninstallQ $1
|
||||
printThis
|
||||
check_for_dependencies
|
||||
download_the_repo
|
||||
Install_tools "S"
|
||||
Install_bin
|
||||
check_path
|
||||
check_for_dependencies
|
||||
|
||||
echo -e "\nInstallation Complete \n"
|
||||
}
|
||||
|
||||
check_path () {
|
||||
echo "$PATH" | grep -q '.local/bin' || echo "bin-dir is not in path, you'll need to add it to the path"
|
||||
}
|
||||
|
||||
function UninstallQ() {
|
||||
|
||||
if [ "$1" == "-rm" ] || [ "$1" == "--rm" ]; then
|
||||
echo "Removing with Stow"
|
||||
Install_tools "D"
|
||||
echo "Removing..."
|
||||
rm "$HOME/.local/bin/cadmus"
|
||||
rm "${INSTALL_DIR}"
|
||||
exit 0
|
||||
fi
|
||||
|
||||
@@ -24,7 +34,7 @@ function UninstallQ() {
|
||||
HelpStatement() {
|
||||
|
||||
if [ "$1" == "-h" ] || [ "$1" == "--help" ]; then
|
||||
echo -e "To uninstall do `basename $0` --rm is the script name,
|
||||
echo -e "To uninstall do `basename $0` --rm ,
|
||||
|
||||
If you are on Arch stow 2.3.1-2 is broken, downgrade with
|
||||
|
||||
@@ -53,7 +63,7 @@ printThis () {
|
||||
safePrint $me
|
||||
|
||||
|
||||
echo "Are you happy to proceed? Press y to continue"
|
||||
echo -e "\nAre you happy to proceed? Press y to continue \n"
|
||||
read -d '' -s -n1 proceedQ
|
||||
if [ "$proceedQ" != "y" ]; then
|
||||
exit 0
|
||||
@@ -62,71 +72,100 @@ printThis () {
|
||||
|
||||
safePrint () {
|
||||
if hash highlight 2>/dev/null; then
|
||||
highlight "$@"
|
||||
highlight "${1}" --syntax=bash --stdout
|
||||
else
|
||||
cat "$@"
|
||||
cat "${1}"
|
||||
fi
|
||||
}
|
||||
|
||||
|
||||
check_for_dependencies () {
|
||||
|
||||
echo "Press Any Key to Check for dependencies, press the c Key to Skip this"
|
||||
read -d '' -s -n1 CheckDepQ
|
||||
if [ "$CheckDepQ" == "c" ]; then
|
||||
return
|
||||
fi
|
||||
## echo "Press Any Key to Check for dependencies, press the c Key to Skip this"
|
||||
## read -d '' -s -n1 CheckDepQ
|
||||
## if [ "$CheckDepQ" == "c" ]; then
|
||||
## return
|
||||
## fi
|
||||
##
|
||||
depLog="$(mktemp)"
|
||||
|
||||
for i in ${StringArray[@]}; do
|
||||
command -v "$i" >/dev/null 2>&1 || { echo >&2 "I require $i but it's not installed. Aborting."; exit 1; }
|
||||
command -v "$i" >/dev/null 2>&1 || { echo $i >> "${depLog}"; }
|
||||
done
|
||||
|
||||
echo "All Dependencies Satisfied"
|
||||
if [[ $(cat "${depLog}") == "" ]]; then
|
||||
echo -e "\nAll Dependencies Satisfied\n"
|
||||
else
|
||||
echo -e "\e[1;31m \nMissing the Following Dependencies \e[0m \n"
|
||||
echo -e " \e[1;31m -------------------------\e[0m "
|
||||
echo -e "\e[1;32m \n"
|
||||
addBullets "$(cat "${depLog}")"
|
||||
echo -e "\e[0m \n"
|
||||
echo -e "They are listed in \e[1;34m "${depLog}" \e[0m \n"
|
||||
fi
|
||||
}
|
||||
|
||||
|
||||
addBullets() {
|
||||
command -v sed >/dev/null 2>&1 || { echo >&2 "I require sed but it's not installed. Aborting."; exit 1; }
|
||||
echo "$1" | sed 's/^/\t‣\ /g'
|
||||
}
|
||||
|
||||
download_the_repo () {
|
||||
|
||||
echo "Press y to download the repo"
|
||||
read -d '' -s -n1 downloadQ
|
||||
if [ "$downloadQ" != "y" ]; then
|
||||
return
|
||||
fi
|
||||
if [[ -d "${INSTALL_DIR}" ]]; then
|
||||
echo -e "Detected a cadmus install"
|
||||
|
||||
mkdir -p $HOME/DotFiles/
|
||||
cd $HOME/DotFiles
|
||||
|
||||
|
||||
if [[ -d ".git" ]]; then
|
||||
echo "Detected a Git Repo, Press y to add a submodule or any key to exit"
|
||||
|
||||
read -d '' -s -n1 CheckDepQ
|
||||
if [ "$CheckDepQ" != "y" ]; then
|
||||
echo "You pressed any key"
|
||||
if [ -f "${INSTALL_DIR}/config.json" ]; then
|
||||
oldConfigFile="$(mktemp)" && cat "${INSTALL_DIR}/config.json" > "${oldConfigFile}"
|
||||
echo -e "\n\tConfig File Backed up for later restore\n"
|
||||
fi
|
||||
|
||||
git submodule add https://github.com/RyanGreenup/cadmus && echo "Submodule succesfully added"
|
||||
|
||||
elif [[ -f ".git" ]]; then
|
||||
echo "You have a file called .git In there, delete that first.";
|
||||
ask_to_remove
|
||||
download_the_repo
|
||||
return
|
||||
else
|
||||
git clone https://github.com/RyanGreenup/cadmus
|
||||
git clone https://github.com/RyanGreenup/cadmus "$HOME/.cadmus"
|
||||
fi
|
||||
|
||||
echo "Repository is downloaded"
|
||||
echo -e "Repository is downloaded\n\n"
|
||||
|
||||
if [[ "$CheckDepQ" == "y" ]] && [[ -f "${oldConfigFile}" ]]; then
|
||||
echo -e "Press y to restore the old config or any other key to continue otherwise\n"
|
||||
read -d '' -s -n1 CheckDepQ
|
||||
cp "${oldConfigFile}" "${INSTALL_DIR}/config.json"
|
||||
echo -e "Config Successfully restored"
|
||||
fi
|
||||
}
|
||||
|
||||
Install_tools () {
|
||||
ask_to_remove () {
|
||||
echo "press y to remove "${INSTALL_DIR}""
|
||||
|
||||
DIR=$(dirname "$0")
|
||||
cd "$DIR" && cd ../
|
||||
echo "Stow package $DIR, target $HOME"
|
||||
stow -t $HOME -$1 "$(basename "$DIR")"
|
||||
read -d '' -s -n1 CheckDepQ
|
||||
if [ "$CheckDepQ" == "y" ]; then
|
||||
rm -rf "${INSTALL_DIR}"
|
||||
else
|
||||
exit 1
|
||||
fi
|
||||
}
|
||||
|
||||
Install_bin() {
|
||||
if [ -f "${BIN_DIR}/cadmus" ]; then
|
||||
echo -e "The executable \e[1;32m "${BIN_DIR}"/cadmus \e[0m already exists, it must be replaced, press y to continue or any key to exit"
|
||||
read -d '' -s -n1 CheckDepQ
|
||||
if [ "$CheckDepQ" == "y" ]; then
|
||||
rm "${BIN_DIR}/cadmus"
|
||||
else
|
||||
exit 1
|
||||
fi
|
||||
Install_bin
|
||||
else
|
||||
ln -s "$HOME/.cadmus/bin/cadmus" "$HOME/.local/bin/" && echo -e "\nSuccessfully created symlink from $HOME/.cadmus/bin/cadmus to $HOME/.local/bin/ \n"
|
||||
fi
|
||||
}
|
||||
|
||||
# Declare an array of string with type
|
||||
declare -a StringArray=("R"
|
||||
declare -a StringArray=(
|
||||
"highlight"
|
||||
"node"
|
||||
"nvim"
|
||||
@@ -135,11 +174,15 @@ declare -a StringArray=("R"
|
||||
"sk"
|
||||
"rg"
|
||||
"perl"
|
||||
"tectonic"
|
||||
"stow"
|
||||
"python"
|
||||
"tmsu"
|
||||
"ranger"
|
||||
"mdcat"
|
||||
"jq"
|
||||
"shift"
|
||||
"ip"
|
||||
"xclip"
|
||||
"sd"
|
||||
"fd"
|
||||
|
BIN
media/Many_Commands_Bigger.png
Normal file
BIN
media/Many_Commands_Bigger.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 419 KiB |
BIN
media/Many_Examples.png
Normal file
BIN
media/Many_Examples.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 167 KiB |
BIN
media/TagsExample.gif
Normal file
BIN
media/TagsExample.gif
Normal file
Binary file not shown.
After Width: | Height: | Size: 9.7 MiB |
Reference in New Issue
Block a user