dotfiles

configuration files for shell, text editor, graphical environment, etc.
git clone git://src.adamsgaard.dk/dotfiles
Log | Files | Refs | README | LICENSE Back to index

compile (3078B)


      1 #!/bin/sh
      2 opener=xdg-open
      3 
      4 show_help() {
      5 	echo "usage: ${0##*/} [OPTIONS] FILE ..."
      6 	echo "compiles each FILE based on its extension."
      7 	echo
      8 	echo "OPTIONS are one or more of the following:"
      9 	echo "   -h    show this message"
     10 	echo "   -c    continuously recompile upon file changes (requires entr(1))"
     11 	echo "   -o    open output file after compiling (requires ${opener}(1))"
     12 	echo "   --    do not consider any following args as options"
     13 }
     14 
     15 die() {
     16 	printf '%s: error: %s\n' "${0##*/}" "$1" >&2
     17 	exit 1
     18 }
     19 
     20 regeximatch() {
     21 	printf '%s' "$1" | grep -iEq "$2"
     22 }
     23 
     24 extract_tex_include() {
     25 	d="$(grep -v ".*%.*\\${2}" "$1" |
     26 	     sed -nE "/.*\\${2}\\[*.*\\]*\\{([^}]*)\\}.*/{ s//\\1/;p; }")"
     27 	if [ "$2" = "bibliography" ] && [ -n "$d" ]; then
     28 		d="${d%.bib}.bib"
     29 	fi
     30 	if [ -n "$d" ]; then
     31 		printf '%s\n' "$d"
     32 	fi
     33 }
     34 
     35 find_dependencies() {
     36 	case "$1" in
     37 		*.tex)
     38 			printf '%s\n' "$1"
     39 			if grep -q -e '\input{' \
     40 					   -e '\include[graphics]' \
     41 					   -e '\addbibresource{' \
     42 					   -e '\bibliography{' \
     43 					   "$1"; then
     44 				extract_tex_include "$1" 'input'
     45 				extract_tex_include "$1" 'include'
     46 				extract_tex_include "$1" 'includegraphics'
     47 				extract_tex_include "$1" 'addbibresource'
     48 				extract_tex_include "$1" 'bibliography'
     49 			fi;;
     50 		*)
     51 			die "cannot find dependencies in unknown file type $1";;
     52 	esac
     53 }
     54 
     55 run_compile() {
     56 	if [ "$continuous" = 1 ]; then
     57 		printf '%s\n' "$2" | entr -s "$1"
     58 	else
     59 		eval "$1"
     60 	fi
     61 }
     62 
     63 handle_target() {
     64 	base="$(basename "${1%.*}")"
     65 	if [ -e "$1" ]; then
     66 		case "$1" in
     67 			*.tex)
     68 				deps="$1"
     69 				deps="$(find_dependencies "$1")"
     70 				for d in $deps; do
     71 					if [ "${d##*.}" = "tex" ]; then
     72 						deps="$(printf '%s\n%s\n' "${deps}" "$(find_dependencies "$d")")"
     73 					fi
     74 				done
     75 				deps="$(printf '%s\n' "$deps" | sort | uniq)"
     76 				printf 'deps=%s\n' "$deps"
     77 				if regeximatch "$deps" '\.bib'; then
     78 					compile_string="pdflatex '$1'; bibtex '${1%.tex}'; pdflatex '$1'; pdflatex '$1'"
     79 				else
     80 					compile_string="pdflatex '$1' && pdflatex '$1'"
     81 				fi
     82 				run_compile "$compile_string" "$deps"
     83 				if [ "$open" = 1 ]; then
     84 					$opener "${1%.tex}.pdf"
     85 				fi
     86 				;;
     87 			*.gp)
     88 				run_compile "gnuplot '$1'" "$1";;
     89 			*.[0-9])
     90 				out="$(basename "${base}").pdf"
     91 				if [ "$open" = 1 ]; then
     92 					run_compile "refer -PS -e '$1' | groff -mandoc -T pdf > '$out' && $opener '$out'" "$1"
     93 				else
     94 					run_compile "refer -PS -e '$1' | groff -mandoc -T pdf > '$out'" "$1"
     95 				fi;;
     96 			*.mom)
     97 				out="$(basename "${base}").pdf"
     98 				if [ "$open" = 1 ]; then
     99 					run_compile "pdfmom '$1' > '$out' && $opener '$out'" "$1"
    100 				else
    101 					run_compile "pdfmom '$1' > '$out'" "$1"
    102 				fi;;
    103 			*)
    104 				die "File type ${1##*.} not supported\\n";;
    105 		esac
    106 	else
    107 		die "cannot read $1"
    108 	fi
    109 }
    110 
    111 continuous=0
    112 open=0
    113 while :; do
    114 	case "$1" in
    115 		-h|-\?)
    116 			show_help
    117 			exit 0;;
    118 		-c)
    119 			continuous=1;;
    120 		-o)
    121 			open=1;;
    122 		--) # end all options
    123 			shift
    124 			break;;
    125 		-?*)
    126 			die 'unknown option specified';;
    127 		*)  # No more options
    128 			break
    129 	esac
    130 	shift
    131 done
    132 
    133 if [ $# -lt 1 ]; then
    134 	show_help
    135 	exit 1
    136 else
    137 	for f in "$@"; do
    138 		handle_target "$f"
    139 	done
    140 fi