我正在使用 Tikz,有两条极坐标曲线r=1.5+cos(t)
和r=1.5
。我想填充(阴影)曲线之间的区域(图片上箭头所示)。我该怎么做?也许使用\clip
或其他方法?
我试过了\tikzfillbetween
但它在极坐标中表现得很奇怪。
\documentclass{article}
\usepackage{pgfplots}
\usetikzlibrary{arrows, intersections, fillbetween}
\begin{document}
\begin{tikzpicture}
\begin{axis}[grid = both]
% Outer curve
\addplot [data cs=polar, domain=0:360, samples=180, black,
line width=1pt, smooth](x, {1.5+cos(x)});
% Inner curve
\addplot [data cs=polar, domain=0:360, samples=180, green,
line width=1pt, smooth](x, 1.5);
\end{axis}
\end{tikzpicture}
\end{document}
答案1
您可以使用intersection segments
:
\documentclass{article}
\usepackage{pgfplots}
\pgfplotsset{compat=1.15}% <- added!!
\usepgfplotslibrary{fillbetween}% <- changed
\begin{document}
\begin{tikzpicture}
\begin{axis}[grid = both,
set layers% <- added
]
% Outer curve
\addplot [data cs=polar, domain=0:360, samples=180, black,
line width=1pt, smooth,
name path=outer
](x, {1.5+cos(x)});
% Inner curve
\addplot [data cs=polar, domain=0:360, samples=180, green,
line width=1pt, smooth,
name path=inner
](x, 1.5);
% Filling
\begin{pgfonlayer}{axis background}
\fill [orange!30,
intersection segments={
of=inner and outer,
sequence={L0--L1--R1[reverse]--R0[reverse]}
}];
\end{pgfonlayer}
\end{axis}
\end{tikzpicture}
\end{document}
结果:
显示片段的示例:
\documentclass{article}
\usepackage{pgfplots}
\pgfplotsset{compat=1.15}% <- added!!
\usepgfplotslibrary{fillbetween}% <- changed
\begin{document}
\begin{tikzpicture}
\begin{axis}[grid = both,
set layers% <- added
]
% Outer curve
\addplot [data cs=polar, domain=0:360, samples=180, black,
line width=1pt, smooth,
name path=outer
](x, {1.5+cos(x)});
% Inner curve
\addplot [data cs=polar, domain=0:360, samples=180, green,
line width=1pt, smooth,
name path=inner
](x, 1.5);
% Filling
\begin{pgfonlayer}{axis background}
\fill [orange!30,
intersection segments={
of=inner and outer,
sequence={L0--L1--R1[reverse]--R0[reverse]}
}];
\end{pgfonlayer}
\end{axis}
% Showing the segments
\begin{scope}[line width=2pt,->,font=\bfseries]
\foreach[count=\i from 0] \c in {green,orange,purple}{
\edef\temp{\noexpand\draw [\c,
intersection segments={of=inner and outer,sequence={L\i}}]node[left]{L\i};}
\temp}
\foreach[count=\i from 0] \c in {blue,gray,yellow}{
\edef\temp{\noexpand\draw [\c,
intersection segments={of=inner and outer,sequence={R\i}}]node[right]{R\i};}
\temp}
\end{scope}
\end{tikzpicture}
\end{document}
答案2
我找到了一个解决方案,也许不是最佳解决方案,但它可以推广。在(axis cs: {(1.5)*cos(\x)}, {(1.5)*sin(\x)})
框架内,scope
可以用形式r(\x)
为 的任何极坐标方程代替 (both) 1.5
。
\documentclass{article}
\usepackage{pgfplots}
\usetikzlibrary{arrows, intersections, fillbetween}
\begin{document}
\begin{tikzpicture}
\begin{axis}[grid = both]
% Outer curve
\addplot [data cs=polar, domain=0:360, samples=180, black,
line width=1pt, smooth](x, {1.5+cos(x)});
% Inner curve
\addplot [data cs=polar, domain=0:360, samples=180, green,
line width=1pt, smooth](x, 1.5);
% Shading
\begin{scope}
% Frame (inversed)
\path[clip] plot[domain=0:360, samples=180]
(axis cs: {(1.5)*cos(\x)}, {(1.5)*sin(\x)})
-- (current page.north east) -- (current page.south east)
-- (current page.south west) -- (current page.north west)
-- (current page.north east);
% framed plot
\addplot [data cs=polar, domain=0:360, samples=180, draw=none,
fill = yellow!40!white, fill opacity = 0.5,
line width=1pt, smooth](x, {1.5+cos(x)});
\end{scope}
\end{axis}
\end{tikzpicture}
\end{document}
答案3
使用 MetaPost 来实现这一目的的方法,可能会引起人们的兴趣。
编辑 我的第一次尝试使用了非常方便的buildcycle
宏,但我刚刚意识到,在这种特殊情况下,填充心形然后取消填充圆圈要简单得多。
\documentclass[border=3mm]{standalone}
\usepackage{luatex85, luamplib}
\mplibsetformat{metafun}
\begin{document}
\begin{mplibcode}
vardef plrfcn(expr tmin, tmax, tstep)(text r_t) =
save t; t := tmin;
(r_t)*dir t forever: hide(t := t + tstep) exitunless t <= tmax;
.. (r_t)*dir t
endfor
if t-tstep < tmax: hide(t := tmax) .. (r_t)*dir t fi
enddef;
u = cm; xmin = -2; xmax = 3; ymax = -ymin = 2;
beginfig(1);
% grid
for x = xmin upto xmax:
draw u*(x, ymin) -- u*(x, ymax) withcolor .8white;
if x>xmin: label.bot(TEX("$" & decimal x & "$"), u*(x, ymin)) fi;
endfor;
for y = ymin upto ymax:
draw u*(xmin, y) -- u*(xmax, y) withcolor .8white;
label.lft(TEX("$" & decimal y & "$"), u*(xmin, y));
endfor;
% polar curves and filled area
path cardio, circle;
circle = (plrfcn(0, 359, 1)(1.5) .. cycle) scaled u;
cardio = (plrfcn(0, 359, 1)(1.5 + cosd t) .. cycle) scaled u;
fill cardio withcolor .25[white, yellow]; unfill circle;
draw cardio; draw circle withcolor green;
endfig;
\end{mplibcode}
\end{document}
答案4
使用 PSTricks 的仅用于紧急情况的解决方案。
\documentclass[pstricks,border=1cm]{standalone}
\usepackage{pst-plot}
\begin{document}
\begin{pspicture}[algebraic,polarplot,plotpoints=100](-3,-3)(3,3)
\psaxes[axesstyle=polar,tickcolor=gray!25,ylabelFactor=^\circ](3,0)
\pscustom[fillstyle=solid,fillcolor=yellow!25]
{
\psplot{PiDiv2}{PiDiv2 neg}{1.5}
\psplot{PiDiv2 neg}{PiDiv2}{1.5+cos(x)}
}
\psplot[linecolor=blue]{0}{TwoPi}{1.5}
\psplot[linecolor=red]{0}{TwoPi}{1.5+cos(x)}
\end{pspicture}
\end{document}