我正在尝试使用 TikZ 复制该图像。
到目前为止,我已经能够做到这一点:
但是缩放比例有点奇怪,我想将其设为 1:1,因为它看起来被拉伸了。此外,为了给该区域着色,我见过其他示例,但这个示例的问题是曲线不会同时生成。
\begin{center}
\begin{tikzpicture}[scale=1]
\begin{axis}
% Outer curve
\addplot [data cs=polar, domain=0:360, samples=180, white,
line width=1pt, smooth](x, {3*cos(3*x)});
% Inner curve
\addplot [data cs=polar, domain=0:360, samples=180, white,
line width=1pt, smooth](x, {1+2*sin(x)});
% Shading
\end{axis}
\end{tikzpicture}
\end{center}
任何帮助将不胜感激。
答案1
这是一个元帖子比较版本:
\documentclass[border=5mm]{standalone}
\usepackage{luamplib}
\begin{document}
\mplibtextextlabel{enable}
\begin{mplibcode}
beginfig(1);
numeric u; u = 60;
path xx, yy, limacon, propeller;
xx = (left -- right) scaled 3.5u;
yy = xx rotated 90;
limacon = (for t = 0 upto 359: (1 + 2 sind(t)) * dir t .. endfor cycle) scaled u;
propeller = (for t = 0 upto 179: (3 cosd(3t)) * dir t .. endfor cycle) scaled u;
path shaded_area;
shaded_area = buildcycle(
subpath (90, 120) of propeller,
subpath (90, 150) of limacon,
subpath (120, 150) of propeller,
subpath (330, 270) of limacon);
fill shaded_area withcolor 3/4[blue, white];
% This is useful to work out the correct subpaths of the shapes for buildcycle
% for i=0 step 30 until length limacon - 1: dotlabel.top(decimal i, point i of limacon); endfor
% for i=0 step 20 until length propeller - 1: dotlabel.top(decimal i, point i of propeller); endfor
draw limacon;
draw propeller;
drawarrow xx; label.rt("$x$", point 1 of xx);
drawarrow yy; label.top("$y$", point 1 of yy);
for t = -2, 2:
draw (left--right) shifted (0, t*u); label.lft("$" & decimal t & "$", (0, t*u));
draw (down--up) shifted (t*u, 0); label.bot("$" & decimal t & "$", (t*u, 0));
endfor
endfig;
\end{mplibcode}
\end{document}
编译此可得到lualatex
:
如果您确实想要黑底白字的版本,这里有一种方法可以在 Metapost 中实现。
删除行
fill shaded_area withcolor 3/4[blue, white]
并在之前添加以下五行
endfig;
picture P; P = currentpicture; currentpicture := nullpicture; bboxmargin := 20; fill bbox P withcolor black; fill shaded_area withcolor 3/4[blue, white]; draw P withcolor white;
然后再次编译以
lualatex
获得此版本:
答案2
正如评论中所建议的那样这个问题,如果您想设置xmin
和xmax
以及ymin
和ymax
,使用axis equal image
将是获得 1:1 纵横比的方法。在下面的示例中,我使用fillbetween
和backgrounds
库添加了阴影。
由于舍入误差,两条路径的交点(尤其是路径多次相遇的原点处的交点)可能无法准确计算。为了解决这个问题,我移动了路径的范围,使它们的起点和终点都位于原点,这是绘制形状的关键坐标。
\documentclass[border=10pt]{standalone}
\usepackage{pgfplots}
\pgfplotsset{compat=1.18}
\usetikzlibrary{fillbetween, backgrounds}
\begin{document}
\begin{tikzpicture}
\begin{axis}[
axis equal image,
axis lines=center,
xlabel={$x$},
ylabel={$y$},
xmin=-3.75, xmax=3.75,
ymin=-3.75, ymax=3.75
]
% Outer curve
\addplot[data cs=polar, domain=-30:150, samples=257, red,
line width=1pt, name path=A] (x, {3*cos(3*x)});
% Inner curve
\addplot[data cs=polar, domain=-30:330, samples=257, blue,
line width=1pt, name path=B] (x, {1+2*sin(x)});
% Shading
\begin{pgfonlayer}{background}
\fill[yellow, intersection segments={of=A and B,
sequence={L4 -- R4 -- L6 -- R6[reverse]}}] -- cycle;
\end{pgfonlayer}
\end{axis}
\end{tikzpicture}
\end{document}