r3555@krups: intrigeri | 2005-11-15 13:59:57 +0100
[matthijs/upstream/backupninja.git] / lib / easydialog.sh
1 #!/bin/bash
2
3 # copyright 2002 lmoore@tump.com under the terms of the GNU LGPL.
4 # additions 2005 collective@riseup.net
5
6 # whiptail has trouble being called in the foo=$(whiptail ...) fashion for
7 # some reason.  this is very annoying.  this means that we need to use
8 # temporary files to store the answers from the input and list based boxes
9 # and then read the answers into a REPLY variable.  that just really
10 # stinks, oh well, that's what you get when you have a weak link
11 # implementation...
12 #
13 # inputBox and passwordBox could be refactored to use a common function
14
15 test -z "$WIDTH" && WIDTH=0
16 test -z "$HEIGHT" && HEIGHT=0
17 BACKTITLE=""
18 DIALOG=dialog
19 HELP=
20
21 setApplicationTitle() {
22     BACKTITLE=$*
23 }
24
25 setHelp() {
26     HELP="$@"
27 }
28
29 setDimension() {
30     WIDTH=$1
31     HEIGHT=$2
32 }
33
34 booleanBox() {
35     $DIALOG --backtitle "$BACKTITLE" --title "$1" \
36         `[ "$3" == no ] && echo '--defaultno'` --yesno "$2" $HEIGHT $WIDTH
37 }
38
39 msgBox() {
40     $DIALOG --backtitle "$BACKTITLE" --title "$1" \
41         --msgbox "$2" $HEIGHT $WIDTH
42 }
43
44 gaugeBox() {
45     $DIALOG --backtitle "$BACKTITLE" --title "$1" \
46         --gauge "$2" $HEIGHT $WIDTH 0
47 }
48
49 inputBox() {
50     local temp=$(mktemp -t) || exit 1
51     trap "rm -f $temp" 0
52     REPLY=
53     $DIALOG --backtitle "$BACKTITLE" --title "$1" \
54         --inputbox "$2" $HEIGHT $WIDTH "$3" 2> $temp
55     local status=$?
56     [ $status = 0 ] && REPLY=$(cat $temp)
57     rm -f $temp
58     return $status
59 }
60
61 # Xdialog and {dialog,whiptail} use different mechanism to "qoute" the
62 # values from a checklist.  {dialog,whiptail} uses standard double quoting
63 # while Xdialog uses a "/" as the separator.  the slash is arguably better,
64 # but the double quoting is more standard.  anyway, this function can be
65 # overridden to allow a derived implementation to change it's quoting
66 # mechanism to the standard double-quoting one.  it receives two
67 # arguements, the file that has the data and the box type.
68 _listReplyHook() {
69     cat $1
70 }
71
72 # this is the base implementation of all the list based boxes, it works
73 # out nicely that way.  the real function just passes it's arguments to
74 # this function with an extra argument specifying the actual box that
75 # needs to be rendered.
76 _genericListBox() {
77     local box=$1
78     shift 1
79     local title=$1
80     local text=$2
81     shift 2
82     local temp=$(mktemp -t) || exit 1
83     trap "rm -f $temp" 0
84     REPLY=
85     $DIALOG $HELP $_DEFAULT --backtitle "$BACKTITLE" --title "$title" \
86         $box "$text" $HEIGHT $WIDTH 10 \
87         "$@" 2> $temp
88     local status=$?
89     [ $status = 0 ] && REPLY=$(_listReplyHook $temp $box)
90     rm -f $temp
91     _DEFAULT=
92     return $status
93 }
94
95 setDefault() {
96   _DEFAULT="--default-item $1"
97 }
98
99 menuBox() {
100     _genericListBox --menu "$@"
101 }
102
103 ## a menu box with additional help info displayed
104 ## at the bottom of the window when an item is selected
105 menuBoxHelp() {
106         HELP="--item-help"
107         _genericListBox --menu "$@"
108         status=$?
109         HELP=
110         return $status
111 }
112
113 ## a menu box with an addition button 'help'
114 menuBoxHelpFile() {
115         HELP="--help-button"
116         _genericListBox --menu "$@"
117         status=$?
118         HELP=
119         return $status
120 }
121
122 checkBox() {
123     _genericListBox --checklist "$@"
124 }
125
126 radioBox() {
127     _genericListBox --radiolist "$@"
128 }
129
130 textBox() {
131     $DIALOG --backtitle "$BACKTITLE" --title "$1" --textbox "$2" $HEIGHT $WIDTH
132 }
133
134 passwordBox() {
135     local temp=$(mktemp -t) || exit 1
136     trap "rm -f $temp" 0
137     REPLY=
138     $DIALOG --backtitle "$BACKTITLE" --title "$1" \
139         --passwordbox "$2" $HEIGHT $WIDTH 2> $temp
140     local status=$?
141     [ $status = 0 ] && REPLY=$(cat $temp)
142     rm -f $temp
143     return $status
144 }
145
146
147 #########################################################
148 ## begin-item-display style lists
149 ## 
150 ## these lists are built by calling fuctions multiple times.
151 ## this can make it easier to build your list in a loop
152 ##
153
154 listBegin() {
155    _menu_title=$1
156    _menu_msg=$2
157    _menu_items=0
158    _menu_text=
159    _menu_labels=
160    _menu_status=
161 }
162
163 listItem() {
164    _menu_labels[$_menu_items]=$1
165    _menu_text[$_menu_items]=$2
166    _menu_status[$_menu_items]=$3 # available only for checklist
167    let "_menu_items += 1"
168 }
169
170
171 ##
172 ## takes one of:
173 ## menu, checklist, radiolist
174 ##
175 listDisplay() {
176    boxtype=$1
177    local temp=$(mktemp -t) || exit 1
178    trap "rm -f $temp" 0
179    
180    local label
181    local text
182    local status
183    (
184       echo -ne " $HELP $_DEFAULT "
185       echo -ne " --backtitle '$BACKTITLE' "
186       echo -ne " --title '$_menu_title' "
187       echo -ne " --$boxtype '$_menu_msg' "
188       echo -ne " $HEIGHT $WIDTH 10 "
189       for ((i=0; i < $_menu_items ; i++)); do
190         label=${_menu_labels[$i]}
191         text=${_menu_text[$i]}
192         status=${_menu_status[$i]}
193         echo -ne " $label '$text' $status "
194       done
195    ) | xargs $DIALOG 2> $temp
196    
197    local status=$?
198    REPLY=""
199    [ $status = 0 ] && REPLY=`cat $temp`
200    rm -f $temp
201    _DEFAULT=
202    return $status
203 }
204
205 ####################################################
206 ## FORM
207
208 _form_gap=2
209 formBegin() {
210    _form_title=$1
211    _form_items=0
212    _form_labels=
213    _form_text=
214 }
215
216 formItem() {
217    _form_labels[$_form_items]=$1
218    _form_text[$_form_items]=$2
219    let "_form_items += 1"
220 }
221     
222 formDisplay() {
223    local temp=$(mktemp -t) || exit 1
224    
225    max_length=0
226    for ((i=0; i < ${#_form_labels[@]} ; i++)); do
227       label=${_form_labels[$i]}
228       length=`expr length $label`
229       if [ $length -gt $max_length ]; then
230          max_length=$length
231       fi
232    done
233    let "max_length += 2"
234     
235    local xpos=1
236    (
237       echo -n -e "--form '$_form_title' 0 0 20"
238       for ((i=0; i < $_form_items ; i++)); do
239         label=${_form_labels[$i]}
240         text=${_form_text[$i]}
241         echo -n -e " $label $xpos 1 '$text' $xpos $max_length 30 30"
242         let "xpos += _form_gap"
243       done
244    ) | xargs $DIALOG 2> $temp
245    local status=$?
246    
247    REPLY=
248    if [ $status = 0 ]; then
249       IFS=$''
250       REPLY=`cat $temp`
251       IFS=$' \t\n'
252    fi
253    rm -f $temp
254    return $status
255 }