能否通过ImageMagick Convert动态计算图片水印的旋转角度?
解决ImageMagick 6中斜向水印旋转角度计算的问题
你的思路完全正确,但ImageMagick 6确实存在两个限制导致你的原命令失效:一是子命令(括号内处理水印的部分)无法直接引用主图片的宽高变量(u.w/u.h),二是IM6的-rotate参数不支持动态的%[fx:]表达式,必须传入预先计算好的数值。下面是具体的解决方法:
方法一:用Convert直接计算角度(推荐)
可以利用ImageMagick的info输出模式,一次性获取主图和水印的宽高并计算旋转角度,避免多次调用外部工具:
# 1. 预先计算旋转角度(单位:度) angle_deg=$(convert "$pic" "$wmark" -format "%[fx:atan((($w/$h)-($w2/$h2))/(1-($w/$h)*($w2/$h2)))*180/pi]" info:) # 2. 执行水印合成 convert -background none -gravity center -density 300 "$pic" \ \( "$wmark" -rotate "$angle_deg" \) \ -compose over -composite "$result"
原理说明:
- 传入
$pic和$wmark两个图片时,IM会自动将第一个图片的宽高赋值给$w/$h,第二个的宽高赋值给$w2/$h2。 fx表达式里的atan()返回弧度,乘以180/pi转成角度,正好符合-rotate的参数要求。
方法二:用Identify+BC分步计算
如果你更习惯分步处理,也可以用identify获取宽高,再用bc计算角度:
# 1. 获取主图片和水印的宽高 pic_w=$(identify -format "%w" "$pic") pic_h=$(identify -format "%h" "$pic") wmark_w=$(identify -format "%w" "$wmark") wmark_h=$(identify -format "%h" "$wmark") # 2. 计算宽高比和旋转角度(弧度转角度) ratio1=$(echo "scale=10; $pic_w / $pic_h" | bc -l) ratio2=$(echo "scale=10; $wmark_w / $wmark_h" | bc -l) angle_rad=$(echo "scale=10; a(($ratio1 - $ratio2)/(1 - $ratio1*$ratio2))" | bc -l) angle_deg=$(echo "scale=10; $angle_rad * 180 / (4*a(1))" | bc -l) # 4*a(1)是BC中π的表示 # 3. 执行合成 convert -background none -gravity center -density 300 "$pic" \ \( "$wmark" -rotate "$angle_deg" \) \ -compose over -composite "$result"
为什么原命令失效?
- 你提到的
u.w/u.h取值为0:在IM6中,括号内的子命令是独立的进程上下文,无法访问主图片的u(上游图片)变量,所以这些值默认是0。 -rotate不支持%[fx:]:IM6的-rotate只能接受固定数值,IM7才支持动态表达式作为参数。
内容的提问来源于stack exchange,提问作者AFoeee
相关产品推荐
相关产品推荐

