Skip to content

Commit

Permalink
Add files via upload
Browse files Browse the repository at this point in the history
  • Loading branch information
Megaf authored Sep 14, 2022
1 parent 1a2dceb commit a0bd17c
Showing 1 changed file with 335 additions and 0 deletions.
335 changes: 335 additions & 0 deletions libsay
Original file line number Diff line number Diff line change
@@ -0,0 +1,335 @@
#!/bin/bash
#
# FlightGear Installer
# libsay
# Library that adds the command "say" to print nice looking messages.
#
# Author: Megaf - https://github.com/Megaf - mmegaf [at] gmail [dot] com
# Date: 03/09/2022
# GitHub: https://github.com/Megaf/FlightGear-Installer
# License: GPL V3

set_colour()
{
local clrs=(
black red green yellow blue magenta cyan
white grey
light_red light_green light_yellow light_blue light_magenta light_cyan
bright_white bright_black
)

local chg_clr="tput" # Colour command to be used.
local clr_arg="$2"

[ "$1" = "fg" ] && local arg="setaf" # Colour command argument to set the foreground colour.
[ "$1" = "bg" ] && local arg="setab" # Colour command argument to set the foreground colour.
[ -z "$2" ] && [ "$1" != "fg" -o "$1" != "bg" ] && local arg="setaf" && local clr_arg="$1" # Foreground/cackground arg not passed. Assuming foreground.

local clr_cmd=(
"$chg_clr $arg 0" "$chg_clr $arg 1" "$chg_clr $arg 2" "$chg_clr $arg 3" "$chg_clr $arg 4" "$chg_clr $arg 5" "$chg_clr $arg 6"
"$chg_clr $arg 7" "$chg_clr $arg 8"
"$chg_clr $arg 9" "$chg_clr $arg 10" "$chg_clr $arg 11" "$chg_clr $arg 12" "$chg_clr $arg 13" "$chg_clr $arg 14"
"$chg_clr $arg 15" "$chg_clr $arg 16"
)

for i in ${!clrs[@]}; do
[[ "${clrs[$i]}" == "$clr_arg" ]] && ${clr_cmd[$i]} && break
done

unset clrs chg_clr clr_cmd clr_arg arg
}

# Turns underline on/off.
underline_on() { tput smul; }
underline_off() { tput rmul; }
# Turns standout mode on/off.
standout_on() { tput smso; }
standout_off() { tput rmso; }

bold_on() { tput bold; } # Turns mode on (use rst to reset).

# Message type parse. Colour schemes for these types of message
c_error() { tput smul; set_colour bg black; set_colour fg red; } # Set for Error.
c_info() { set_colour bg black; set_colour fg green; } # Set for Information.
c_warning() { set_colour bg black; tput smul; tput smso; set_colour fg yellow; } # Set for Warning.
c_debug() { set_colour bg black; set_colour fg cyan; } # Set for Debug.

# Resets the terminal to the default style.
rst() { tput sgr0; } # Resets all colour and formating settings.

