#!/bin/bash if [ -z "$DIRECTORY" ]; then DIRECTORY="$(readlink -f "$(dirname "$(dirname "$0")")")" fi function error { echo -e "\e[91m$1\e[39m" exit 1 } #Only one instance of this script should run at a time. wait if another process other than this one is running #skip this check if this instance does not have an ARG (running as a GUI) if [ ! -z "$1" ];then # processes which are using categoryedit for scripting (not a GUI) will have additional column 3 and 4 output (the arguments) # output of below command is: PID /bin/bash ARG1 ARG2 # pgrep -af ${DIRECTORY}/etc/categoryedit # remove all output from the list if there is no second column (aka, there was not argument, meaning it is a GUI) # pgrep -af ${DIRECTORY}/etc/categoryedit | awk '{print $1, $3}' | awk '$2 != ""' # now only print the first column (the PIDs) # pgrep -af ${DIRECTORY}/etc/categoryedit | awk '{print $1, $3}' | awk '$2 != ""' | awk '{print $1}' while [[ $(pgrep -af ${DIRECTORY}/etc/categoryedit | awk '{print $1, $3}' | awk '$2 != ""' | awk '{print $1}' | sort | head -n 1) != $$ ]]; do # waiting for another instance of categoryedit to finish sleep 0.02 done fi #for read_category_files() if ! command -v read_category_files >/dev/null ;then source "${DIRECTORY}/api" || error "failed to source ${DIRECTORY}/api" fi refresh() { #set the categories variable to the current categories categories="$(read_category_files)" } refresh set_category() { #place the $1 app in the $2 category - don't write to files, only change the local_categories local app="$1" [ -z "$app" ] && error "set_category: app field empty!" local category="$2" #the category field may be left blank. #store the contents of the global categories file and the local category-overrides file #these are purposely not local-variables. [ -z "$local_categories" ] && local_categories="$(cat "${DIRECTORY}/data/category-overrides")" [ -z "$global_categories" ] && global_categories="$(cat "${DIRECTORY}/etc/categories")" #the app may be: in both files, in global file, in overrides file, or in neither file if echo "$local_categories" | grep -q "^${app}|" ;then #if app is already listed in local categories file if echo "$global_categories" | grep -qx "${app}|${category}" ;then #if the app is already in that category in the global category file echo "$app is already in the $category category in the global categories file; removing entry from the overrides file." local_categories="$(echo "$local_categories" | grep -v "^${app}|")" else #the app is NOT already in that category in the global category file #add it to the overrides list echo "$app is not in the $category category in the global categories file; adding entry to the overrides file." local_categories="$(echo "$local_categories" | grep -v "^${app}|")\n${app}|${category}" fi else #app is not listed in local categories file if echo "$global_categories" | grep -qx "${app}|${category}" ;then #if the app is already in that category in the global category file echo "$app is already in the $category category in the global categories file; doing nothing." true #do nothing - don't add the app to the overrides file else #the app is NOT currently in the desired category in the global category file echo "$app is not in the $category category in the global categories file; adding entry to the overrides file." local_categories="$(echo "$local_categories" | grep -v "^${app}|")\n${app}|${category}" fi fi local_categories="$(echo -e "$local_categories" | sort)" #echo "Line in file: $(echo -e "$local_categories" | grep "^${app}|")" } save_changes() { #writes the $local_categories variable to the category-overrides file if [ "$local_categories" != "$(cat "${DIRECTORY}/data/category-overrides")" ];then echo "$local_categories" > "${DIRECTORY}/data/category-overrides" fi } APPS="$(list_apps local)" #command line argument handler: $1 is app, $2 is category. (--delete means to remove the app from category-overrides) if [ ! -z "$1" ];then if ! echo "$APPS" | grep -q "$1" ;then error "The '$1' app does not exist!" fi set_category "$1" "$2" save_changes exit 0 fi while true;do #repeat the main window until Save or Exit clicked #generate a virtual file system with apps in folders represented as subdirectories IFS=$'\n' LIST='' for app in $APPS do category="$(echo "$categories" | grep "$app"'|' | awk -F '|' '{print $2}' | tr -d '.' | head -n1)" #echo "category for $app is $category." LIST="${LIST}${DIRECTORY}/apps/$app/icon-24.png $app $category " done LIST="${LIST::-1}" categories="$(echo -e "$LIST" | yad --center --title='Category editor' --height=400 \ --list --text="Changes saved to: $(echo "${DIRECTORY}/data/category-overrides" | sed "s+$HOME+~+g")" --editable --editable-cols=3 --multiple --dclick-action=true --print-all \ --separator='|' --window-icon="${DIRECTORY}/icons/settings.png" \ --column=:IMG --column=Name --column=Category:TEXT \ --button=Reset!"${DIRECTORY}/icons/backup.png"!"Removes all category overrides.":4 \ --button=All!"${DIRECTORY}/icons/trash.png"!"Clears categories so all apps are in one list.":2 \ --button=Cancel!"${DIRECTORY}/icons/exit.png"!"Don't save any changes.":1 \ --button=Save!"${DIRECTORY}/icons/check.png":0 )" button=$? if [ "$button" == 0 ];then #save #remove first and last characters from each line --- and '(null)' messaged from yad --- and sort it alphabetically categories="$(echo "$categories" | sed 's/.$//; s/^.//' | sed "s/(null)//g" | sort)" break #exit the loo to save the changes elif [ "$button" == 2 ];then #delete all # remove categories from all lines, while leaving hidden ones intact categories="$(echo -e "$(echo "$categories" | grep -v '|hidden' | sed 's/|.*/|/')\n$(echo "$categories" | grep '|hidden')" | sort)" elif [ "$button" == 4 ];then #reset - ignore the local category-overrides file # list the global categories file |-----and all apps------------| filter out duplicates categories="$( (cat "${DIRECTORY}/etc/categories" ; list_apps local | sed 's/$/|/g') | awk -F'|' '!seen[$1]++')" else #cancel or WM X echo "User exited" exit 0 #exit the script without saving changes fi done #for every line in the output set the category with the set_category function IFS=$'\n' for line in $categories ;do set_category "$(echo "$line" | awk -F'|' '{print $1}')" "$(echo "$line" | awk -F'|' '{print $2}')" done #The set_category function made modifications to the local_categories variable. save_changes #Now save those changes to file. #reload app-list in background "${DIRECTORY}/etc/preload-daemon" "$(cat "${DIRECTORY}/data/settings/App List Style")" once &