#include "TMath.h"
#include "TGraph2D.h"
#include "TGraphDelaunay.h"
ClassImp(TGraphDelaunay)
/*
<img src="gif/dtvd.gif">
<br>
<a href="http://www.cs.cornell.edu/Info/People/chew/Delaunay.html">This applet</a>
gives a nice practical view of Delaunay triangulation and Voronoi diagram. 
*/
//End_Html
TGraphDelaunay::TGraphDelaunay()
            : TNamed("TGraphDelaunay","TGraphDelaunay")
{
   
   fGraph2D    = 0;
   fX          = 0;
   fY          = 0;
   fZ          = 0;
   fNpoints    = 0;
   fTriedSize  = 0;
   fZout       = 0.;
   fNdt        = 0;
   fNhull      = 0;
   fHullPoints = 0;
   fXN         = 0;
   fYN         = 0;
   fOrder      = 0;
   fDist       = 0;
   fPTried     = 0;
   fNTried     = 0;
   fMTried     = 0;
   fInit       = kFALSE;
   SetMaxIter();
}
TGraphDelaunay::TGraphDelaunay(TGraph2D *g)
            : TNamed("TGraphDelaunay","TGraphDelaunay")
{
   
   fGraph2D    = g;
   fX          = fGraph2D->GetX();
   fY          = fGraph2D->GetY();
   fZ          = fGraph2D->GetZ();
   fNpoints    = fGraph2D->GetN();
   fTriedSize  = 0;
   fZout       = 0.;
   fNdt        = 0;
   fNhull      = 0;
   fHullPoints = 0;
   fXN         = 0;
   fYN         = 0;
   fOrder      = 0;
   fDist       = 0;
   fPTried     = 0;
   fNTried     = 0;
   fMTried     = 0;
   fInit       = kFALSE;
   SetMaxIter();
}
TGraphDelaunay::~TGraphDelaunay()
{
   
   if (fPTried)     delete [] fPTried;
   if (fNTried)     delete [] fNTried;
   if (fMTried)     delete [] fMTried;
   if (fHullPoints) delete [] fHullPoints;
   if (fOrder)      delete [] fOrder;
   if (fDist)       delete [] fDist;
   if (fXN)         delete [] fXN;
   if (fYN)         delete [] fYN;
   fPTried     = 0;
   fNTried     = 0;
   fMTried     = 0;
   fHullPoints = 0;
   fOrder      = 0;
   fDist       = 0;
   fXN         = 0;
   fYN         = 0;
}
Double_t TGraphDelaunay::ComputeZ(Double_t x, Double_t y)
{
   
   
   
   
   if (!fInit) {
      CreateTrianglesDataStructure();
      FindHull();
      fInit = kTRUE;
   }
   
   Double_t xx, yy;
   xx = (x+fXoffset)*fScaleFactor;
   yy = (y+fYoffset)*fScaleFactor;
   Double_t zz = Interpolate(xx, yy);
   
   
   if (zz==0) {
      xx += 0.001;
      yy += 0.001;
      zz = Interpolate(xx, yy);
   }
   return zz;
}
void TGraphDelaunay::CreateTrianglesDataStructure()
{
   
   
   
   
   
   Double_t xmax = fGraph2D->GetXmax();
   Double_t ymax = fGraph2D->GetYmax();
   Double_t xmin = fGraph2D->GetXmin();
   Double_t ymin = fGraph2D->GetYmin();
   fXoffset      = -(xmax+xmin)/2.;
   fYoffset      = -(ymax+ymin)/2.;
   fScaleFactor  = 2./((xmax-xmin)+(ymax-ymin));
   fXNmax        = (xmax+fXoffset)*fScaleFactor;
   fXNmin        = (xmin+fXoffset)*fScaleFactor;
   fYNmax        = (ymax+fYoffset)*fScaleFactor;
   fYNmin        = (ymin+fYoffset)*fScaleFactor;
   fXN           = new Double_t[fNpoints+1];
   fYN           = new Double_t[fNpoints+1];
   for (Int_t n=0; n<fNpoints; n++) {
      fXN[n+1] = (fX[n]+fXoffset)*fScaleFactor;
      fYN[n+1] = (fY[n]+fYoffset)*fScaleFactor;
   }
   
   
   
   fTriedSize = 2*fNpoints;
   fPTried    = new Int_t[fTriedSize];
   fNTried    = new Int_t[fTriedSize];
   fMTried    = new Int_t[fTriedSize];
}
Bool_t TGraphDelaunay::Enclose(Int_t t1, Int_t t2, Int_t t3, Int_t e) const
{
   
   Int_t a = 0, b = 0;
   Double_t dx1,dx2,dx3,dy1,dy2,dy3,u,v;
   
   if (((fXN[t1]-fXN[e])*(fYN[t1]-fYN[t2])) == ((fYN[t1]-fYN[e])*(fXN[t1]-fXN[t2]))) {
      
      a = t1;
      b = t2;
   } else if (((fXN[t1]-fXN[e])*(fYN[t1]-fYN[t3])) == ((fYN[t1]-fYN[e])*(fXN[t1]-fXN[t3]))) {
      
      a = t1;
      b = t3;
   } else if (((fXN[t2]-fXN[e])*(fYN[t2]-fYN[t3])) == ((fYN[t2]-fYN[e])*(fXN[t2]-fXN[t3]))) {
      
      a = t2;
      b = t3;
   }
   if (a != 0) {
      
      
      if (fXN[a] != fXN[b]) {
         if (((fXN[e]-fXN[a])*(fXN[e]-fXN[b])) <= 0) return kTRUE;
      } else {
         if (((fYN[e]-fYN[a])*(fYN[e]-fYN[b])) <= 0) return kTRUE;
      }
      
      return kFALSE;
   }
   
   
   
   
   
   dx1 = fXN[e]-fXN[t1];
   dy1 = fYN[e]-fYN[t1];
   
   dx2 = fXN[e]-fXN[t2];
   dy2 = fYN[e]-fYN[t2];
   
   dx3 = fXN[t3]-fXN[e];
   dy3 = fYN[t3]-fYN[e];
   u = (dx2*dy3-dx3*dy2)/(dx2*dy1-dx1*dy2);
   v = (dx1*dy3-dx3*dy1)/(dx1*dy2-dx2*dy1);
   if ((u>=0) && (v>=0)) return kTRUE;
   return kFALSE;
}
void TGraphDelaunay::FileIt(Int_t p, Int_t n, Int_t m)
{
   
   
   
   Bool_t swap;
   Int_t tmp, ps = p, ns = n, ms = m;
   
L1:
   swap = kFALSE;
   if (ns > ps) { tmp = ps; ps = ns; ns = tmp; swap = kTRUE;}
   if (ms > ns) { tmp = ns; ns = ms; ms = tmp; swap = kTRUE;}
   if (swap) goto L1;
   
   if (fNdt> fTriedSize) {
      Int_t newN   = 2*fTriedSize;
      Int_t *savep = new Int_t [newN];
      Int_t *saven = new Int_t [newN];
      Int_t *savem = new Int_t [newN];
      memcpy(savep,fPTried,fTriedSize*sizeof(Int_t));
      memset(&savep[fTriedSize],0,(newN-fTriedSize)*sizeof(Int_t));
      delete [] fPTried;
      memcpy(saven,fNTried,fTriedSize*sizeof(Int_t));
      memset(&saven[fTriedSize],0,(newN-fTriedSize)*sizeof(Int_t));
      delete [] fNTried;
      memcpy(savem,fMTried,fTriedSize*sizeof(Int_t));
      memset(&savem[fTriedSize],0,(newN-fTriedSize)*sizeof(Int_t));
      delete [] fMTried;
      fPTried    = savep;
      fNTried    = saven;
      fMTried    = savem;
      fTriedSize = newN;
   }
   
   fNdt++;
   fPTried[fNdt-1] = ps;
   fNTried[fNdt-1] = ns;
   fMTried[fNdt-1] = ms;
}
void TGraphDelaunay::FindAllTriangles()
{
   
   
   
   
   
   
   
   
   
   
   if (fAllTri) return; else fAllTri = kTRUE;
   Double_t xcntr,ycntr,xm,ym,xx,yy;
   Double_t sx,sy,nx,ny,mx,my,mdotn,nn,a;
   Int_t t1,t2,pa,na,ma,pb,nb,mb,p1=0,p2=0,m,n,p3=0;
   Bool_t s[3];
   Double_t alittlebit = 0.0001;
   
   
   
   
   xcntr = 0;
   ycntr = 0;
   for (n=1; n<=fNhull; n++) {
      xcntr = xcntr+fXN[fHullPoints[n-1]];
      ycntr = ycntr+fYN[fHullPoints[n-1]];
   }
   xcntr = xcntr/fNhull+alittlebit;
   ycntr = ycntr/fNhull+alittlebit;
   
   Interpolate(xcntr,ycntr);
   
   
   
   
   t1 = 1;
   while (t1 <= fNdt) {
      
      pa = fPTried[t1-1];
      na = fNTried[t1-1];
      ma = fMTried[t1-1];
      
      s[0]  = kFALSE;
      s[1]  = kFALSE;
      s[2]  = kFALSE;
      
      for (t2=1; t2<=fNdt; t2++) {
         if (t2 != t1) {
            
            pb = fPTried[t2-1];
            nb = fNTried[t2-1];
            mb = fMTried[t2-1];
            
            if ((pa==pb && na==nb) || (pa==pb && na==mb) || (pa==nb && na==mb)) {
               
               s[0] = kTRUE;
            } else if ((pa==pb && ma==nb) || (pa==pb && ma==mb) || (pa==nb && ma==mb)) {
               
               s[1] = kTRUE;
            } else if ((na==pb && ma==nb) || (na==pb && ma==mb) || (na==nb && ma==mb)) {
               
               s[2] = kTRUE;
            }
         }
         
         
         if (s[0] && s[1] && s[2]) continue;
      }
      
      
      
      
      for (m=1; m<=3; m++) {
         if (!s[m-1]) {
            
            if (m == 1) {
               p1 = pa;
               p2 = na;
               p3 = ma;
            } else if (m == 2) {
               p1 = pa;
               p2 = ma;
               p3 = na;
            } else if (m == 3) {
               p1 = na;
               p2 = ma;
               p3 = pa;
            }
            
            xm = (fXN[p1]+fXN[p2])/2.;
            ym = (fYN[p1]+fYN[p2])/2.;
            
            
            
            sx = fXN[p1]-fXN[p2];
            sy = fYN[p1]-fYN[p2];
            
            
            nx    = sy;
            ny    = -sx;
            nn    = TMath::Sqrt(nx*nx+ny*ny);
            nx    = nx/nn;
            ny    = ny/nn;
            mx    = fXN[p3]-xm;
            my    = fYN[p3]-ym;
            mdotn = mx*nx+my*ny;
            if (mdotn > 0) {
               
               nx = -nx;
               ny = -ny;
            }
            
            
            
            a  = TMath::Abs(TMath::Max(alittlebit*xm,alittlebit*ym));
            xx = xm+nx*a;
            yy = ym+ny*a;
            
            Interpolate(xx,yy);
            
            
         }
      }
      t1++;
   }
}      
void TGraphDelaunay::FindHull()
{
   
   
   
   
   
   Int_t n,nhull_tmp;
   Bool_t in;
   if (!fHullPoints) fHullPoints = new Int_t[fNpoints];
   nhull_tmp = 0;
   for(n=1; n<=fNpoints; n++) {
      
      
      
      in = InHull(n,n);
      if (!in) {
         
         
         nhull_tmp++;
         fHullPoints[nhull_tmp-1] = n;
      }
   }
   fNhull = nhull_tmp;
}
Bool_t TGraphDelaunay::InHull(Int_t e, Int_t x) const
{
   
   Int_t n1,n2,n,m,ntry;
   Double_t lastdphi,dd1,dd2,dx1,dx2,dx3,dy1,dy2,dy3;
   Double_t u,v,vNv1,vNv2,phi1,phi2,dphi,xx,yy;
   Bool_t deTinhull = kFALSE;
   xx = fXN[e];
   yy = fYN[e];
   if (fNhull > 0) {
      
      
      ntry = fNhull;
   } else {
      
      ntry = fNpoints;
   }
   
   
   
   
   
   n1 = 1;
   n2 = 2;
   if (n1 == x) {
      n1 = n2;
      n2++;
   } else if (n2 == x) {
      n2++;
   }
   
   dx1  = xx-fXN[n1];
   dy1  = yy-fYN[n1];
   dx2  = xx-fXN[n2];
   dy2  = yy-fYN[n2];
   phi1 = TMath::ATan2(dy1,dx1);
   phi2 = TMath::ATan2(dy2,dx2);
   dphi = (phi1-phi2)-((Int_t)((phi1-phi2)/TMath::TwoPi())*TMath::TwoPi());
   if (dphi < 0) dphi = dphi+TMath::TwoPi();
   lastdphi = dphi;
   for (n=1; n<=ntry; n++) {
      if (fNhull > 0) {
         
         m = fHullPoints[n-1];
      } else {
         m = n;
      }
      if ((m!=n1) && (m!=n2) && (m!=x)) {
         
         
         dx1 = xx-fXN[n1];
         dy1 = yy-fYN[n1];
         dx2 = xx-fXN[n2];
         dy2 = yy-fYN[n2];
         dx3 = xx-fXN[m];
         dy3 = yy-fYN[m];
         dd1 = (dx2*dy1-dx1*dy2);
         dd2 = (dx1*dy2-dx2*dy1);
         if (dd1*dd2!=0) {
            u = (dx2*dy3-dx3*dy2)/dd1;
            v = (dx1*dy3-dx3*dy1)/dd2;
            if ((u<0) || (v<0)) {
               
               
               
               
               vNv1 = (dx1*dx3+dy1*dy3)/TMath::Sqrt(dx1*dx1+dy1*dy1);
               vNv2 = (dx2*dx3+dy2*dy3)/TMath::Sqrt(dx2*dx2+dy2*dy2);
               if (vNv1 > vNv2) {
                  n1   = m;
                  phi1 = TMath::ATan2(dy3,dx3);
                  phi2 = TMath::ATan2(dy2,dx2);
               } else {
                  n2   = m;
                  phi1 = TMath::ATan2(dy1,dx1);
                  phi2 = TMath::ATan2(dy3,dx3);
               }
               dphi = (phi1-phi2)-((Int_t)((phi1-phi2)/TMath::TwoPi())*TMath::TwoPi());
               if (dphi < 0) dphi = dphi+TMath::TwoPi();
               if (((dphi-TMath::Pi())*(lastdphi-TMath::Pi())) < 0) {
                  
                  
                  goto L10;
               }
               lastdphi = dphi;
            }
         }
      }
   }
   
   goto L999;
L10:
   deTinhull = kTRUE;
L999:
   return deTinhull;
}
Double_t TGraphDelaunay::InterpolateOnPlane(Int_t TI1, Int_t TI2, Int_t TI3, Int_t e) const
{
   
   
   Int_t tmp;
   Bool_t swap;
   Double_t x1,x2,x3,y1,y2,y3,f1,f2,f3,u,v,w;
   Int_t t1 = TI1;
   Int_t t2 = TI2;
   Int_t t3 = TI3;
   
L1:
   swap = kFALSE;
   if (t2 > t1) { tmp = t1; t1 = t2; t2 = tmp; swap = kTRUE;}
   if (t3 > t2) { tmp = t2; t2 = t3; t3 = tmp; swap = kTRUE;}
   if (swap) goto L1;
   x1 = fXN[t1];
   x2 = fXN[t2];
   x3 = fXN[t3];
   y1 = fYN[t1];
   y2 = fYN[t2];
   y3 = fYN[t3];
   f1 = fZ[t1-1];
   f2 = fZ[t2-1];
   f3 = fZ[t3-1];
   u  = (f1*(y2-y3)+f2*(y3-y1)+f3*(y1-y2))/(x1*(y2-y3)+x2*(y3-y1)+x3*(y1-y2));
   v  = (f1*(x2-x3)+f2*(x3-x1)+f3*(x1-x2))/(y1*(x2-x3)+y2*(x3-x1)+y3*(x1-x2));
   w  = f1-u*x1-v*y1;
   return u*fXN[e]+v*fYN[e]+w;
}
Double_t TGraphDelaunay::Interpolate(Double_t xx, Double_t yy)
{
   
   
   
   Double_t thevalue;
   Int_t it, ntris_tried, p, n, m;
   Int_t i,j,k,l,z,f,d,o1,o2,a,b,t1,t2,t3;
   Int_t ndegen=0,degen=0,fdegen=0,o1degen=0,o2degen=0;
   Double_t vxN,vyN;
   Double_t d1,d2,d3,c1,c2,dko1,dko2,dfo1;
   Double_t dfo2,sin_sum,cfo1k,co2o1k,co2o1f;
   Bool_t shouldbein;
   Double_t dx1,dx2,dx3,dy1,dy2,dy3,u,v,dxz[3],dyz[3];
   
   if (!fInit) {
      CreateTrianglesDataStructure();
      FindHull();
      fInit = kTRUE;
   }
   
   if (!fOrder) {
      fOrder = new Int_t[fNpoints];
      fDist  = new Double_t[fNpoints];
   }
   
   fXN[0] = xx;
   fYN[0] = yy;
   
   thevalue = fZout;
   
   ntris_tried = 0;
   
   if ((xx>fXNmax) || (xx<fXNmin) || (yy>fYNmax) || (yy<fYNmin)) return thevalue;
   
   for (it=1; it<=fNdt; it++) {
      p = fPTried[it-1];
      n = fNTried[it-1];
      m = fMTried[it-1];
      
      
      if (Enclose(p,n,m,0)) {
         
         thevalue = InterpolateOnPlane(p,n,m,0);
         return thevalue;
      }
   }
   
   shouldbein = InHull(0,-1);
   if (!shouldbein) return thevalue;
   
   
   for (it=1; it<=fNpoints; it++) {
      vxN = fXN[it];
      vyN = fYN[it];
      fDist[it-1] = TMath::Sqrt((xx-vxN)*(xx-vxN)+(yy-vyN)*(yy-vyN));
   }
   
   TMath::Sort(fNpoints, fDist, fOrder, kFALSE);
   for (it=0; it<fNpoints; it++) fOrder[it]++;
   
   
   for (k=3; k<=fNpoints; k++) {
      m = fOrder[k-1];
      for (j=2; j<=k-1; j++) {
         n = fOrder[j-1];
         for (i=1; i<=j-1; i++) {
            p = fOrder[i-1];
            if (ntris_tried > fMaxIter) {
               
               return thevalue;
            }
            ntris_tried++;
            
            d1 = TMath::Sqrt((fXN[p]-fXN[n])*(fXN[p]-fXN[n])+(fYN[p]-fYN[n])*(fYN[p]-fYN[n]));
            d2 = TMath::Sqrt((fXN[p]-fXN[m])*(fXN[p]-fXN[m])+(fYN[p]-fYN[m])*(fYN[p]-fYN[m]));
            d3 = TMath::Sqrt((fXN[n]-fXN[m])*(fXN[n]-fXN[m])+(fYN[n]-fYN[m])*(fYN[n]-fYN[m]));
            if ((d1+d2<=d3) || (d1+d3<=d2) || (d2+d3<=d1)) goto L90;
            
            if (!Enclose(p,n,m,0)) goto L90;
            
            
            
            
            
            ndegen = 0;
            for ( z=1; z<=fNpoints; z++) {
               if ((z==p) || (z==n) || (z==m)) goto L50;
               
               
               
               
               for (l=1; l<=fNpoints; l++) {
                  if (fOrder[l-1] == z) {
                     if ((l<i) || (l<j) || (l<k)) {
                        
                        
                        
                        if (Enclose(p,n,m,z)) goto L90;
                     } else {
                        
                        
                        goto L1;
                     }
                  }
               }
               
L1:
               if (((fXN[p]-fXN[z])*(fYN[p]-fYN[n])) == ((fYN[p]-fYN[z])*(fXN[p]-fXN[n]))) {
                  
                  a = p;
                  b = n;
               } else if (((fXN[p]-fXN[z])*(fYN[p]-fYN[m])) == ((fYN[p]-fYN[z])*(fXN[p]-fXN[m]))) {
                  
                  a = p;
                  b = m;
               } else if (((fXN[n]-fXN[z])*(fYN[n]-fYN[m])) == ((fYN[n]-fYN[z])*(fXN[n]-fXN[m]))) {
                  
                  a = n;
                  b = m;
               } else {
                  a = 0;
                  b = 0;
               }
               if (a != 0) {
                  
                  
                  if (fXN[a] != fXN[b]) {
                     if (((fXN[z]-fXN[a])*(fXN[z]-fXN[b])) < 0) {
                        goto L90;
                     } else if (((fXN[z]-fXN[a])*(fXN[z]-fXN[b])) == 0) {
                        
                        
                        
                        
                        
                        Warning("Interpolate", "Two of these three points are coincident %d %d %d",a,b,z);
                     }
                  } else {
                     if (((fYN[z]-fYN[a])*(fYN[z]-fYN[b])) < 0) {
                        goto L90;
                     } else if (((fYN[z]-fYN[a])*(fYN[z]-fYN[b])) == 0) {
                        
                        Warning("Interpolate", "Two of these three points are coincident %d %d %d",a,b,z);
                     }
                  }
                  
                  goto L50;
               }
               
               
               
               
               dxz[0] = fXN[p]-fXN[z];
               dyz[0] = fYN[p]-fYN[z];
               dxz[1] = fXN[n]-fXN[z];
               dyz[1] = fYN[n]-fYN[z];
               dxz[2] = fXN[m]-fXN[z];
               dyz[2] = fYN[m]-fYN[z];
               for(l=1; l<=3; l++) {
                  dx1 = dxz[l-1];
                  dx2 = dxz[l%3];
                  dx3 = dxz[(l+1)%3];
                  dy1 = dyz[l-1];
                  dy2 = dyz[l%3];
                  dy3 = dyz[(l+1)%3];
                  u = (dy3*dx2-dx3*dy2)/(dy1*dx2-dx1*dy2);
                  v = (dy3*dx1-dx3*dy1)/(dy2*dx1-dx2*dy1);
                  if ((u>=0) && (v>=0)) {
                     
                     
                     if (l == 1) {
                        f  = m;
                        o1 = p;
                        o2 = n;
                     } else if (l == 2) {
                        f  = p;
                        o1 = n;
                        o2 = m;
                     } else {
                        f  = n;
                        o1 = m;
                        o2 = p;
                     }
                     goto L2;
                  }
               }
               
               f  = m;
               o1 = p;
               o2 = n;
L2:
               
               
               
               cfo1k  = ((fXN[f]-fXN[o1])*(fXN[z]-fXN[o1])+(fYN[f]-fYN[o1])*(fYN[z]-fYN[o1]))/
                        TMath::Sqrt(((fXN[f]-fXN[o1])*(fXN[f]-fXN[o1])+(fYN[f]-fYN[o1])*(fYN[f]-fYN[o1]))*
                        ((fXN[z]-fXN[o1])*(fXN[z]-fXN[o1])+(fYN[z]-fYN[o1])*(fYN[z]-fYN[o1])));
               co2o1k = ((fXN[o2]-fXN[o1])*(fXN[z]-fXN[o1])+(fYN[o2]-fYN[o1])*(fYN[z]-fYN[o1]))/
                        TMath::Sqrt(((fXN[o2]-fXN[o1])*(fXN[o2]-fXN[o1])+(fYN[o2]-fYN[o1])*(fYN[o2]-fYN[o1]))*
                        ((fXN[z]-fXN[o1])*(fXN[z]-fXN[o1])  + (fYN[z]-fYN[o1])*(fYN[z]-fYN[o1])));
               co2o1f = ((fXN[o2]-fXN[o1])*(fXN[f]-fXN[o1])+(fYN[o2]-fYN[o1])*(fYN[f]-fYN[o1]))/
                        TMath::Sqrt(((fXN[o2]-fXN[o1])*(fXN[o2]-fXN[o1])+(fYN[o2]-fYN[o1])*(fYN[o2]-fYN[o1]))*
                        ((fXN[f]-fXN[o1])*(fXN[f]-fXN[o1]) + (fYN[f]-fYN[o1])*(fYN[f]-fYN[o1]) ));
               if ((cfo1k>co2o1k) || (cfo1k>co2o1f)) {
                  
                  goto L50;
               }
               
               
               
               dko1    = TMath::Sqrt((fXN[z]-fXN[o1])*(fXN[z]-fXN[o1])+(fYN[z]-fYN[o1])*(fYN[z]-fYN[o1]));
               dko2    = TMath::Sqrt((fXN[z]-fXN[o2])*(fXN[z]-fXN[o2])+(fYN[z]-fYN[o2])*(fYN[z]-fYN[o2]));
               dfo1    = TMath::Sqrt((fXN[f]-fXN[o1])*(fXN[f]-fXN[o1])+(fYN[f]-fYN[o1])*(fYN[f]-fYN[o1]));
               dfo2    = TMath::Sqrt((fXN[f]-fXN[o2])*(fXN[f]-fXN[o2])+(fYN[f]-fYN[o2])*(fYN[f]-fYN[o2]));
               c1      = ((fXN[z]-fXN[o1])*(fXN[z]-fXN[o2])+(fYN[z]-fYN[o1])*(fYN[z]-fYN[o2]))/dko1/dko2;
               c2      = ((fXN[f]-fXN[o1])*(fXN[f]-fXN[o2])+(fYN[f]-fYN[o1])*(fYN[f]-fYN[o2]))/dfo1/dfo2;
               sin_sum = c1*TMath::Sqrt(1-c2*c2)+c2*TMath::Sqrt(1-c1*c1);
               
               if (sin_sum < -1.E-6) {
                  
                  goto L90;
               } else if (TMath::Abs(sin_sum) <= 1.E-6) {
                  
                  
                  
                  
                  
                  ndegen++;
                  degen   = z;
                  fdegen  = f;
                  o1degen = o1;
                  o2degen = o2;
               }
L50:
            continue;
            }
            
            if (ndegen > 0) {
               
               
               
               
               
               
               d  = degen;
               f  = fdegen;
               o1 = o1degen;
               o2 = o2degen;
               if ((fZ[o1-1]+fZ[o2-1]) > (fZ[d-1]+fZ[f-1])) {
                  
                  
                  t1 = p;
                  t2 = n;
                  t3 = m;
                  
                  FileIt(p, n, m);
                  FileIt(d, o1, o2);
               } else {
                  
                  
                  
                  t1 = f;
                  t2 = d;
                  if (Enclose(f,d,o1,0)) {
                     t3 = o1;
                  } else {
                     t3 = o2;
                  }
                  
                  FileIt(f, d, o1);
                  FileIt(f, d, o2);
               }
            } else {
               
               FileIt(p, n, m);
               t1 = p;
               t2 = n;
               t3 = m;
            }
            
            thevalue = InterpolateOnPlane(t1,t2,t3,0);
            return thevalue;
L90:
            continue;
         }
      }
   }
   if (shouldbein) {
      Error("Interpolate", 
            "Point outside hull when expected inside: this point could be dodgy %g %g %d",
             xx, yy, ntris_tried);
   }
   return thevalue;
}
void TGraphDelaunay::SetMaxIter(Int_t n)
{
   
   
   fAllTri  = kFALSE;
   fMaxIter = n;
}
void TGraphDelaunay::SetMarginBinsContent(Double_t z)
{
   
   
   fZout = z;
}
Last change: Tue May 13 17:18:07 2008
Last generated: 2008-05-13 17:18
This page has been automatically generated. If you have any comments or suggestions about the page layout send a mail to ROOT support, or contact the developers with any questions or problems regarding ROOT.