在GNU/Linux下设置与定时更换桌面壁纸
1 简介
在电脑桌面设置一组可以定时更换的壁纸已经不是什么新奇的功能了。比如,Windows 7、KDE桌面环境都可以实现这样的效果。可是,自己目前使用的Debian系统并未安装KDE、GNOME这样的桌面环境,只是简单的X视窗系统与Sawfish窗口管理。因此,要想实现加载壁纸并定时更换的功能就需要另想办法了。经过一番思考与编程,我现在可以用如下一系列脚本程序来完成这个任务:
- get_img_size.sh :调用 identify 命令显示图片信息并使用 gawk 命令从中提取出图片的尺寸。
- set_wallpaper.sh :调用 xloadimage 程序,加载单张图片作为壁纸。其中,该脚本会调用 get_img_size.sh 以获取该图片的尺寸,并根据指定的屏幕大小与其所在位置,对该图片进行适当的缩放与平移,使其显示于屏幕中间,且保持原比例充满屏幕。
- set_multi_wallpapers.sh :读入包含壁纸图片列表的配置文件,以指定的时间间隔来调用 set_wallpaper.sh ,从而逐个将这些图片加载为壁纸。
- gen_multi_wallpapers.sh :根据指定的匹配模式,使用 find 命令列出匹配到的图片文件,并生成能被 set_multi_wallpapers.sh 使用的配置文件。
下面对上述脚本进行具体说明。
2 加载单张图片作为壁纸: set_wallpaper.sh
将图片作为壁纸显示是通过 xloadimage 命令来实现的。通常,可以按如下的方式使用它:
xloadimage -fullscreen -onroot -border black -zoom 100 -rotate 90 -at 0,0 image_file
其中, -fullscreen 与 -onroot 的使用就可以将图片作为壁纸显示而不是被放到一个窗口里。其余的命令行选项的含义都是不言自明的。 set_wallpaper.sh 脚本程序并不是简单地调用 xloadimage ,其还会根据图片的大小与屏幕尺寸计算出 -zoom 选项的值,从而自动缩放图片,使其恰好完整地填满屏幕。此外,若电脑连接有多个显示器,可以通过设置 set_wallpaper.sh 的 -x 与 -y 选项来指定待加载壁纸屏幕左上角的坐标,以及设置 -W 与 -H 选项来指定该屏幕的宽和高。最终,图片就会只在该屏幕上显示了。
set_wallpaper.sh 的源码如下:
#!/bin/bash script_name="set_wallpaper.sh"
script_usage=$(cat <<EOF
$script_name [OPTION] image_file
EOF
)
script_function=$(cat <<EOF
This script is used to load an image onto root screen as wallpaper.
EOF
)
script_doc=$(cat <<EOF
-h Display this help.
-r Set the rotation angle of the image.
-W Screen width.
-H Screen height.
-x X position of the image to be loaded onto root screen.
-y Y position of the image to be loaded onto root screen.
EOF
)
script_examples=$(cat <<EOF
$script_name -r 0 -W 1920 -H 1080 -x 1280 -y 0 $picture/wallpapers/sunflower.jpg
EOF
)
state_prefix="==="
warning_prefix="***"
error_prefix="!!!" function display_help() {
if [ -n "$script_usage" ]; then
echo -e "Usage: $script_usage"
fi if [ -n "$script_function" ]; then
echo -e "$script_function"
fi if [ -n "$script_doc" ] ; then
echo -e "\n$script_doc"
fi if [ -n "$script_examples" ]; then
echo -e "\nExamples"
echo -e "$script_examples"
fi
} # Default parameters
declare -i rot_angle=0 screen_width=1920 screen_height=1080 screen_x=0 screen_y=0 zoom_factor=100 x_res=0 y_res=0 x_res_scaled=0 y_res_scaled=0 at_x=0 at_y=0 while getopts ":r:W:H:x:y:h" opt; do
case $opt in
r ) rot_angle=$OPTARG
if [ $(((($rot_angle % 90) != 0) || (($rot_angle < 90) && ($rot_angle != 0)))) = 1 ]; then
echo "The rotation angle of the image should be 0 or multiple of 90 degrees!"
exit 1
fi ;;
W ) screen_width=$OPTARG ;;
H ) screen_height=$OPTARG ;;
x ) screen_x=$OPTARG ;;
y ) screen_y=$OPTARG ;;
h ) display_help
exit 0 ;;
\? ) display_help
exit 1 ;;
esac
done shift $(($OPTIND - 1)) if [ -n "$1" ]; then
echo "Loading image $1"
resolution=`get_img_size.sh "$1"`
x_res=`echo $resolution | gawk -F x '{print $1}'`
y_res=`echo $resolution | gawk -F x '{print $2}'` # If the rotation angle is odd times of 90 degrees swap x and y
# resolutions of the image
if [ $((($rot_angle / 90 % 2) == 1)) = 1 ]; then
tmp_res=$x_res
x_res=$y_res
y_res=$tmp_res
fi
echo "Image resolution is ${x_res}x${y_res}" # Calculate the scaling factor of the image to fit to the screen
if [ $((($x_res * 100 / $y_res) < ($screen_width * 100 / $screen_height))) = 1 ]; then
# Scale the height of the image
if [ $(($y_res > $screen_height)) = 1 ]; then
zoom_factor=$(($screen_height * 100 / $y_res))
else
zoom_factor=$(($y_res * 100 / $screen_height))
fi
echo "Scaling in the y direction!"
at_y=$screen_y
at_x=$((($screen_width - $x_res * $zoom_factor / 100) / 2 + $screen_x))
else
# Scale the width of the image
if [ $(($x_res > $screen_width)) = 1 ]; then
zoom_factor=$(($screen_width * 100 / $x_res))
else
zoom_factor=$(($x_res * 100 / $screen_width))
fi
echo "Scaling in the x direction!"
at_x=$screen_x
at_y=$((($screen_height - $y_res * $zoom_factor / 100) / 2 + $screen_y))
fi
echo "Zoom factor is $zoom_factor"
echo "Image location is $at_x,$at_y" rot_opt=""
if [ $(($rot_angle != 0)) = 1 ]; then
rot_opt="-rotate $rot_angle"
fi
xloadimage -fullscreen -onroot -border black -zoom $zoom_factor $rot_opt -at $at_x,$at_y "$1"
else
echo "Please provide an image!"
exit 1
fi
其中,用于获取图片大小的脚本 get_img_size.sh 内容如下:
#!/bin/bash if [ -n "$1" ]; then
identify "$1" | gawk '{if(match($0, /([[:digit:]]+)x([[:digit:]]+)/, res) != 0) print res[0];}'
else
echo "Please provide an image!"
exit 1
fi
3 定时加载多张壁纸: set_multi_wallpapers.sh
通过 -s 选项,可以指定配置文件,其由该脚本读入后以默认的时间间隔60秒或由 -t 选项指定的时间间隔来逐个显示列表中的图片。配置文件的格式如下:
# Configuration file storing list of images to be loaded onto root screen as wallpapers. # Description of data columns (columns are separated by TAB):
# Column 1: Absolute path to image
# Column 2: Rotation angle applied to the image
# Column 3: X position of the image to be loaded onto the root screen
# Column 4: Y position of the image to be loaded onto the root screen /home/orlando/Pictures/wallpapers/Windows 10 wallpapers/02 - wqQXJGJ.jpg 0 1280 0
/home/orlando/Pictures/wallpapers/Windows 10 wallpapers/03 - jVKcv41.jpg 0 1280 0
/home/orlando/Pictures/wallpapers/Windows 10 wallpapers/04 - wPpANVz.jpg 0 1280 0
/home/orlando/Pictures/wallpapers/Windows 10 wallpapers/05 - yGQyrcX.jpg 0 1280 0
/home/orlando/Pictures/wallpapers/Windows 10 wallpapers/07 - XaanvJe.jpg 0 1280 0
/home/orlando/Pictures/wallpapers/Windows 10 wallpapers/08 - zl3dIFY.jpg 0 1280 0
/home/orlando/Pictures/wallpapers/Windows 10 wallpapers/09 - VD7t2al.jpg 0 1280 0
/home/orlando/Pictures/wallpapers/Windows 10 wallpapers/10 - GjUEn90.jpg 0 1280 0
/home/orlando/Pictures/wallpapers/Windows 10 wallpapers/11 - qX58uOK.jpg 0 1280 0
/home/orlando/Pictures/wallpapers/Windows 10 wallpapers/20 - 1QqFwJU.jpg 0 1280 0
/home/orlando/Pictures/wallpapers/Windows 10 wallpapers/Diver.jpg 0 1280 0
set_multi_wallpapers.sh 脚本内容如下:
#!/bin/bash script_name="set_multi_wallpapers.sh"
script_usage=$(cat <<EOF
$script_name [OPTION]
EOF
)
script_function=$(cat <<EOF
This script is used to display a set of images onto root screen as wallpapers.
EOF
)
script_doc=$(cat <<EOF
-h Display this help.
-s Source file storing list of image paths and parameters. If this is not given, ~/.multi_wallpapers will be used.
-t Time interval between each image. If this is not given, default interval is 60 seconds.
-W Screen width.
-H Screen height.
EOF
)
script_examples=$(cat <<EOF
$script_name # Load images in ~/.multi_wallpapers as wallpapers with an interval of 60 seconds.
$script_name -s /path/to/image_list_file -t 5 # Specify image list file and time interval.
EOF
)
state_prefix="==="
warning_prefix="***"
error_prefix="!!!" function display_help() {
if [ -n "$script_usage" ]; then
echo -e "Usage: $script_usage"
fi if [ -n "$script_function" ]; then
echo -e "$script_function"
fi if [ -n "$script_doc" ] ; then
echo -e "\n$script_doc"
fi if [ -n "$script_examples" ]; then
echo -e "\nExamples"
echo -e "$script_examples"
fi
} # Default parameters
image_source_file="/home/orlando/.multi_wallpapers"
time_interval=60
screen_width=1920
screen_height=1080 # Process command options
while getopts ":ht:s:W:H:" opt; do
case $opt in
h ) display_help
exit 0 ;;
s ) image_source_file=$OPTARG ;;
t ) time_interval=$OPTARG ;;
W ) screen_width=$OPTARG ;;
H ) screen_height=$OPTARG ;;
\? ) display_help
exit 1 ;;
esac
done
shift $(($OPTIND - 1)) # Start execute the command
IFS=$'\n'
if [ -e "$image_source_file" ]; then
while [ 1 ]; do
for image_info in `cat "$image_source_file" | grep "^[^#].*"`; do
image_name=`echo "$image_info" | cut -f 1`
rot_angle=`echo "$image_info" | cut -f 2`
x_pos=`echo "$image_info" | cut -f 3`
y_pos=`echo "$image_info" | cut -f 4` if [ -e "$image_name" ]; then
set_wallpaper.sh -r "$rot_angle" -W "$screen_width" -H "$screen_height" -x "$x_pos" -y "$y_pos" "$image_name"
else
echo -e "$error_prefix Image $image_name does not exist!"
fi sleep $time_interval
done
done
else
echo -e "$error_prefix Configuration file $image_source_file does not exist!"
fi
4 生成多张壁纸配置文件: gen_multi_wallpapers.sh
该脚本可以在指定的目录下(第一个参数),根据指定的正则表达式(第二个参数)来搜索出匹配的图片文件,然后将其按上述配置文件的格式显示出来。脚本内容如下:
#!/bin/bash script_name="gen_multi_wallpapers.sh"
script_usage=$(cat <<EOF
$script_name [OPTION] path_name regex_pattern
EOF
)
script_function=$(cat <<EOF
Generate configuration for a list of wallpaper images.
EOF
)
script_doc=$(cat <<EOF
-h Display this help.
-c Display the comment for configuration file.
-x X position of the image to be loaded onto root screen.
-y Y position of the image to be loaded onto root screen.
EOF
)
script_examples=$(cat <<EOF
$script_name -x 1280 ./ "\\(.*jpg\\)\\|\\(.*JPG\\)"
EOF
)
state_prefix="==="
warning_prefix="***"
error_prefix="!!!" function display_help() {
if [ -n "$script_usage" ]; then
echo -e "Usage: $script_usage"
fi if [ -n "$script_function" ]; then
echo -e "$script_function"
fi if [ -n "$script_doc" ] ; then
echo -e "\n$script_doc"
fi if [ -n "$script_examples" ]; then
echo -e "\nExamples"
echo -e "$script_examples"
fi
} # Default parameters
x_pos=0
y_pos=0
comment_string=$(cat <<EOF
# Configuration file storing list of images to be loaded onto root screen as wallpapers. # Description of data columns (columns are separated by TAB):
# Column 1: Absolute path to image
# Column 2: Rotation angle applied to the image
# Column 3: X position of the image to be loaded onto the root screen
# Column 4: Y position of the image to be loaded onto the root screen
EOF
)
is_display_comment=0 # Process command options
while getopts ":chx:y:" opt; do
case $opt in
x ) x_pos=$OPTARG ;;
y ) y_pos=$OPTARG ;;
c ) is_display_comment=1 ;;
h ) display_help
exit 0 ;;
\? ) display_help
exit 1 ;;
esac
done
shift $(($OPTIND - 1)) # Start execute the command
if [ -n "$1" ] && [ -n "$2" ]; then
if [ "$is_display_comment" = 1 ]; then
echo -e "$comment_string\n"
fi gawk_cmd=`echo "gawk '{print \\$0\"\\t0\\t$x_pos\\t$y_pos\"}'"`
find "$1" -regex "$2" -print0 | xargs -n 1 -0 fullpath.sh | eval "$gawk_cmd"
else
echo "$error_prefix Please specify search path name and file name pattern!"
fi
可以看出,该脚本又用到了 fullpath.sh ,用于显示图片文件的绝对路径。 fullpath.sh 的内容如下:
#!/bin/bash echo $(cd $(dirname "$1") && pwd -P)/$(basename "$1")
5 脚本的使用
至此,一切都准备就续,可以按下面的步骤来实战了:
首先,切换到包含自己喜欢图片的文件夹,执行下面的命令生成配置文件:
gen_multi_wallpapers.sh -c -x 1280 ./ "\\(.*jpg\\)\\|\\(.*JPG\\)" > ./.multi_wallpapers
接下来,将下面的命令加入到 ~/.xinitrc 中:
set_multi_wallpapers.sh -s ./.multi_wallpapers -t 300 &
最后,重启X server即可生效。截了一个视频在这里(不好意思,用的是微软最新发布的Windows 10壁纸)。
在GNU/Linux下设置与定时更换桌面壁纸的更多相关文章
- 我在GNU/Linux下使用的桌面环境工具组合
为了使GNU/Linux桌面环境下加载的程序较少以节省内存资源和提高启动时间,我目前并不使用重量级的桌面环境KDE和Gnome,甚至连登录窗界面gdm或xdm都不用,而是直接启动到控制台,登录后调用s ...
- linux下使用crontab定时备份MYSQL数据库的方法:
摘要 linux下使用crontab定时备份MYSQL数据库的方法: 只需按照下面3步做,一切都在你的掌控之下: 第一步:在服务器上配置备份目录代码: ------------------------ ...
- GNU/Linux下Freeplane的界面渲染问题
如下图所示,思维导图软件Freeplane在GNU/Linux下默认的界面渲染效果是很差的,即便将Preferences → Appearance → Antialias设置为Antialias al ...
- 在GNU/Linux下将CD音乐转为mp3
以前我欣赏古典音乐都是听的CD,因而珍藏了不少光盘以及下载到电脑上的ape与flac格式的音乐文件.随着手机硬件性能(如电池续航能力.处理器速度.音质.存储容量等)和软件功能(音乐播放器对于曲目的管理 ...
- Linux下设置网卡静态ip
Linux下设置网卡静态ip 如果是服务器版,没有图形界面只用用命令行修改配置文件 如果是客户端版本,可以用图形界面 配置的前提是要在root用户下才能重启网卡服务 图形界面: system-conf ...
- Ubuntu Linux下设置IP的配置命令
Ubuntu Linux下设置IP的配置命令 今天装了Ubuntu,但是发现不能上网,开始排查问题: 1.首先确定网络连接是否正确,所用的网线是否可以正常工作 2.查看网卡是否能正常工作,检测的方法如 ...
- Linux下设置时间
Linux下设置时间 提供两种最根本有效的方式,就是更改时区.这里以更改为国内上海时间例子,其他地方时区同理. 方法一 备份文件 mv /etc/localtime /etc/localtime.ba ...
- linux下设置计划任务执行python脚本
linux下设置计划任务执行python脚本 简介 crontab命令被用来提交和管理用户的需要周期性执行的任务,与windows下的计划任务类似,当安装完成操作系统后,默认会安装此服务工具,并且会自 ...
- CentOS/Linux下设置IP地址
CentOS/Linux下设置IP地址 1:临时修改:1.1:修改IP地址# ifconfig eth0 192.168.100.100 1.2:修改网关地址# route add default g ...
随机推荐
- TCP为什么是个可靠的协议
一直以来,我们都被告知TCP是可靠的.但为什么是可靠的,很多人都会说“三次握手.四次挥手”.然后我们就进入一个误区:TCP可靠是因为它在建立链路时进行了“多次”地确认.然后又有人问,“多次确认就可靠了 ...
- revel框架教程之CSRF(跨站请求伪造)保护
revel框架教程之CSRF(跨站请求伪造)保护 CSRF是什么?请看这篇博文“浅谈CSRF攻击方式”,说的非常清楚. 现在做网站敢不防CSRF的我猜只有两种情况,一是没什么人访问,二是局域网应用.山 ...
- unittest 框架
unittest 框架 学习unittest 很好的一个切入点就是从selenium IDE 录制导出脚本.相信不少新手学习selenium 也是从IED 开始的. IDE学习参考: 菜鸟学自动化测试 ...
- HighCharts 图表高度动态调整
HighCharts 图表高度动态调整 前言 在使用HighCharts控件过程中,发现图表可以自适应div的高度,无法根据图表x.y轴的数量动态调整div高度,否则图标挤在一起,看起来非常不美观,也 ...
- Python:Python学习总结
Python:Python学习总结 背景 PHP的$和->让人输入的手疼(PHP确实非常简洁和强大,适合WEB编程),Ruby的#.@.@@也好不到哪里(OO人员最该学习的一门语言). Pyth ...
- JS左侧菜单-04
<script language="javascript" type="text/javascript"> function HideShow() ...
- C# 编写简易 ASP.NET Web 服务器
C# 编写简易 ASP.NET Web 服务器 你是否有过这样的需求——想运行 ASP.NET 程序,又不想安装 IIS 或者 Visual Studio?我想如果你经常编写 ASP.NET 程序的话 ...
- 这几天有django和python做了一个多用户博客系统(可选择模板)
这几天有django和python做了一个多用户博客系统(可选择模板) 没完成,先分享下 断断续续2周时间吧,用django做了一个多用户博客系统,现在还没有做完,做分享下,以后等完善了再慢慢说 做的 ...
- C++中内存泄漏的检测方法介绍
C++中内存泄漏的检测方法介绍 首先我们需要知道程序有没有内存泄露,然后定位到底是哪行代码出现内存泄露了,这样才能将其修复. 最简单的方法当然是借助于专业的检测工具,比较有名如BoundsCheck, ...
- linux下http服务器开发
linux下http服务器开发 1.mystery引入 1)超文本传输协议(HTTP)是一种应用于分布式.合作式.多媒体信息系统的应用层协议 2)工作原理 1)客户端一台客户机与服务器建立连接后,会发 ...