Commit | Line | Data |
---|---|---|
f617db13 | 1 | #! /bin/bash |
8e08f814 MW |
2 | ### |
3 | ### X startup script | |
f617db13 | 4 | |
8e08f814 MW |
5 | ###-------------------------------------------------------------------------- |
6 | ### Utility functions. | |
f617db13 | 7 | |
8e08f814 MW |
8 | ## Progress indicators. |
9 | info=yes | |
10 | info () { | |
11 | case $info in yes) echo "- $*" >&2 ;; esac | |
12 | } | |
f617db13 | 13 | |
8e08f814 MW |
14 | run=yes |
15 | run () { | |
16 | local what=$1; shift | |
17 | local bg=no | |
f617db13 | 18 | |
8e08f814 MW |
19 | case $what in bg*) bg=yes what=${what#bg} ;; esac |
20 | info "run $what: $*" | |
f617db13 | 21 | |
8e08f814 MW |
22 | case "$run,$bg" in |
23 | yes,no) "$@" ;; | |
24 | yes,yes) "$@" & ;; | |
25 | esac | |
26 | } | |
eebca092 | 27 | |
8e08f814 | 28 | ## Program choice |
eebca092 | 29 | pick_program () { |
8e08f814 MW |
30 | local what=$1; shift |
31 | local choice=false | |
eebca092 | 32 | for i in "$@"; do |
8e08f814 | 33 | if type -t >/dev/null "$i"; then choice=$i; break; fi |
eebca092 | 34 | done |
8e08f814 MW |
35 | info "pick $what = $choice" |
36 | echo "$choice" | |
eebca092 MW |
37 | } |
38 | ||
8e08f814 MW |
39 | ###-------------------------------------------------------------------------- |
40 | ### Parse arguments. | |
f617db13 | 41 | |
8e08f814 MW |
42 | vnc=no |
43 | atomtag= | |
44 | start=yes | |
45 | wait=yes | |
f617db13 | 46 | |
8e08f814 MW |
47 | for opt; do |
48 | case "$opt" in | |
49 | help) | |
50 | cat <<EOF | |
51 | Options: | |
52 | tag=TAG | |
53 | [no]trace | |
54 | [no]info | |
55 | [no]run | |
56 | [no]start | |
57 | [no]wait | |
58 | [no]vnc | |
59 | EOF | |
60 | exit | |
61 | ;; | |
f617db13 | 62 | |
8e08f814 MW |
63 | tag=*) atomtag=/${opt#tag=} ;; |
64 | trace) set -x ;; | |
65 | notrace) set +x ;; | |
66 | info | run | start | wait | vnc) eval "$opt=yes" ;; | |
67 | noinfo | norun | nostart | nowait | novnc) eval "${opt#no}=no" ;; | |
68 | ||
69 | *) echo "unknown option $opt" >&2; exit 1 ;; | |
70 | esac | |
71 | done | |
72 | ||
73 | ###-------------------------------------------------------------------------- | |
74 | ### Iniitial settings. | |
75 | ||
76 | ## Assume X sessions are secure. | |
77 | export __mdw_sechost="`hostname`" | |
78 | ||
79 | ## Obtain the screen dimensions. | |
80 | case ",$XWIDTH,$XHEIGHT," in | |
81 | *,,*) eval $(xscsize -bx) ;; | |
82 | esac | |
83 | info "screen size = $XWIDTH x $XHEIGHT" | |
84 | ||
85 | initialize () { | |
86 | ## Load the X resource database. | |
87 | run init xrdb -override $HOME/.Xdefaults | |
88 | ||
89 | ## Random xsettery. | |
90 | run init xset b 10 2000 50 | |
91 | run init xset r rate 500 50 | |
92 | run init xset m 2 1 | |
93 | ||
f4450ac9 MW |
94 | ## Key mappings. |
95 | xmodmap -e 'keysym BackSpace = BackSpace BackSpace' | |
96 | ||
8e08f814 MW |
97 | ## Gnome settings. |
98 | case $vnc in no) run bginit gnome-settings-daemon ;; esac | |
99 | } | |
100 | ||
101 | ###-------------------------------------------------------------------------- | |
102 | ### Start a window manager. | |
103 | ||
104 | wm=$(pick_program window-manager enlightenment e16 twm) | |
105 | wmopts="" | |
106 | case "$wm,$vnc" in | |
107 | enlightenment,yes | e16,yes) | |
108 | wmopts="$eopts -econfdir $HOME/.enlightenment-vnc" | |
109 | ;; | |
110 | esac | |
111 | ||
16ee7a8c | 112 | start-e16 () { |
8e08f814 | 113 | run bginit $wm $wmopts |
16ee7a8c MW |
114 | win=nil |
115 | for i in $(seq 10); do | |
b35a9c36 | 116 | sleep 1 |
16ee7a8c MW |
117 | if eesh version >/dev/null 2>&1; then |
118 | win=t | |
119 | break | |
120 | fi | |
16ee7a8c MW |
121 | done |
122 | case $win in | |
123 | t) | |
124 | info "$wm started ok" | |
125 | run init xsetroot -cursor_name left_ptr | |
126 | ;; | |
127 | nil) | |
128 | info "$wm failed to start!" | |
129 | ;; | |
130 | esac | |
131 | } | |
132 | ||
133 | start-window-manager () { | |
134 | case $(type -t start-$wm || echo "not-found") in | |
135 | function) | |
136 | start-$wm $wmopts | |
137 | ;; | |
138 | *) | |
139 | run bginit $wm $wmopts | |
140 | ;; | |
141 | esac | |
8e08f814 MW |
142 | } |
143 | ||
144 | ###-------------------------------------------------------------------------- | |
145 | ### Random useful clients. | |
146 | ||
54951353 MW |
147 | start-clients-local () { :; } |
148 | ||
49aa87a2 MW |
149 | scsv=$(pick_program screensaver gnome-screensaver xscreensaver) |
150 | case $scsv in | |
151 | xscreensaver) | |
152 | scsvopts="-no-splash" | |
153 | ;; | |
154 | *) | |
155 | scsvopts="" | |
156 | ;; | |
157 | esac | |
158 | ||
8e08f814 MW |
159 | start-clients () { |
160 | ## Mail notification. | |
161 | run bginit mail-notification | |
162 | ||
b35a9c36 MW |
163 | ## Gnome session. With great reluctance. At least it doesn't actually do |
164 | ## anything. | |
165 | run bginit gnome-session | |
166 | ||
59a62625 | 167 | ## Policykit authentication agent. |
4906574e | 168 | agent=/usr/lib/policykit-1-gnome/polkit-gnome-authentication-agent-1 |
59a62625 MW |
169 | if [ -x $agent ]; then run bginit $agent; fi |
170 | ||
8e08f814 MW |
171 | ## System monitor. |
172 | case $vnc in no) run bginit gkrellm ;; esac | |
173 | ||
c02999e8 MW |
174 | ## Screensaver. |
175 | case $vnc in | |
176 | no) | |
177 | run init xscreensaver-command -exit | |
49aa87a2 | 178 | run bginit $scsv $scsvopts |
c02999e8 MW |
179 | ;; |
180 | esac | |
181 | ||
8e08f814 MW |
182 | ## Panel. |
183 | case $vnc in no) run bginit gnome-panel ;; esac | |
54951353 MW |
184 | |
185 | ## Local clients. | |
186 | start-clients-local | |
8e08f814 MW |
187 | } |
188 | ||
189 | ###-------------------------------------------------------------------------- | |
190 | ### Main screen layout. | |
f617db13 | 191 | |
8e08f814 | 192 | ## Choose appropriate clients. |
0c47c911 | 193 | emacs=$(pick_program emacs emacs23 emacs22 emacs21 emacs) |
8e08f814 | 194 | term=$(pick_program terminal pterm Eterm xterm) |
f617db13 | 195 | |
8e08f814 | 196 | ## Emacs window measurements. |
85bbf8d3 | 197 | case "$emacs" in |
8e08f814 | 198 | emacs21 | emacs) |
85bbf8d3 MW |
199 | e_colwd=492 e_hextra=34 |
200 | e_colchars=82 e_cextra=-2 | |
201 | e_lineht=13 e_vextra=52 | |
202 | ;; | |
0c47c911 | 203 | emacs22 | emacs23) |
85bbf8d3 MW |
204 | e_colwd=492 e_hextra=8 |
205 | e_colchars=82 e_cextra=-6 | |
206 | e_lineht=13 e_vextra=46 | |
207 | ;; | |
208 | esac | |
f617db13 | 209 | |
8e08f814 | 210 | ## Terminal window measurements. |
85bbf8d3 | 211 | case "$term" in |
e2b44bd9 | 212 | pterm) t_wd=504 t_lineht=13 t_vextra=23 geom=-geometry;; |
85bbf8d3 MW |
213 | Eterm) t_wd=504 t_lineht=13 t_vextra=23 geom=-g;; |
214 | xterm) t_wd=507 t_lineht=13 t_vextra=27 geom=-geometry;; | |
215 | esac | |
f617db13 | 216 | |
8e08f814 | 217 | ## GNOME stuff measurements. |
f617db13 MW |
218 | declare -i xbound="XWIDTH - 113" |
219 | ||
8e08f814 MW |
220 | ## Choose a width for Emacs. |
221 | ## | |
222 | ## We'd like it to be as wide as possible, allowing for a column of xterms | |
223 | ## down the right hand side. However, I'd prefer a double-width Emacs to a | |
224 | ## single-width Emacs and xterms. If it's not going to work at all, a single | |
225 | ## Emacs column will have to do. Also, there's a strange thing with Emacs21 | |
226 | ## and the toolbar, so we add on some rows which are later mysteriously | |
227 | ## subtracted. | |
f617db13 | 228 | |
85bbf8d3 MW |
229 | declare -i ecols="(xbound - t_wd - e_hextra)/e_colwd" |
230 | if (( ecols < 2 && xbound > e_colwd * 2 + e_hextra )); then | |
f617db13 MW |
231 | ecols=2 |
232 | elif (( ecols < 1 )); then | |
233 | ecols=1 | |
234 | fi | |
235 | ||
8e08f814 MW |
236 | declare -i \ |
237 | emacsx="ecols * e_colchars + e_cextra" \ | |
238 | emacsy="(XHEIGHT - e_vextra)/e_lineht" | |
239 | ||
240 | start-emacs () { | |
bf057abe MW |
241 | GDK_NATIVE_WINDOWS=1 run bgclients noip \ |
242 | $emacs -geometry ${emacsx}x${emacsy}+0+0 | |
8e08f814 MW |
243 | } |
244 | ||
245 | ## Now place some xterms. | |
246 | ## | |
247 | ## A few smaller xterms are in general better than one great big one. 35 | |
248 | ## lines is a good height for most terminals. 25 lines is a minimum. The | |
249 | ## strategy for doling out xterms into a column is to make as many 35-liners | |
250 | ## as we can, until the remaining space would be too small for a 25-liner. | |
251 | ## If we can get two 25s out of that then we do (largest first); otherwise | |
252 | ## just make one big one. We stop at the end of a page, once we've made | |
253 | ## three xterms. | |
254 | ||
255 | start-xterms () { | |
256 | ||
257 | ## Initialize some parameters. | |
6b4faba6 | 258 | declare -i x="ecols * e_colwd + e_hextra" xb=xbound |
8e08f814 MW |
259 | declare -i n=0 pgx=0 l h y ht |
260 | declare -i hstd="35 * t_lineht + t_vextra" hmin="25 * t_lineht + t_vextra" | |
261 | ||
262 | ## Do the placement. | |
263 | while :; do | |
264 | ||
265 | ## Start a new iteration. | |
6b4faba6 | 266 | if ((x + t_wd > xb)); then |
8e08f814 | 267 | if ((n >= 3)); then break; fi |
6b4faba6 | 268 | x="pgx + XWIDTH" pgx="pgx + XWIDTH" xb="xb + XWIDTH" |
8e08f814 MW |
269 | fi |
270 | ||
271 | ## Make large xterms. | |
272 | y=0 ht=XHEIGHT | |
273 | while ((ht - hstd >= hmin)); do | |
274 | run bgclients $term $geom 80x35+$x+$y | |
275 | y="y + hstd" ht="ht - hstd" n="n + 1" | |
276 | done | |
277 | ||
278 | ## Fill the remaining space. | |
279 | if ((ht >= 2 * hmin)); then h="ht - hmin"; else h=ht; fi | |
280 | l="(h - t_vextra)/t_lineht" h="l * t_lineht + t_vextra" | |
281 | run bgclients $term $geom 80x$l+$x+$y | |
282 | y="y + h" ht="ht - h" n="n + 1" | |
283 | if ((ht >= hmin)); then | |
284 | run bgclients $term $geom 80x25+$x+$y | |
285 | n="n + 1" | |
286 | fi | |
287 | x="x + t_wd" | |
f617db13 | 288 | done |
8e08f814 | 289 | } |
f617db13 | 290 | |
8e08f814 | 291 | ###-------------------------------------------------------------------------- |
3bdada49 MW |
292 | ### Requesters. |
293 | ||
294 | req () { | |
295 | declare title=$1 hist=$2; shift 2 | |
3f88bd1f | 296 | cmd=$(xgetline -t "$title" -p "_Command:" -Hl "$HOME/$hist") && |
3bdada49 MW |
297 | exec "$@" "$cmd" |
298 | } | |
299 | ||
300 | ###-------------------------------------------------------------------------- | |
8e08f814 MW |
301 | ### Final waiting. |
302 | ||
303 | atom=XINIT_COMMAND$atomtag | |
304 | ||
305 | xwait () { | |
306 | while :; do | |
307 | xatom delete $atom | |
308 | info "waiting on $atom" | |
309 | line=$(xatom wait $atom) | |
310 | info "xatom: $line" | |
311 | ||
312 | case "$line" in | |
313 | :help) | |
314 | xmsg -I -t "xinitrc help" -d "xinitrc commands" - <<EOF & | |
315 | :help | |
316 | :emacs :xterms :window-manager :clients | |
3bdada49 | 317 | :ask-run :ask-command |
8e08f814 MW |
318 | :init |
319 | :terminal | |
320 | ! SHELL-COMMAND | |
321 | CLIENT | |
322 | EOF | |
323 | ;; | |
324 | :emacs | :xterms | :window-manager | :clients) | |
325 | start-${line#:} | |
326 | ;; | |
327 | :terminal) | |
328 | run bgclients $term | |
329 | ;; | |
330 | :init) | |
331 | initialize | |
332 | ;; | |
333 | :exec) | |
334 | info "restarting xinitrc" | |
335 | exec "$0" wait nostart | |
336 | ;; | |
3bdada49 MW |
337 | :ask-run) |
338 | req "Shell command" .cmd.hist xcatch -FMiscFixed6x13 -- sh -c& | |
339 | ;; | |
340 | :ask-command) | |
341 | req "xinit command" .xinit.hist xatom set XINIT_COMMAND$atomtag& | |
342 | ;; | |
8e08f814 MW |
343 | :*) |
344 | xmsg -E -t "xinitrc error" "Unknown command \`$line'" & | |
345 | ;; | |
346 | !*) | |
347 | eval "${line#!}" | |
348 | ;; | |
349 | *) | |
350 | set -- $line | |
351 | run bgclients "$@" | |
352 | ;; | |
353 | esac | |
354 | done | |
355 | } | |
356 | ||
357 | ###-------------------------------------------------------------------------- | |
358 | ### Actually start things up. | |
359 | ||
54951353 MW |
360 | if [ -f $HOME/.xinitrc-local ]; then |
361 | . $HOME/.xinitrc-local | |
362 | fi | |
363 | ||
8e08f814 MW |
364 | case "$start" in |
365 | yes) | |
366 | info "starting standard clients" | |
367 | initialize | |
368 | start-window-manager | |
369 | start-clients | |
370 | start-emacs | |
371 | start-xterms | |
372 | ;; | |
373 | no) | |
374 | info "not starting standard clients" | |
375 | ;; | |
376 | esac | |
377 | ||
378 | case "$wait" in | |
379 | yes) | |
380 | xwait | |
381 | ;; | |
382 | no) | |
383 | info "not waiting before exit" | |
384 | ;; | |
385 | esac | |
f617db13 | 386 | |
8e08f814 | 387 | ###----- That's all, folks -------------------------------------------------- |