POV-Ray : Newsgroups : povray.advanced-users : [Long] Points on a sphere? Not really. : [Long] Points on a sphere? Not really. Server Time
29 Jul 2024 14:14:30 EDT (-0400)
  [Long] Points on a sphere? Not really.  
From: Deaken
Date: 16 Jan 2002 06:16:22
Message: <3C45612B.22351095@sw-tech.com>
A few things by way of introduction:

I'm not an advanced user, but it was suggested that this problem belongs
here.

I know that this problem has already been solved.  I know that it's
amazingly inefficient to do this as a macro instead of just importing
the points.  Neither of those, however, are the real issue anymore.

The real issue is that I am trying to convert spherepoints.c to a macro,
and I keep failing.  Well, actually, it works, it just gives different
results than I expect.  I would like someone with more skill than I at
SDL (or perhaps C, since neither are my "native language") to explain
where I am going astray in the conversion.  This strikes me as a useful
skill to have, and when something this simple is beyond my grasp, well,
I'd like to understand why, and try to fix it.

I've trimmed this down as much as I could.  Please forgive the size.

Um, if word-wrapping kills the formatting, please assume that it is
correct in the source files.

The source code to spherepoints.c can be found at
<URL:http://astronomy.swin.edu.au/pbourke/geometry/spherepoints/>.  I
have made the following minor changes, which should be obvious to place.

   /* Create the initial random cloud */
/*   for (i=0;i<n;i++) { */
       p[0].x = (0.2);
       p[0].y = (0.3);
       p[0].z = (0.5);
       Normalise(&p[0],r);
       p[1].x = (0.8);
       p[1].y = (0.1);
       p[1].z = (0.2);
       Normalise(&p[1],r);
       p[2].x = (0.0);
       p[2].y = (0.4);
       p[2].z = (0.7);
       Normalise(&p[2],r);
       p[3].x = (0.9);
       p[3].y = (0.2);
       p[3].z = (0.5);
       Normalise(&p[3],r);
/*    } */

[...]

    /* Write out the points in your favorite format */
    for (i=0;i<n;i++) {
      printf("#declare X%d = <%f,%f,%f>;\n",
       i,
       p[i].z, p[i].y, p[i].x
      );
    }
/* xyz xzy yxz yzx zxy zyx */

Here is my faulty macro.

#declare MovePercent = 1;
// This will be changed to 5% once it works, to speed up the macro a
bit.
#declare PlusElem = 1 + ( MovePercent / 100 );
#declare MinusElem = ( MovePercent / 100 );
#macro Normalize ( Vector )
  Vector / vlength ( Vector )
#end
#macro MyThing ( NumDots, Iters )
  #declare DotsArray = array[NumDots]
//  #declare Loop = 0;
//  #while ( Loop < NumDots )
//    #declare DotsArray[Loop] = Normalize (
<(rand(R1)*2)-1,(rand(R1)*2)-1,(rand(R1)*2)-1> );
//    #declare Loop = Loop + 1;
//  #end
  #declare DotsArray[0] = Normalize ( <0.2, 0.3, 0.5> );
  #declare DotsArray[1] = Normalize ( <0.8, 0.1, 0.2> );
  #declare DotsArray[2] = Normalize ( <0.0, 0.4, 0.7> );
  #declare DotsArray[3] = Normalize ( <0.9, 0.2, 0.5> );
  #declare Loop = 0;
  #while ( Loop < Iters )
    #declare MinP1 = 0;
    #declare MinP2 = 1;
    #declare MinD = vlength ( DotsArray[MinP1] - DotsArray[MinP2] );
    #declare MaxD = MinD;
    #declare SubLoopI = 0;
    #while ( SubLoopI < ( NumDots - 1 ) )
      #declare SubLoopJ = ( SubLoopI + 1 );
      #while ( SubLoopJ < NumDots )
        #declare CheckD = vlength ( DotsArray[SubLoopI] -
DotsArray[SubLoopJ] );
        #if ( CheckD < MinD )
          #declare MinD = CheckD;
          #declare MinP1 = SubLoopI;
          #declare MinP2 = SubLoopJ;
        #end
        #if ( CheckD > MaxD )
          #declare MaxD = CheckD;
        #end
        #declare SubLoopJ = ( SubLoopJ + 1 );
      #end
      #declare SubLoopI = ( SubLoopI + 1 );
    #end
    #declare P1 = DotsArray[MinP1];
    #declare P2 = DotsArray[MinP2];
    #declare DotsArray[MinP2] = Normalize (
      (
        <
          ( DotsArray[MinP1].x + PlusElem ) * ( DotsArray[MinP2].x -
DotsArray[MinP1].x ),
          ( DotsArray[MinP1].y + PlusElem ) * ( DotsArray[MinP2].y -
DotsArray[MinP1].y ),
          ( DotsArray[MinP1].z + PlusElem ) * ( DotsArray[MinP2].z -
DotsArray[MinP1].z ),
        >
      )
    );
    #declare DotsArray[MinP1] = Normalize (
      (
        <
          ( DotsArray[MinP1].x - MinusElem ) * ( DotsArray[MinP2].x -
DotsArray[MinP1].x ),
          ( DotsArray[MinP1].y - MinusElem ) * ( DotsArray[MinP2].y -
DotsArray[MinP1].y ),
          ( DotsArray[MinP1].z - MinusElem ) * ( DotsArray[MinP2].z -
DotsArray[MinP1].z ),
        >
      )
    );
    #declare Loop = Loop + 1;
  #end
  union {
    sphere {
      <0,0,0>, 1
      texture { pigment { color rgbt <0.7, 1, 0.7, 0.8+0.15> } }
    }
    #declare Loop = 0;
    #while ( Loop < NumDots )
      sphere {
        DotsArray[Loop]*0.9825,
        0.025
        texture {
          pigment {
            color rgbt <0, 1, 0, 0.5>
          }
        }
      }
      #declare Loop = Loop + 1;
    #end
  }
#end

I then do this:

#declare R1 = seed ( 2 );
object { MyThing ( 4, 10000 ) }
// This is the output from spherepoints
#declare X0 = <0.661471,-0.572393,0.484585>;
#declare X1 = <-0.910131,-0.285771,0.299995>;
#declare X2 = <0.152255,0.950505,0.270848>;
#declare X3 = <0.089845,-0.084676,-0.992350>;
#declare Test4_10K = union {
  cylinder { X0, X1, 0.01 }
  cylinder { X0, X2, 0.01 }
  cylinder { X0, X3, 0.01 }
  cylinder { X1, X2, 0.01 }
  cylinder { X1, X3, 0.01 }
  cylinder { X2, X3, 0.01 }
}
object { Test4_10K }

Yes, I've tried all possible permutations of X, Y and Z coordinates in
the spherepoints output.  I invoke the program as "./spherepoints 4 1
10000".

I thought the problem might be in the multi-line DotsArray[MinP2] (and
MinP1) statements, but I've tried many things there, and none of them
have worked.

The person for whom I offered to do this has pretty much accepted the
idea that it would be "better", if less "elegant", to use the output of
spherepoints in a .inc file, instead of running a 40-hour macro, but
this has moved from a specific problem to a general one, in my opinion. 
Any pointers would be gratefully accepted.

Thank you.

Deaken


Post a reply to this message

Copyright 2003-2023 Persistence of Vision Raytracer Pty. Ltd.