我最近发现pgf图我很喜欢。我正在将论文中的数字转换为pgf图,或者至少是我自己制作的。我的一个图是我使用 Matlab 制图工具箱创建的地图。我很想将它转换为 LaTeX +pgf图,但我感觉我并没有真正的工具。对于绘图,需要:
- 投影,例如从 GIS 坐标转换为纬度/经度(或 UTM/UPS,或...)。这应该可以在现有的数学引擎之上构建。等距矩形投影最简单。最好是相当集成的,这样就可以将其用作坐标系,例如
(axis latlon:30.0,40.0)
。 - 用于跟踪比例的某些东西,例如直接添加比例尺会很好。
- 还要别的吗?
到目前为止,我使用了 Matlab,但对结果不太满意。有人尝试过破解类似的东西吗?
(这应该是一个社区维基问题,但我没有看到任何按钮来标记它,也许我没有声誉?)
答案1
我过去曾使用 PGFplots 生成一些局部区域的地图,在 GRASS 中进行分水岭计算并将矢量导出为 ASCII 文件,这些文件可以相对轻松地通过 PGFplots 绘制。这只需要一个 xy 坐标系(空间范围约为 100 公里 x 100 公里),失真可以忽略不计。
正如您提到的,在(近)全球范围内,事情变得更加复杂,而板块托运是迄今为止最容易入手的事情。
这是一个非常基本的入门尝试(我一直想研究这个问题):
等距矩形(Plate Caree)投影的世界地图,其中天梭指示线以蓝色显示,百慕大三角以橙色显示
世界地图是 Gnuplot 数据的一部分:世界数据
通过在 PGFplots 中设置disabledatascaling
,您可以使用普通坐标而不是坐标,并且在和axis cs
中可以使用在画布坐标和数据坐标之间转换的比例因子。\pgfplotunitxlength
\pgfplotsunitylength
axis equal
确保 x 和 y 单位长度相同。
我编写了一个名为 的键scale circle
,您可以将其添加到 的选项中\draw circle
。该键将根据纬度缩放 x 半径。
这种方法无法实现不遵循经度或纬度的曲线。我不确定最好的方法是什么,我猜是某种to path
魔法(Andrew Stacey?)或某种\addplot
表达。我会考虑一下。
\documentclass{article}
\usepackage{pgfplots}
\begin{document}
\makeatletter
\pgfmathsetmacro\kmAtEquator{36/4200} % Degree/km at equator
\tikzset{
scale circle/.code={
\pgfgetlastxy{\x@coord}{\y@coord}
\pgfmathsetmacro\xscale{\pgfkeysvalueof{/tikz/x radius}*1/cos(\y@coord/\pgfplotsunitylength)}
\tikzset{/tikz/x radius=\xscale}
},
scale bar/.code={
\pgfgetlastxy{\x@coord}{\y@coord}
\pgfmathsetmacro\xscale{1/cos(\y@coord/\pgfplotsunitylength)}
\tikzset{
insert path={
node [
below,
font=\scriptsize
] {0}
+(0,-2pt) -- +(0,0) -- ++(#1*\xscale*\kmAtEquator,0)
node [
below,
font=\scriptsize,
inner xsep=1pt,
label={[inner sep=0pt,font=\scriptsize]right:km}] {#1}
-- +(0,-2pt)
}
}
},
scale bar/.default=2000
}
\makeatother
\begin{tikzpicture}
\begin{axis}[
grid=both, ytick={-60,-30,...,90}, xtick={-180,-150,...,180},
grid style=black!10,
enlargelimits=false,
axis equal,
scale only axis,
width=10cm,
height=5cm,
disabledatascaling, clip=false
]
\addplot [] table {world.dat};
\pgfplotsextra{
\foreach \x in {-160,-120,...,160}{
\foreach \y in {-75,-50,...,75}{
\fill [cyan, opacity=0.25] (\x,\y) circle [radius=5, scale circle];
}
}
\fill [orange] (-64.9,32.3) -- (-66.1,18.5) node [anchor=mid west, inner sep=1pt, orange!75!black, fill=white, text opacity=1,fill opacity=0.75, align=left] {Bermuda\\Triangle} -- (-80.4,25.2) -- cycle;
\draw (185,0) [scale bar];
\draw (185,45) [scale bar];
\draw (185,60) [scale bar];
}
\end{axis}
\end{tikzpicture}
\end{document}