November 24th, 2009progress on login
这里是指在linux下, 在我们的环境中由于在登录系统的时候需要比较久的时候(5-15秒), 在那里看着不动的屏幕总归会有些不爽, 于是便写了一个小小的进度条来.
首先呢, 我们先完成一个画一个转圈的直线的程序来(其实就是轮流打印”-\|-/”这几个字符, 它每转完一圈后会打印一个加号.) — 当然每次打印要有一个间隔, 不然会很快, 这个时间间隔我们能过程序参数来传递.
#! /bin/bash
count=0
#c is the array for the characters we'll print
c[0]='-\b'
c[1]='\\\b'
c[2]='|\b'
c[3]='/\b'
c[4]='-\b'
c[5]='+'
while true
do
let "count = $count %6"
echo -n -e "${c[$count]}"
sleep $1 #sleep sometime to continue....
let "count = $count + 1"
done
在上面我们使用了echo 的两个参数, -n 是让它不打印一个多余的换行, -e让它解释转义字符, 而\b则是退格符.
好的, 下面就保存这个脚本并让它可执行(chmod +x ), 这里我把它命名为~/bin/timedot, 能过执行 ./timedot 0.2 来看一下效果吧. (请确定你的sleep程序可以接受小数形式的参数).
嗯, 看上去不错, 好的, 让我们把它加入到启动脚本里, 基本思路是把它作为一个后台程序运行.
~/bin/timedot 0.2& timedotPID=$! #$! 是bash的内置变量, 它保存最后一个后台进行的pid. ...... #把你的很慢的代码放在这里. kill $timedotPID #杀掉打印进度条的进程.
好了, 试一下, 嗯, 似乎工作的还不错. 不过似乎有一个问题: 在每次启动的时候你都会看到一个类似下面的消息:
[1234]- Terminated ~/bin/timedot 0.2&
之所以会有这行消息是因为你在后台运行一个程序的时候, bash会关注所有属于它的后台进程的状态, 并在后台进程结束后通知前台程序某个程序已经死掉啦(或者是已经完成了), 不过毫无疑问我们不希望看到关于timedot的通知消息(太丑陋了), 于是我们可以通过disown 命令来让bash放弃对timedot的管理.
好, 在这里似乎一切都很完美了, 不过假如你在一次登录的时候, 实在忍受不了长时间的等待了, 于是你按下了ctrl+c来中止当前的初始化脚本, 然后你就会发现了另外一个问题… 你会发现在你打字的时候总是会有”|/|-+”这几个字符蹦出来 —- 而这是因为你的ctrl+c虽然中止了你的初始化脚本, 但它却没有中此我们的这个后台进行的进度条进程. 好吧, 让我们修好它:
~/bin/timedot 0.2&
timedotPID=$! #$! 是bash的内置变量, 它保存最后一个后台进行的pid.
my_control_c()
{
kill $timedotPID #杀死后台进程<br />
trap SIGINT #重置SIGINT,
}
trap my_control_c SIGINT #我们设置一个control+c的钩子, 当用户按下control+c的时候会调用我们的my_control_c函数
...... #把你的很慢的代码放在这里.
kill $timedotPID #杀掉打印进度条的进程.
trap SIGINT #重置SIGINT为默认值.
这里使用了trap命令来设置ctrl+c的钩子, 这样每次要中止初始化脚本的时候就会调用我们自己的函数, 而它会杀掉后台进度条进程, 当然不要忘记重置钩子, 我们不需要再以后用到它了.






