答案1
我不了解 Tikz,但这里有一个 MetaPost/MetaFun 入门教程,也许可以帮你入门。编译自context
。玩得开心!
\starttext
\startMPpage[offset=3bp,instance=doublefun]
u:=1cm;% overall unit
% (theta,phi) spherical coordinates for viewpoint direction
theta:=-80;
phi:=15;
% scalar product
primarydef u cdotprod v =
redpart u*redpart v + greenpart u*greenpart v + bluepart u*bluepart v
enddef;
% Projection from 3D to 2D
vardef P primary x =
save ct,st,sp;
ct:=cosd(theta);
st:=sind(theta);
sp:=sind(phi);
(x cdotprod (-st,ct,0),x cdotprod (-ct*sp,-st*sp,cosd(phi)))
enddef;
path S[],seam[],torso,waist,knee[],innerpants,outerpants[],grays[];
pair toe[],scrotch;
% The planes
S[1] = (P(-3.5,-2.5,0)
--
P(2,-2.5,0)
--
P(2,2.5,0)
--
P(-3.5,2.5,0)
--
cycle)
randomizedcontrols 0.75 scaled u;
S[2] = (P(-3.5,-2.5,3)
--
P(2,-2.5,3)
--
P(2,2.5,3)
--
P(-3.5,2.5,3)
--
cycle)
randomizedcontrols 0.75 scaled u;
% The body
torso = (P(1,0,6)
...
P(0,1,6)
...
P(-1,0,6)
...
P(0,-1,6)
...
cycle)
randomizedcontrols 0.2 scaled u;
waist = (P(1,0,3)
...
P(0,1,3)
...
P(-1,0,3)
...
P(0,-1,3)
...
cycle)
randomizedcontrols 0.2 scaled u;
knee[1] = (P(1,0,0)
...
P(0.75,0.4,0)
...
P(0.5,0,0)
...
P(0.75,-0.4,0)
...
cycle)
randomized 0.0 scaled u;
knee[2] = (P(-0.5,0,0)
...
P(-0.75,0.4,0)
...
P(-1,0,0)
...
P(-0.75,-0.4,0)
...
cycle)
randomized 0.0 scaled u;
toe[1] = P(0.8,-0.3,-2.3) scaled u;
toe[2] = P(-0.9,0,-1.8) scaled u;
scrotch = P(0,0,1.5) scaled u;
outerpants[1] = (directionpoint dir 80 of torso){dir -100}
..
{down}(directionpoint up of waist)
..
(directionpoint up of knee[1])
..
toe[1];
outerpants[2] = (directionpoint dir -80 of torso){dir -80}
..
{down}(directionpoint down of waist)
..
(directionpoint down of knee[2])
..
{dir -80}toe[2];
innerpants = (toe[1]
..
(directionpoint down of knee[1])
..
{dir 115}scrotch{dir -105}
..
(directionpoint up of knee[2])
..
{dir -105}toe[2]);
for i=1 upto 5:
seam[i] = (point 2.3+0.08i of torso){dir -87}
..
(point 2.2+0.075i of waist)
..
(point 2.35+0.2i of knee[2])
..
toe[2];
endfor;
for i=6 upto 10:
seam[i] = (point 2.8+0.06i of torso){dir -90}
..
(point 2.7+0.065i of waist)
..
{dir -90}(point 2.3-0.1(i-5) of innerpants);
endfor;
grays[1] = subpath(xpart(reverse outerpants[1] intersectiontimes waist),
xpart(reverse outerpants[1] intersectiontimes torso))
of reverse outerpants[1]
--
subpath(xpart(torso intersectiontimes outerpants[1]),
xpart(torso intersectiontimes outerpants[2]))
of torso
--
subpath(xpart(outerpants[2] intersectiontimes torso),
xpart(outerpants[2] intersectiontimes waist))
of outerpants[2]
--
subpath(xpart(reverse waist intersectiontimes outerpants[2]),
xpart(reverse waist intersectiontimes outerpants[1]))
of reverse waist
--
cycle;
grays[2] = subpath(xpart(outerpants[1] intersectiontimes knee[1]),
xpart(outerpants[1] intersectiontimes subpath(0,1) of S[2]))
of outerpants[1]
--
reverse subpath(xpart(S[2] intersectiontimes reverse outerpants[1]),
xpart(S[2] intersectiontimes reverse outerpants[2]))
of S[2]
--
subpath(xpart(outerpants[2] intersectiontimes (subpath(0,1) of S[2])), xpart(outerpants[2] intersectiontimes knee[2]))
of outerpants[2]
--
subpath(xpart(knee[2] intersectiontimes outerpants[2]),
xpart(knee[2] intersectiontimes innerpants))
of knee[2]
--
subpath(xpart(reverse innerpants intersectiontimes knee[2]),
xpart(reverse innerpants intersectiontimes knee[1]))
of reverse innerpants
--
subpath(xpart(knee[1] intersectiontimes innerpants),
xpart(knee[1] intersectiontimes outerpants[1]))
of knee[1]
--
cycle;
grays[3] = subpath(0,
xpart(reverse outerpants[1] intersectiontimes S[1]))
of reverse outerpants[1]
--
reverse subpath(xpart(S[1] intersectiontimes reverse subpath(0,1) of innerpants),
xpart(S[1] intersectiontimes reverse outerpants[1]))
of S[1]
--
reverse subpath(0,
xpart(innerpants intersectiontimes S[1]))
of innerpants
--
cycle;
grays[4] = subpath(0,
xpart(reverse innerpants intersectiontimes S[1]))
of reverse innerpants
--
reverse subpath(xpart (S[1] intersectiontimes reverse outerpants[2]), xpart (S[1] intersectiontimes reverse innerpants))
of S[1]
--
reverse subpath(0,
xpart (reverse outerpants[2] intersectiontimes S[1])) of (reverse outerpants[2])
--
cycle;
% Drawing time
% The planes
draw S[1];
draw S[2];
% Fill
for i = 1 upto 4:
fill grays[i] withcolor 0.75white;
endfor;
draw grays[3];
draw grays[4];
% Fix parts that were filled
draw subpath(xpart (S[2] intersectiontimes reverse outerpants[2]),
xpart (S[2] intersectiontimes reverse outerpants[1]))
of S[2];
draw subpath(xpart (S[1] intersectiontimes reverse outerpants[2]),
xpart (S[1] intersectiontimes reverse innerpants))
of S[1];
draw subpath(xpart (S[1] intersectiontimes innerpants),
xpart (S[1] intersectiontimes reverse outerpants[1]))
of S[1];
% Draw the rest of the parts
draw torso;
draw subpath(0,
xpart(outerpants[1] intersectiontimes waist))
of outerpants[1];
draw subpath(xpart(reverse outerpants[1] intersectiontimes knee[1]),
xpart(reverse outerpants[1] intersectiontimes S[2]))
of reverse outerpants[1];
draw subpath(0,
xpart(reverse outerpants[1] intersectiontimes S[1]))
of reverse outerpants[1];
draw subpath(0,
xpart(innerpants intersectiontimes S[1]))
of innerpants;
draw subpath(xpart(innerpants intersectiontimes knee[1]),
xpart(innerpants intersectiontimes knee[2]))
of innerpants;
draw subpath(xpart(outerpants[2] intersectiontimes torso),
xpart(outerpants[2] intersectiontimes waist))
of outerpants[2];
draw subpath(xpart(reverse outerpants[2] intersectiontimes knee[2]),
xpart(reverse outerpants[2] intersectiontimes S[2]))
of reverse outerpants[2];
for i=1 upto 10:
draw subpath(0,
xpart(seam[i] intersectiontimes reverse waist))
of seam[i];
endfor;
for i=1 upto 5:
draw subpath(xpart(reverse seam[i] intersectiontimes reverse knee[2]),
xpart(reverse seam[i] intersectiontimes S[2]))
of reverse seam[i];
draw subpath(0,
xpart(reverse seam[i] intersectiontimes S[1]))
of reverse seam[i];
endfor;
for i=6 upto 10:
draw subpath(0,
xpart(reverse seam[i] intersectiontimes S[2]))
of reverse seam[i];
endfor;
\stopMPpage
\stoptext