我想创建一个\rating
命令,根据 0 到 100 之间的数字参数绘制部分填充的圆圈:
问题:我该如何修改确定 中角度的表达式arc
,以便填充在整个值范围内更稳定地上升?目前,从 0 到 20 的评级看起来是空的,80 到 100 的评级看起来完全填充,并且只有在两者之间才有稳步上升。
澄清:我寻找的不是数学上严谨的表达式,而是最简单的表达式看起来不错,即\rating{25}
,\rating{50}
和\rating{75}
在视觉上看起来像1/4、2/4和3/4。
\documentclass{minimal}
\usepackage{tikz}
\newcommand{\rating}[1]{
\begin{tikzpicture}
\fill[lightgray] ({270-1.8*#1}:1ex) arc ({270-1.8*#1}:{270+1.8*#1}:1ex) -- cycle;
\draw[black, thin, radius=1ex] (0,0) circle;
\end{tikzpicture}}
\begin{document}
This really should scale\dots
\rating{0} \rating{10} \rating{20} \rating{30} \rating{40} \rating{50}
\rating{50} \rating{60} \rating{70} \rating{80} \rating{90} \rating{100}
\dots linearly.
\end{document}
答案1
另外,请参阅为什么要避免使用最小类?
这是使用 TikZ 中的 ped 路径的解决方案clip
。请注意,剪辑路径不能添加额外的选项,因此我按照您的要求单独绘制了圆圈,超出了路径的范围\clip
。
\documentclass{article}
\usepackage{tikz}
\newcommand{\rating}[1]{%
\begin{tikzpicture}[x=1ex,y=1ex]
\begin{scope}
\clip (0,1) circle (1);
\fill[lightgray] (-1,0) rectangle (1,#1/50);
\end{scope}
\draw[black, thin, radius=1] (0,1) circle;
\end{tikzpicture}%
}
\begin{document}
This really should scale\dots
\foreach \h in {0,5,...,100} {\rating{\h}}
\dots linearly.
\end{document}
答案2
另一种带有TikZ
但不带有明确剪辑的方式:
\documentclass[border=5]{standalone}
\usepackage{tikz}
\usetikzlibrary{calc}
\tikzset{circle mark/.pic={
\draw [path picture={%
\fill (path picture bounding box.south west) |-
($(path picture bounding box.south east)!#1/100!(path picture bounding box.north east)$)
|- cycle;}] circle [radius=1ex];
}}
\begin{document}
\foreach \i in {0,10,...,100}
\tikz\path pic{circle mark=\i};
\end{document}
答案3
您所需要的只是角度的不同参数化;详情请参阅下文。
此外,
- 因为您似乎使用
\rating
“inline”,所以您可能只想使用它\tikz
而不是tikzpicture
环境; - 避免在 的定义中出现虚假空格
\rating
(而是在 的调用之间插入一个空格\rating
,无论何时需要); 1ex
不要将其硬编码为半径,而是使其成为可选参数,以获得更大的灵活性;- 正如保罗在他的回答,
minimal
使用时避免使用该类tikz
。
\documentclass{article}
\usepackage{tikz}
\usepackage{amsmath}
\newcommand{\rating}[2][1ex]{%
\pgfmathsetmacro\th{asin(#2/50-1)}% (theta angle of polar coordinates)
\tikz{%
\fill[lightgray] (\th:#1) arc (\th:-180-\th:#1) -- cycle;
\draw[black, thin, radius=#1] (0,0) circle;
}%
}
\begin{document}
This really should scale\dots
\foreach \h in {0,10,...,100} {\rating{\h} }
\dots linearly.
\section*{Parameterisation explained}
Let~\(R\) be the disk radius. In polar coordinates,
%
\[
y = R \sin \theta \,.
\]
%
Therefore,
%
\[
\theta = \arcsin \frac{y}{R} \,.
\]
%
Because the quantity~\(y/R\) varies over~\([-1,1]\)
but you want a parameter~\(u\) that varies over~\([0,100]\),
the right affine transformation will get you there:
%
\[
\frac{y}{R} = \frac{u}{50} - 1 \,.
\]
%
\end{document}
答案4
运行xelatex
\documentclass{article}
\usepackage{pstricks}
\def\rateColor{black!40}
\newcommand\rating[2][]{%
\ifx\relax#1\relax\else\gdef\rateColor{#1}\fi
\psset{unit=1ex}%
\pspicture[dimen=inner](-1.2,-1.2)(1.2,1.2)
\psclip{\pscircle{1}}
\psframe*[linecolor=\rateColor](-1,-1)(!1 #2 100 div 2 mul 1 sub)
\endpsclip\pscircle{1}
\endpspicture}
\begin{document}
This really should scale \dots
\tiny
\multido{\iA=0+10}{21}{\ifnum\iA>100\expandafter\rating\expandafter{\the\numexpr200-\iA}\else\rating{\iA}\fi} \par
\normalsize
\rating[red]{0}
\multido{\iA=10+10}{20}{\ifnum\iA>100\expandafter\rating\expandafter{\the\numexpr200-\iA}\else\rating{\iA}\fi} \par
\Large
\rating[blue]{0}
\multido{\iA=10+10}{20}{\ifnum\iA>100\expandafter\rating\expandafter{\the\numexpr200-\iA}\else\rating{\iA}\fi} \par
\end{document}