draw()
{
[ ! "$style" ] && local style="boxdoubleline"
local prnt_args="%s" # Command args to use in the "print" command.
prnt() { printf "$prnt_args" "$*"; } # "print" command the script uses. In theory it will be easy to use other things than "printf".

local dynmc_cmd="do_" # Set this string as a "dynamic command", instead of printing a symbol in the array, it will execute an action.

# Array with valid options for draw command.
local parts_cmds=(
topleftcorner top toprightcorner
leftside rightside
leftside_c rightside_c
bottomleftcorner bottom bottomrightcorner
line do_space do_godown do_save_pos do_go_pos
do_linefill do_margin do_autofill
do_topfill do_bottomfill
)

# Styles
# BoxDoubleLine Style
[ "$style" == "boxdoubleline" ] && local parts=(
╔ ═ ╗
║ ║
╠ ╣
╚ ═ ╝
)

[ "$style" == "boxverticalsinglehorizontaldouble" ] && local parts=(
╒ ═ ╕
│ │
├ ┤
╘ ═ ╛
)

[ "$style" == "boxverticaldoublehorizontalsingle" ] && local parts=(
╓ ─ ╖
║ ║
╠ ╣
╙ ─ ╜
)

[ "$style" == "boxsingleline" ] && local parts=(
┌ ─ ┐
│ │
├ ┤
└ ─ ┘
)

[ "$style" == "boxsolid" ] && local parts=(
█ ▀ █
█ █
█ █
█ ▄ █
)

local prnt_clr="set_colour fg $colour;"
local bordr_clr_cmds=(
"prnt_clr ${parts[1]}" "0" "0"
"0" "0"
"0" "0"
"0" "0" "0"
"0"
)

do_linefill() { printf "%0.s${parts[10]}" $(seq 1 "$linesize"); }
do_topfill() { printf "%0.s${parts[1]}" $(seq 1 "$linesize"); }
do_bottomfill() { printf "%0.s${parts[8]}" $(seq 1 "$linesize"); }
do_space() { printf "%0.s "; }
do_margin() { printf "%0.s " $(seq 1 "$margin"); }
do_autofill() { printf "%0.s " $(seq 1 "$bsize"); }
do_save_pos() { tput sc; }
do_go_pos() { tput rc; }
do_godown() { printf "\n"; }

# Array that contains the commands that are executed with "do_commands", like "do_margin"
local dynmc_cmds=(
"0" "0" "0"
"0" "0"
"0" "0"
"0" "0" "0"
"0" "do_space" "do_godown" "do_save_pos" "do_go_pos"
"do_linefill" "do_margin" "do_autofill"
"do_topfill" "do_bottomfill"
)

# 'for loop' to check if the required symbol is a static or a dynamic symbol.
for i in "$@"; do
local index=0
for n in "${parts_cmds[@]}"; do
if [[ ! "$n" == "$i" ]]; then
index="$((index+1))"
elif [[ "$n" == "$i" ]]; then
if [[ "${parts_cmds[$index]}" == "$dynmc_cmd"* ]]; then
"${dynmc_cmds[$index]}"
else
prnt "${parts[$index]}"
fi
unset index
break
fi
done
done

unset index prnt_args dynmc_cmd prnt parts_cmds parts prnt_clr bordr_clr_cmds do_linefill do_topfill do_bottomfill do_space do_margin do_autofill do_save_pos do_go_pos do_godown dynmc_cmds
}

draw_a_box()
{
draw \
topleftcorner top top top toprightcorner do_godown \
leftside do_space do_space do_space rightside do_godown \
bottomleftcorner bottom bottom bottom bottomrightcorner do_godown
}

