#!/bin/bash ###################################################################### # The ASCII lightsaber # # # # By: Jansen Price # # November 19, 2015 # # ▁▁▁▁▁▁▁▁▁▁▁▁▁ ▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁ # # |▍░▐░░▣░▒░▒░▒▕| ▌ # # ▔▔▔▔▔▔▔▔▔▝▔▔▔ ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔ # ###################################################################### lsaberVersion="lsaber-1.0" # Determine width and height of terminal WIDTH=`tput cols` HEIGHT=`tput lines` HILT=(" ▁▁▁▁▁▁▁▁▁▁▁▁▁ " "▐▍░▐░░▣░▒░▒░▒▕|" " ▔▔▔▔▔▔▔▔▔▝▔▔▔ ") BLADE=("▁" "█" "▔") TIP=(" " "▌" " ") COLORNAMES=("red" "green" "yellow" "blue" "purple" "cyan") COLORCODES=("\E[31m" "\E[32m" "\E[33m" "\E[34m" "\E[35m" "\E[36m") displayUsage() { echo "$lsaberVersion - An animated ASCII lightsaber" echo "Usage: lsaber [-l ] [message]" echo " -l Length of the lightsaber" echo " -c Color of blade (valid colors: ${COLORNAMES[@]})" echo echo "Example: lsaber -l 44 -c green 'May the force be with you'" } # Handle --help arg if [ -n "$1" -a "$1" == "--help" ]; then displayUsage exit 1 fi # Default blade length and color bladeLength=55 bladeColor=red # Process user options while getopts "l:c:" opt; do case $opt in l) # Set the bladelength (option -l ) bladeLength=$OPTARG ;; c) # Set the color (option -c ) bladeColor=$OPTARG ;; esac done # Shift off the used args shift $((OPTIND-1)) # Get message if [ -n "$1" ]; then message="$@" fi # Define hilt length hiltLength=${#HILT} # Get blade length maxSaberLength=$((($WIDTH-$hiltLength)/2)) isNumber='^[0-9]+$' if ! [[ $bladeLength =~ $isNumber ]] ; then echo "Error: Blade length must be a number" >&2 exit 1 fi if [ "$bladeLength" -gt "$maxSaberLength" ]; then bladeLength=$maxSaberLength fi # Define saber length saberLength=$((${#HILT}+$bladeLength)) # Get blade color if [[ ${COLORNAMES[@]} =~ $bladeColor ]]; then for c in $(seq 0 $((${#COLORNAMES[@]} - 1))); do if [ "${COLORNAMES[c]}" == "$bladeColor" ]; then bladeColorCode=${COLORCODES[c]} fi done else echo "Error: Invalid color name for blade" >&2; echo displayUsage exit 1 fi drawHilt() { local row=$1 local col=$2 # Preserve whitespace in strings local IFS='%' tput cup $(($row-1)) $col echo ${HILT[0]} tput cup $row $col echo ${HILT[1]} tput cup $(($row+1)) $col echo ${HILT[2]} # Reset whitespace preserving directive unset IFS } animateBlade() { local row=$1 local col=$2 local hiltLength=$3 local bladeLength=$4 bladeStart=$(($col+$hiltLength)) # Hide the cursor tput civis for (( i=0; i<$bladeLength; i++ )) do tput cup $(($row-1)) $(($bladeStart+$i)); echo ${BLADE[0]} tput cup $row $(($bladeStart+$i)); echo ${BLADE[1]} tput cup $(($row+1)) $(($bladeStart+$i)); echo ${BLADE[2]} tput cup $(($row-1)) $(($bladeStart+$i+1)); echo ${TIP[0]} tput cup $row $(($bladeStart+$i+1)); echo ${TIP[1]} tput cup $(($row+1)) $(($bladeStart+$i+1)); echo ${TIP[2]} sleep 0.001 done # Display the cursor tput cnorm } showMessage() { local row=$1 local message=$2 messageLength=${#message} center=$((($WIDTH-$messageLength)/2)) tput cup $(($row+3)) $center echo "$message" } # ------------------------------------------------------ # Main program execution # Clear the screen tput clear # Calculate center of screen centerRow=$(($HEIGHT/2)) centerCol=$((($WIDTH-$saberLength)/2)) drawHilt $centerRow $centerCol printf "$bladeColorCode" animateBlade $centerRow $centerCol $hiltLength $bladeLength if [ -n "$message" ]; then showMessage $centerRow "$message" fi # Move cursor down to bottom of screen tput cup $HEIGHT 0 tput op exit 0