This repository has been archived on 2023-10-09. You can view files and clone it, but cannot push or open issues or pull requests.
Files
blender-archive/source/blender/render/intern/source/rayobject_blibvh.c

141 lines
3.5 KiB
C
Raw Normal View History

2009-05-29 22:55:06 +00:00
/**
* $Id$
*
* ***** BEGIN GPL LICENSE BLOCK *****
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software Foundation,
* Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*
* The Original Code is Copyright (C) 2009 Blender Foundation.
* All rights reserved.
*
* The Original Code is: all of this file.
*
* Contributor(s): André Pinto.
*
* ***** END GPL LICENSE BLOCK *****
*/
#include <assert.h>
#include "MEM_guardedalloc.h"
#include "BKE_utildefines.h"
#include "BLI_kdopbvh.h"
#include "BLI_arithb.h"
#include "RE_raytrace.h"
#include "render_types.h"
#include "rayobject.h"
static int RE_rayobject_blibvh_intersect(RayObject *o, Isect *isec);
static void RE_rayobject_blibvh_add(RayObject *o, RayObject *ob);
static void RE_rayobject_blibvh_done(RayObject *o);
static void RE_rayobject_blibvh_free(RayObject *o);
static void RE_rayobject_blibvh_bb(RayObject *o, float *min, float *max);
2009-05-29 22:55:06 +00:00
static RayObjectAPI bvh_api =
{
RE_rayobject_blibvh_intersect,
RE_rayobject_blibvh_add,
RE_rayobject_blibvh_done,
RE_rayobject_blibvh_free,
RE_rayobject_blibvh_bb
2009-05-29 22:55:06 +00:00
};
typedef struct BVHObject
{
RayObject rayobj;
BVHTree *bvh;
float bb[2][3];
2009-05-29 22:55:06 +00:00
} BVHObject;
RayObject *RE_rayobject_blibvh_create(int size)
2009-05-29 22:55:06 +00:00
{
BVHObject *obj= (BVHObject*)MEM_callocN(sizeof(BVHObject), "BVHObject");
assert( RE_rayobject_isAligned(obj) ); /* RayObject API assumes real data to be 4-byte aligned */
2009-05-29 22:55:06 +00:00
obj->rayobj.api = &bvh_api;
obj->bvh = BLI_bvhtree_new(size, 0.0, 4, 6);
2009-05-29 22:55:06 +00:00
INIT_MINMAX(obj->bb[0], obj->bb[1]);
return RE_rayobject_unalignRayAPI((RayObject*) obj);
2009-05-29 22:55:06 +00:00
}
static void bvh_callback(void *userdata, int index, const BVHTreeRay *ray, BVHTreeRayHit *hit)
{
Isect *isec = (Isect*)userdata;
2009-05-29 22:55:06 +00:00
RayObject *face = (RayObject*)index;
if(RE_rayobject_intersect(face,isec))
2009-05-29 22:55:06 +00:00
{
hit->index = index;
if(isec->mode == RE_RAY_SHADOW)
hit->dist = 0;
else
hit->dist = isec->labda*isec->dist;
2009-05-29 22:55:06 +00:00
}
}
static int RE_rayobject_blibvh_intersect(RayObject *o, Isect *isec)
2009-05-29 22:55:06 +00:00
{
BVHObject *obj = (BVHObject*)o;
BVHTreeRayHit hit;
float dir[3];
VECCOPY(dir, isec->vec);
Normalize(dir);
hit.index = 0;
hit.dist = isec->labda*isec->dist;
2009-05-29 22:55:06 +00:00
return BLI_bvhtree_ray_cast(obj->bvh, isec->start, dir, 0.0, &hit, bvh_callback, isec);
2009-05-29 22:55:06 +00:00
}
static void RE_rayobject_blibvh_add(RayObject *o, RayObject *ob)
2009-05-29 22:55:06 +00:00
{
BVHObject *obj = (BVHObject*)o;
float min_max[6];
INIT_MINMAX(min_max, min_max+3);
RE_rayobject_merge_bb(ob, min_max, min_max+3);
DO_MIN(min_max , obj->bb[0]);
DO_MAX(min_max+3, obj->bb[1]);
BLI_bvhtree_insert(obj->bvh, (int)ob, min_max, 2 );
2009-05-29 22:55:06 +00:00
}
static void RE_rayobject_blibvh_done(RayObject *o)
2009-05-29 22:55:06 +00:00
{
BVHObject *obj = (BVHObject*)o;
BLI_bvhtree_balance(obj->bvh);
}
static void RE_rayobject_blibvh_free(RayObject *o)
2009-05-29 22:55:06 +00:00
{
BVHObject *obj = (BVHObject*)o;
if(obj->bvh)
BLI_bvhtree_free(obj->bvh);
MEM_freeN(obj);
}
static void RE_rayobject_blibvh_bb(RayObject *o, float *min, float *max)
2009-05-29 22:55:06 +00:00
{
BVHObject *obj = (BVHObject*)o;
DO_MIN( obj->bb[0], min );
DO_MAX( obj->bb[1], max );
2009-05-29 22:55:06 +00:00
}