say()
{
unset msg

check_options()
{
[ "$1" = "colour_command" ] && local options=( --colour --color )
[ "$1" = "alignment_command" ] && local options=( --align )
[ "$1" = "colour" ] && local options=(black red green yellow blue magenta cyan
white grey light_red light_green light_yellow light_blue light_magenta light_cyan
bright_white bright_black
)
[ "$1" = "alignment" ] && local options=( centre center left right )

for i in "${options[@]}"; do
[ "$i" = "$2" ] && return 3
done
unset options
}

validade_command()
{
for i in "$*"; do
check_options colour_command "$1"
if [ "$?" = 3 ]; then
check_options colour "$2"
if [ "$?" = 3 ]; then
colour="$2"; shift 2
else
shift 2
fi
fi

check_options alignment_command "$1"
if [ "$?" = 3 ]; then
check_options alignment "$2"
if [ "$?" = 3 ]; then
align="$2"; shift 2
else
shift 2
fi
fi

check_options colour_command "$1"; colour_result="$?"
check_options alignment_command $1; align_result="$?"
if [ "$colour_result" = 0 ] && [ "$align_result" = 0 ]; then
if [[ "$1" == "--"* ]]; then
shift 1
fi
fi

# If no command line arg was passed and the user doesn't want to open a txt file...
if [[ ! "$1" == "--"* ]] && [[ ! "$1" == *".txt" ]]; then
msg="$*" # ...Then grabs the whole input line as the text to use.
fi
done
unset args
}

local args=( "$@" )
validade_command "${args[@]}"

# Checks if input is coming from the standard input.
if [ ! -t 0 ]; then
msg="$(cat)"
elif [[ "$1" == *".txt" ]]; then # Or if it's coming from a text file.
msg="$(cat $1)"
fi

# Main print loop. It will do all calculations and printing.
print_centre()
{
local margin=1 # Default margin size between the side of the box and text.
local spacesize=3 # Basically adjust the amount of space on both sides of the text to the box.
local minimal_size=10 # Box will not be smaller than this, no matter how little the text is.
local length=$(awk -S '{print length}' <<< $msg | sort -nr | head -1); # Finds the longest line in the text and sets the box size according to it.
# local blength=$(awk -S '{print length}' <<< $msg | sort -nr | head -2 | tail -n 1); # Finds the second longest line.
# Checking if the longest line is shorter than the minimal size wanted.
[ "$length" -le "$minimal_size" ] && local linesize="$minimal_size"
[ "$length" -ge "$minimal_size" ] && local linesize="$((length+spacesize))"
# [ "$size" = "full" ] && local linesize="$(($(tput cols) - spacesize))" # For future use. Makes the box size "full screen".

# Draws the top of the box
draw topleftcorner do_topfill toprightcorner do_godown

# While loop that brakes the whole text in individual lines for processing and printing.
# Highly inneficient and slow, perhaps you can find a better way? :)
while IFS= read -r a; do

# Just do it loop, It runs per line calculations and printing.
just_do_it()
{

rst
[ ! "$a" ] && draw leftside_c do_linefill || draw leftside

# Checks if the line contain any of these works and apply colour code.
if [[ "$a" == "ERROR:"* ]] || [[ "$a" == "ERR:"* ]]; then
bold_on; set_colour fg red; set_colour bg white; local formatted="true"
elif [[ "$a" == "INFO:"* ]]; then
set_colour fg green; set_colour bg black; local formatted="true"
elif [[ "$a" == "WARN:"* ]] || [[ "$a" == "WARNING:"* ]]; then
standout_on; bold_on; set_colour fg yellow; set_colour bg black; local formatted="true"
elif [[ "$a" == "DEBUG:"* ]] || [[ "$a" == "DBG:"* ]] || [[ "$a" == "ADV_DBG:"* ]]; then
set_colour fg cyan; set_colour bg black; local formatted="true"
elif [[ "$a" == "NOTICE:"* ]]; then
bold_on; set_colour fg light_yellow; set_colour bg black; local formatted="true"
elif [[ "$a" == "TITLE:"* ]]; then
standout_on; bold_on; local formatted="true"
fi

# Final loop, calculates the line and spaces size and then prints the line.
write_out()
{
local txt_size="${#4}"
local asize="$((txt_size+margin))"
local bsize="$((linesize-asize))"
local linesize_="$((linesize-1))"

centre_txt() { sed -e :a -e "s/^.\{1,$linesize_\}$/ & /;ta" | tr -d '\n' | head -c $linesize; }

[ "$weight" = "bold" -o "$2" = "bold" ] && bold_on
[ ! "$formatted" = "true" ] && [ "$colour" ] && set_colour fg "$3"

[ "$1" = "centre" -o "$1" = "center" ] && printf '%s' "$4" | centre_txt && rst
[ "$1" = "left" ] || [ -z "$1" ] && draw do_margin && printf '%s' "$4" && draw do_autofill && rst
[ "$1" = "right" ] && draw do_autofill && printf '%s' "$4" && draw do_margin && rst
unset formatted centre_txt txt_size asize bsize linesize_
}

[ "$a" ] && write_out "$align" "$weight" "$colour" "$a"
rst
[ ! "$a" ] && draw rightside_c do_godown || draw rightside do_godown
}

# Only prints a line, if either the line doesn't contain debug of if debug is enabled.
[ ! "$debug" = "true" ] && [[ ! "$a" =~ "DEBUG:"* ]] && just_do_it
[ "$debug" = "true" ] && just_do_it

done <<< $msg

# Draws the bottom of the box
draw bottomleftcorner do_bottomfill bottomrightcorner do_godown

unset margin spacesize minimal_size length linesize a just_do_it write_out weight
}

# Debug checker for single line messages.
if [ "$msg" ] && [[ ! "$debug" == "true" ]] && [[ ! "$msg" == "DEBUG:"* ]] && [[ ! "$msg" == "DBG:"* ]]; then
print_centre
elif [ "$msg" ] && [[ "$debug" == "true" ]]; then
print_centre
fi

unset msg print_centre colour_result align_result align colour
}

0 comments on commit a0bd17c

Please sign in to comment.