Back to index

radiance  4R0+20100331
o_instance.c
Go to the documentation of this file.
00001 #ifndef lint
00002 static const char RCSid[] = "$Id: o_instance.c,v 2.8 2004/03/30 16:13:01 schorsch Exp $";
00003 #endif
00004 /*
00005  *  o_instance.c - routines for computing ray intersections with octrees.
00006  */
00007 
00008 #include "copyright.h"
00009 
00010 #include  "ray.h"
00011 #include  "instance.h"
00012 #include  "rtotypes.h"
00013 
00014 
00015 extern int
00016 o_instance(          /* compute ray intersection with octree */
00017        OBJREC  *o,
00018        register RAY  *r
00019 )
00020 {
00021        RAY  rcont;
00022        double  d;
00023        register INSTANCE  *ins;
00024        register int  i;
00025                                    /* get the octree */
00026        ins = getinstance(o, IO_ALL);
00027                                    /* copy and transform ray */
00028        rcont = *r;
00029        multp3(rcont.rorg, r->rorg, ins->x.b.xfm);
00030        multv3(rcont.rdir, r->rdir, ins->x.b.xfm);
00031        for (i = 0; i < 3; i++)
00032               rcont.rdir[i] /= ins->x.b.sca;
00033        rcont.rmax *= ins->x.b.sca;
00034                                    /* clear and trace it */
00035        rayclear(&rcont);
00036        if (!localhit(&rcont, &ins->obj->scube))
00037               return(0);                  /* missed */
00038        if (rcont.rot * ins->x.f.sca >= r->rot)
00039               return(0);                  /* not close enough */
00040 
00041        if (o->omod != OVOID) {            /* if we have modifier, use it */
00042               r->ro = o;
00043               r->rox = NULL;
00044        } else {                    /* else use theirs */
00045               r->ro = rcont.ro;
00046               if (rcont.rox != NULL) {
00047                      newrayxf(r);         /* allocate transformation */
00048                                    /* NOTE: r->rox may equal rcont.rox! */
00049                      multmat4(r->rox->f.xfm, rcont.rox->f.xfm, ins->x.f.xfm);
00050                      r->rox->f.sca = rcont.rox->f.sca * ins->x.f.sca;
00051                      multmat4(r->rox->b.xfm, ins->x.b.xfm, rcont.rox->b.xfm);
00052                      r->rox->b.sca = ins->x.b.sca * rcont.rox->b.sca;
00053               } else
00054                      r->rox = &ins->x;
00055        }
00056                                    /* transform it back */
00057        r->rot = rcont.rot * ins->x.f.sca;
00058        multp3(r->rop, rcont.rop, ins->x.f.xfm);
00059        multv3(r->ron, rcont.ron, ins->x.f.xfm);
00060        multv3(r->pert, rcont.pert, ins->x.f.xfm);
00061        d = 1./ins->x.f.sca;
00062        for (i = 0; i < 3; i++) {
00063               r->ron[i] *= d;
00064               r->pert[i] *= d;
00065        }
00066        r->rod = rcont.rod;
00067        r->uv[0] = rcont.uv[0];
00068        r->uv[1] = rcont.uv[1];
00069                                    /* return hit */
00070        return(1);
00071 }