aboutsummaryrefslogtreecommitdiff
path: root/bash/bashrc.d/pd.bash
blob: f9fb2ab768967263a60f47c3e849cec99f2aba40 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
# Attempt to change into the argument's parent directory; preserve any options
# and pass them to cd. This is intended for use when you've got a file path in
# a variable, or in history, or in Alt+., and want to quickly move to its
# containing directory. In the absence of an argument, this just shifts up a
# directory, i.e. `cd ..`
pd() {
    local arg
    local -a opts
    for arg in "$@" ; do
        case $arg in
            --)
                shift
                break
                ;;
            -*)
                shift
                opts=("${opts[@]}" "$arg")
                ;;
            *)
                break
                ;;
        esac
    done
    if (($#)) ; then
        case $# in
            1)
                target=$1
                target=${target%/}
                target=${target%/*}
                ;;
            2)
                printf 'bash: pd: too many arguments\n' >&2
                return 1
                ;;
        esac
    else
        target=..
    fi
    if [[ $target ]] ; then
        builtin cd "${opts[@]}" -- "$target"
    else
        printf 'bash: pd: error calculating parent directory\n' >&2
        return 1
    fi
}