我想使用提供的代码Tom Bombadil 在 TikZ 中变身 3D 人体这会创建漂亮的球体,具体如下(为了显示半径略有不同):
\draw (-1,0) arc (180:360:1cm and 0.5cm);%
\draw[dashed] (-1,0) arc (180:0:1cm and 0.5cm);%
\draw (0,1) arc (90:270:0.5cm and 1cm);%
\draw[dashed] (0,1) arc (90:-90:0.5cm and 1cm);%
\draw (0,0) circle (1cm);%
\shade[ball color=blue!10!white,opacity=0.20] (0,0) circle (1cm);%
\fill[fill=black] (0,0) circle (1pt);%
\draw[dashed] (0,0) -- node[above left]{$r$} (1,0);%
生成结果:
我很难将此代码转换为可以放置在任意位置的命令,并将半径更改为另一个值,然后更新相关值。使用 etc 时,我的尝试不起作用,\the\numexpr#3/2cm
而且我还不够熟悉tikz
。例如,当使用更简单的球体代码这是我尝试让它适应不同坐标的结果:
我的用例是每次显示 4 个残基的 PDB 碳原子球形搜索以查找螺旋(如果所有 4 个碳原子点都位于球体中,则很有可能位于螺旋区域),在我的主standalone
文档中如下所示:
请问我该如何将上述代码转换为可放置在任意位置和可修改半径的自定义命令?抱歉,这是基本的,但我已经尝试了半个小时,如果我遇到困难,那么其他人可能也会遇到困难,如果是这样的话,我将不胜感激(我曾尝试在这里搜索)。
\documentclass[border=0pt,tikz]{standalone}
\begin{document}%
\newcommand\drawsphere[3]{%
\draw (-1,0) arc (180:360:1cm and 0.5cm);%
\draw[dashed] (-1,0) arc (180:0:1cm and 0.5cm);%
\draw (0,1) arc (90:270:0.5cm and 1cm);%
\draw[dashed] (0,1) arc (90:-90:0.5cm and 1cm);%
\draw (0,0) circle (1cm);%
\shade[ball color=blue!10!white,opacity=0.40] (0,0) circle (1cm);%
\fill[fill=black] (0,0) circle (1pt);%
\draw[dashed] (0,0) -- node[above left]{$r$} (1,0);%
}%
\begin{tikzpicture}%
\draw (-1,0) arc (180:360:1cm and 0.5cm);%
\draw[dashed] (-1,0) arc (180:0:1cm and 0.5cm);%
\draw (0,1) arc (90:270:0.5cm and 1cm);%
\draw[dashed] (0,1) arc (90:-90:0.5cm and 1cm);%
\draw (0,0) circle (1cm);%
\shade[ball color=blue!10!white,opacity=0.20] (0,0) circle (1cm);%
\fill[fill=black] (0,0) circle (1pt);%
\draw[dashed] (0,0) -- node[above left]{$r$} (1,0);%
\end{tikzpicture}
\end{document}
答案1
尽管使用pics
会更好,但是有一种快速而肮脏的方法:
\documentclass[border=2.7mm,tikz]{standalone}
\newcommand\drawsphere[3]{%scale, x, y
\begin{scope}[scale=#1, shift={(#2,#3)}]
\draw (-1,0) arc (180:360:1cm and 0.5cm);
\draw[dashed] (-1,0) arc (180:0:1cm and 0.5cm);
\draw (0,1) arc (90:270:0.5cm and 1cm);
\draw[dashed] (0,1) arc (90:-90:0.5cm and 1cm);
\draw (0,0) circle (1cm);
\shade[ball color=blue!10!white,opacity=0.40] (0,0) circle (1cm);
\fill[fill=black] (0,0) circle (1pt);
\draw[dashed] (0,0) -- node[above left]{$r$} (1,0);
\end{scope}
}
\begin{document}
\begin{tikzpicture}
\drawsphere{1}{0}{0}
\drawsphere{2}{2}{2}
\drawsphere{0.5}{-1}{-1}
\end{tikzpicture}
\end{document}
正如 Qrrbrbirlbel 所注意到的,选项的顺序scale
很重要(这里也缩放了移位坐标),而且中心点也缩放了。也许更好的实现是
\documentclass[border=2.7mm,tikz]{standalone}
\newcommand\drawsphere[3]{%scale, x, y
\begin{scope}[shift={(#2,#3)}, scale=#1,
% transform shape % if you want the "r" scaled too
]
\draw (-1,0) arc (180:360:1 and 0.5);
\draw[dashed] (-1,0) arc (180:0:1 and 0.5);
\draw (0,1) arc (90:270:0.5 and 1);
\draw[dashed] (0,1) arc (90:-90:0.5 and 1);
\draw (0,0) circle (1);
\shade[ball color=blue!10!white,opacity=0.40] (0,0) circle (1);
\draw[dashed] (0,0) -- node[above left]{$r$} (1,0);
\end{scope}
\fill[black] (#2,#3) circle [radius=1pt];
}
\begin{document}
\begin{tikzpicture}
\drawsphere{1}{0}{0}
\drawsphere{2}{2}{2}
\drawsphere{0.5}{-1}{-1}
\end{tikzpicture}
\end{document}
答案2
以下是使用 s 执行此操作的一些方法\pic
,同时还显示了剩余的工作。主要主题:
- 使用
\pic
无参数参数 - 使用
\pic
参数参数
1. 无参数
只需\newcommand
像这样重新制作:
\begin{tikzpicture}[
sph/.pic={% ~~~ with fixed radius ~~~~~~~~~
\draw (-1,0) arc (180:360:1cm and 0.5cm);%
\draw[dashed] (-1,0) arc (180:0:1cm and 0.5cm);%
\draw (0,1) arc (90:270:0.5cm and 1cm);%
\draw[dashed] (0,1) arc (90:-90:0.5cm and 1cm);%
\draw (0,0) circle (1cm);%
\shade[ball color=blue!10!white,opacity=0.20] (0,0) circle (1cm);%
\fill[fill=black] (0,0) circle (1pt);%
\draw[dashed] (0,0) -- node[above left]{$r$} (1,0);%
}
]
...
并将其命名为有点像 \node 的东西,这里的节点只是充当标题:
\pic at (0,0) {sph}; \node at (0,-1.3){1};
现在图片 1-5 展示了此调用的一些变化:
- 定期呼叫
- 不同颜色,旋转!!内部标签“r”需要重新制作
- 相同,但尺寸变小 >> 未改变标签“r”
- 类似 3,但标签也经过缩放
- 扩大它
- 由于某种原因而错误计数 == 缺失
带有参数
一开始就\tikzset
向您展示了如何做到这一点,而使用它的调用只是 --- 请注意传递参数:
\pic at (45:5) {sphr={2cm}};
现在,正如您在图 7 中看到的,工作仍未完成,因为所有圆弧都需要进行更多计算...这不仅仅是替换。也许这里的设计方法应该1cm
经过#1
深思熟虑和改进。
即成功的返工需要替换所有硬编码:
1cm
+1
协调-1
协调- 计算
half of #1
替换0.5cm
这可能从一开始就做得更好……例如:
- 重构,例如这里讨论,将有助于,即引入实线和虚线半弧
\pic
- 当然Qrrbirbirbel 的评论应该考虑到
\documentclass[10pt,border=3mm,tikz]{standalone}
\tikzset{% ~~~ unfinished sketch for \pic taking argument(s) ~~~
pics/sphr/.style args={#1}{% #1=radius, obviously
code={
\draw (-1,0) arc (180:360:#1 and 0.5cm);%
\draw[dashed] (-1,0) arc (180:0:1cm and 0.5cm);%
\draw ( 0,1) arc (90:270:0.5cm and 1cm);%
\draw[dashed] ( 0,1) arc (90:-90:0.5cm and 1cm);%
\draw ( 0,0) circle (#1);%
\shade[ball color=blue!10!white,opacity=0.20]
( 0,0) circle (#1);%
\fill[fill=black] ( 0,0) circle (1pt);%
\draw[dashed] ( 0,0) -- node[above left]{$r$} (1,0);%
}
}
}
\begin{document}
\begin{tikzpicture}[
sph/.pic={% ~~~ with fixed radius ~~~~~~~~~
\draw (-1,0) arc (180:360:1cm and 0.5cm);%
\draw[dashed] (-1,0) arc (180:0:1cm and 0.5cm);%
\draw (0,1) arc (90:270:0.5cm and 1cm);%
\draw[dashed] (0,1) arc (90:-90:0.5cm and 1cm);%
\draw (0,0) circle (1cm);%
\shade[ball color=blue!10!white,opacity=0.20] (0,0) circle (1cm);%
\fill[fill=black] (0,0) circle (1pt);%
\draw[dashed] (0,0) -- node[above left]{$r$} (1,0);%
}
]
\pic at (0,0) {sph}; \node at (0,-1.3){1};
\pic[red,rotate=30] at (5,0) {sph}; \node at (5,-1.3){2};
\pic[scale=.5] at (3,0) {sph}; \node at (3,-.8 ){3};
\pic[scale=.5,transform shape] at (3,-2) {sph};\node at (3,-2.8){4};
\pic[scale=2] at (-2,3) {sph};\node at (-2,.6){5};
\pic at (45:5) {sphr={2cm}}; \node at (20:5.5){7};
\end{tikzpicture}
\end{document}