Main Page | Namespace List | Class Hierarchy | Class List | File List | Class Members | File Members

src/expde/formulas/boundy.h

Go to the documentation of this file.
00001 //    expde: expression templates for partial differential equations.
00002 //    Copyright (C) 2001  Christoph Pflaum
00003 //    This program is free software; you can redistribute it and/or modify
00004 //    it under the terms of the GNU General Public License as published by
00005 //    the Free Software Foundation; either version 2 of the License, or
00006 //    (at your option) any later version.
00007 //
00008 //    This program is distributed in the hope that it will be useful,
00009 //    but WITHOUT ANY WARRANTY; without even the implied warranty of
00010 //    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00011 //    GNU General Public License for more details.
00012 //
00013 //                 SEE  Notice1.doc made by 
00014 //                 LAWRENCE LIVERMORE NATIONAL LABORATORY
00015 //
00016 
00017 // ------------------------------------------------------------
00018 //
00019 // boundy.h
00020 //
00021 // ------------------------------------------------------------
00022 
00023 #ifndef BOUNDY_H_
00024 #define BOUNDY_H_
00025         
00026 class Bo_description;
00027 
00029 // 1. Tetraeder
00030 // 2. Beschreibung einer Randzelle;
00031 // 3. Speicher fuer Randzellfreiheitsgrad
00032 // 4. ( lokale Randzellen-Matrizen ) existiert nicht mehr
00033 // 5. Beschreibung einer Randzelle;
00034 // 6. inline Implementierung einiger Memberfunktionenen
00036 
00037 
00039 // 1. Tetraeder
00041 
00042 
00043 class Tetraeder_storage {
00044  public:
00045   // Constructor for interior tetrahedrals
00046   inline Tetraeder_storage(Bo_description* desc,
00047                     int P0, int P1, int P2, int P3,
00048                     Tetraeder_storage* Next);
00049   // Constructor for tetrahedrals with boundary face
00050   Tetraeder_storage(Tetraeder_storage* Next) {
00051     next = Next;
00052     var = NULL;
00053   }
00054   
00055   // Alles zur Listenverwaltung; Next
00056   void Put_Next(Tetraeder_storage* Next) {
00057     next = Next;
00058   }
00059   Tetraeder_storage* Next() { return next; }
00060 
00061   // Alles zur Determinante
00062   inline void Put_det(double deter) { det = deter; }
00063   inline double Det() { return det; }  
00064 
00065   // Nummer der Eckpunkte
00066   int N0() { return num0; }
00067   int N1() { return num1; }
00068   int N2() { return num2; }
00069   int N3() { return num3; }
00070 
00071   // Speicher fuer lokale Steifigkeitsmatrizen
00072   double Xm0, Ym0, Zm0;
00073   double Xm1, Ym1, Zm1;
00074   double Xm2, Ym2, Zm2;
00075   double Xm3, Ym3, Zm3;
00076 
00077   // Fuer Tetraeder, die eine Randflaeche haben
00078   virtual bool Boundary_tet() { return false; }
00079   virtual double Give_det_surface() { return 0.0; }
00080   virtual void    Put_det_surface(double value) { };
00081 
00082   // test interior edge and face angles
00083   inline bool Check_angles(Bo_description* desc);
00084 
00085   // for cell variable
00086   double *Give_variable() { return var; };
00087   void    Set_var(double *v) { var = v; };
00088 
00089   virtual ~Tetraeder_storage() {
00090     delete next;
00091     if(var!=NULL) delete var;
00092   }
00093 
00094  protected:
00095   int num0;  int num1;  int num2;  int num3;
00096   double det;
00097   Tetraeder_storage* next;
00098 
00099   // for cell variable
00100   double *var;
00101 };
00102 
00103 // Tetraeder, die eine Randflaeche haben
00104 class Boundary_tetraeder_storage : public Tetraeder_storage {
00105  public:
00106   Boundary_tetraeder_storage(Bo_description* desc, 
00107                              int P0, int P1, int P2, int P3,
00108                              Tetraeder_storage* Next) : 
00109     Tetraeder_storage(Next) {
00110     num0 = P0; num1 = P1; num2 = P2; num3 = P3;
00111   };
00112 
00113   bool Boundary_tet() { return true; }
00114   double Give_det_surface()             { return det_surface; }
00115   void    Put_det_surface(double value) { det_surface = value; }
00116 
00117   ~Boundary_tetraeder_storage() {
00118     delete next;
00119     if(var!=NULL) delete var;
00120   }
00121  private:
00122   double det_surface;
00123 };
00124 
00125 
00127 // 2. Beschreibung einer Randzelle;
00128 // dies wird jedoch nicht abgespeichert,
00129 // sondern nur temporaer erzeugt
00131 
00132 class BoCeData;
00133 
00134 class Bo_description {
00135  public:
00136   Bo_description(); // Konstruktor, setzt alles false bzw. 0.0
00137   void Put_zero();  // setzt alles false bzw. 0.0, wie Konstruktor
00138 
00139   // Abfragen der Informationen ueber die Zelle
00140   bool corner_point(dir_sons e);          // Ist Eckpunkt e im Gebiet?
00141   bool edge_point(dir_sons e,dir_3D d);   // Ist Kantenpunkt mit Ecke e und
00142                                           // Richtung d im Gebiet?
00143                                           // (Hier ist gemeint EW, NS, TD) 
00144   bool edge_point(Edge_Corner_point poi);
00145   double h(dir_sons e,dir_3D d);          // Falls edge_point(e,d)==true :
00146                                           // Abstand von Ecke e in Richtung d
00147                                           // zum Randpunkt
00148   bool Edge(Edges_cell ed);               // Ist ed innere Kante?
00149   double Meshsize();                      // Gib Maschenweite der Zelle
00150   int  edge_info();                       // Gib die ganze Information 
00151                                           // ueber Kanten
00152 
00153   // Koordinaten der Punkte:  bezueglich [0,h^3]
00154   D3vector coord(dir_sons e);             // Koordinate eines Eckpunktes
00155   D3vector coord(dir_sons e,dir_3D);      // Koordinate eines Kantenpunktes
00156   D3vector coord(Edge_Corner_point poi);
00157 
00158   // Setzen der Informationen ueber die Zelle
00159   void Put_corner_point(dir_sons e);                 // Setze einen Eckpunkt
00160   void Put_edge_point(dir_sons e,dir_3D d,double h); // Setze einen Kantenpunkt
00161   void Put_Meshsize(double H);                       // Setze Maschenweite 
00162   void Put_edge(Edges_cell ed);                      // Setze innere Kante
00163 
00164   // Funktionen zum Testen:  muss spaeter wohl weg:
00165   void Test_Initialisierung();
00166 
00167   // Nummern der Eck und Kantenpunkte, die man spaeter setzen kann
00168   void Set_num_corner(dir_sons e, int num);
00169   void Set_num_edge_poi(dir_sons e, dir_3D d, int num);
00170   void Set_num_cellpoi(int num);
00171   int Num_corner(dir_sons e);
00172   int Num_edge_poi(dir_sons e,dir_3D d);
00173   int Num(Edge_Corner_point poi);
00174   
00175   // For calc of max interior angle
00176   void Put_bocedata(BoCeData* boce) { bocedat=boce; };
00177   BoCeData* Give_bocedata() { return bocedat; };
00178 
00179   // Only for some testing:
00180   double * Give_dis() { return dis; }
00181 
00182  private:
00183   bool corner[8];    // Info ueber Eckpunkte                
00184   bool edge_poi[24]; // Info ueber  Kantenpunkte, Implementierung: e*3+(d>>1) 
00185   double dis[24];    // Abstand bei Kantenpunkte, Implementierung: e*3+(d>>1) 
00186   int  edge;         // Info ueber Kanten
00187   double H;        // Maschenweite
00188 
00189   // Hilfsspeicher, in diesen stehen spaeter die Nummern der Punkte
00190   int num_corner[8];
00191   int num_edge_poi[24];
00192   int num_cellpoi; 
00193 
00194   BoCeData* bocedat; 
00195 };
00196 
00197 
00199 // 3. Speicher fuer Randzellfreiheitsgrad
00200 // Die lokale Koordinate local_coord
00201 // bezieht sich auf den Mittelpunkt der Randzelle
00202 // Randzelle [-H/2,H/2]^3 Zelle
00204 class Bocellpoint {
00205  public:
00206   Bocellpoint(D3vector l_coord) { 
00207     local_coord=l_coord;
00208     label_level=NULL;
00209   };
00210   D3vector Give_local_coord() { return local_coord; };
00211   void Set_number_avs(int avs_num) { number_avs = avs_num; };
00212   int  Number_avs() { return number_avs; };
00213 
00214   int *label_level; // for boundary labels
00215  private:
00216   D3vector local_coord;
00217   int number_avs;
00218 };
00219 
00220 
00221 
00222 
00224 // 5. Beschreibung einer Randzelle;
00225 // und Informationen ueber FE-Tetraeder
00226 // und Information ueber Randzellfreiheitsgrad
00227 // dies wird abgespeicher
00229 
00230 
00231 class BoCeData {
00232  public:
00233   BoCeData() { bocellpoint=NULL; 
00234                Tets_boundary=NULL;
00235                Tets=NULL;
00236                vars = NULL;                //neu
00237                info = NULL;                //neu
00238                hhh  = NULL;
00239   };
00240 
00241 
00242   // Additionals:
00243   int  Give_total_number_points() const;
00244   bool Is_point_clipped_point(int num) const;
00245 
00246   void Set_h(double *h, Bo_description& desc);
00247 
00248 
00249   // Funktionen zu FE-Tetraeder:
00250   void Calc_FE_elements(Bo_description& desc);   // Berechne FE-elemente
00251   int Give_number_points() const; // Gib Anzahl N der Punkte (Eck- und Kanten-)
00252                                   // Nummerierung: 0,...,N-1
00253                                   // N ist Nummer des  Randzellfreiheitsgrad
00254                                   // falls vorhanden
00255   void Add_Tetraeder(Bo_description* desc, int P0, int P1, int P2, int P3);
00256   void Add_Tetraeder_bo(Bo_description* desc, int P0, int P1, int P2, int P3);
00257 
00258   // Koordinaten der Punkte bezueglich [0,H]^3 Zelle
00259   D3vector coord(int num, double* h);       
00260   double *hhh;            // neu fuer Andreas
00261 
00262   // Funktionen die Informationen ueber Punktes mit Nummer num angeben:
00263   inline dir_sons corner(int num) const;   // Ecke des Punktes mit Nummer num
00264   inline Cell_type_points edge_point(int num) const; 
00265                         // Ist Punkt mit Nummer num
00266                         // Kantenpunkt, oder Eckpunkt oder Zellfreiheitsgrad?
00267   inline dir_3D edge_dir(int num); // Falls Punkt mit Nummer num Kantenpunkt:
00268                                    // In welcher Richtung liegt die Kante?
00269   bool Edge(Edges_cell ed);        // Ist ed innere Kante?
00270 
00271   inline double Meshsize();        // Gib Maschenweite der Zelle
00272 
00273   // Funktionen die die Implementierung der lokalen Bilinearform vereinfachen:
00274   bool boundary_EW(int num);       // Gibt es in EW von Ecke num aus Randpunkt?
00275   bool boundary_NS(int num);       // Gibt es in NS von Ecke num aus Randpunkt?
00276   bool boundary_TD(int num);       // Gibt es in TD von Ecke num aus Randpunkt?
00277 
00278   // Anfang der Liste der Tetraeder:
00279   Tetraeder_storage* Give_tets() const { return Tets; } 
00280   Boundary_tetraeder_storage* Give_boundary_tets() const
00281     { return Tets_boundary; } 
00282 
00283   // Randzellfreiheitsgrad
00284   bool Exists_bocellpoint() const { return bocellpoint!=NULL; }
00285   int* Give_label_level() const { return bocellpoint->label_level; }
00286   void Set_label_level(int* ll) { bocellpoint->label_level = ll; }
00287   void Set_Dirichlet(int num)   { bocellpoint->label_level[num-1]=true; }
00288   bool Is_Dirichlet(int num) const { return bocellpoint->label_level[num-1]; }
00289 
00290   void Set_number_avs(int avs_num);
00291   int Number_avs();
00292   void Add_Bo_freedom(D3vector local_coord); 
00293   D3vector Local_coord_bocellpoint(); // bezueglich [-H/2,H/2]^3 Zelle
00294   inline D3vector Coord_bocellpoint(); // bezueglich [0,H]^3 Zelle
00295   inline D3vector Coord_bocellpoint_normal() const; // bezueglich [0,1]^3 Zelle
00296 
00297 
00298   // Zum setzen der Zeiger auf die Variablen
00299   void Set_variable_pointer(int num, double* poi);
00300   // Zeiger auf die Variablen der Punkte
00301   double** vars; // zerst Nummer des Punktes, dann Nummer der Variable
00302 
00303   // Zur Fehlersuche: Informationen ausdrucken:
00304   void Print();
00305   void Analyse_angles(Bo_description& desc);   // Analysiere Winkel
00306 
00307   ~BoCeData() {
00308     if(bocellpoint!=NULL)
00309       delete bocellpoint;
00310     if(Tets!=NULL)
00311       delete Tets;
00312     if(vars!=NULL)                //neu
00313       delete vars;                //neu
00314     if(info!=NULL)                //neu
00315       delete info;                //neu
00316   };
00317 
00318 private:
00319   // Setzt Informationen ueber Punkte und H entsprechend desc
00320   void Initialize(Bo_description& desc);
00321   // Diese Funktion verwendet folgende 
00322   // Funktionen zur Eingabe:
00323   void Put_corner_point(int num, dir_sons c);       // Setze Eckpunkt
00324   void Put_edge_point(int num,dir_sons c,dir_3D d); // Setze Kantenpunkt
00325   void Allocate(int n_points);              // Stelle Speicher fuer n_points
00326                                             // bereit
00327   void Put_edge_info(int ed);
00328   void Put_Meshsize(double h);                      // Setze Maschenweite 
00329 
00330   int number_points;     // Anzahl der Ecken
00331   int*    info;           // Zeiger auf den Vektor der Informationen 
00332                           // ueber dir Ecken
00333   int  edge;              // Info ueber Kanten
00334   double H;               // Maschenweite
00335 
00336 
00337 
00338   // Anfang der Liste der Tetraeder:
00339   Tetraeder_storage* Tets; 
00340   Boundary_tetraeder_storage* Tets_boundary; 
00341 
00342   // Zeiger auf eventuell vorhandenen Randzellfreiheitsgrad
00343   Bocellpoint* bocellpoint;
00344 
00345   // Erklaerung zu info (Zur Anwendung unwichtig!!)
00346   // -----------------------------------------------------------------
00347   // Bit:    1-3       | 4            | 5 - 7                        |
00348   // Typ     dir_sons  | bool         | dir_3D                       |
00349   // Inhalt: Ecke      | Kantenpunkt? | Richtung der Kante           |
00350   // -----------------------------------------------------------------
00351 
00352 
00353   // Einfache Printfunktionen:
00354   void Print(dir_3D d);
00355   void Print(dir_sons d);
00356   void Print(Edges_cell ed);
00357 };
00358 
00359 
00361 // 6. inline Implementierung einiger Memberfunktionenen
00363 
00364 
00365 inline Bo_description::Bo_description() {
00366   static int i;
00367   for(i=0;i<8;++i)  corner[i] = false;
00368   for(i=0;i<24;++i) edge_poi[i]   = false;
00369   for(i=0;i<24;++i) dis[i]    = 0.0;
00370   edge = 0;
00371 }
00372 
00373 inline void Bo_description::Put_zero() {
00374   static int i;
00375   for(i=0;i<8;++i)  corner[i] = false;
00376   for(i=0;i<24;++i) edge_poi[i]   = false;
00377   for(i=0;i<24;++i) dis[i]    = 0.0;
00378   edge = 0;
00379 }
00380 
00381 inline bool Bo_description::corner_point(dir_sons e) {
00382   return corner[e];
00383 };  
00384 
00385 inline bool Bo_description::edge_point(dir_sons e,dir_3D d) {
00386   return edge_poi[3*e + (d>>1)];
00387 }
00388 
00389 inline void Bo_description::Set_num_corner(dir_sons e, int num) {
00390   num_corner[e]=num;
00391 }
00392 inline void Bo_description::Set_num_edge_poi(dir_sons e, dir_3D d, int num) {
00393   num_edge_poi[3*e + (d>>1)] = num;
00394 };
00395 inline void Bo_description::Set_num_cellpoi(int num) {
00396   num_cellpoi = num;
00397 };
00398 
00399 inline int Bo_description::Num_corner(dir_sons e) {
00400   /*
00401  if(e<0 || e>10) { // yet another uninitialized obj
00402    e=(dir_sons)0;
00403    printf("%4d ../boundary.h : Ne=%d\n",
00404           __LINE__,e);
00405  }
00406  fflush(stdout);                  
00407   */
00408   return num_corner[e];
00409 }
00410 inline int Bo_description::Num_edge_poi(dir_sons e, dir_3D d) {
00411   return num_edge_poi[3*e + (d>>1)];
00412 };
00413 
00414 inline int Bo_description::Num(Edge_Corner_point poi) {
00415   if(poi.edge_point == edge_poi_typ)   return Num_edge_poi(poi.corner,poi.d);
00416   if(poi.edge_point == corner_poi_typ) return Num_corner(poi.corner);
00417   return num_cellpoi; 
00418 }
00419 
00420 
00421 inline bool Bo_description::edge_point(Edge_Corner_point poi) {
00422   return edge_point(poi.corner,poi.d);
00423 };
00424 
00425 inline double Bo_description::h(dir_sons e,dir_3D d) {
00426   return dis[3*e + (d>>1)];
00427 }
00428 
00429 inline double Bo_description::Meshsize() {
00430   return H;
00431 }
00432 
00433 inline void Bo_description::Put_Meshsize(double h) {
00434   H=h;
00435 }
00436 
00437 inline void Bo_description::Put_corner_point(dir_sons e) {
00438   corner[e]=true;
00439 }
00440 
00441 inline void Bo_description::Put_edge_point(dir_sons e,dir_3D d,double h) {
00442   edge_poi[3*e + (d>>1)] = true;
00443   dis[3*e + (d>>1)] = h;
00444   // New:
00445   Put_corner_point(e);
00446 }
00447 
00448 inline bool Bo_description::Edge(Edges_cell ed) {
00449   return (bool)((edge>>ed)&1);
00450 }
00451 
00452 inline int Bo_description::edge_info() { return edge; };
00453 
00454 inline void Bo_description::Put_edge(Edges_cell ed) {
00455   edge = edge|(1<<ed);
00456   // New:
00457   Put_corner_point(Transform(ed,Ld));
00458   Put_corner_point(Transform(ed,Rd));
00459 }
00460 
00461 inline D3vector Bo_description::coord(dir_sons e) {
00462   return D3vector((e&1)*H,((e>>1)&1)*H,(e>>2)*H);
00463 };
00464 
00465 inline D3vector Bo_description::coord(dir_sons e,dir_3D d) {
00466   if(d < Sdir)
00467      return D3vector((e&1)*H +  h(e,d) *(2*d-1), 
00468                      ((e>>1)&1)*H,(e>>2)*H);
00469   if(d > Ndir)
00470     return D3vector((e&1)*H,((e>>1)&1)*H,
00471                     (e>>2)*H + h(e,d) * (2*d-9));
00472   return D3vector((e&1)*H, 
00473                   ((e>>1)&1)*H + h(e,d) * (2*d-5),(e>>2)*H);
00474 
00475 };
00476 
00477 inline D3vector Bo_description::coord(Edge_Corner_point poi) {
00478   if(poi.edge_point == edge_poi_typ) return coord(poi.corner,poi.d);
00479   if(poi.edge_point == corner_poi_typ) return coord(poi.corner);
00480   return Give_bocedata()->Coord_bocellpoint();
00481 }
00482 
00484 
00485 inline D3vector BoCeData::Local_coord_bocellpoint() {
00486   if(developer_version) {
00487     if(bocellpoint == NULL)
00488       cout << " \n Fehler in BoCeData::Local_coord_bocellpoint!" << endl;
00489   }
00490   return bocellpoint->Give_local_coord();
00491 }
00492 
00493 inline D3vector BoCeData::Coord_bocellpoint() {
00494   if(developer_version) {
00495     if(bocellpoint == NULL)
00496       cout << " \n Fehler in BoCeData::Local_coord_bocellpoint!" << endl;
00497   }
00498   return bocellpoint->Give_local_coord() + D3vector(0.5,0.5,0.5)*H;
00499 }
00500 
00501 inline D3vector BoCeData::Coord_bocellpoint_normal() const {
00502   return bocellpoint->Give_local_coord() / H + D3vector(0.5,0.5,0.5);
00503 }
00504 
00505 inline int BoCeData::Number_avs() {
00506   if(developer_version) {
00507     if(bocellpoint == NULL)
00508       cout << " \n Fehler in BoCeData::Number_avs!" << endl;
00509   }
00510   return bocellpoint->Number_avs();
00511 }
00512 
00513 inline void BoCeData::Set_number_avs(int avs_num) {
00514   if(developer_version) {
00515     if(bocellpoint == NULL)
00516       cout << " \n Fehler in BoCeData::Set_number_avs!" << endl;
00517   }
00518   bocellpoint->Set_number_avs(avs_num);
00519 }
00520 
00521 inline void BoCeData::Add_Bo_freedom(D3vector local_coord) {
00522   if(developer_version) {
00523     if(bocellpoint != NULL)
00524       cout << " \n Randzellfreiheitsgrad existiert schon! " << endl;
00525   }
00526   bocellpoint = new Bocellpoint(local_coord);
00527 }
00528 
00529 
00530 inline void BoCeData::Add_Tetraeder(Bo_description* desc,
00531                                     int P0, int P1, int P2, int P3) {
00532   Tets = new Tetraeder_storage(desc,P0,P1,P2,P3,Tets);
00533 }
00534 
00535 inline void BoCeData::Add_Tetraeder_bo(Bo_description* desc,
00536                                        int P0, int P1, int P2, int P3) {
00537   Tets_boundary =
00538     new Boundary_tetraeder_storage(desc,P0,P1,P2,P3,Tets_boundary);
00539 }
00540 
00541 
00542 inline D3vector BoCeData::coord(int num, double *h) {
00543   dir_sons e;
00544   dir_3D d;
00545   if(developer_version) {
00546     if(num<0 || num > number_points) {
00547       cout << " \n Fehler in BoCeData::coord " << endl;
00548       return D3vector(0,0,0);
00549     }
00550   }
00551   if(num == number_points) {
00552     return bocellpoint->Give_local_coord() + D3vector(0.5,0.5,0.5)*H;
00553   }
00554   e = corner(num);
00555   if(edge_point(num)) {
00556     d = edge_dir(num);
00557     if(d < Sdir)
00558       return D3vector((e&1)*H +  h[num] *(2*d-1), 
00559                       ((e>>1)&1)*H,(e>>2)*H);
00560     if(d > Ndir)
00561       return D3vector((e&1)*H,((e>>1)&1)*H,
00562                       (e>>2)*H + h[num] * (2*d-9));
00563     return D3vector((e&1)*H, 
00564                     ((e>>1)&1)*H + h[num] * (2*d-5),(e>>2)*H);
00565   }
00566   else {
00567     return D3vector((e&1)*H,((e>>1)&1)*H,(e>>2)*H);
00568   }
00569 }
00570 
00571                            
00572 
00573 inline bool BoCeData::Edge(Edges_cell ed) {
00574   return (bool)((edge>>ed)&1);
00575 }
00576 
00577 inline void BoCeData::Put_edge_info(int ed) { edge=ed; };
00578 
00579 inline double BoCeData::Meshsize() {
00580   return H;
00581 }
00582 
00583 inline void BoCeData::Put_Meshsize(double h) {
00584   H=h;
00585 }
00586 
00587 
00588 
00589 inline int BoCeData::Give_number_points() const {
00590   return number_points;
00591 };
00592 
00593 
00594 inline dir_sons BoCeData::corner(int num) const {
00595   if(developer_version) {
00596     if(num<0 || num >= number_points) {
00597       cout << " \n Fehler in BoCeData::corner " << endl;
00598       return WSDd;
00599     }
00600   }
00601   return (dir_sons)(info[num]&7);
00602 }; 
00603 
00604 inline Cell_type_points BoCeData::edge_point(int num) const {
00605   if(developer_version) {
00606     if(num<0 || num > number_points) {
00607       cout << " \n Fehler in BoCeData::edge_point " << endl;
00608       return corner_poi_typ;
00609     }
00610   }
00611   if( num == number_points) return cell_poi_typ;
00612   else return (Cell_type_points)((info[num]>>3)&1);
00613 };
00614 
00615 
00616 inline dir_3D BoCeData::edge_dir(int num) {
00617   if(developer_version) {
00618     if(num<0 || num >= number_points) {
00619       cout << " \n Fehler in BoCeData::edge_dir " << endl;
00620       return Wdir;
00621     }
00622   }
00623   return (dir_3D)((info[num]>>4)&7);
00624 }
00625 
00626 
00627 inline bool BoCeData::boundary_EW(int num) {
00628   if(developer_version) {
00629     if(num<0 || num >= number_points) {
00630       cout << " \n Fehler in BoCeData::boundary_EW " << endl;
00631       return false;
00632     }
00633   }
00634   return (bool)((info[num]>>7)&1);
00635 };  
00636 
00637 
00638 inline bool BoCeData::boundary_NS(int num) {
00639   if(developer_version) {
00640     if(num<0 || num >= number_points) {
00641       cout << " \n Fehler in BoCeData::boundary_NS " << endl;
00642       return false;
00643     }
00644   }
00645   return (bool)((info[num]>>8)&1);
00646 };  
00647 
00648 
00649 inline bool BoCeData::boundary_TD(int num) {
00650   if(developer_version) {
00651     if(num<0 || num >= number_points) {
00652       cout << " \n Fehler in BoCeData::boundary_TD " << endl;
00653       return false;
00654     }
00655   }
00656   return (bool)((info[num]>>9)&1);
00657 };  
00658 
00659 
00660 inline void BoCeData::Put_corner_point(int num, dir_sons c) {
00661   if(developer_version) {
00662     if(num<0 || num >= number_points) {
00663       cout << " \n Fehler in BoCeData::Put_corner " << endl;
00664       return;
00665     }
00666   }
00667   info[num] = c; 
00668 }
00669 
00670 inline void BoCeData::Put_edge_point(int num,dir_sons c, dir_3D d) {
00671   if(developer_version) {
00672     if(num<0 || num >= number_points) {
00673       cout << " \n Fehler in BoCeData::Put_edge_point " << endl;
00674       return;
00675     }
00676   }
00677   info[num] = c; 
00678   info[num] =  info[num] | (1<<3); 
00679   info[num] = (info[num] & (~(7<<4))) | (d<<4); 
00680 }
00681 
00682 inline void BoCeData::Allocate(int n_points) {
00683   static int i;
00684   number_points = n_points;
00685   info   = new int[number_points];
00686   for(i=0;i<number_points;i++) info[i]=0;
00687   Tets   = NULL; 
00688 }
00689 
00690 inline void BoCeData::Set_variable_pointer(int num, double* poi) {
00691   vars[num]=poi;
00692 };
00694 
00695 inline Tetraeder_storage::Tetraeder_storage(Bo_description* desc,
00696                                      int P0, int P1, int P2, int P3,
00697                                      Tetraeder_storage* Next) {
00698     next = Next; num0 = P0; num1 = P1; num2 = P2; num3 = P3; 
00699     var= NULL;
00700 
00701     if(developer_version) {
00702       Check_angles(desc);
00703     }
00704 };
00705 
00706 inline bool Tetraeder_storage::Check_angles(Bo_description* desc) {
00707   bool oh_key;
00708 
00709   oh_key = true;
00710   // 1. Calc Edge_Corner_point of Tet
00711   Edge_Corner_point ec0;
00712   Edge_Corner_point ec1;
00713   Edge_Corner_point ec2;
00714   Edge_Corner_point ec3;
00715   
00716   ec0.edge_point=desc->Give_bocedata()->edge_point(num0);
00717   if(ec0.edge_point!=cell_poi_typ)
00718     ec0.corner    =desc->Give_bocedata()->corner(num0);
00719   if(ec0.edge_point==edge_poi_typ)
00720     ec0.d = desc->Give_bocedata()->edge_dir(num0);
00721   
00722   
00723   ec1.edge_point=desc->Give_bocedata()->edge_point(num1);
00724   if(ec1.edge_point!=cell_poi_typ)
00725     ec1.corner    =desc->Give_bocedata()->corner(num1);
00726   if(ec1.edge_point==edge_poi_typ)
00727     ec1.d = desc->Give_bocedata()->edge_dir(num1);
00728   
00729   
00730   ec2.edge_point=desc->Give_bocedata()->edge_point(num2);
00731   if(ec2.edge_point!=cell_poi_typ)
00732     ec2.corner    =desc->Give_bocedata()->corner(num2);
00733   if(ec2.edge_point==edge_poi_typ)
00734     ec2.d = desc->Give_bocedata()->edge_dir(num2);
00735   
00736   ec3.edge_point=desc->Give_bocedata()->edge_point(num3);
00737   if(ec3.edge_point!=cell_poi_typ)
00738     ec3.corner    =desc->Give_bocedata()->corner(num3);
00739   if(ec3.edge_point==edge_poi_typ)
00740     ec3.d = desc->Give_bocedata()->edge_dir(num3);
00741   
00742   // Berechnung der Winkel
00743   double max_face_ang;
00744   double max_edge_ang;
00745   max_face_ang = calc_maximal_face_angle(desc->coord(ec0),
00746                                          desc->coord(ec1),
00747                                          desc->coord(ec2),
00748                                          desc->coord(ec3));
00749   if(max_face_ang > 163) {
00750     cout << "\n Error: Too large interior angle!" <<
00751       " Tell Christoph Pflaum this error! ";
00752     cout << "\n Maximal interior face angle: " << max_face_ang << endl;
00753     desc->coord(ec0).Print();  cout << endl;
00754     desc->coord(ec1).Print();  cout << endl;
00755     desc->coord(ec2).Print();  cout << endl;
00756     desc->coord(ec3).Print();  cout << endl;
00757     oh_key = false;
00758   }
00759   max_edge_ang = calc_maximal_edge_angle(desc->coord(ec0),
00760                                          desc->coord(ec1),
00761                                          desc->coord(ec2),
00762                                          desc->coord(ec3));
00763   if(max_edge_ang > 144) {
00764     cout << "\n Error: Too large interior angle!" <<
00765       " Tell Christoph Pflaum this error! ";
00766     cout << "\n Maximal interior edge angle: " << max_edge_ang << endl;
00767     desc->coord(ec0).Print();  cout << endl;
00768     desc->coord(ec1).Print();  cout << endl;
00769     desc->coord(ec2).Print();  cout << endl;
00770     desc->coord(ec3).Print();  cout << endl;
00771     oh_key = false;
00772   }
00773   return oh_key;
00774 };
00775 
00776 
00777 
00778 // For Ralf
00779 inline int  BoCeData::Give_total_number_points() const {
00780   if(Exists_bocellpoint()) return number_points+1;
00781   else                     return number_points;
00782 }
00783 
00784 inline bool BoCeData::Is_point_clipped_point(int num) const {
00785   if(num<number_points) return true;
00786   return false;
00787 }
00788 
00789 #endif

Generated on Fri Nov 2 01:25:58 2007 for IPPL by doxygen 1.3.5