// -*- C++ -*-
#ifndef RIPROJECTEDAREACLUSTER_H
#define RIPROJECTEDAREACLUSTER_H
/* Copyright 1996 
 * Thu Oct 23 17:49:14 1997  Brian Smits  (bes@phoenix.cs.utah.edu)
 * 
 * RiProjectedAreaCluster.H
 * 
 *	
 * 
 * $Id: RiProjectedAreaCluster.H,v 1.1 1998/06/22 17:36:45 bes Exp $ 
 * 
 */
#ifndef RICOMMON_H
#include <RiCommon.H>
#endif


#ifndef RIRADOBJECT_H
#include <RiRadObject.H>
#endif

#ifndef RIBBOX_H
#include <RiBBox.H>
#endif

#include <rw/tvordvec.h>

/***************************************************************
CLASS
    RiProjectedAreaCluster
     <one line summary> 

DESCRIPTION
    This class holds a cube representing the projected area in each direction.
    Each cube face has 9 cells on it.  When an object is added to the cluster,
    each cell has the projected area in its direction incremented appropriately.

****************************************************************/

class RiProjectedAreaCluster : public RiRadObject {
    friend class RiProjectedAreaClusterBuilder;
  public:
				// GROUP: Constructors and assignment
				//// Default Constructor
    RiProjectedAreaCluster();
				// GROUP: Members
				//// Fills in the data in sample, and returns the Area Weight
				//   for the sample (area of the object.
    virtual RiReal GetSample(RiRadRegion &sample, const RiVector2 &uv);
				//// Fills in the data in sample, and returns the Form Factor weight
				//   for the sample to the interestedSample.  interestedSample is used to 
				//   direct the object so that it will hopefully pick a point visible to
				//   the intersted point, reducing variance.
    virtual RiReal GetFormFactorSample(RiRadRegion &sample, const RiMaterialRegion &interestedSample,
				       const RiVector2 &uv);
				//// Get the Rad Data from the object
    virtual RiRadData  *GetRadData();
				//// Get a convex hull containing the object
    virtual RiConvexHull GetConvexHull();
				//// Can the object see the convex hull.  Note that this operation ONLY
				//   involves the object and the hull, not the environment.  This is
				//   the equivalent of back face culling.
    virtual bool	 IsVisible(const RiConvexHull &hull);
				//// Compute transfer data for links and lighting
    virtual void	 ComputeTransfer(const RiMaterialRegion &sample, RiTransferData &data);
				// GROUP: Structural
				//// Determine the number of children this object has. (0 if no
				//     subdivision has been done	
    virtual int		 GetNumChildren();
				//// Get the ith child (i MUST be less than GetNumChildren)
    virtual RiRadObject *GetChild(int i);
				//// Subdivide if possible.  If already subdivided, do nothing. Return
				//  true if subdividable.
    virtual bool	 Subdivide();
				//// Compute the surface area (or a good estimate of it) of the object
    virtual RiReal	 GetArea();
//  protected:
				//// Add an object to the list.
    void AddRadObject(RiRadObject *obj);
				//// Allow building of hierarchy
    void AddProjectedAreaObject(RiProjectedAreaCluster *obj);
private:
				//// Get the bin for a particular direction
    int				GetIndex(const RiVector3 &);
				//// Total area of all children
    RiReal 			totalArea;
				////  RiRadData info
    RiRadData			radData;
				//// holds projected area
    RiReal			projArea[6];
				////
    RiBBox bbox;
				////  Vector of children
    RWTValOrderedVector<RiRadObject *> child;
};




#endif /* RIPROJECTEDAREACLUSTER_H */

