[pstricks] passing arguments? in pst3d-solides

Zbigniew Nitecki zbigniew.nitecki at tufts.edu
Wed Jul 21 16:11:26 CEST 2010


Again, I am trying to create a macro to draw three level sets of the function (x^2+y^2)/A^2+z^2/B^2,
one for a positive value (say, =1), one for zero, and one for a negative value (say, -1).

I have successfully created macros to draw each of the three levels separately, with an optional argument for "action",
the default being "action=draw**". (Code for these is copied at the bottom of this message).

Now I am trying to combine the three macros to create a single picture.
The following code draws all three, but of course since they are unrelated graphic objects the appropriate hiding does not occur:

> \begin{pspicture}(-5,-6.5)(3,6.5) 
> 
> \psset{unit=0.75}
> \psset{lightsrc=50 -20 50, viewpoint=20 -0.1 30 rtp2xyz,
> 	Decran=50}
> %\psset{solidmemory}
> %
> \cuthyperboloid{0.5}{1.0}{4}{20}{20}{gray!85}{gray!45}{4}	
> \cutcone{0.5}{1.0}{3.6}{20}{20}{red!65}{red!15}{2}	
> \hyperboloidtwosheet {0.5}{1.0}{1.8}{20}{20}{blue!55}{blue!15}	
> %%
> %\psSolid[
> %	object=fusion,
> %	action=draw**,
> %	base=cuthyperboloid cutcone hyperboloidtwosheet, 
> %]
> %%
> %\composeSolid
> \end{pspicture}


Here is the resulting picture:



