[styler] Add universal theme filter function
Added universal theme filtering. Universal means the theme exists for each installed package. This is a (rough) way of knowing that it can apply to every intended application -- though of course will not work if more packages are installed than intended to be changed with processors. The `styler list themes` command will default to only show universal themes. To list all themes invoke with `styler list themes all`. Styler will cache the available themes after the first retrieval. The first retrieval still takes a while (~8.7 seconds for me), but subsequent retrievals are much quicker. Cache will automatically be rebuilt whenever a new package is downloaded, or an already downloaded package is updated. The filter function, as it stands it quite inefficient and could use a better algorithm. Uses rg or grep in descending preference.
This commit is contained in:
parent
a6096c25ef
commit
8635b580bd
1 changed files with 119 additions and 9 deletions
|
@ -1,11 +1,26 @@
|
||||||
#!/usr/bin/env bash
|
#!/usr/bin/env bash
|
||||||
|
|
||||||
readonly BASE_PATH="${STYLER_DATA_PATH:-${XDG_DATA_HOME:-$HOME/.local/share}/styler}"
|
readonly BASE_PATH="${STYLER_DATA_PATH:-${XDG_DATA_HOME:-$HOME/.local/share}/styler}"
|
||||||
|
readonly CACHE_PATH="${STYLER_CACHE_PATH:-${XDG_CACHE_HOME:-$HOME/.cache}/styler}"
|
||||||
|
|
||||||
readonly PACKAGE_PATH="$BASE_PATH/packages"
|
readonly PACKAGE_PATH="$BASE_PATH/packages"
|
||||||
readonly PROCESSOR_PATH="$BASE_PATH/processors"
|
readonly PROCESSOR_PATH="$BASE_PATH/processors"
|
||||||
|
|
||||||
readonly VERSION="0.3.0"
|
readonly VERSION="0.4.1"
|
||||||
|
|
||||||
|
# ensures that some grep-like program is available, prefers rg
|
||||||
|
setgrepper() {
|
||||||
|
if command -v rg 1>/dev/null 2>&1; then
|
||||||
|
GREPPER="rg"
|
||||||
|
elif command -v grep 1>/dev/null 2>&1; then
|
||||||
|
GREPPER="grep"
|
||||||
|
else
|
||||||
|
notify-send "grep missing" "styler needs grep, or preferably rg to work."
|
||||||
|
echo "grep missing!" "styler needs grep, or preferably rg to work."
|
||||||
|
exit 127
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
setgrepper
|
||||||
|
|
||||||
main() {
|
main() {
|
||||||
local cmd=""
|
local cmd=""
|
||||||
|
@ -34,7 +49,7 @@ main() {
|
||||||
esac
|
esac
|
||||||
shift
|
shift
|
||||||
|
|
||||||
$cmd "$1"
|
$cmd "$@"
|
||||||
ret=$((ret + $?))
|
ret=$((ret + $?))
|
||||||
exit $ret
|
exit $ret
|
||||||
}
|
}
|
||||||
|
@ -56,6 +71,8 @@ usage() {
|
||||||
" Same as 'theme' option, but changes will be made permanent." \
|
" Same as 'theme' option, but changes will be made permanent." \
|
||||||
"" \
|
"" \
|
||||||
" list [processors|packages|themes] Print out all currently installed processors, templates, or themes from selection. " \
|
" list [processors|packages|themes] Print out all currently installed processors, templates, or themes from selection. " \
|
||||||
|
" list themes Will print out themes which are available for all installed packages." \
|
||||||
|
" list themes all Will print out every single installed theme, regardless of its universal availability." \
|
||||||
"" \
|
"" \
|
||||||
" download [username/repository] Download a base16 template into the package directory or download a processor16" \
|
" download [username/repository] Download a base16 template into the package directory or download a processor16" \
|
||||||
" into the processor directory. Use user/repo format to automatically pull from github." \
|
" into the processor directory. Use user/repo format to automatically pull from github." \
|
||||||
|
@ -99,7 +116,7 @@ get_processors() {
|
||||||
for processor in "$package"/*; do
|
for processor in "$package"/*; do
|
||||||
[[ -e "$processor" ]] || break
|
[[ -e "$processor" ]] || break
|
||||||
[[ -f "$processor" ]] || break
|
[[ -f "$processor" ]] || break
|
||||||
if grep -q -e '/theme_[[:alnum:]]\{1,\}$' <<<"$processor"; then
|
if ${GREPPER} -q -e '/theme_[[:alnum:]]\{1,\}$' <<<"$processor"; then
|
||||||
printf "%s\n" "$(basename -- "$processor")"
|
printf "%s\n" "$(basename -- "$processor")"
|
||||||
fi
|
fi
|
||||||
done
|
done
|
||||||
|
@ -107,11 +124,103 @@ get_processors() {
|
||||||
done
|
done
|
||||||
}
|
}
|
||||||
|
|
||||||
# retrieves all installed themes from all packages, appends applications they exist for
|
# retrieves all installed themes available to all packages
|
||||||
|
# can be called with `all` argument to return themes which only exist for some packages
|
||||||
get_themes() {
|
get_themes() {
|
||||||
local themes
|
local themes
|
||||||
themes=$(find "$PACKAGE_PATH" -type f -name 'base16-*')
|
themes=$(find "$PACKAGE_PATH" -type f -name 'base16-*')
|
||||||
echo "$themes" | sed "s/.*\\/base16-//" | sed "s/\\..*//" | sort | uniq
|
|
||||||
|
local filtered
|
||||||
|
if [[ "$1" = "all" ]]; then
|
||||||
|
filtered="$(get_unique_themes "$themes")"
|
||||||
|
else
|
||||||
|
filtered="$(get_universal_themes "$themes")"
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo "$filtered"
|
||||||
|
}
|
||||||
|
|
||||||
|
# filter down the list passed in to keep repeating base16 themes only once per name
|
||||||
|
# and remove surrounding path information (and file ending)
|
||||||
|
get_unique_themes() {
|
||||||
|
if _cache_invalid "$CACHED_UNIQUE_THEMES" "$PACKAGE_PATH"; then
|
||||||
|
notify-send "styler cache invalid" "rebuilding cache will take a moment..."
|
||||||
|
_cache_rebuild "$CACHED_UNIQUE_THEMES" _fetch_unique_themes "$@"
|
||||||
|
else
|
||||||
|
cat "$CACHED_UNIQUE_THEMES"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
readonly CACHED_UNIQUE_THEMES=${CACHE_PATH}/unique_themes
|
||||||
|
|
||||||
|
# returns themes which are available in all installed packages
|
||||||
|
# returns cached version or rebuilds cache
|
||||||
|
get_universal_themes() {
|
||||||
|
if _cache_invalid "$CACHED_UNIVERSAL_THEMES" "$PACKAGE_PATH"; then
|
||||||
|
notify-send "styler cache invalid" "rebuilding cache will take a moment..."
|
||||||
|
_cache_rebuild "$CACHED_UNIVERSAL_THEMES" _fetch_universal_themes "$@"
|
||||||
|
else
|
||||||
|
cat "$CACHED_UNIVERSAL_THEMES"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
readonly CACHED_UNIVERSAL_THEMES=${CACHE_PATH}/universal_themes
|
||||||
|
|
||||||
|
_fetch_unique_themes() {
|
||||||
|
echo "$1" | sed "s/.*\\/base16-//;s/\\..*//" | sort | uniq
|
||||||
|
}
|
||||||
|
|
||||||
|
# only keep themes which are available in every installed package
|
||||||
|
_fetch_universal_themes() {
|
||||||
|
local themes="$1"
|
||||||
|
local unique
|
||||||
|
unique="$(get_unique_themes "$themes")"
|
||||||
|
|
||||||
|
local packages
|
||||||
|
packages="$(get_packages)"
|
||||||
|
|
||||||
|
local filtered
|
||||||
|
for t in $unique; do
|
||||||
|
for p in $packages; do
|
||||||
|
if ! echo "$themes" | ${GREPPER} -qe "^.*$p.*$t.*$" -; then
|
||||||
|
themes="$(echo "$themes" | sed "/$t/d")"
|
||||||
|
unique="$(echo "$unique" | sed "/$t/d")"
|
||||||
|
break
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
done
|
||||||
|
echo "$unique"
|
||||||
|
}
|
||||||
|
|
||||||
|
# returns true if changes to $2 are newer than $1
|
||||||
|
# used to pass in cache file for $1, what it is caching for $2
|
||||||
|
_cache_invalid() {
|
||||||
|
cache_upd="$(_last_update "$1")"
|
||||||
|
live_upd="$(_last_update "$2")"
|
||||||
|
if [ "${live_upd%.*}" -gt "${cache_upd%.*}" ]; then
|
||||||
|
true
|
||||||
|
else
|
||||||
|
false
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# recreates target cache with output of function
|
||||||
|
# arguments: "target_cache_file" "function_name" "arguments_for_function"
|
||||||
|
_cache_rebuild() {
|
||||||
|
local target="$1"
|
||||||
|
shift
|
||||||
|
local fct="$1"
|
||||||
|
shift
|
||||||
|
local new
|
||||||
|
new="$($fct "$@")"
|
||||||
|
mkdir -p "$CACHE_PATH"
|
||||||
|
echo "$new" | tee "$target"
|
||||||
|
}
|
||||||
|
|
||||||
|
# returns time of last update to argument passed in
|
||||||
|
# argument can be path to file or directory (searched recursively)
|
||||||
|
# if argument does not exist gives 0
|
||||||
|
_last_update() {
|
||||||
|
[[ ! -e "$1" ]] && echo 0 && return
|
||||||
|
find "$1" -type f -printf "%T@\n" | sort -n | tail -n 1
|
||||||
}
|
}
|
||||||
|
|
||||||
# temporarily switch theme, same thing as setting, only with permanence flag turned off for processors
|
# temporarily switch theme, same thing as setting, only with permanence flag turned off for processors
|
||||||
|
@ -152,7 +261,7 @@ set_theme() {
|
||||||
appext=$(sed -e 's|^[A-Za-z0-9-]\{1,\}/base16-||' <<<"$pkg")
|
appext=$(sed -e 's|^[A-Za-z0-9-]\{1,\}/base16-||' <<<"$pkg")
|
||||||
|
|
||||||
# Compares application extension with existing processors and runs the appropriate processor if found
|
# Compares application extension with existing processors and runs the appropriate processor if found
|
||||||
processor=$(find "$PROCESSOR_PATH" -type f | grep -e "theme_$appext")
|
processor=$(find "$PROCESSOR_PATH" -type f | ${GREPPER} -e "theme_$appext")
|
||||||
if [[ -f "$processor" ]]; then
|
if [[ -f "$processor" ]]; then
|
||||||
"$processor" "$PACKAGE_PATH" "$pkg" "$theme" "$permanent"
|
"$processor" "$PACKAGE_PATH" "$pkg" "$theme" "$permanent"
|
||||||
else
|
else
|
||||||
|
@ -164,6 +273,7 @@ set_theme() {
|
||||||
|
|
||||||
list() {
|
list() {
|
||||||
local selected="$1"
|
local selected="$1"
|
||||||
|
shift
|
||||||
|
|
||||||
case "$selected" in
|
case "$selected" in
|
||||||
packages)
|
packages)
|
||||||
|
@ -173,7 +283,7 @@ list() {
|
||||||
get_processors
|
get_processors
|
||||||
;;
|
;;
|
||||||
themes)
|
themes)
|
||||||
get_themes
|
get_themes "$@"
|
||||||
;;
|
;;
|
||||||
*)
|
*)
|
||||||
echo "Please select one of packages | processors | themes to list."
|
echo "Please select one of packages | processors | themes to list."
|
||||||
|
@ -205,9 +315,9 @@ download() {
|
||||||
|
|
||||||
# if package has patter name/base16-program, put it in packages; if name/process16-program put it in processors
|
# if package has patter name/base16-program, put it in packages; if name/process16-program put it in processors
|
||||||
# if none of the above, assume it's a processor but warn the user
|
# if none of the above, assume it's a processor but warn the user
|
||||||
if grep -q -e '^[0-9A-Za-z-]\{1,\}/base16-[0-9A-Za-z-]\{1,\}$' <<<"$pkg"; then
|
if ${GREPPER} -q -e '^[0-9A-Za-z-]\{1,\}/base16-[0-9A-Za-z-]\{1,\}$' <<<"$pkg"; then
|
||||||
git clone "$repo" "$PACKAGE_PATH/$pkg"
|
git clone "$repo" "$PACKAGE_PATH/$pkg"
|
||||||
elif grep -q -e '^[0-9A-Za-z-]\{1,\}/process16-[0-9A-Za-z-]\{1,\}$' <<<"$pkg"; then
|
elif ${GREPPER} -q -e '^[0-9A-Za-z-]\{1,\}/process16-[0-9A-Za-z-]\{1,\}$' <<<"$pkg"; then
|
||||||
git clone "$repo" "$PROCESSOR_PATH/$pkg"
|
git clone "$repo" "$PROCESSOR_PATH/$pkg"
|
||||||
else
|
else
|
||||||
echo "Package does not fit default naming scheme of packages/processors. Assuming it is a processor but please check manually."
|
echo "Package does not fit default naming scheme of packages/processors. Assuming it is a processor but please check manually."
|
||||||
|
|
Loading…
Reference in a new issue