2016-11-23 127 views
0

我想为自定义屏幕保护程序写一个简单的bash脚本,我想要简单的去黑屏,如果在闲置,并返回正常,如果不是。条件评估意外

#!/bin/bash 
#sets display gamma very low, for screensaver purposes 


idle=false 
idle_after=3000 #in milliseconds 

while true; do 

#if system is idle 
if [[ idle_now=$(xprintidle) -gt "$idle_after" && "$idle"=false ]] ;then 

echo "1" 

     `xrandr --output HDMI-0 --brightness 0.01` 
     idle=true 

fi 

if [[ idle_now=$(xprintidle) -lt "$idle_after" && "$idle"=true ]] ; then 
echo "2" 
     `xrandr --output HDMI-0 --brightness 1` #set screen back to normal 
     exit 
fi 


done 

我真的不知道为什么第二个查询是先执行的。 我认为空闲变量在启动时初始化为“false” 有人可以向我解释这一点吗?如果有人对我的方法给予改进,我将非常感激,谢谢

+4

有你的脚本,将通过http://www.shellcheck.net/ –

+0

标识除了在条件语句的问题的一些基本问题,为什么你在'xrandr'命令周围有反引号?这需要命令的输出(如果有的话),并尝试执行它作为一个命令......我不认为这是'xrandr'如何工作。 –

回答

1

您的测试表达式是错误的。

第二个if首先被执行的原因是操作数和运算符在测试内部没有空格([[]])。

为了更好的理解,让我们看到一个可能的变量替换在第一循环假设xprintidle回报10

[[ idle_now=$(xprintidle) -lt "$idle_after" && "$idle"=true ]] 
# becomes 
[[ idle_now=10 -lt 3000 && false=true ]] 

现在你想比较10对3000,但现在你要比较字符串"idle_now=10"3000 。正如任何字符串转换成零,如果字符不是数字,它像你这样:

[[ 0 -lt 3000 && false=true ]] 
# that becomes 
[[ <true> && false=true ]] 

现在,第二个操作数也是一个字符串“假=真”(不是比较),和任何字符串转换布尔值为空时为false。这不是你的情况,字符串有10个字符,所以它的计算结果为true。

[[ <true> && <true> ]] 
# that becomes 
<true> 

注:我用<true><false>只是为了澄清,他们真的是布尔值的内部表示。

修复它

我想象idle_now本来是一个变量,它从来没有使用过,所以我们会忽略它。

所以如果表达式应该是:

[[ "$(xprintidle)" -gt "$idle_after" && "$idle" = false ]] 
# and 
[[ "$(xprintidle)" -lt "$idle_after" && "$idle" = true ]] 
+0

非常感谢您的帮助,所以正确地说:在if表达式中,不带空格的'='意味着分配,并带有空格 - >比较? – user5356132

+0

不,没有空格就意味着像其他任何字符串:例如。 '[[a = 1]]等于'[[“a = 1”]]',它被转换为,因为它不是空字符串。要分配一个变量,你必须在'[[]]'之外或者像'((a = 1))'这样的bash表达式内部进行。 – WPomier