// Persistence of Vision Ray Tracer Include File
//          File: book.inc
//       Version: 3.1g
//   Description: a book with the pages blowing
//       Created: 10/24/1999 
// Last Modified: 10/26/1999 
//        Author: Heather Cousineau

//\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\
//                                OPEN BOOK MACRO                              //
// This macro creates a book that can be opened to any angle and the pages     //
// will be distributed at equal intervals between the cover                    //
//                                                                             //
// Although setting the angle to 0 will yeild a closed book, it is not an      //
// exciting closed book, as all the pages end up flat, so you can only see the //
// cover.                                                                      //
//\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\
//												VARIABLES											 //
// The macro includes the following variables:											 //
//		numPgs  		  - the number of pages in the book                          //
//    degreesOpen   - number of degrees the book is open                       //  
//    flatPagesBack - number of pages on the back of the book                  //
//    flatPagesCover- number of pages on the cover side of the book            //
//    windStrength  - higher numbers gives the impression of                   //
//					 		 a stronger wind.                                         //
//		chaosOfWind   - the higher the number the more twisted the pages are     //
// 						 as if the wind were blowing in circles                   //
//		thickOfCover  - how thick the book cover is                              //
//		roundOfCover  - how far out the rounding goes                            //
//    heightOfBook  - how tall the cover is                                    //
//    widthOfBook   - how wide the cover is                                    //
//		pagesTexture  - the texture of the pages, it is on each individual page  //
//       frontCoverTexture - The front cover texture                           //
//	      useCoverPic       - 0 = don't use cover pic, 1 = use cover pic        //
//	      frontCoverPic     - the front cover pic, if useCoverPic = 2, just put //
//                           some gibberish in like: "none"                    //
//    frontCoverTexture    - Texture on the front cover                        //
//    backCoverTexture     - texture on the back cover                         //
//    bindingCoverTexture  - texture on the binding                            //
//    spiral       - pass either a 0 or 1, 0 for normal 1 for spiral           //
//\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\
//												SCALING												 //  
//	* The scaling dimesions are for the front cover. 									 //
// * Setting heightOfBook & widthOfBook to 1 gives you a 1 unit x 1 unit cover //
//   * note that when it is open 180 degrees, the book is twice as wide 		 //
// * Opens on to the x-axis                                                    //
//\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\
//											TESTING AND EXAMPLE 									 //
// #include "colors.inc"                                                       //
// camera{location <2,2,-2> look_at 0*z}                                       //
// background { color rgb 0 }                                                  //
// light_source{<10,10,-10>,1 White}                                           //
// plane{y,-3 pigment {Red}}                                                   //  
// ----------------------------------------------------------------------------//
// EXAMPLE:                                                                    //
// openBook (15, 180,         // numPgs,      degreesOpen,                     //
//           75,  50,         // flatPagesBack, flatPagesCover                 //
//	   	     2,   2,         // windStrength, chaosOfWind,                    //
//	   	   .03, .25,  	      // thickOfCover, roundOfCover,                   //
//	   	     1,   1,         // heightOfBook, widthOfBook                     //
//	   		 pigment{White},  // pagesTexture                                  //
//	   		   pigment{Red},  // frontCoverTexture,                            //
//	   		   0,             // useCoverPic                                   //
//	   		   "none",        // frontCoverPic,                                //
//	   		 pigment{Blue},   // backCoverTexture                              //
//	   		 pigment{Grey},   // bindingCoverTexture)                          //
//	   		 0)  // spiral (0=normal 1=spiral)                                 //
//\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\ 
//											KNOWN PROBLEMS											 //  
//	* If you put in too many pages they bend very unaturally							 //  
// * It gets really weird if you open it more than 360 degrees                 //
//\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\
//											IN THE FUTURE											 //
//	* I would like to put in a binding that looks like a binding                //
//\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\ 
//                                CLOSED BOOK                                  //
// It is now possible to create a closed book, but only under one circumstance //
// * set the angle to 0                                                        //
// * set the flatPagesCover to 0                                               //
// * set the number of pages 50                                                // 
// ----------------------------------------------------------------------------//
// EXAMPLE:                                                                    //
// openBook (15,   0,         // numPgs,      degreesOpen,                     //
//            0,  50,         // flatPagesBack, flatPagesCover                 //
//	   	     2,   2,         //windStrength, chaosOfWind,                     //
//	   	   .03, .25,  	      //thickOfCover, roundOfCover,                    //
//	   	     1,   1,         //heightOfBook, widthOfBook                      //
//	   		 pigment{White},  //pagesTexture                                   //
//	   		   pigment{Red},  //frontCoverTexture,                             //
//	   		   1,             //useCoverPic                                    //
//	   		   "plasma3.gif", //frontCoverPic,                                 //
//	   		 pigment{Blue},   //backCoverTexture                               //
//	   		 pigment{Grey},   //bindingCoverTexture)                           //
//	   		 0)  // spiral (0=normal 1=spiral)                                 //
//\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\/\ 


