650 lines
26 KiB
Bash
650 lines
26 KiB
Bash
#!/bin/bash
|
|
|
|
error() { #red text and exit 1
|
|
echo -e "\e[91m$1\e[0m" 1>&2
|
|
exit 1
|
|
}
|
|
|
|
if ! command -v yad &>/dev/null; then
|
|
error "YAD needs to be installed to run Artian-Apps."
|
|
fi
|
|
|
|
if [[ $(id -u) == 0 ]]; then
|
|
echo "Artian-Apps is not designed to be run as root! Please try again as a regular user." | yad --center --window-icon="${DIRECTORY}/icons/logo.png" \
|
|
--width=700 --height=300 --text-info --title="Error" \
|
|
--image="${DIRECTORY}/icons/error.png" --image-on-top --fontname=12 \
|
|
--button='OK'
|
|
error "Artian-Apps is not designed to be run as root! Please try again as a regular user."
|
|
fi
|
|
|
|
# set GUI format versioning
|
|
export GUI_FORMAT_VERSION=2
|
|
|
|
#display first 4 arguments this script receives (for debugging)
|
|
if false;then
|
|
echo "1 $1" 1>&2
|
|
echo "2 $2" 1>&2
|
|
echo "3 $3" 1>&2
|
|
echo "4 $4" 1>&2
|
|
fi
|
|
|
|
#if this script runs itself with a 3rd argument, then yad used it.
|
|
if [ ! -z "$3" ];then
|
|
input="$3" #the 3rd argument is the "sysname" column - invisible and used internally for scripts.
|
|
|
|
echo "Selection: $input" 1>&2
|
|
|
|
refresh_list() { #Refresh the current list of apps in the event of a change
|
|
if [ ! -z "$pipe" ];then
|
|
echo -e "\f" > "$pipe"
|
|
"${DIRECTORY}/preload" yad "$prefix" > "$pipe" 2>/dev/null
|
|
fi
|
|
}
|
|
|
|
if [[ "$input" == *'Updates/' ]];then
|
|
#updater window
|
|
get_positions
|
|
|
|
"${DIRECTORY}/updater" gui fast $geometry2 --skip-taskbar --close-on-unfocus
|
|
exitcode=$? #0 if update successful, 1 if list of updates was closed
|
|
|
|
#figure out which prefix we are on and refresh the app list
|
|
prefix="$(echo "$input" | sed 's+Updates/$++g')"
|
|
|
|
if [ $exitcode == 0 ];then
|
|
refresh_list
|
|
fi
|
|
elif [ "$input" == 'Search/' ];then
|
|
#search window
|
|
get_positions
|
|
|
|
source "${DIRECTORY}/api" #to set the yadflags array variable
|
|
|
|
app="$(yadflags+=("$geometry2") ; app_search_gui)"
|
|
|
|
if [ ! -z "$app" ];then
|
|
"${DIRECTORY}/gui" '' "$app" "/$app" "$app"
|
|
fi
|
|
|
|
elif [[ "$input" == */ ]];then
|
|
#app folder selected
|
|
echo -e '\f' > $pipe #clear the yad list
|
|
"${DIRECTORY}/preload" yad "${input::-1}" >> $pipe #send yad the app-list - derived from folder name but dropping the final slash character
|
|
|
|
else #app details window
|
|
|
|
# make sure terminal_manage function is available
|
|
# the old updater did not source the new api script
|
|
typeset -f terminal_manage &>/dev/null || { set -a; source "${DIRECTORY}/api"; }
|
|
|
|
#app is in format $prefix/$app, so split them out
|
|
app="$(basename "$input")"
|
|
prefix="$(dirname "$input")"
|
|
|
|
#add status heading
|
|
app_status="$(app_status "${app}")"
|
|
|
|
#text to the right of the app icon
|
|
abovetext="<b>$app</b> ($(sed 's/corrupted/corrupted - installation failed/g' <<<"$app_status" | sed 's/disabled/disabled - installation is prevented on your system/g'))"
|
|
|
|
#If package-app, show what packages it installs
|
|
if [ -f "${DIRECTORY}/apps/${app}/packages" ];then
|
|
packages="$(cat "${DIRECTORY}/apps/${app}/packages")"
|
|
if [ "$(wc -w <<<"$packages")" == 1 ];then
|
|
#if package-app uses only 1 package, use singular case
|
|
abovetext+=$'\n'"- This app installs the <b>${packages}</b> package."
|
|
else
|
|
#if package-app uses multiple packages, use plural case
|
|
abovetext+=$'\n'"- This app installs these packages: <b>$(sed 's/ /, /g' <<<"$packages")</b>"
|
|
fi
|
|
fi
|
|
|
|
#show app's website if available
|
|
if [ -f "${DIRECTORY}/apps/${app}/website" ];then
|
|
website="$(head -n1 "${DIRECTORY}/apps/${app}/website")"
|
|
abovetext+=$'\n'"- Website: <a href="\""$website"\"">$website</a>"
|
|
|
|
#show credits link if available - on same line as website link
|
|
if [ -f "${DIRECTORY}/apps/${app}/credits" ];then
|
|
abovetext+=" | <a href="\""file://${DIRECTORY}/apps/${app}/credits"\"">Credits</a>"
|
|
fi
|
|
|
|
else #website unavailable
|
|
#show credits link standalone, if available
|
|
if [ -f "${DIRECTORY}/apps/${app}/credits" ];then
|
|
abovetext+=$'\n'"- <a href="\""file://${DIRECTORY}/apps/${app}/credits"\"">Credits</a>"
|
|
fi
|
|
fi
|
|
|
|
num_users="$(usercount "$app")"
|
|
if [ ! -z "$num_users" ] && [ "$num_users" -gt 20 ];then
|
|
#list the number of users, using this printf command to add commas (,) for every thousand number
|
|
abovetext+=$'\n'"- <b>$(printf "%'d" "$num_users")</b> users"
|
|
|
|
if [ "$num_users" -ge 10000 ];then
|
|
#if this app has over 10,000 users, add two exclamation points!!
|
|
abovetext+="!!"
|
|
elif [ "$num_users" -ge 1500 ];then
|
|
#if this app has over 1500 users, add an exclamation point!
|
|
abovetext+="!"
|
|
fi
|
|
fi
|
|
|
|
#array holding various buttons that may be passed to yad
|
|
whichbutton=()
|
|
|
|
if [ -f "${DIRECTORY}/apps/$app/uninstall" ] || [ -f "${DIRECTORY}/apps/$app/install" ] || [ -f "${DIRECTORY}/apps/$app/install-$arch" ];then
|
|
whichbutton+=("--button=Scripts!${DIRECTORY}/icons/shellscript.png!Feel free to see how an app is installed!"$'\n'"Perfect for learning or troubleshooting.:6")
|
|
fi
|
|
if [ "$(cat "${DIRECTORY}/data/settings/Show Edit button")" == 'Yes' ];then
|
|
#if edit button enabled, show it
|
|
whichbutton+=("--button=Edit!${DIRECTORY}/icons/edit.png!Make changes to the app:8")
|
|
fi
|
|
|
|
#display buttons based on app's installation status
|
|
if [ "$app_status" == 'installed' ];then
|
|
#if installed, display uninstall button
|
|
whichbutton+=("--button=Uninstall!${DIRECTORY}/icons/uninstall.png:2")
|
|
elif [ "$app_status" == 'uninstalled' ];then
|
|
#if uninstalled, display install button
|
|
whichbutton+=("--button=Install!${DIRECTORY}/icons/install.png:4")
|
|
elif [ "$app_status" == 'disabled' ];then
|
|
#if disabled, display only an 'enable' button
|
|
whichbutton+=("--button=<b>Enable</b>!!Force this app to install on your system."$'\n'"This app was disabled for a reason so if you enable it..."$'\n'"YOU HAVE BEEN WARNED.:12")
|
|
else
|
|
#if app status is 'corrupted', and a log file exists for this app, then display a button to view the log file
|
|
if [ "$app_status" == 'corrupted' ];then
|
|
logfile="$(ls "$DIRECTORY/logs"/* -t | grep "fail-${app}" | head -n1)"
|
|
if [ ! -z "$logfile" ];then
|
|
whichbutton+=("--button=Errors!${DIRECTORY}/icons/log-file.png!$app failed to $(echo "$(basename "$logfile")" | awk -F'-' '{print $1}'). Click this button to view the error output saved in the log file.:14")
|
|
fi
|
|
fi
|
|
#if status is corrupted or unknown, then show both buttons
|
|
whichbutton+=("--button=Uninstall!${DIRECTORY}/icons/uninstall.png:2" "--button=Install!${DIRECTORY}/icons/install.png:4")
|
|
fi
|
|
|
|
#only display app icon if it exists
|
|
if [ -f "${DIRECTORY}/apps/${app}/icon-64.png" ];then
|
|
imageline=(--image="${DIRECTORY}/apps/${app}/icon-64.png" --image-on-top)
|
|
fi
|
|
|
|
#Make sure app details window is focused (necessary for openbox window manager)
|
|
(i=0
|
|
while [ "$(xdotool getactivewindow getwindowname)" != "Details of ${app}" ] && [ $i -lt 20 ]; do
|
|
wmctrl -a "Details of ${app}" #Raise the window named "Details of ${app}"
|
|
sleep 0.2
|
|
i=$((i+1))
|
|
done) &
|
|
|
|
#display app details window
|
|
get_positions
|
|
(cat "${DIRECTORY}/apps/$app/description" || echo "Description unavailable") | yad --class Artian-Apps --name "Artian-Apps" --text-info --fontname=12 --wrap --show-uri \
|
|
--text="$(sed 's/&/&/g' <<<"$abovetext")" \
|
|
"${imageline[@]}" \
|
|
--title="Details of ${app}" --window-icon="${DIRECTORY}/icons/logo.png" \
|
|
$geometry2 --close-on-unfocus --skip-taskbar \
|
|
"${whichbutton[@]}"
|
|
button=$?
|
|
|
|
case $button in
|
|
4)
|
|
#install
|
|
terminal_manage install "$app" &
|
|
;;
|
|
2)
|
|
#uninstall
|
|
terminal_manage uninstall "$app" &
|
|
;;
|
|
6)
|
|
#scripts
|
|
install_script="${DIRECTORY}/apps/${app}/$(script_name_cpu "$app")"
|
|
uninstall_script="${DIRECTORY}/apps/${app}/uninstall"
|
|
|
|
text_editor "$uninstall_script" &
|
|
sleep 0.1
|
|
text_editor "$install_script" &
|
|
|
|
"${DIRECTORY}/gui" "$@" #open details window again
|
|
;;
|
|
8)
|
|
#edit
|
|
"${DIRECTORY}/createapp" "$app"
|
|
refresh_list
|
|
;;
|
|
12)
|
|
#enable
|
|
|
|
#remove status file containing 'disabled'
|
|
rm -f "${DIRECTORY}/data/status/${app}"
|
|
refresh_list &
|
|
"${DIRECTORY}/gui" "$@" #open details window again
|
|
;;
|
|
14)
|
|
#viewlog
|
|
echo "Viewing error log of $app..."
|
|
echo "Log filepath: $logfile"
|
|
"${DIRECTORY}/etc/viewlog" "$logfile"
|
|
|
|
"${DIRECTORY}/gui" "$@" #open details window again
|
|
;;
|
|
*)
|
|
#unknown button
|
|
exit 0
|
|
;;
|
|
esac
|
|
|
|
fi
|
|
exit 0
|
|
fi
|
|
|
|
DIRECTORY="$(readlink -f "$(dirname "$0")")"
|
|
|
|
#check mission-critical scripts and re-download them if they contain a syntax error
|
|
(
|
|
sleep 10
|
|
command -v shellcheck >/dev/null || exit 0
|
|
|
|
if shellcheck "${DIRECTORY}/updater" --color=always | grep '\[31m' --before 1 ;then
|
|
echo "Downloading updater script to repair syntax error"
|
|
errors="$(wget -O "${DIRECTORY}/updater" 'https://git.fdc.abrish.ir/a.kamyar/PublicFiles/Artian-Apps/updater' 2>&1)" || echo "$errors"
|
|
fi | sed 's/]31m//g'
|
|
|
|
if shellcheck "${DIRECTORY}/api" --color=always | grep '\[31m' --before 1 ;then
|
|
echo "Downloading api script to repair syntax error"
|
|
errors="$(wget -O "${DIRECTORY}/api" 'https://git.fdc.abrish.ir/a.kamyar/PublicFiles/Artian-Apps/api' 2>&1)" || echo "$errors"
|
|
fi | sed 's/]31m//g'
|
|
) &
|
|
|
|
set -a #make all functions in the api available to subprocesses
|
|
source "${DIRECTORY}/api" || error "failed to source ${DIRECTORY}/api"
|
|
|
|
#For systems with older versions of yad, the text color column cannot be left blank. This python script determines the default text color from GTK bindings.
|
|
if [ -z "${text_color+x}" ];then
|
|
#0400 is the latest version
|
|
yad_version="$(zcat /usr/share/doc/yad/NEWS.gz | head -n 1 | tr -cd '0123456789\n')"
|
|
if [ $yad_version -lt 0400 ]; then
|
|
if command -v python3 &>/dev/null; then
|
|
python_version="python3"
|
|
else
|
|
python_version="python2"
|
|
fi
|
|
export text_color=$(echo "import gi
|
|
gi.require_version('Gtk', '3.0')
|
|
from gi.repository import Gtk
|
|
from gi.repository import Gdk
|
|
tv = Gtk.TextView()
|
|
style = tv.get_style_context()
|
|
textcolor = style.get_color(Gtk.StateType.NORMAL)
|
|
print(Gdk.RGBA.to_string(textcolor))
|
|
" | $python_version -)
|
|
else
|
|
export text_color=""
|
|
fi
|
|
fi
|
|
|
|
#display the Artian-Apps logo in the terminal
|
|
generate_logo &
|
|
|
|
#install dependencies
|
|
runonce <<"EOF"
|
|
dependencies='yad curl wget aria2 lsb-release software-properties-common apt-utils apt-transport-https gnupg imagemagick bc librsvg2-bin locales shellcheck git wmctrl xdotool x11-utils rsync'
|
|
# Install dependencies if necessary
|
|
if ! dpkg -s $dependencies >/dev/null 2>&1; then
|
|
sudo_popup apt install $dependencies -y -f --no-install-recommends
|
|
fi
|
|
EOF
|
|
|
|
#Various stuff to run in background (enclosed in brackets so Geany IDE can collapse the code)
|
|
{
|
|
mkdir -p "${DIRECTORY}/data/status" "${DIRECTORY}/data/update-status" \
|
|
"${DIRECTORY}/data/preload" "${DIRECTORY}/data/settings" \
|
|
"${DIRECTORY}/data/status" "${DIRECTORY}/data/update-status" \
|
|
"${DIRECTORY}/data/categories"
|
|
|
|
#check for updates
|
|
"${DIRECTORY}/updater" set-status &
|
|
trap "kill $! &>/dev/null" EXIT #kill the above subprocess on exit
|
|
|
|
#Click Artian-Apps usage link every time the GUI is run only if the 'Enable Analytics' setting is enabled
|
|
if [ "$(cat "${DIRECTORY}/data/settings/Enable analytics")" == 'Yes' ];then
|
|
#click it
|
|
curl -s -X 'GET' "https://git.fdc.abrish.ir/a.kamyar/PublicFiles/Artian-Apps" -H 'accept: image/gif' -A "Artian-Apps software manager for Artian company" >/dev/null &
|
|
fi
|
|
}
|
|
|
|
#Determine the app list mode. Allowed values: 'yad-*', 'xlunch-*'
|
|
guimode="$(cat "${DIRECTORY}/data/settings/App List Style")"
|
|
[ -z "$guimode" ] && guimode=yad-default
|
|
|
|
#In YAD mode, two windows are handled in a side-by-side configuration. As a group, they must be centered on the the screen.
|
|
#In Xlunch mode, the window must be centered, but xlunch only handles absolute offsets.
|
|
get_positions() {
|
|
#determine screen_width and screen_height
|
|
screen_dimensions="$(xrandr --nograb --current | awk -F 'connected |\\+|\\(' '/ connected.*[0-9]+x[0-9]+\+/ && $2 {printf $2 ", "}' | sed -n -e 's/^.*primary //p' | tr 'x+' ' ' | tr ',+' ' ')"
|
|
if [ -z "$screen_dimensions" ];then
|
|
# if screen_dimensions is empty, this could be a single monitor wayland display which does not have the word "primary" in the output
|
|
# workaround is to get the first output returned for the connected display
|
|
screen_dimensions="$(xrandr --nograb --current | awk -F 'connected |\\+|\\(' '/ connected.*[0-9]+x[0-9]+\+/ && $2 {printf $2 ", "}' | tr 'x+' ' ' | tr ',+' ' ')"
|
|
fi
|
|
screen_width="$(awk '{print $1}' <<<"$screen_dimensions")"
|
|
screen_height="$(awk '{print $2}' <<<"$screen_dimensions")"
|
|
unset screen_dimensions
|
|
|
|
if [[ "$guimode" == yad* ]];then
|
|
|
|
# if this is being run by yad, there should be a yad window id
|
|
# store in arrary of x and y
|
|
# this allows for windows to be moved by the user and the second window to still show up where expected
|
|
main_yad_window=$YAD_XID
|
|
if [ -n "${main_yad_window}" ]; then
|
|
window_info=$(xwininfo -id $main_yad_window)
|
|
# for speed of execution, we are assuming the order of matches from xwininfo
|
|
# this is safe as the output order has been standardized for over a decade
|
|
# this is the location of where the window content starts inside the title bar and window borders (pos x then pos y)
|
|
main_yad_window_pos=($(echo "$window_info" | sed -n 's/Absolute upper-left.*://p'))
|
|
# these are the dimensions of where the window content starts inside the title bar and window borders (dim x then dim y)
|
|
main_yad_window_dim=($(echo "$window_info" | sed -n 's/Width://p;s/Height://p'))
|
|
# again, for speed, all border widths are saved to one array
|
|
# left, right, title, bottom [0, 1, 2, 3]
|
|
# this is the size of the window borders (including title bar)
|
|
border_widths=($(xprop _NET_FRAME_EXTENTS -id "$main_yad_window" | sed -n 's/_NET_FRAME_EXTENTS.*=//p' | tr ',' '\n'))
|
|
#total dimensions for both yad windows side by side
|
|
if [ $screen_width -le 1000 ] || [ $screen_height -le 600 ];then
|
|
#gui size for small screens
|
|
height=${main_yad_window_dim[1]}
|
|
width=600
|
|
|
|
#width of first window
|
|
width1=${main_yad_window_dim[0]}
|
|
#width of second window
|
|
width2=350
|
|
else
|
|
#gui size for large screens
|
|
height=${main_yad_window_dim[1]}
|
|
width=800
|
|
|
|
#width of first window
|
|
width1=${main_yad_window_dim[0]}
|
|
#width of second window
|
|
width2=480
|
|
fi
|
|
#how far down the top of the title bar of yad window is from the top of the screen
|
|
yoffset=$((main_yad_window_pos[1]-border_widths[2]))
|
|
|
|
#screen offsets for window 1
|
|
#use current position of the left side of the main window border
|
|
xoffset1=$((main_yad_window_pos[0]-border_widths[0]))
|
|
#screen offsets for window 2
|
|
#use current position of the right side of the main window border
|
|
xoffset2=$((xoffset1+border_widths[0]+width1+border_widths[1]))
|
|
|
|
#set completed location arguments for both yad windows
|
|
geometry1="--geometry=${width1}x${height}+${xoffset1}+${yoffset}"
|
|
geometry2="--geometry=${width2}x${height}+${xoffset2}+${yoffset}"
|
|
else
|
|
# default positions when the main window does not exist yet
|
|
#total dimensions for both yad windows side by side
|
|
if [ $screen_width -le 1000 ] || [ $screen_height -le 600 ];then
|
|
#gui size for small screens
|
|
height=400
|
|
width=600
|
|
|
|
#width of first window
|
|
width1=250
|
|
#width of second window
|
|
width2=$((width - width1))
|
|
else
|
|
#gui size for large screens
|
|
height=600
|
|
width=800
|
|
|
|
#width of first window
|
|
width1=320
|
|
#width of second window
|
|
width2=$((width - width1))
|
|
fi
|
|
#how far down the top of the title bar of yad window is from the top of the screen
|
|
yoffset=$(((screen_height/2)-(height/2)))
|
|
|
|
#screen offsets for window 1
|
|
xoffset1=$(((screen_width/2)-(width/2)))
|
|
#screen offsets for window 2
|
|
xoffset2=$(((screen_width/2)-(width/2)+width1))
|
|
|
|
#set completed location arguments for both yad windows
|
|
geometry1="--geometry=${width1}x${height}+${xoffset1}+${yoffset}"
|
|
geometry2="--geometry=${width2}x${height}+${xoffset2}+${yoffset}"
|
|
fi
|
|
|
|
elif [[ "$guimode" == xlunch* ]];then
|
|
#desired dimensions for xlunch window
|
|
height=700
|
|
width=800
|
|
#determine
|
|
xoffset=$(((screen_width/2)-(width/2)))
|
|
yoffset=$(((screen_height/2)-(height/2)))
|
|
else
|
|
error "Unrecognized app list style '$guimode'!"
|
|
fi
|
|
}
|
|
# run get_positions once incase sometime requires the position value immediatly
|
|
get_positions
|
|
|
|
#Compile xlunch if required
|
|
if [[ "$guimode" == xlunch* ]] && ([ ! -d "${DIRECTORY}/xlunch" ] || [ ! -f /usr/bin/xlunch ]);then
|
|
#signal files
|
|
rm -f /tmp/xlunchfailed /tmp/xlunchfinished /tmp/terminalexit
|
|
echo '' > /tmp/terminalexit
|
|
"${DIRECTORY}/etc/terminal-run" "
|
|
function error {
|
|
echo -e "\""\e[91m$1\e[39m"\""
|
|
echo 'Close this terminal to exit.'
|
|
echo '' > /tmp/xlunchfailed
|
|
sleep infinity
|
|
}
|
|
trap 'echo "\"""\"" > /tmp/terminalexit' EXIT
|
|
|
|
#uninstall xlunch first
|
|
sudo rm -rf /etc/xlunch /usr/share/xlunch /usr/bin/xlunch /usr/bin/genentries /usr/bin/updateentries /usr/bin/genentries.desktop.sh /usr/share/icons/hicolor/48x48/apps/xlunch_ghost.png /usr/share/icons/hicolor/48x48/apps/xlunch.png /usr/share/applications/genentries.desktop
|
|
|
|
rm -f /tmp/terminalexit
|
|
sudo rm -rf /usr/bin/xlunch "\""$DIRECTORY/xlunch"\"" 2>/dev/null
|
|
sudo apt install -y libimlib2-dev libx11-dev || error 'APT failed to install libimlib2-dev and libx11-dev packages!'
|
|
cd "\""$DIRECTORY"\""
|
|
git clone https://github.com/Tomas-M/xlunch.git || error 'Failed to clone xlunch repository!'
|
|
cd "\""$DIRECTORY/xlunch"\""
|
|
echo 'Running make...'
|
|
echo "\"""\$"(cat '${DIRECTORY}/xlunch/Makefile' | grep -v 'genentries \|cp -r svgicons/')"\"" > '${DIRECTORY}/xlunch/Makefile'
|
|
make -j8 || error 'make command failed!'
|
|
echo 'Running sudo make install...'
|
|
sudo make install || error 'sudo make install failed!'
|
|
sudo rm -f /usr/share/applications/genentries.desktop
|
|
cd $HOME
|
|
if [ ! -f /usr/bin/xlunch ];then
|
|
error 'xlunch should be installed now, but /usr/bin/xlunch does not exist!'
|
|
fi
|
|
echo '' > /tmp/xlunchfinished
|
|
" 'Compiling xlunch...'
|
|
|
|
#if terminal doesn't start in 3 seconds, then /tmp/terminalexit will exist.
|
|
sleep 3
|
|
|
|
#check for an exit status code from the running terminal
|
|
while true; do
|
|
if [ -f /tmp/xlunchfinished ];then
|
|
echo "xlunch finished installing."
|
|
break
|
|
elif [ -f /tmp/xlunchfailed ];then
|
|
#revert back to yad
|
|
echo 'yad-default' > "{DIRECTORY}/data/settings/App List Style"
|
|
error "xlunch failed to compile!"
|
|
elif [ -f /tmp/terminalexit ];then #if terminal doesn't start in 3 seconds, then /tmp/terminalexit will exist.
|
|
#revert back to yad
|
|
echo 'yad-default' > "{DIRECTORY}/data/settings/App List Style"
|
|
error "The xlunch compilation terminal exited prematurely."
|
|
else
|
|
sleep 1
|
|
fi
|
|
done
|
|
fi
|
|
|
|
#Determine message of the day. If announcements file missing or over a day old, download it.
|
|
if [ ! -f "${DIRECTORY}/data/announcements" ] || [ ! -z "$(find "${DIRECTORY}/data/announcements" -mtime +1 -print)" ]; then
|
|
announcements="$(wget -qO- https://git.fdc.abrish.ir/a.kamyar/PublicFiles/Artian-Apps)"
|
|
echo "$announcements" > "${DIRECTORY}/data/announcements"
|
|
fi & #use $announcements and & here to avoid delaying launch or emptying the file before download completes
|
|
|
|
if [[ "$guimode" == yad* ]];then
|
|
|
|
#create a named pipe to send app list through to yad
|
|
pipe="$(mktemp -u)" #get a random filename to work with
|
|
mkfifo $pipe #make the named pipe
|
|
trap "rm -f $pipe" EXIT #remove this named pipe on exit
|
|
echo pipe is $pipe
|
|
|
|
while true;do #main operating loop for yad window
|
|
#in background process, send initial app list to yad; first echo line waits until yad is accepting input, then use small delay to prevent items from being missed
|
|
(echo -e '\f' > $pipe
|
|
sleep 0.5
|
|
"${DIRECTORY}/preload" yad '' >> $pipe) &
|
|
|
|
#retrieve a random line from the announcements file for this session
|
|
motd="$(shuf -n 1 "${DIRECTORY}/data/announcements")"
|
|
|
|
#constantly read from the pipe and send all output to yad
|
|
#if an item is selected, this script will be run with the row's contents
|
|
{ yad --class Artian-Apps --name "Artian-Apps" --center --title='Artian-Apps' \
|
|
--image="${DIRECTORY}/icons/logo-64.png" --image-on-top --text "$motd" \
|
|
--list --no-headers --column=:IMG --column=Name --column=Sysname:HD --column=tip:HD --column=@fore@:HD \
|
|
--separator='\n' --window-icon="${DIRECTORY}/icons/logo.png" \
|
|
--tooltip-column=4 \
|
|
--dclick-action "env pipe=$pipe '${DIRECTORY}/gui'" --select-action "env pipe=$pipe '${DIRECTORY}/gui'" \
|
|
--button="!${DIRECTORY}/icons/search.png"!'Search':"env pipe=$pipe '${DIRECTORY}/gui' '' '' Search/ Search/" \
|
|
--button="!${DIRECTORY}/icons/options.png"!'Settings':2 \
|
|
"$geometry1"; button=$?; kill "$!"; } < <(exec tail -f --retry $pipe)
|
|
|
|
case $button in
|
|
2) #settings
|
|
# remove pipe early so that nothing attempts to write to it
|
|
rm -f "$pipe"
|
|
"${DIRECTORY}/settings"
|
|
"${DIRECTORY}/gui" "$@" #run new instance of this script
|
|
exit 0
|
|
;;
|
|
|
|
3) #search
|
|
app="$(yadflags+=("$geometry2") ; app_search_gui)"
|
|
|
|
if [ ! -z "$app" ];then
|
|
"${DIRECTORY}/gui" '' "$app" "/$app" "$app"
|
|
fi
|
|
;;
|
|
*) #unknown button
|
|
exit 0
|
|
;;
|
|
esac
|
|
done
|
|
#END of yad main window loop
|
|
|
|
elif [[ "$guimode" == xlunch* ]];then
|
|
|
|
#create a named pipe to send app list through to yad
|
|
pipe="$(mktemp -u)" #get a random filename to work with
|
|
mkfifo $pipe #make the named pipe
|
|
trap "rm $pipe" EXIT #remove this named pipe on exit
|
|
echo pipe is $pipe
|
|
|
|
#disabled, but too cool to remove: this can make the transparent background of xlunch blurry - like Windows 7
|
|
if false;then
|
|
scrot -a "$((xoffset+1)),$((yoffset+33)),${width},${height}" blur.png #blur_init.png
|
|
convert -blur 10x5 ~/blur.png ~/blur.png
|
|
fi
|
|
|
|
#Depending on the xlunch theme, different arguments will be used.
|
|
if [ "$guimode" == xlunch-light-3d ];then
|
|
#light mode
|
|
xlunchflags=(--multiple --dontquit -WoCS -s 64 --bc e0e0e000 --tc 000000 --pc 6060ffff --hc ffffff50 \
|
|
-p "Search: " -a -c $([ $width -lt 550 ] && echo 1 || echo 2) --title "Artian-Apps: Artian app store" \
|
|
--icon "${DIRECTORY}/icons/logo.png" --scrollbarcolor ffffff40 --scrollindicatorcolor 0000ff80 \
|
|
--width $width --height $height --xposition $xoffset --yposition $yoffset \
|
|
--button "${DIRECTORY}/icons/logo-3d.png;;$((($width/2)-(300/2))),0;:exec echo Artian-apps-homepage" \
|
|
--button "${DIRECTORY}/icons/settings-dark.png;;$(($width-140)),30;:exec echo Artian-apps-settings" \
|
|
-g "${DIRECTORY}/icons/background-3d.png")
|
|
elif [ "$guimode" == xlunch-dark-3d ];then
|
|
#dark mode, 3d opaque version
|
|
xlunchflags=(--multiple --dontquit -WoCS -s 64 --bc ffffff00 --tc DCDDDE --pc ffffffa0 --hc ffffff30 \
|
|
-p "Search: " -a -c $([ $width -lt 550 ] && echo 1 || echo 2) --title "Artian-Apps: Artian app store" \
|
|
--icon "${DIRECTORY}/icons/logo.png" --scrollbarcolor ffffff20 --scrollindicatorcolor ffffff40 \
|
|
--width $width --height $height --xposition $xoffset --yposition $yoffset \
|
|
--button "${DIRECTORY}/icons/logo-3d-dark.png;;$((($width/2)-(300/2))),0;:exec echo Artian-apps-homepage" \
|
|
--button "${DIRECTORY}/icons/settings-light.png;;$(($width-140)),30;:exec echo Artian-apps-settings" \
|
|
-g "${DIRECTORY}/icons/background-3d-dark.png")
|
|
else
|
|
#dark mode, transparent version
|
|
xlunchflags=(--multiple --dontquit -WoCS -s 64 --bc 000000A0 --tc ffffffff --pc 6060ffff --hc ffffff30 \
|
|
-p "Search: " -a -c $([ $width -lt 550 ] && echo 1 || echo 2) --title "Artian-Apps: Artian app store" \
|
|
--icon "${DIRECTORY}/icons/logo.png" --scrollbarcolor ffffff40 --scrollindicatorcolor 0000ff80 \
|
|
--width $width --height $height --xposition $xoffset --yposition $yoffset \
|
|
--button "${DIRECTORY}/icons/logo-128.png;;$((($width/2)-(128/2))),0;:exec echo Artian-apps-homepage" \
|
|
--button "${DIRECTORY}/icons/logo-text.png;;$([ -z "$prefix" ] && echo '45' || echo '65'),$([ -z "$prefix" ] && echo '10' || echo '0');:exec echo Artian-apps-homepage" \
|
|
--button "${DIRECTORY}/icons/settings-light.png;;$(($width-140)),30;:exec echo Artian-apps-settings")
|
|
fi
|
|
|
|
|
|
#in background process, send initial app list to xlunch; first echo line waits until xlunch is accepting input
|
|
(
|
|
#set initial value to make xlunch keep listening
|
|
echo 'botspot is cool' > $pipe
|
|
echo "$("${DIRECTORY}/preload" xlunch '')" > $pipe) &
|
|
|
|
#read pipe pipe to xlunch read output of xlunch
|
|
tail -f --retry $pipe | xlunch "${xlunchflags[@]}" | while read -r line; do
|
|
echo "Received '$line'"
|
|
|
|
if [ "$line" == 'Updates/' ];then
|
|
echo > $pipe #clear list
|
|
|
|
#in subprocess, open details window for app
|
|
geometry2="--center --height=$((height/2)) --width=$width" pipe='' "${DIRECTORY}/gui" '' '' "$line" "$line"
|
|
|
|
#back to main level
|
|
"${DIRECTORY}/preload" xlunch '' > $pipe
|
|
|
|
#category selected
|
|
elif [[ "$line" == */ ]];then
|
|
echo > $pipe #clear list
|
|
"${DIRECTORY}/preload" xlunch "$(echo "$line" | sed 's+/$++g')" > $pipe
|
|
|
|
#Artian-apps logo button clicked
|
|
elif [ "$line" == 'Artian-apps-homepage' ];then
|
|
x-www-browser "$(cat "https://artianhpc.ir/")" &
|
|
# x-www-browser "$(cat "${DIRECTORY}/etc/git_url")" &
|
|
|
|
#Settings button clicked
|
|
elif [ "$line" == 'Artian-apps-settings' ];then
|
|
#close xlunch
|
|
echo ':quit' > $pipe
|
|
|
|
#run settings, then run Artian-apps gui
|
|
"${DIRECTORY}/settings"
|
|
"${DIRECTORY}/gui" "$@"
|
|
|
|
#exit this script
|
|
exit 0
|
|
|
|
#app selected
|
|
else
|
|
echo > $pipe #clear list
|
|
|
|
#in subprocess, open details window for app
|
|
geometry2="--center --height=$((height/2)) --width=$width" pipe='' "${DIRECTORY}/gui" '' '' "$line" "$line"
|
|
|
|
#show app list again
|
|
"${DIRECTORY}/preload" xlunch "$(dirname "$line" | sed 's/^.$//g')" > $pipe
|
|
fi
|
|
done
|
|
|
|
fi
|
|
|
|
|