 
 USING: arrays accessors float-arrays io io.files
 io.encodings.binary kernel math math.functions math.vectors
-math.parser make sequences sequences.private words ;
+math.parser make sequences sequences.private words hints ;
 IN: benchmark.raytracer
 
 ! parameters

C: <sphere> sphere

: sphere-v ( sphere ray -- v )
    swap center>> swap orig>> v- ; inline

: sphere-b ( ray v -- b ) swap dir>> v. ; inline

: sphere-disc ( sphere v b -- d )
    sq swap norm-sq - swap radius>> sq + ; inline

: -+ ( x y -- x-y x+y ) [ - ] 2keep + ; inline

: sphere-b/d ( b d -- t )
    -+ dup 0.0 <
    [ 2drop 1.0/0.0 ] [ [ [ 0.0 > ] keep ] dip ? ] if ; inline

: ray-sphere ( sphere ray -- t )
    2dup sphere-v tuck sphere-b [ sphere-disc ] keep
    over 0.0 < [ 2drop 1.0/0.0 ] [ swap sqrt sphere-b/d ] if ;
    inline

: sphere-n ( ray sphere l -- n )
    pick dir>> n*v swap center>> v- swap orig>> v+ ;
    inline

: if-ray-sphere ( hit ray sphere quot -- hit )
    #! quot: hit ray sphere l -- hit
    [
        pick lambda>> [ 2dup swap ray-sphere dup ] dip >=
        [ 3drop ]
    ] dip if ; inline

M: sphere intersect-scene ( hit ray sphere -- hit )
    [ [ sphere-n normalize ] keep <hit> nip ] if-ray-sphere ;

: ray-g ( hit -- g ) normal>> light v. ; inline

: cast-ray ( ray scene -- g )
    2dup initial-intersect dup lambda>> 1/0. = [
        3drop 0.0
    ] [
        [ sray-intersect lambda>> 1/0. = ] keep swap
        [ ray-g neg ] [ drop 0.0 ] if
    ] if ; inline