However, when I uncomment the \psset{solidmemory} command
as well as the \pstSolid[object=fusion... and \composeSolid commands,
and insert [none] at the beginning of each of the three argument lists,
I get an error message
> Error: /undefined in cuthyperboloid
> Operand stack:
>    base   --nostringval--
> Execution stack:
>    %interp_exit   .runexec2   --nostringval--   --nostringval--   --nostringval--   2   %stopped_push   --nostringval--   --nostringval--   --nostringval--   false   1   %stopped_push   1862   1   3   %oparray_pop   1861   1   3   %oparray_pop   1845   1   3   %oparray_pop   1739   1   3   %oparray_pop   --nostringval--   %errorexec_pop   .runexec2   --nostringval--   --nostringval--   --nostringval--   2   %stopped_push   --nostringval--
> Dictionary stack:
>    --dict:1150/1684(ro)(G)--   --dict:0/20(G)--   --dict:80/200(L)--   --dict:771/1012(L)--   --dict:175/300(L)--   --dict:38/200(L)--   --dict:122/200(L)--
> Current allocation mode is local
> Last OS error: 2
> Current file position is 432819
> GPL Ghostscript 8.70: Unrecoverable error, exit code 1
> ### FAILED to generate /tmp/altpdflatex.47607-1279721078/pst3dtest5.1.pdf ()


It appears that something is not getting through, but I can't see what it is, or how.

On a related but different question, is there a way I could turn the master command into a macro calling the other three,
whose inputs would be similar to the above, but with the height of each adjusted from a single input value h so that the height
is a different fraction of h depending on which surface is being defined;  along the same lines, so that I input two colors, say color1
and color2, and the calls to the two hyperboloid macros would enter for theme an incolor value color1!65 for the fillcolor and color1!25 for the incolor 
(for the first surface, and same but with color2 instead of color1 for the second)?
I guess this question is, how can I get the macro to compute something from input that could then be used as an input to one of the called macros?
Of course, answering this question is only useful if I can resolve the first problem.

> %************************************************************************
> \newcommand{\cuthyperboloid}[9][draw**]{%
> %surface (x^{2}+y^{2})/A^{2}-z^{2}/B^{2}=1
> %	action=#1:  default= draw**,  alternative=none
> %	A=#2
> %	B=#3
> %	h=#4  (total height of hyperboloid)
> %	a=#5 number of levels (vertical division)
> %	b=#6 number of meridians (division of circles)
> %	#7=fillcolor
> %	#8=incolor
> %	#9=number of cells removed at each level
> \psSolid
> [
> 	object=new,
> 	fillcolor=#7,
> 	incolor=#8,
> 		hollow, 
> 	a=#5, %% nb d’etages 
> 	b=#6, %% diviseur de 360, nb de meridiens 
> 	h=#4, %% hauteur
> %	c=#9
> 						%one cell automatically taken off;
> %	/c1 {#9 2 idiv} def		%c1=number of extra cells to take off on right
> %	/c2 {#9 1 sub 2 idiv} def	%c2=number of extra cells to take off on left 
> 	sommets=
> 		/A #2 def
> 		/B #3 def
> 		/z0 h neg 2 div def 	%z0:=-h/2
> %		/a1 a 1 add 2 idiv 2 mul def	%a1=floor{(a+1)/2}*2=a if even, a+1 if odd
> %				% (make no. facelevels even by subdividing middle one into two
> %				% (for consistency with \cutcone)
> %		 a 1 add 2 idiv 2 mul 
> 		a
> 		 -1 
> 		 0 
> 		{
> 			/k exch def	%k:=counter1
> 			0 1 b 1 sub 				
> 			%stack is a  0  0  1  b-1
> 				{
> 					/i exch def 		%i:=counter2
> 					/r z0 h a div 
> 						 k mul 
> 						add
> 						B div 
> 						dup mul 
> 						1 add
> 						sqrt 
> 						A mul
> 						def 
> 								%r:=A*\sqrt{(({hk/a}+z0)^2)/B^{2}+1}
> 					360 b idiv 
> 					i mul 
> 					cos r mul 		%add to stack r*cos([360/b]i)
> 					360 b idiv 
> 					i mul 
> 					sin r mul 		%add to stack r*sin([360/b]i)
> 					z0 h a div 
> 					k mul 
> 					add			%add to stack (hk/a)+z0
> 				} for 
> 				% stack is 0 0 1 b-1 {r*cos([360/b]i) r*sin([360/b]i) (hk/a)+z0}
> 				% so: for counter2 starting at 0
> 				%	incremented by 1
> 				%	until b-1
> 				%	calculate   r*cos([360/b]i) r*sin([360/b]i) (hk/a)+z0
> 		} for
> 		% stack is a -1 0
> 		% so: for counter1 starting at a
> 		% decreased by 1
> 		% until 0
> 		% do the calculation of the three quantities above (for the values in that loop)
> 	, 
> 	faces=
> 	{
> 								%one cell automatically taken off;
> 		/c1 {#9 2 idiv} def		%c1=number of extra cells to take off on right
> 		/c2 {#9 1 sub 2 idiv} def	%c2=number of extra cells to take off on left 
> 		0 
> 		1 
> %		a 1 add 2 idiv 2 mul 1 sub
> 		a 1 sub
> 		% stack is 0 1 a1-1 
> 		{ 
> 			/k exch def 	% k:=counter1
> 				k b mul 
> 				1 add 	% kb+1
> 				c1 add	% kb+1+c1
> 				1 
> 				k 1 add
> 				b mul 	
> 				1 
> 				sub	 % (k+1)b-1
> 				c2 sub %(k+1)b-1-c2
> 				% stack is kb+1+c1  1 (k+1)b-1-c2
> 				{ 
> 					/i exch def %i=counter1?
> 					[
> 						i 		
> 						i 1 sub		% i-1
> 						b i add 1 sub 	% b+i-1
> 						b i add		%b+i
> 					]
> 				} for 
> 				% for counter2 starting at kb+1
> 				% incremented by 1
> 				% until (k+1)b-1
> 				% calculate the array above
> %				[
> %					k b mul 	% kb
> %					k 1 add 
> %					b mul 		
> %					1 sub 		% (k+1)b-1
> %					k 2 add 
> %					b mul 
> %					1 sub 		% (k+2)b-1
> %					k 1 add
> %					b mul		% (k+1)b
> %				] 
> 		} for
> 		% for counter1 starting at 0
> 		% incremented by 1
> 		% until a-1
> 		% calculate the array (4 elements) above
> 	}, 
> 	action=#1,
> 	name=cuthyperboloid,
> ]
> }
> 
> %************************************************************************************
> \newcommand{\cutcone}[9][draw**]{%
> %	cone with vertical cut opened
> %	action=#1default is draw**;  alternative is none
> %	A=#2
> %	B=#3
> %	h=#4  (total height of hyperboloid)
> %	a=#5 number of levels (vertical division)
> %	b=#6 number of meridians (division of circles)
> %	#7=fillcolor
> %	#8=incolor
> %	#9=number of cells removed at each level
> \psSolid
> [
> 	object=new,
> 	fillcolor=#7,
> 	incolor=#8,
> 		hollow, 
> 	a=#5, %% nb d’etages 
> 	b=#6, %% diviseur de 360, nb de meridiens 
> 	h=#4, %% hauteur
> %	c=#9
> 						%one cell automatically taken off;
> %	/c1 {#9 2 idiv} def		%c1=number of extra cells to take off on right
> %	/c2 {#9 1 sub 2 idiv} def	%c2=number of extra cells to take off on left 
> 	sommets=
> 		/A #2 def
> 		/B #3 def
> 		/z0 h neg 2 div def 	%z0:=-h/2
> 		/a1 a 1 add 2 idiv 2 mul def	%a1=floor{(a+1)/2}*2=a if even, a+1 if odd
> 				% (make no. facelevels even by subdividing middle one into two
> %		 a 1 add 2 idiv 2 mul 
> 		 a  
> 		 -1 
> 		 0 
> 		{
> 			/k exch def	%k:=counter1
> 			0 1 b 1 sub 				
> 			%stack is a  0  0  1  b-1
> 				{
> 					/i exch def 		%i:=counter2
> 					/z z0 h a1 div k mul add def  %z=(hk/a1)+z0
> 					/r z abs A mul B div def	%r=Az/B
> 					360 b idiv 
> 					i mul 
> 					cos r mul 		%add to stack r*cos([360/b]i)
> 					360 b idiv 
> 					i mul 
> 					sin r mul 		%add to stack r*sin([360/b]i)
> 					z
> 				} for 
> 				% stack is 0 0 1 b-1 {r*cos([360/b]i) r*sin([360/b]i) (hk/a)+z0}
> 				% so: for counter2 starting at 0
> 				%	incremented by 1
> 				%	until b-1
> 				%	calculate   r*cos([360/b]i) r*sin([360/b]i) (hk/a)+z0
> 		} for
> 		% stack is  a1 -1 0
> 		% so: for counter1 starting at a1=floor{(a+1)/2}*2
> 		% decreased by 1
> 		% until 0
> 		% do the calculation of the three quantities above (for the values in that loop)
> 	, 
> 	faces=
> 	{
> 								%one cell automatically taken off;
> 		/c1 {#9 2 idiv} def		%c1=number of extra cells to take off on right
> 		/c2 {#9 1 sub 2 idiv} def	%c2=number of extra cells to take off on left 
> 		0 
> 		1 
> 		a 1 add 2 idiv  1 sub
> %
> 		% stack is 0 1{(a2=floor{(a+1)/2}) -1} 
> 		{ 
> 			/k exch def 	% k:=counter1
> 				k b mul 
> 				1 add 	% kb+1
> 				c1 add	% kb+1+c1
> 				1 
> 				k 1 add
> 				b mul 	
> 				1 
> 				sub	 % (k+1)b-1
> 				c2 sub %(k+1)b-1-c
> 				% stack is kb+1+c  1 (k+1)b-1-c
> 				{ 
> 					/i exch def %i=counter2
> 					[
> 						i 		
> 						i 1 sub		% i-1
> 						b i add 1 sub 	% b+i-1
> 						b i add		%b+i
> 					]
> 				} for 
> 		} for
> 		% for counter1 starting at 0
> 		% incremented by 1
> 		% until a2
> 		% calculate the array (4 elements) above
> %
> %%
> 		/k a 1 add 2 idiv  1 sub def
> 		%row above tip of upper cone
> 				k b mul 
> 				1 add 	% kb+1
> 				c1 add	% kb+1+c1
> 				1 
> 				k 1 add
> 				b mul 	
> 				1 
> 				sub	 % (k+1)b-1
> 				c2 sub %(k+1)b-1-c
> 				% stack is kb+1+c  1 (k+1)b-1-c
> 				{ 
> 					/i exch def %i=counter2
> 					[
> 						i 		
> 						i 1 sub		% i-1
> 						b i add 1 sub 	% b+i-1
> %						b i add		%b+i			%eliminate extra zero vertex
> 					]
> 				} for 
> %
> 		/k a 1 add 2 idiv  def
> %		% row below tip of lower cone		
> 				k b mul 
> 				1 add 	% kb+1
> 				c1 add	% kb+1+c1
> 				1 
> 				k 1 add
> 				b mul 	
> 				1 
> 				sub	 % (k+1)b-1
> 				c2 sub %(k+1)b-1-c
> 				% stack is kb+1+c  1 (k+1)b-1-c
> 				{ 
> 					/i exch def %i=counter2
> 					[
> 						i 		
> %						i 1 sub		% i-1			%eliminate extra zero vertex
> 						b i add 1 sub 	% b+i-1
> 						b i add		%b+i
> 					]
> 				} for 
> %		} for
> %
> %
> 		a 1 add 2 idiv  1 add
> 		1
> 		a 1 add 2 idiv 2 mul 1 sub
> 		% stack is {(a2=floor{(a+1)/2})+1} 1{(a1=floor{(a+1)/2}*2)-1}  
> 		{ 
> 			/k exch def 	% k:=counter1
> 				k b mul 
> 				1 add 	% kb+1
> 				c1 add	% kb+1+c1
> 				1 
> 				k 1 add
> 				b mul 	
> 				1 
> 				sub	 % (k+1)b-1
> 				c2 sub %(k+1)b-1-c
> 				% stack is kb+1+c  1 (k+1)b-1-c
> 				{ 
> 					/i exch def %i=counter2
> 					[
> 						i 		
> 						i 1 sub		% i-1
> 						b i add 1 sub 	% b+i-1
> 						b i add		%b+i
> 					]
> 				} for 
> 		} for
> 		% for counter1 starting at a2
> 		% incremented by 1
> 		% until a1-1
> 		% calculate the array (4 elements) above
> 	}, 
> 	action=#1,
> 	name=cutcone,
> ]
> }
> %************************************************************************************************
> \newcommand{\hyperboloidtwosheet}[8][draw**]{%
> %surface (x^{2}+y^{2})/A^{2}-z^{2}/B^{2}=-1
> %	action=#1:  default= draw**,  alternative=none
> %	A=#2
> %	B=#3
> %	h=#4  (total height of hyperboloid)
> %	a=#5 number of levels (vertical division)
> %	b=#6 number of meridians (division of circles)
> %	#7=fillcolor
> %	#8=incolor
> %
> %%
> 
> \defFunction{hypup}(u,v)
> 	{u v cos mul}
> 	{u v sin mul}
> 	{u #2 div dup mul 1 add sqrt #3 mul}
> \psSolid[
> 	object=surfaceparametree,
> 	base=0 #4 #3 div dup mul 1 sub #2 mul 0 360,
> 	fillcolor=#7,
> 	incolor=#8,
> 	function=hypup,
> 	ngrid=#5 #6,
> 	action=none,
> 	name=inner1,
> ]
> \defFunction{hypdown}(u,v)
> 	{u v cos mul}
> 	{u v sin mul}
> 	{u #2 div dup mul 1 add sqrt #3 mul neg}
> \psSolid[
> 	object=surfaceparametree,
> 	base=0 #4 #3 div dup mul 1 sub #2 mul 0 360,
> 	fillcolor=#7,
> 	incolor=#8,
> 	function=hypdown,
> 	ngrid=#5 #6,
> 	action=none,
> 	name=inner2,
> ]
> \psSolid[
> 	object=fusion,
> 	action=#1,
> 	base=inner1 inner2, 
> ]
> %
> \composeSolid
> }
> %************************************************************************************************




Zbigniew Nitecki
Department of Mathematics
Tufts University
Medford, MA 02155

telephones:
Office    (617)627-3843
Dept.    (617)627-3234
Dept. fax    (617)627-3966
http://www.tufts.edu/~znitecki/

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://tug.org/pipermail/pstricks/attachments/20100721/331083ce/attachment-0002.html>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: pst3dtest5.1.pdf
Type: application/pdf
Size: 51843 bytes
Desc: not available
URL: <http://tug.org/pipermail/pstricks/attachments/20100721/331083ce/attachment-0001.pdf>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://tug.org/pipermail/pstricks/attachments/20100721/331083ce/attachment-0003.html>


More information about the PSTricks mailing list