packages feed

sindre-0.1: examples/filesel

#!/bin/sh

history=${XDG_CACHE_HOME:-~/.cache}/filesel/history

mkdir -p $(dirname historyfile)

history() {
    tac $history |\
awk '{gsub("\"", "\"\""); print "value=\""$0"\" show=\"^fg(white)(History) ^fg()"$0"\""; fflush(); }' |\
head -n 5
}

updatehistory() {
    (rm "$history" && awk '$0!=SEL' "SEL=$1" > "$history") < "$history"
    echo "$1" >> "$history"
}

entry() {
    awk '{gsub("\"", "\"\""); print "value=\""$0"\" show=\""substr($0, match($0, "/[^/]*/?$")+1)"\""; fflush(); }'
}

files() {
    ls -A -F "$1" | awk '{print DIR $0}' "DIR=$1"
}

gui() {
    code=$(cat <<EOF
input->changed(from, to) {
  if (to == "") {
    input.value = "/";
    next;
  }
  list.clear();
  insertfile();
  print folder(to);
}
function complete() {
  if (list.selected) {
    if (match(list.selected, "^/")) {
      input.value = list.selected
    } else {
      input.value = folder(input.value) list.selected
    }
  }
}
function folder(str) { return substr(str, 0, match(str, "/[^/]*$")) }
function file(str) { return substr(str, match(input.value, "[^/]*$"), RLENGTH); }
function insertfile() {
  if (filename) { filename = gsub("\"", "\"\"", filename);
                  list.insert("value=\"" filename "\" show=\"^fg(white)" filename "\"" ) }
}
BEGIN { insertfile(); }
function filter() { list.filter(file(input.value)); }
function quit() { print; exit }
option filename(,--filename,"Default filename if a directory is selected", "filename");
EOF
    )
    dir=$(mktemp -p "${TMPDIR:-/tmp}" -d dir-XXXXXX) || exit 1
    fifo=$dir/fifo
    mkfifo "$fifo" || { rmdir "$dir"; exit 1; }
    sinmenu -l 10 -e "$code" -p File: -c $PWD/ "$@" < $fifo |\
while read line; do
    echo $line 1>&3
    history "$line"
    files "$line" 2>/dev/null | sed 's/\*$//' | entry
    done 3>&1 1>$fifo | tail -n 1 | sed '/^$/d'
    rm $fifo
    rmdir $dir
}

ret=$(gui "$@")

[ -z "$ret" ] && exit 1 || (updatehistory "$(dirname "$ret")/"; echo "$ret")