#macro openBook ( numPgs,		    degreesOpen,
   	            flatPagesCover, flatPagesBack
						windStrength,   chaosOfWind, 
						thickOfCover,   roundOfCover, 
						heightOfBook,   widthOfBook
						pagesTexture, 
					      frontCoverTexture, 
					      useCoverPic
					      frontCoverPic,
					   backCoverTexture, 
					   bindingCoverTexture
					   spiral)

	#local front_cover_texture   = texture{frontCoverTexture}
	#local back_cover_texture    = texture{backCoverTexture}   
	#local binding_cover_texture = texture{bindingCoverTexture}   
	#local book_pages_texture    = texture{pagesTexture}
	
	// randomness for the pages
	#local thetaRnd = (rand(seed(1))-.5)/10;
	#local tipRnd   = (rand(seed(2))-.5);  
	#local tipRnd2   = (rand(seed(2))-.5);
	
	// A whole bunch of Variables           
	#local wind = windStrength;
	
	#local numPages = numPgs; 
	#local numPages = numPages -1; // adjusts for off-by-one problem
	#local page = 0;   
	#local rim = 0;
	#local endVar = degreesOpen*(pi/180)-.1;
	#local t1V = 0; #local t1Vend = endVar;
	#local t2V = 0; #local t2Vend = endVar;
	#local t3V = 0; #local t3Vend = endVar;   
	#local adj = abs(wind/numPages);
	#local chaosOfWind = chaosOfWind;      
	
	#local thick = thickOfCover; // how thick the cover is
	#local rS    =  .5; // .5 the width of the binding
	
