00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #include "Riostream.h"
00021 #include "TGeoHalfSpace.h"
00022 #include "TMath.h"
00023
00024 ClassImp(TGeoHalfSpace)
00025
00026
00027 TGeoHalfSpace::TGeoHalfSpace()
00028 {
00029
00030 SetShapeBit(TGeoShape::kGeoHalfSpace);
00031 SetShapeBit(TGeoShape::kGeoInvalidShape);
00032 memset(fP, 0, 3*sizeof(Double_t));
00033 memset(fN, 0, 3*sizeof(Double_t));
00034 }
00035
00036
00037 TGeoHalfSpace::TGeoHalfSpace(const char *name, Double_t *p, Double_t *n)
00038 :TGeoBBox(name, 0,0,0)
00039 {
00040
00041 SetShapeBit(TGeoShape::kGeoHalfSpace);
00042 SetShapeBit(TGeoShape::kGeoInvalidShape);
00043 Double_t param[6];
00044 memcpy(param, p, 3*sizeof(Double_t));
00045 memcpy(¶m[3], n, 3*sizeof(Double_t));
00046 SetDimensions(param);
00047 }
00048
00049
00050 TGeoHalfSpace::TGeoHalfSpace(Double_t *param)
00051 :TGeoBBox(0,0,0)
00052 {
00053
00054 SetShapeBit(TGeoShape::kGeoHalfSpace);
00055 SetShapeBit(TGeoShape::kGeoInvalidShape);
00056 SetDimensions(param);
00057 }
00058
00059
00060 TGeoHalfSpace::~TGeoHalfSpace()
00061 {
00062
00063 }
00064
00065
00066 void TGeoHalfSpace::ComputeNormal(Double_t * , Double_t *dir, Double_t *norm)
00067 {
00068
00069 memcpy(norm, fN, 3*sizeof(Double_t));
00070 if (norm[0]*dir[0]+norm[1]*dir[1]+norm[2]*dir[2]<0) {
00071 norm[0] = -norm[0];
00072 norm[1] = -norm[1];
00073 norm[2] = -norm[2];
00074 }
00075 }
00076
00077
00078 Bool_t TGeoHalfSpace::Contains(Double_t *point) const
00079 {
00080
00081 Double_t r[3];
00082 r[0] = fP[0]-point[0];
00083 r[1] = fP[1]-point[1];
00084 r[2] = fP[2]-point[2];
00085 Double_t rdotn = r[0]*fN[0]+r[1]*fN[1]+r[2]*fN[2];
00086 if (rdotn < 0) return kFALSE;
00087 return kTRUE;
00088 }
00089
00090
00091 Int_t TGeoHalfSpace::DistancetoPrimitive(Int_t , Int_t )
00092 {
00093
00094 return 999;
00095 }
00096
00097
00098 Double_t TGeoHalfSpace::DistFromInside(Double_t *point, Double_t *dir, Int_t iact, Double_t step, Double_t *safe) const
00099 {
00100
00101 Double_t r[3];
00102 r[0] = fP[0]-point[0];
00103 r[1] = fP[1]-point[1];
00104 r[2] = fP[2]-point[2];
00105 Double_t rdotn = r[0]*fN[0]+r[1]*fN[1]+r[2]*fN[2];
00106 if (iact<3 && safe) {
00107 *safe = rdotn;
00108 if (iact==0) return TGeoShape::Big();
00109 if ((iact==1) && (*safe>step)) return TGeoShape::Big();
00110 }
00111
00112 Double_t snxt = TGeoShape::Big();
00113 Double_t ddotn = dir[0]*fN[0]+dir[1]*fN[1]+dir[2]*fN[2];
00114 if (TMath::Abs(ddotn)<TGeoShape::Tolerance()) return snxt;
00115 snxt = rdotn/ddotn;
00116 if (snxt<0) return TGeoShape::Big();
00117 return snxt;
00118 }
00119
00120
00121 Double_t TGeoHalfSpace::DistFromOutside(Double_t *point, Double_t *dir, Int_t iact, Double_t step, Double_t *safe) const
00122 {
00123
00124 Double_t r[3];
00125 r[0] = fP[0]-point[0];
00126 r[1] = fP[1]-point[1];
00127 r[2] = fP[2]-point[2];
00128 Double_t rdotn = r[0]*fN[0]+r[1]*fN[1]+r[2]*fN[2];
00129 if (iact<3 && safe) {
00130 *safe = -rdotn;
00131 if (iact==0) return TGeoShape::Big();
00132 if ((iact==1) && (step<*safe)) return TGeoShape::Big();
00133 }
00134
00135 Double_t snxt = TGeoShape::Big();
00136 Double_t ddotn = dir[0]*fN[0]+dir[1]*fN[1]+dir[2]*fN[2];
00137 if (TMath::Abs(ddotn)<TGeoShape::Tolerance()) return snxt;
00138 snxt = rdotn/ddotn;
00139 if (snxt<0) return TGeoShape::Big();
00140 return snxt;
00141 }
00142
00143
00144 TGeoVolume *TGeoHalfSpace::Divide(TGeoVolume * , const char * , Int_t , Int_t ,
00145 Double_t , Double_t )
00146 {
00147
00148 Error("Divide", "Half-spaces cannot be divided");
00149 return 0;
00150 }
00151
00152
00153 void TGeoHalfSpace::GetMeshNumbers(Int_t &nvert, Int_t &nsegs, Int_t &npols) const
00154 {
00155
00156 nvert = 0;
00157 nsegs = 0;
00158 npols = 0;
00159 }
00160
00161
00162 void TGeoHalfSpace::InspectShape() const
00163 {
00164
00165 printf("*** Shape %s: TGeoHalfSpace ***\n", GetName());
00166 printf(" Point : %11.5f, %11.5f, %11.5f\n", fP[0], fP[1], fP[2]);
00167 printf(" Normal : %11.5f, %11.5f, %11.5f\n", fN[0], fN[1], fN[2]);
00168 }
00169
00170
00171 Double_t TGeoHalfSpace::Safety(Double_t *point, Bool_t ) const
00172 {
00173
00174
00175 Double_t r[3];
00176 r[0] = fP[0]-point[0];
00177 r[1] = fP[1]-point[1];
00178 r[2] = fP[2]-point[2];
00179 Double_t rdotn = r[0]*fN[0]+r[1]*fN[1]+r[2]*fN[2];
00180 return TMath::Abs(rdotn);
00181 }
00182
00183
00184 void TGeoHalfSpace::SavePrimitive(ostream &out, Option_t * )
00185 {
00186
00187 if (TObject::TestBit(kGeoSavePrimitive)) return;
00188 out << " // Shape: " << GetName() << " type: " << ClassName() << endl;
00189 out << " point[0] = " << fP[0] << ";" << endl;
00190 out << " point[1] = " << fP[1] << ";" << endl;
00191 out << " point[2] = " << fP[2] << ";" << endl;
00192 out << " norm[0] = " << fN[0] << ";" << endl;
00193 out << " norm[1] = " << fN[1] << ";" << endl;
00194 out << " norm[2] = " << fN[2] << ";" << endl;
00195 out << " TGeoShape *" << GetPointerName() << " = new TGeoHalfSpace(\"" << GetName() << "\", point,norm);" << endl;
00196 TObject::SetBit(TGeoShape::kGeoSavePrimitive);
00197 }
00198
00199
00200 void TGeoHalfSpace::SetDimensions(Double_t *param)
00201 {
00202
00203 memcpy(fP, param, 3*sizeof(Double_t));
00204 memcpy(fN, ¶m[3], 3*sizeof(Double_t));
00205 Double_t nsq = TMath::Sqrt(fN[0]*fN[0]+fN[1]*fN[1]+fN[2]*fN[2]);
00206 fN[0] /= nsq;
00207 fN[1] /= nsq;
00208 fN[2] /= nsq;
00209 }