1#!/usr/local/bin/bash 2# 3# Siddharth Dushantha 2020 4# 5# Dependencies: sxiv, imagemagick, xdotool, fzf 6 7VERSION=1.0.6 8 9# Default values 10SEARCH_PROMPT="❯ " 11SIZE=532x365 12POSITION="+0+0" 13FONT_SIZE=38 14BG_COLOR="#ffffff" 15FG_COLOR="#000000" 16PREVIEW_TEXT="ABCDEFGHIJKLM\nNOPQRSTUVWXYZ\nabcdefghijklm\nnopqrstuvwxyz\n1234567890\n!@$\%(){}[]" 17 18show_help() { 19printf "%s" "\ 20usage: fontpreview [-h] [--size \"px\"] [--position \"+x+y\"] [--search-prompt SEARCH_PROMPT] 21 [--font-size \"FONT_SIZE\"] [--bg-color \"BG_COLOR\"] [--fg-color \"FG_COLOR\"] 22 [--preview-text \"PREVIEW_TEXT\"] [-i font.otf] [-o preview.png] [--version] 23 24┌─┐┌─┐┌┐┌┌┬┐┌─┐┬─┐┌─┐┬ ┬┬┌─┐┬ ┬ 25├┤ │ ││││ │ ├─┘├┬┘├┤ └┐┌┘│├┤ │││ 26└ └─┘┘└┘ ┴ ┴ ┴└─└─┘ └┘ ┴└─┘└┴┘ 27Very customizable and minimal font previewer written in bash 28 29optional arguments: 30 -h, --help show this help message and exit 31 -i, --input filename of the input font (.otf, .ttf, .woff are supported) 32 -o, --output filename of the output preview image (input.png if not set) 33 --size size of the font preview window 34 --position the position where the font preview window should be displayed 35 --search-prompt input prompt of fuzzy searcher 36 --font-size font size 37 --bg-color background color of the font preview window 38 --fg-color foreground color of the font preview window 39 --preview-text preview text that should be displayed in the font preview window 40 --version show the version of fontpreview you are using 41" 42} 43 44pre_exit() { 45 # Get the proccess ID of this script and kill it. 46 # We are dumping the output of kill to /dev/null 47 # because if the user quits sxiv before they 48 # exit this script, an error will be shown 49 # from kill and we dont want that 50 kill -9 "$(cat "$PIDFILE" 2>/dev/null)" &> /dev/null 51 52 # Delete tempfiles, so we don't leave useless files behind. 53 rm -rf "$FONTPREVIEW_DIR" 54} 55 56generate_preview(){ 57 # Credits: https://bit.ly/2UvLVhM 58 convert -size $SIZE xc:"$BG_COLOR" \ 59 -gravity center \ 60 -pointsize $FONT_SIZE \ 61 -font "$1" \ 62 -fill "$FG_COLOR" \ 63 -annotate +0+0 "$PREVIEW_TEXT" \ 64 -flatten "$2" 65} 66 67main(){ 68 # Checkig if needed dependencies are installed 69 dependencies=(xdotool sxiv convert fzf) 70 for dependency in "${dependencies[@]}"; do 71 type -p "$dependency" &>/dev/null || { 72 echo "error: Could not find '${dependency}', is it installed?" >&2 73 exit 1 74 } 75 done 76 77 # Checking for enviornment variables which the user might have set. 78 # This config file for fontpreview is pretty much the bashrc, zshrc, etc 79 # Majority of the variables in fontpreview can changed using the enviornment variables 80 # and this makes fontpreview very customizable 81 [[ $FONTPREVIEW_SEARCH_PROMPT != "" ]] && SEARCH_PROMPT=$FONTPREVIEW_SEARCH_PROMPT 82 [[ $FONTPREVIEW_SIZE != "" ]] && SIZE=$FONTPREVIEW_SIZE 83 [[ $FONTPREVIEW_POSITION != "" ]] && POSITION=$FONTPREVIEW_POSITION 84 [[ $FONTPREVIEW_FONT_SIZE != "" ]] && FONT_SIZE=$FONTPREVIEW_FONT_SIZE 85 [[ $FONTPREVIEW_BG_COLOR != "" ]] && BG_COLOR=$FONTPREVIEW_BG_COLOR 86 [[ $FONTPREVIEW_FG_COLOR != "" ]] && FG_COLOR=$FONTPREVIEW_FG_COLOR 87 [[ $FONTPREVIEW_PREVIEW_TEXT != "" ]] && PREVIEW_TEXT=$FONTPREVIEW_PREVIEW_TEXT 88 89 # Save the window ID of the terminal window fontpreview is executed in. 90 # This is so that when we open up sxiv, we can change the focus back to 91 # the terminal window, so that the user can search for the fonts without 92 # having to manualy change the focus back to the terminal. 93 xdotool getactivewindow > "$TERMWIN_IDFILE" 94 95 # Flag to run some commands only once in the loop 96 FIRST_RUN=true 97 98 while true; do 99 # List out all the fonts which imagemagick is able to find, extract 100 # the font names and then pass them to fzf 101 font=$(convert -list font | awk -F: '/^[ ]*Font: /{print substr($NF,2)}' | fzf --prompt="$SEARCH_PROMPT") 102 103 # Exit if nothing is returned by fzf, which also means that the user 104 # has pressed [ESCAPE] 105 [[ -z $font ]] && return 106 107 generate_preview "$font" "$FONT_PREVIEW" 108 109 if [[ $FIRST_RUN == true ]]; then 110 FIRST_RUN=false 111 112 # Display the font preview using sxiv 113 #sxiv -g "$SIZE$POSITION" "$FONT_PREVIEW" -N "fontpreview" -b & 114 sxiv -N "fontpreview" -b -g "$SIZE$POSITION" "$FONT_PREVIEW" & 115 116 # Change focus from sxiv, back to the terminal window 117 # so that user can continue to search for fonts without 118 # having to manually change focus back to the terminal window 119 xdotool windowfocus "$(cat "$TERMWIN_IDFILE")" 120 121 # Save the process ID so that we can kill 122 # sxiv when the user exits the script 123 echo $! >"$PIDFILE" 124 125 # Check for crashes of sxiv 126 elif [[ -f $PIDFILE ]] ; then 127 if ! pgrep -F "$PIDFILE" >/dev/null 2>&1; then 128 echo "Restart sxiv - You maybe using a obsolete version. " >&2 129 # Display the font preview using sxiv 130 sxiv -g "$SIZE$POSITION" -N "fontpreview" -b "$FONT_PREVIEW" & 131 132 # Change focus from sxiv, back to the terminal window 133 # so that user can continue to search for fonts without 134 # having to manually change focus back to the terminal window 135 xdotool windowfocus "$(cat "$TERMWIN_IDFILE")" 136 137 # Save the process ID so that we can kill 138 # sxiv when the user exits the script 139 echo $! >"$PIDFILE" 140 fi 141 142 fi 143 done 144} 145 146# Disable CTRL-Z because if we allowed this key press, 147# then the script would exit but, sxiv would still be 148# running 149trap "" SIGTSTP 150 151trap pre_exit EXIT 152 153# Use mktemp to create a temporary directory that won't 154# collide with temporary files of other application. 155FONTPREVIEW_DIR="$(mktemp -d "${TMPDIR:-/tmp}/fontpreview_dir.XXXXXXXX")" || exit 156PIDFILE="$FONTPREVIEW_DIR/fontpreview.pid" 157touch "$PIDFILE" || exit 158FONT_PREVIEW="$FONTPREVIEW_DIR/fontpreview.png" 159touch "$FONT_PREVIEW" || exit 160TERMWIN_IDFILE="$FONTPREVIEW_DIR/fontpreview.termpid" 161touch "$TERMWIN_IDFILE" || exit 162 163font=$1 164 165 166# Parse the arguments 167options=$(/usr/local/bin/getopt -o hi:o: --long position:,size:,version,search-prompt:,font-size:,bg-color:,fg-color:,preview-text:,input:,output:,help -- "$@") 168eval set -- "$options" 169 170while true; do 171 case "$1" in 172 --size) 173 shift 174 FONTPREVIEW_SIZE=$2 175 ;; 176 --position) 177 shift 178 FONTPREVIEW_POSITION=$2 179 ;; 180 -h|--help) 181 show_help 182 exit 183 ;; 184 --version) 185 echo $VERSION 186 exit 187 ;; 188 -i|--input) 189 input_file="$2" 190 ;; 191 -o|--output) 192 output_file="$2" 193 ;; 194 --search-prompt) 195 FONTPREVIEW_SEARCH_PROMPT=$2 196 ;; 197 --font-size) 198 FONTPREVIEW_FONT_SIZE=$2 199 ;; 200 --bg-color) 201 FONTPREVIEW_BG_COLOR=$2 202 ;; 203 --fg-color) 204 FONTPREVIEW_FG_COLOR=$2 205 ;; 206 --preview-text) 207 FONTPREVIEW_PREVIEW_TEXT=$2 208 ;; 209 --) 210 shift 211 break 212 ;; 213 esac 214 shift 215done 216 217 218# Point a font file to fontpreview and it will preview it. 219# Example: 220# $ fontpreview /path/to/fontFile.ttf 221# 222# This is useful because people can preview fonts which they have not 223# installed onto their system. So if they want to preview a font file that 224# is in their Downloads directory, then they can easily preview it. 225if [ -f "$font" ]; then 226 generate_preview "$font" "$FONT_PREVIEW" 227 228 # Display the font preview using sxiv 229 sxiv -g "$SIZE$POSITION" -N "fontpreview" -b "$FONT_PREVIEW" & 230 231 # For some strange reason, sxiv just doesnt have time to read the file 232 sleep 0.1 233 exit 234fi 235 236# Check if the user gave an input file if they did, then create a preview 237# and then save the preview to the current working directory 238if [ "$input_file" != "" ] ; then 239 [ -z "$output_file" ] && output_file="${input_file}.png" 240 generate_preview "$input_file" "$output_file" 241 exit 242fi 243 244main 245