我正在使用 gnuplot 5.2 qt 进行交互式绘图。
我想旋转绘图上的一些标签,使它们相对于坐标网格处于一致的角度。 例如,如果我在 (0,0) 处有一个旋转“45 度”的标签,我希望它指向 (1,1),无论窗口是什么形状以及我如何放大。
我通过计算 GPVAL_X_MIN、GPVAL_X_MAX、GPVAL_TERM_XSIZE 等的纵横比并在我的绘图命令中进行适当的数学计算,成功地实现了这一点。 我遇到的问题是这些 GPVAL 仅在绘图更新后才更新。因此,如果我放大,我会看到标签角度没有变化,但如果我刷新绘图(或再次缩放到同一位置),角度就会正确更新。 阅读文档,我认为这些变量仅在绘图完成后才会更新 - 但我不知道如何在绘图期间获取纵横比。
下面的绘图脚本演示了我的旋转逻辑。它工作正常,但例如,如果在绘图之前更改 xrange,则需要重新绘图才能再次正确更新角度。
# Define function to adjust angle based on window size and zoom
reorient(angle) = atan(tan(angle) * (GPVAL_X_MAX - GPVAL_X_MIN) * GPVAL_TERM_YSIZE / (GPVAL_Y_MAX - GPVAL_Y_MIN) / GPVAL_TERM_XSIZE) - 180 * (angle < -90)
# Open a plot window
plot x
# Plot text "45" at (0, 0) rotated by 45 degrees, with reference points at (-1, -1) and (1, 1)
set angles degrees
plot '<echo "-1, -1, 0\n0 0 45\n1 1 90"' using 1:2:3:(reorient($3)) with labels rotate variable
我热衷于避免需要重新绘制,因为忘记这样做是潜在的错误来源,而且因为我运行的完整绘图脚本非常慢,所以每次缩放时都必须重新渲染两次是痛苦的。
with labels
,角度显然取决于绘图的纵横比。然后您需要
GPVAL_...
变量来纠正它,正如您所尝试的那样。然而,绘图的这些 GPVAL_...
变量的值仅在 after绘图后才可用,并且需要重新绘图,这是不实际或不理想的,尤其是在放大交互式终端时,例如像
wxt
或 qt
。有一个解决方法:
通过 set label
放置的标签与图形纵横比无关。
使用stats
将坐标和角度放入数组(误)中循环设置标签
stats
来获取总行数)。
脚本:(由于使用数组,需要 gnuplot>=5.2.0)
### add rotated labels with correct angle independent of plot aspect ratio
reset session
set term qt
$Data <<EOD
-1.0 -1 0
-0.5 -0.5 30
0.0 0.0 45
0.5 0.5 60
1.0 1.0 90
EOD
N = |$Data|
array L[3*N]
stats $Data u (i=$0+1, L[3*i-2]=$1, L[3*i-1]=$2, L[3*i]=$3) nooutput
set for [i=1:N] label i at L[3*i-2],L[3*i-2] sprintf("%g",L[3*i]) rotate by L[3*i] font ",20"
set xrange[-2:2]
plot -x
### end of script
(qt 终端的屏幕截图)