// ------------------------------ The pages ------------------------------    
		   
	#macro flatPageBack(numFlatPages) 
	union { 
	   #local ctrFP = 0;
	   #local yAdj = 0; 
	   #while (ctrFP < numFlatPages)	   
		   bicubic_patch
			{
			  type 1 // patch_type (0..1)
			  flatness 0 // flatness value (lower = flatter)
			  u_steps 3  v_steps 3 
			  // back   nBack    nFront  front
			  <rS,yAdj,0> <1,yAdj,0> <2,yAdj,0> <3,yAdj,0>  // Rim  (0)
			  <rS,yAdj,1> <1,yAdj,1> <2,yAdj,1> <3,yAdj,1>  // nRim (1)
			  <rS,yAdj,3> <1,yAdj,3> <2,yAdj,3> <3,yAdj,3>  // nEnd (2)
			  
			  <rS,yAdj,5-yAdj*yAdj>
			  <1,yAdj,5-yAdj*yAdj>  
			  <2,yAdj,5-yAdj*yAdj> 
			  <3,yAdj,5-yAdj*yAdj>  // end  (3) 
			  texture {pagesTexture}
		}            
		   #local ctrFP = ctrFP + 1; 
		   #local yAdj = yAdj + .01;
		  #end  
	}
   #end 
   
	#macro flatPageCover(numFlatPages) 
	union { 
	   #local ctrFP = 0;
	   #local yAdj = 0; 
	   #while (ctrFP < numFlatPages)	   
		   bicubic_patch
			{
			  type 1 // patch_type (0..1)
			  flatness 0 // flatness value (lower = flatter)
			  u_steps 3  v_steps 3 
			  // back   nBack    nFront  front
			  <0,yAdj,0> <1,yAdj,0> <2,yAdj,0> <3,yAdj,0>  // Rim  (0)
			  <0,yAdj,-1><1,yAdj,-1><2,yAdj,-1><3,yAdj,-1>  // nRim (1)
			  <0,yAdj,-3><1,yAdj,-3><2,yAdj,-3><3,yAdj,-3>  // nEnd (2)
			  
			  <0,yAdj,-5+yAdj*yAdj>
			  <1,yAdj,-5+yAdj*yAdj>  
			  <2,yAdj,-5+yAdj*yAdj> 
			  <3,yAdj,-5+yAdj*yAdj>  // end  (3) 
			  
			  texture {pagesTexture}
			  rotate <180-degreesOpen,0,0> 
		   }            
		   #local ctrFP = ctrFP + 1; 
		   #local yAdj = yAdj + .01;
		  #end  
	}
   #end


	#local flying_pages = union
	{
		#while (page <= numPages)  
			#local y1V =  1*sin(t1V);      
			#local z1V =  1*cos(t1V); 
			#local y2V =  4*sin(t2V);
			#local z2V =  4*cos(t2V); 
			#local y3V =  5*sin(t3V);
			#local z3V =  5*cos(t3V);   
			#local tipRnd    = (rand(seed(2))-.5)*chaosOfWind;  
			#local tipRnd2   = (rand(seed(3))-.5)*chaosOfWind;
			
		   bicubic_patch
			{
			  type 1 // patch_type (0..1)
			  flatness 0 // flatness value (lower = flatter)
			  u_steps 3  v_steps 3 
			  // back     			nBack        nFront     front
			  <0,0,rim>   			<1,0,rim>   <2,0,rim>   <3,0,rim>   	     // Rim  (0)
			  <0,y1V,z1V> 			<1,y1V,z1V> <2,y1V,z1V> <3,y1V,z1V>  		  // nRim (1)
			  <0,y2V,z2V> 			<1,y2V,z2V> <2,y2V,z2V> <3,y2V,z2V> 		  // nEnd (2)
			  <0,y3V,z3V+tipRnd2><1,y3V,z3V> <2,y3V,z3V> <3,y3V,z3V+tipRnd>  // end  (3) 
			  texture {book_pages_texture }
			}
			
			#local page = page + 1;
	
			#local t1V = t1V + t1Vend/numPages;	
			#if(wind = 0 )												// if the wind is 0, 
				#local t2V = t2V + t2Vend/numPages;        // then, don't adjust it
				#else													   
					#local t2V = t2V + t2Vend/numPages*adj;	
					#end
			#local t3V = t3V + t3Vend/numPages;	
		   #local adj = adj + adj/numPages+thetaRnd;
			#local rim = rim +.1;
		#end           
	}         
   // ----- COVER -----
	#local front_part = union
	{  object{
         superellipsoid{<.3,.2>            
            #if(degreesOpen = 0)
               translate -6*y
            #end
            scale <.6,thick,.6> 
            translate -rS*x 
            
            texture {frontCoverTexture} 
            #if(useCoverPic = 1)
               texture
               {
                  pigment
                  {  
                     image_map { gif frontCoverPic map_type 0 interpolate 2 once }
                     rotate x*90 // lay X-Y image map down onto X-Z height field plane 
                     translate <-1,0,-.5>
                  }     
               }
            #end            

   }  }  } 

   #local back_part = union
	{      
	   object{
         superellipsoid{<.3,.2>            
            scale <.6,thick,.6> 
            translate rS*x            
            texture {backCoverTexture}
   }  }  }
	
   //  ------ BINDING ------	
   #if (spiral = 0)
      #local binder = 
      object{
         superellipsoid{<.3,.2>            
            #if(degreesOpen = 0)
               scale <(flatPagesBack*.002),thick,.6>
            #else
               scale <.05,thick,.6>
            #end
         } 
         rotate <0,0,-(180-degreesOpen)/2> 
      } 
   #end      
   
   #if(spiral = 1)
     #local binder = union 
      {
         #local ctr = -.5;
         #local tVar = 0;
         	#while (tVar < 76)
         	   sphere{<sin(tVar)/10,cos(tVar)/10,ctr> .007 texture {binding_cover_texture}}
         	   #local tVar = tVar + .01;
         	   #local ctr = ctr + 1/7200;
        	   #end 
      }
   #end 
   
     
   // ----- PUT THE BOOK TOGETHER -----
	#local book = union
	{
	   union
   	{  
   	   flatPageBack(flatPagesBack)
   	   flatPageCover(flatPagesCover)
   		object {flying_pages translate <0,(flatPagesBack*.01),-.5>}  
   		translate <-1.5,0,0>
   	   scale <1/3,1/5,1/5>
   	   rotate 90*y
   	}          
	   union 
	   {
   	   object {binder texture{bindingCoverTexture}}    
   	   union 
   	   {
   	      object {back_part }
      	   object {front_part  rotate (180+degreesOpen)*z }
      	   #if(degreesOpen = 0) translate -((flatPagesBack*.002))*y #end
      	}
      }
	}
	   
	// ----- FINAL OBJECT DECLARATION -----
	object {book scale <heightOfBook,widthOfBook,widthOfBook>}	

#end 


