LCOV - code coverage report
Current view: top level - geom/virtual - PartSurfFacetTool.cpp (source / functions) Hit Total Coverage
Test: coverage_sk.info Lines: 1 1141 0.1 %
Date: 2020-06-30 00:58:45 Functions: 2 20 10.0 %
Branches: 2 3238 0.1 %

           Branch data     Line data    Source code
       1                 :            : #include "PartSurfFacetTool.hpp"
       2                 :            : #include "CubitMessage.hpp"
       3                 :            : #include "DLIList.hpp"
       4                 :            : #include "GeometryQueryEngine.hpp"
       5                 :            : 
       6                 :            : #include "PartitionSurface.hpp"
       7                 :            : #include "PartitionCurve.hpp"
       8                 :            : #include "PartitionPoint.hpp"
       9                 :            : #include "TDVGFacetOwner.hpp"
      10                 :            : 
      11                 :            : #include "CubitFacetData.hpp"
      12                 :            : #include "CubitFacetEdgeData.hpp"
      13                 :            : #include "CubitPointData.hpp"
      14                 :            : 
      15                 :            : #include "RefVertex.hpp"
      16                 :            : #include "RefEdge.hpp"
      17                 :            : #include "GfxDebug.hpp"
      18                 :            : #include "GMem.hpp"
      19                 :            : 
      20                 :            : #undef PART_SURF_REFACET
      21                 :            : 
      22                 :          0 : void PartSurfFacetTool::validate_facets( PartitionSurface* mySurface )
      23                 :            : {
      24                 :            :   int i, j, k;
      25         [ #  # ]:          0 :   DLIList<CubitFacetData*> facets;
      26 [ #  # ][ #  # ]:          0 :   DLIList<CubitFacet*> pt_facets, edge_facets;
         [ #  # ][ #  # ]
      27 [ #  # ][ #  # ]:          0 :   DLIList<CubitFacetEdge*> pt_edges;
      28         [ #  # ]:          0 :   mySurface->get_facet_data(facets);
      29 [ #  # ][ #  # ]:          0 :   for( i = facets.size(); i--; )
      30                 :            :   {
      31         [ #  # ]:          0 :     CubitFacetData* facet = facets.get_and_step();
      32         [ #  # ]:          0 :     for ( j = 0; j < 3; j++ )
      33                 :            :     {
      34         [ #  # ]:          0 :       CubitFacetEdge* edge = facet->edge(j);
      35         [ #  # ]:          0 :       if ( !edge )
      36                 :            :       {
      37 [ #  # ][ #  # ]:          0 :         PRINT_ERROR("Facet with NULL edge.\n");
         [ #  # ][ #  # ]
      38                 :          0 :         continue;
      39                 :            :       }
      40                 :            :       
      41 [ #  # ][ #  # ]:          0 :       if ( PartitionEntity* ent = TDVGFacetOwner::get(edge) )
      42                 :            :       {
      43         [ #  # ]:          0 :         PartitionCurve* curve = dynamic_cast<PartitionCurve*>(ent);
      44         [ #  # ]:          0 :         if (!curve)
      45                 :            :         {
      46 [ #  # ][ #  # ]:          0 :           PRINT_ERROR("Facet edge owned by non-curve %s %p\n",
         [ #  # ][ #  # ]
                 [ #  # ]
      47         [ #  # ]:          0 :             typeid(*ent).name(), (void*)ent);
      48         [ #  # ]:          0 :           GfxDebug::draw_line( edge->point(0)->coordinates(),
      49         [ #  # ]:          0 :                                edge->point(1)->coordinates(),
      50 [ #  # ][ #  # ]:          0 :                                CUBIT_RED_INDEX );
                 [ #  # ]
      51                 :          0 :           continue;
      52                 :            :         }
      53                 :            :         
      54                 :          0 :         int edge_use_count = 0;
      55 [ #  # ][ #  # ]:          0 :         for ( k = 0; k < edge->num_adj_facets(); k++ )
      56 [ #  # ][ #  # ]:          0 :           if ( (const PartitionEntity*)TDVGFacetOwner::get(edge->adj_facet(k)) == mySurface )
         [ #  # ][ #  # ]
      57                 :          0 :             edge_use_count++;
      58         [ #  # ]:          0 :         assert(edge_use_count);
      59                 :            :         
      60                 :          0 :         int curve_use_count = 0;
      61                 :          0 :         int coedge_count = 0;
      62                 :          0 :         PartitionCoEdge* coedge = 0;
      63 [ #  # ][ #  # ]:          0 :         while (( coedge = curve->next_coedge(coedge) ))
      64                 :            :         {
      65 [ #  # ][ #  # ]:          0 :           if (coedge->get_loop())
      66                 :            :           {
      67                 :          0 :             coedge_count++;
      68 [ #  # ][ #  # ]:          0 :             if (coedge->get_loop()->get_surface() == mySurface)
                 [ #  # ]
      69                 :          0 :               curve_use_count++;
      70                 :            :           }
      71                 :            :         }
      72                 :            :           
      73 [ #  # ][ #  # ]:          0 :         RefEdge* curve_owner = dynamic_cast<RefEdge*>(curve->topology_entity());
      74 [ #  # ][ #  # ]:          0 :         if ( coedge_count != edge->num_adj_facets() )
      75                 :            :         {
      76 [ #  # ][ #  # ]:          0 :           PRINT_ERROR("Curve %p (RefEdge %d): Curve in %d partition surfaces "
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
      77                 :            :                       "has facet edge in %d facets.\n", (void*)curve,
      78                 :            :                       curve_owner ? curve_owner->id() : 0,
      79         [ #  # ]:          0 :                       coedge_count, edge->num_adj_facets() );
      80         [ #  # ]:          0 :           GfxDebug::draw_line( edge->point(0)->coordinates(),
      81         [ #  # ]:          0 :                                edge->point(1)->coordinates(),
      82 [ #  # ][ #  # ]:          0 :                                CUBIT_RED_INDEX );
                 [ #  # ]
      83                 :            :         }
      84                 :            :         
      85         [ #  # ]:          0 :         if ( curve_use_count != edge_use_count )
      86                 :            :         {
      87 [ #  # ][ #  # ]:          0 :           PRINT_ERROR("Curve %p (RefEdge %d): Curve used in %d coedges of "
         [ #  # ][ #  # ]
                 [ #  # ]
      88                 :            :                       "this surface exists in %d facets of this surface.\n", 
      89                 :            :                       (void*)curve,
      90                 :            :                       curve_owner ? curve_owner->id() : 0,
      91         [ #  # ]:          0 :                       curve_use_count, edge_use_count );
      92         [ #  # ]:          0 :            GfxDebug::draw_line( edge->point(0)->coordinates(),
      93         [ #  # ]:          0 :                                 edge->point(1)->coordinates(),
      94 [ #  # ][ #  # ]:          0 :                                 CUBIT_RED_INDEX );
                 [ #  # ]
      95                 :            :         }
      96                 :            :       }
      97                 :            :       else  // FacetEdge has no owner
      98                 :            :       {
      99 [ #  # ][ #  # ]:          0 :         if (edge->num_adj_facets() != 2)
     100                 :            :         {
     101 [ #  # ][ #  # ]:          0 :           PRINT_ERROR("Interior facet edge is %d-valent.\n", edge->num_adj_facets());
         [ #  # ][ #  # ]
                 [ #  # ]
     102         [ #  # ]:          0 :           GfxDebug::draw_line( edge->point(0)->coordinates(),
     103         [ #  # ]:          0 :                                edge->point(1)->coordinates(),
     104 [ #  # ][ #  # ]:          0 :                                CUBIT_RED_INDEX );
                 [ #  # ]
     105                 :            :         }
     106                 :            :       }
     107                 :            :       
     108                 :          0 :       bool found = false;
     109 [ #  # ][ #  # ]:          0 :       for ( k = 0; k < edge->num_adj_facets(); k++ )
     110                 :            :       {
     111         [ #  # ]:          0 :         CubitFacet* edge_facet = edge->adj_facet(k);
     112         [ #  # ]:          0 :         if( edge_facet == facet )
     113                 :          0 :           found = true;
     114                 :            :         
     115         [ #  # ]:          0 :         int index = edge_facet->edge_index(edge);
     116         [ #  # ]:          0 :         if( index < 0 )
     117                 :            :         {
     118 [ #  # ][ #  # ]:          0 :           PRINT_ERROR("edge->facet link missing facet->edge link.\n");
         [ #  # ][ #  # ]
     119                 :          0 :           continue;
     120                 :            :         }
     121         [ #  # ]:          0 :         CubitPoint* fp1 = edge_facet->point((index+1)%3);
     122         [ #  # ]:          0 :         CubitPoint* fp2 = edge_facet->point((index+2)%3);
     123                 :          0 :         int sense = 1;
     124 [ #  # ][ #  # ]:          0 :         if( fp1 == edge->point(1) && fp2 == edge->point(0) )
         [ #  # ][ #  # ]
                 [ #  # ]
     125                 :          0 :           sense = -1;
     126 [ #  # ][ #  # ]:          0 :         else if( fp1 != edge->point(0) || fp2 != edge->point(1) )
         [ #  # ][ #  # ]
                 [ #  # ]
     127                 :            :         {
     128 [ #  # ][ #  # ]:          0 :           PRINT_ERROR("Facet adjacent to edge does not contain edge end points.\n");
         [ #  # ][ #  # ]
     129         [ #  # ]:          0 :           GfxDebug::draw_line( edge->point(0)->coordinates(),
     130         [ #  # ]:          0 :                                edge->point(1)->coordinates(),
     131 [ #  # ][ #  # ]:          0 :                                CUBIT_RED_INDEX );
                 [ #  # ]
     132                 :          0 :           continue;
     133                 :            :         }
     134         [ #  # ]:          0 :         if ( sense != edge_facet->edge_use(index) )
     135                 :            :         {
     136                 :            :           //PRINT_ERROR("Facet has incorrect edge use\n");
     137                 :            :         }
     138                 :            :       }
     139                 :            :       
     140         [ #  # ]:          0 :       if( !found )
     141 [ #  # ][ #  # ]:          0 :         PRINT_ERROR("facet->edge link missing edge->facet link.\n");
         [ #  # ][ #  # ]
     142                 :            :     }
     143                 :            :     
     144         [ #  # ]:          0 :     for ( j = 0; j < 3; j++ )
     145                 :            :     {
     146         [ #  # ]:          0 :       CubitPoint* point = facet->point(j);
     147         [ #  # ]:          0 :       pt_facets.clean_out();
     148         [ #  # ]:          0 :       point->facets(pt_facets);
     149                 :          0 :       bool found = false;
     150 [ #  # ][ #  # ]:          0 :       for ( k = pt_facets.size(); k--; )
     151                 :            :       {
     152         [ #  # ]:          0 :         CubitFacet* pt_facet = pt_facets.get_and_step();
     153         [ #  # ]:          0 :         if ( pt_facet == facet )
     154                 :          0 :           found = true;
     155 [ #  # ][ #  # ]:          0 :         else if( pt_facet->point_index(point) < 0 )
     156 [ #  # ][ #  # ]:          0 :           PRINT_ERROR("point->facet link missing facet->point link.\n");
         [ #  # ][ #  # ]
     157                 :            :       }
     158         [ #  # ]:          0 :       if( ! found )
     159 [ #  # ][ #  # ]:          0 :         PRINT_ERROR("facet->point link missing point->facet link.\n");
         [ #  # ][ #  # ]
     160                 :            :         
     161         [ #  # ]:          0 :       point->edges(pt_edges);
     162 [ #  # ][ #  # ]:          0 :       while (pt_edges.size())
     163                 :            :       {
     164         [ #  # ]:          0 :         CubitFacetEdge* edge = pt_edges.pop();
     165         [ #  # ]:          0 :         edge_facets.clean_out();
     166         [ #  # ]:          0 :         edge->facets(edge_facets);
     167                 :          0 :         int count = 0;
     168 [ #  # ][ #  # ]:          0 :         while (edge_facets.size())
     169 [ #  # ][ #  # ]:          0 :           if (TDVGFacetOwner::get(edge_facets.pop()) == mySurface)
         [ #  # ][ #  # ]
     170                 :          0 :             count++;
     171                 :            :         
     172                 :          0 :         bool draw = false;
     173         [ #  # ]:          0 :         if (count == 0) // not in this face
     174                 :            :          ;
     175 [ #  # ][ #  # ]:          0 :         else if (PartitionEntity* ent = TDVGFacetOwner::get(edge))
     176                 :            :         {
     177         [ #  # ]:          0 :           PartitionCurve* curve = dynamic_cast<PartitionCurve*>(ent);
     178 [ #  # ][ #  # ]:          0 :           if (curve->is_nonmanifold(mySurface))
     179                 :            :           {
     180         [ #  # ]:          0 :             if (count != 2)
     181                 :            :             {
     182                 :          0 :               draw = true;
     183 [ #  # ][ #  # ]:          0 :               PRINT_ERROR("Edge on non-manifold curve contained in %d facets.\n", count);
         [ #  # ][ #  # ]
     184                 :            :             }
     185                 :            :           } 
     186         [ #  # ]:          0 :           else if (count != 1)
     187                 :            :           {
     188                 :          0 :             draw = true; 
     189 [ #  # ][ #  # ]:          0 :             PRINT_ERROR("Boundary edge contained in %d facets.\n", count); 
         [ #  # ][ #  # ]
     190                 :            :           }
     191                 :            :         }
     192         [ #  # ]:          0 :         else if (count != 2)
     193                 :            :         { 
     194                 :          0 :           draw = true; 
     195 [ #  # ][ #  # ]:          0 :           PRINT_ERROR("Interior edge contained in %d facets.\n", count); 
         [ #  # ][ #  # ]
     196                 :            :         }
     197                 :            :       
     198         [ #  # ]:          0 :         if (draw) {
     199 [ #  # ][ #  # ]:          0 :           CubitVector start = edge->point(0)->coordinates();
     200 [ #  # ][ #  # ]:          0 :           CubitVector step = 0.05 * (edge->point(1)->coordinates() - start);
         [ #  # ][ #  # ]
     201         [ #  # ]:          0 :           for (int k = 0; k < 20; k++)
     202 [ #  # ][ #  # ]:          0 :             GfxDebug::draw_point( start + k * step, CUBIT_RED_INDEX );
                 [ #  # ]
     203         [ #  # ]:          0 :           GfxDebug::flush();
     204                 :            :         }
     205                 :            :       }
     206                 :            :     }
     207                 :            :   }
     208                 :            :   
     209                 :            :   
     210                 :            :     // Check loops for contiguous chains of facet edges.
     211 [ #  # ][ #  # ]:          0 :   DLIList<CubitFacetEdgeData*> curve_edges, loop_edges;
         [ #  # ][ #  # ]
     212                 :          0 :   PartitionLoop* loop = 0;
     213 [ #  # ][ #  # ]:          0 :   while ((loop = mySurface->next_loop(loop)))
     214                 :            :   {
     215         [ #  # ]:          0 :     loop_edges.clean_out();
     216         [ #  # ]:          0 :     PartitionCoEdge* coedge = loop->first_coedge();
     217         [ #  # ]:          0 :     do {
     218         [ #  # ]:          0 :       PartitionCurve* curve = coedge->get_curve();
     219 [ #  # ][ #  # ]:          0 :       if (!curve->is_nonmanifold(mySurface))
     220                 :            :       {
     221         [ #  # ]:          0 :         curve_edges.clean_out();
     222         [ #  # ]:          0 :         curve->get_facet_data(curve_edges);
     223 [ #  # ][ #  # ]:          0 :         if (coedge->sense() == CUBIT_REVERSED)
     224         [ #  # ]:          0 :           curve_edges.reverse();
     225         [ #  # ]:          0 :         loop_edges += curve_edges;
     226                 :            :       }
     227         [ #  # ]:          0 :       coedge = loop->next_coedge(coedge);
     228         [ #  # ]:          0 :     } while (coedge != loop->first_coedge());
     229                 :            :   
     230         [ #  # ]:          0 :     loop_edges.last();
     231         [ #  # ]:          0 :     CubitFacetEdgeData* prev = loop_edges.get_and_step();
     232 [ #  # ][ #  # ]:          0 :     PartitionCurve* prev_curve = dynamic_cast<PartitionCurve*>(TDVGFacetOwner::get(prev));
     233 [ #  # ][ #  # ]:          0 :     for (int i = 0; i < loop_edges.size(); i++)
     234                 :            :     {
     235         [ #  # ]:          0 :       CubitFacetEdgeData* edge = loop_edges.get_and_step();
     236         [ #  # ]:          0 :       CubitPoint* shared = edge->shared_point(prev);
     237 [ #  # ][ #  # ]:          0 :       PartitionCurve* curve = dynamic_cast<PartitionCurve*>(TDVGFacetOwner::get(edge));
     238                 :            :       
     239 [ #  # ][ #  # ]:          0 :       if (!prev_curve || !curve)
     240                 :            :       {
     241 [ #  # ][ #  # ]:          0 :         PRINT_ERROR("Missing facet owner on boundary curve.\n");
         [ #  # ][ #  # ]
     242                 :          0 :         prev_curve = curve;
     243                 :          0 :         prev = edge;
     244                 :          0 :         continue;
     245                 :            :       }
     246                 :            :       
     247         [ #  # ]:          0 :       if (!shared)
     248                 :            :       {
     249 [ #  # ][ #  # ]:          0 :         PRINT_ERROR("Broken facet-edge chain at curve %p (RefEdge %d):\n"
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
     250                 :            :                     "      start of segment (%f,%f,%f)->(%f,%f,%f)\n",
     251                 :            :                     (void*)curve, curve && dynamic_cast<RefEdge*>(curve->topology_entity())?
     252                 :            :                     dynamic_cast<RefEdge*>(curve->topology_entity())->id() : 0,
     253                 :            :                     edge->point(0)->coordinates().x(), 
     254                 :            :                     edge->point(0)->coordinates().y(),
     255                 :            :                     edge->point(0)->coordinates().z(),
     256                 :            :                     edge->point(1)->coordinates().x(), 
     257                 :            :                     edge->point(1)->coordinates().y(),
     258         [ #  # ]:          0 :                     edge->point(1)->coordinates().z());
     259                 :            :       }
     260 [ #  # ][ #  # ]:          0 :       else if(PartitionPoint *pt = dynamic_cast<PartitionPoint*>(TDVGFacetOwner::get(shared)))
                 [ #  # ]
     261                 :            :       {
     262 [ #  # ][ #  # ]:          0 :         if( (prev_curve == curve) &&
                 [ #  # ]
     263 [ #  # ][ #  # ]:          0 :              !(pt == curve->start_point() && pt == curve->end_point()) )
                 [ #  # ]
     264                 :            :         {
     265 [ #  # ][ #  # ]:          0 :           PRINT_ERROR("Edges at point %p (vertex %d) (%f,%f,%f) owned\n"
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
     266                 :            :                       "      by the same curve: %p (RefEdge %d)\n",
     267                 :            :             (void*)pt, dynamic_cast<RefVertex*>(pt->topology_entity()) ?
     268                 :            :             dynamic_cast<RefVertex*>(pt->topology_entity())->id() : 0,
     269                 :            :             pt->coordinates().x(), pt->coordinates().y(), pt->coordinates().z(),
     270                 :            :             (void*)curve, curve && dynamic_cast<RefEdge*>(curve->topology_entity())?
     271         [ #  # ]:          0 :             dynamic_cast<RefEdge*>(curve->topology_entity())->id() : 0);
     272                 :            :         } 
     273 [ #  # ][ #  # ]:          0 :         else if (!curve->other_point(pt))
     274                 :            :         {
     275 [ #  # ][ #  # ]:          0 :           PRINT_ERROR("Edge owner curve %p (RefEdge %d) at point %p \n"
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
     276                 :            :                       "      (vertex %d) (%f,%f,%f) doesn't match topology\n",
     277                 :            :             (void*)curve, curve && dynamic_cast<RefEdge*>(curve->topology_entity())?
     278                 :            :             dynamic_cast<RefEdge*>(curve->topology_entity())->id() : 0,
     279                 :            :             (void*)pt, dynamic_cast<RefVertex*>(pt->topology_entity()) ?
     280                 :            :             dynamic_cast<RefVertex*>(pt->topology_entity())->id() : 0,
     281         [ #  # ]:          0 :             pt->coordinates().x(), pt->coordinates().y(), pt->coordinates().z());
     282                 :            :         }
     283 [ #  # ][ #  # ]:          0 :         else if(!prev_curve->other_point(pt))
     284                 :            :         {
     285 [ #  # ][ #  # ]:          0 :           PRINT_ERROR("Edge owner curve %p (RefEdge %d) at point %p \n"
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
     286                 :            :                       "      (vertex %d) (%f,%f,%f) doesn't match topology\n",
     287                 :            :             (void*)prev_curve, prev_curve && dynamic_cast<RefEdge*>(prev_curve->topology_entity())?
     288                 :            :             dynamic_cast<RefEdge*>(prev_curve->topology_entity())->id() : 0,
     289                 :            :             (void*)pt, dynamic_cast<RefVertex*>(pt->topology_entity()) ?
     290                 :            :             dynamic_cast<RefVertex*>(pt->topology_entity())->id() : 0,
     291         [ #  # ]:          0 :             pt->coordinates().x(), pt->coordinates().y(), pt->coordinates().z());
     292                 :            :         }
     293                 :            :       }
     294         [ #  # ]:          0 :       else if (prev_curve != curve)
     295                 :            :       {
     296 [ #  # ][ #  # ]:          0 :         PRINT_ERROR("Missing point-owner at  transition between\n"
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
                 [ #  # ]
     297                 :            :                   "      curve %p (RefEdge %d) and curve %p (RefEdge %d):\n"
     298                 :            :                   "      at location (%f,%f,%f)\n",
     299                 :            :                   (void*)curve, curve && dynamic_cast<RefEdge*>(curve->topology_entity())?
     300                 :            :                   dynamic_cast<RefEdge*>(curve->topology_entity())->id() : 0,
     301                 :            :                   (void*)prev_curve, prev_curve && dynamic_cast<RefEdge*>(prev_curve->topology_entity())?
     302                 :            :                   dynamic_cast<RefEdge*>(prev_curve->topology_entity())->id() : 0,
     303                 :            :                   shared->coordinates().x(), 
     304                 :            :                   shared->coordinates().y(),
     305         [ #  # ]:          0 :                   shared->coordinates().z() );
     306                 :            :       } 
     307                 :            :       
     308                 :          0 :       prev = edge;
     309                 :          0 :       prev_curve = curve;
     310                 :            :     }
     311         [ #  # ]:          0 :   }
     312                 :          0 : }
     313                 :            :    
     314                 :            : 
     315                 :            : //-------------------------------------------------------------------------
     316                 :            : // Purpose       : Find closest point on passed facet
     317                 :            : //
     318                 :            : // Special Notes : static
     319                 :            : //
     320                 :            : // Creator       : Jason Kraftcheck
     321                 :            : //
     322                 :            : // Creation Date : 03/28/03
     323                 :            : //-------------------------------------------------------------------------
     324                 :          0 : void PartSurfFacetTool::closest_pt_on_facet( CubitFacet* facet,
     325                 :            :                                              const CubitVector& p,
     326                 :            :                                              CubitVector& result )
     327                 :            : {
     328                 :            :     // Get triangle vertices
     329 [ #  # ][ #  # ]:          0 :   CubitVector p0(facet->point(0)->coordinates());
     330 [ #  # ][ #  # ]:          0 :   CubitVector p1(facet->point(1)->coordinates());
     331 [ #  # ][ #  # ]:          0 :   CubitVector p2(facet->point(2)->coordinates());
     332                 :            : 
     333                 :            : /*
     334                 :            :   Algorithm from:
     335                 :            :     "Distance Between Point and Triangle in 3D"
     336                 :            :     David Eberly
     337                 :            :     Magic Software, Inc.
     338                 :            :     Sept. 28, 1999
     339                 :            : 
     340                 :            :   Use barycentric coordinates.  Coordinates are
     341                 :            :   calculated in the range [0,det] rather than [0,1]
     342                 :            :   to avoid the fp division entirely where it can
     343                 :            :   be avoided.
     344                 :            : 
     345                 :            :     ^v*t                                 
     346                 :            :  \R2|                 
     347                 :            :   \ |                 
     348                 :            :    \|                 
     349                 :            :     *p2               
     350                 :            :     |\                
     351                 :            :     | \     R1        
     352                 :            :  R3 |  \              
     353                 :            :     |   \             
     354                 :            :     | R0 \            
     355                 :            :     |     \p1         
     356                 :            :  ---*------*--->u*s   
     357                 :            :     |p0     \  R6     
     358                 :            :  R4 |   R5   \        
     359                 :            :     |         \u+v=det  
     360                 :            : */
     361                 :            : 
     362                 :            : 
     363         [ #  # ]:          0 :   CubitVector s(p1 - p0);  // the u (or s) axis in parameterized space
     364         [ #  # ]:          0 :   CubitVector t(p2 - p0);  // the v (or t) axis in parameterized space
     365         [ #  # ]:          0 :   CubitVector d(p0 - p);   // vector from input position to corner at (u,v) = (0,0)
     366                 :            :     // Pre-calculate all the dot products we need
     367                 :            :     // Name the dot product of vectors 'a' and 'b' as 'ab'
     368         [ #  # ]:          0 :   double ss = s.length_squared();
     369         [ #  # ]:          0 :   double st = s % t;
     370         [ #  # ]:          0 :   double tt = t.length_squared();
     371         [ #  # ]:          0 :   double sd = s % d;
     372         [ #  # ]:          0 :   double td = t % d;
     373                 :            :     // Calculate barycentric coordinates in the range [0,det]
     374                 :          0 :   double det = ss*tt - st*st;
     375                 :          0 :   double u = st*td - tt*sd;
     376                 :          0 :   double v = st*sd - ss*td;
     377                 :            :   
     378                 :            :     // Big tree of conditionals to determine which of the 
     379                 :            :     // regions in the above diagram the projection of
     380                 :            :     // the point into the plane lies in.
     381         [ #  # ]:          0 :   if ( u+v < det )
     382                 :            :   {
     383         [ #  # ]:          0 :     if ( u < 0 )
     384                 :            :     {
     385         [ #  # ]:          0 :       if( v < 0 )    // Region 4 
     386                 :            :       {
     387         [ #  # ]:          0 :         if ( sd < 0 )
     388                 :            :         {
     389         [ #  # ]:          0 :           if ( -sd > ss )
     390         [ #  # ]:          0 :             result = p1;
     391                 :            :           else
     392 [ #  # ][ #  # ]:          0 :             result = p0 + (-sd/ss) * s;
                 [ #  # ]
     393                 :            :         }
     394         [ #  # ]:          0 :         else if ( td < 0 )
     395                 :            :         {
     396         [ #  # ]:          0 :           if ( -td > tt )
     397         [ #  # ]:          0 :             result = p2;
     398                 :            :           else
     399 [ #  # ][ #  # ]:          0 :             result = p0 + (-td/tt) * t;
                 [ #  # ]
     400                 :            :         }
     401                 :            :         else
     402                 :            :         {
     403         [ #  # ]:          0 :           result = p0;
     404                 :            :         }
     405                 :            :       }
     406                 :            :       else           // Region 3 (Edge p2-p0, u->0)
     407                 :            :       {
     408         [ #  # ]:          0 :         if ( td > 0 )
     409         [ #  # ]:          0 :           result = p0;
     410         [ #  # ]:          0 :         else if ( -td > tt )
     411         [ #  # ]:          0 :           result = p2;
     412                 :            :         else
     413 [ #  # ][ #  # ]:          0 :           result = p0 + (-td/tt) * t;
                 [ #  # ]
     414                 :            :       }
     415                 :            :     }
     416         [ #  # ]:          0 :     else if ( v < 0) // Region 5 (Edge p0-p1, v->0)
     417                 :            :     {
     418         [ #  # ]:          0 :       if ( sd > 0 )
     419         [ #  # ]:          0 :         result = p0;
     420         [ #  # ]:          0 :       else if ( -sd > ss )
     421         [ #  # ]:          0 :         result = p1;
     422                 :            :       else 
     423 [ #  # ][ #  # ]:          0 :         result = p0 + (-sd/ss) * s;
                 [ #  # ]
     424                 :            :     }
     425                 :            :     else             // Region 0 (Interior)
     426                 :            :     {
     427 [ #  # ][ #  # ]:          0 :       result = p0 + (1.0/det) * (u*s + v*t);
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
     428                 :            :     }
     429                 :            :   }
     430         [ #  # ]:          0 :   else if ( u < 0 )  // Region 2 
     431                 :            :   {
     432                 :          0 :     double num = tt + td - st - sd;
     433         [ #  # ]:          0 :     if ( num > 0.0 )       
     434                 :            :     {
     435                 :          0 :       double den = ss - 2*st + tt;
     436         [ #  # ]:          0 :       if ( num >= den )    // (Point p1)
     437         [ #  # ]:          0 :         result = p1;
     438                 :            :       else                 // (Edge p1-p2)
     439                 :            :       {
     440                 :          0 :         u = num / den;
     441 [ #  # ][ #  # ]:          0 :         result = p0 + u*s + (1-u)*t;
         [ #  # ][ #  # ]
                 [ #  # ]
     442                 :            :       }
     443                 :            :     } 
     444         [ #  # ]:          0 :     else if ( td >= 0 )    // (Point p0)
     445         [ #  # ]:          0 :       result = p0;
     446         [ #  # ]:          0 :     else if ( tt+td <= 0 ) // (Point p2)
     447         [ #  # ]:          0 :       result = p2;
     448                 :            :     else                   // (Edge p2-p0)
     449 [ #  # ][ #  # ]:          0 :       result = p0 + (-td/tt)*t;
                 [ #  # ]
     450                 :            :   }
     451         [ #  # ]:          0 :   else if ( v < 0 )  // Region 6 
     452                 :            :   {
     453                 :          0 :     double num = tt + td - st - sd;
     454                 :          0 :     double den = ss - 2*st + tt;
     455         [ #  # ]:          0 :     if (num < den)       
     456                 :            :     {
     457         [ #  # ]:          0 :       if ( num < 0 )    // (Point p1)
     458         [ #  # ]:          0 :         result = p2;
     459                 :            :       else                 // (Edge p1-p2)
     460                 :            :       {
     461                 :          0 :         u = num / den;
     462 [ #  # ][ #  # ]:          0 :         result = p0 + u*s + (1-u)*t;
         [ #  # ][ #  # ]
                 [ #  # ]
     463                 :            :       }
     464                 :            :     } 
     465         [ #  # ]:          0 :     else if ( sd >= 0 )    // (Point p0)
     466         [ #  # ]:          0 :       result = p0;
     467         [ #  # ]:          0 :     else if ( ss+sd <= 0 ) // (Point p1)
     468         [ #  # ]:          0 :       result = p1;
     469                 :            :     else                   // (Edge p0-p1)
     470 [ #  # ][ #  # ]:          0 :       result = p0 + (-sd/ss)*s;
                 [ #  # ]
     471                 :            :   }
     472                 :            :   else               // Region 1 (Edge p1-p2, u+v->1)
     473                 :            :   {
     474                 :          0 :     double num = tt + td - st - sd;
     475         [ #  # ]:          0 :     if ( num <= 0 )
     476         [ #  # ]:          0 :       result = p2;
     477                 :            :     else
     478                 :            :     {
     479                 :          0 :       double den = ss - 2*st + tt;
     480         [ #  # ]:          0 :       if ( num >= den )
     481         [ #  # ]:          0 :         result = p1;
     482                 :            :       else
     483                 :            :       {
     484                 :          0 :         u = num/den;
     485 [ #  # ][ #  # ]:          0 :         result = p0 + u*s + (1-u)*t;
         [ #  # ][ #  # ]
                 [ #  # ]
     486                 :            :       }
     487                 :            :     }
     488                 :            :   }
     489                 :          0 : }
     490                 :            : 
     491                 :            : //-------------------------------------------------------------------------
     492                 :            : // Purpose       : Local method for debug output
     493                 :            : //
     494                 :            : // Special Notes : 
     495                 :            : //
     496                 :            : // Creator       : Jason Kraftcheck
     497                 :            : //
     498                 :            : // Creation Date : 12/02/03
     499                 :            : //-------------------------------------------------------------------------
     500                 :          0 : static void draw_edges( DLIList<CubitFacetEdge*>& edges, int edge_color = 0, 
     501                 :            :                  bool label_edges = false, bool draw_points = false,
     502                 :            :                  int point_color = 0, bool label_points = false )
     503                 :            : {
     504                 :            :   char buffer[2*sizeof(void*)+3];
     505                 :            : 
     506         [ #  # ]:          0 :   if (edge_color == 0)
     507                 :          0 :     edge_color = CUBIT_WHITE_INDEX;
     508         [ #  # ]:          0 :   if (point_color == 0)
     509                 :          0 :     point_color = CUBIT_WHITE_INDEX;
     510                 :            :   
     511 [ #  # ][ #  # ]:          0 :   for (int i = edges.size(); i--; )
     512                 :            :   {
     513         [ #  # ]:          0 :     CubitFacetEdge* edge = edges.get_and_step();
     514 [ #  # ][ #  # ]:          0 :     CubitVector start = edge->point(0)->coordinates();
     515 [ #  # ][ #  # ]:          0 :     CubitVector end = edge->point(1)->coordinates();
     516         [ #  # ]:          0 :     GfxDebug::draw_line(start, end, edge_color );
     517                 :            :     
     518         [ #  # ]:          0 :     if (label_edges)
     519                 :            :     {
     520 [ #  # ][ #  # ]:          0 :       CubitVector mid = 0.5 * (start + end);
     521                 :          0 :       sprintf(buffer, "%p", (void*)edge);
     522         [ #  # ]:          0 :       float x = (float)mid.x();
     523         [ #  # ]:          0 :       float y = (float)mid.y();
     524         [ #  # ]:          0 :       float z = (float)mid.z();
     525         [ #  # ]:          0 :       GfxDebug::draw_label( buffer, x, y, z, edge_color );
     526                 :            :     }
     527                 :            :       
     528         [ #  # ]:          0 :     for ( int j = 0; j < 2; j++ )
     529                 :            :     {
     530         [ #  # ]:          0 :       CubitPoint* point = edge->point(j);
     531 [ #  # ][ #  # ]:          0 :       float x = (float)point->coordinates().x();
     532 [ #  # ][ #  # ]:          0 :       float y = (float)point->coordinates().y();
     533 [ #  # ][ #  # ]:          0 :       float z = (float)point->coordinates().z();
     534                 :            :       
     535         [ #  # ]:          0 :       if (draw_points)
     536                 :            :       {
     537         [ #  # ]:          0 :         GfxDebug::draw_point( x, y, z, point_color );
     538                 :            :       }
     539         [ #  # ]:          0 :       if (label_points)
     540                 :            :       {
     541                 :          0 :         sprintf(buffer, "%p", (void*)point);
     542         [ #  # ]:          0 :         GfxDebug::draw_label( buffer, x, y, z, point_color );
     543                 :            :       }
     544                 :            :     }
     545                 :            :   }
     546         [ #  # ]:          0 :   GfxDebug::flush();
     547                 :          0 : }
     548                 :            : 
     549                 :            :     
     550                 :          0 : CubitStatus PartSurfFacetTool::init_facet_data( 
     551                 :            :                                  DLIList<CubitFacetData*>& facets )
     552                 :            : {
     553 [ #  # ][ #  # ]:          0 :   assert(!mySurface->has_facets());
     554                 :            :   
     555                 :            :   int i;
     556                 :            :   CubitStatus rval;
     557 [ #  # ][ #  # ]:          0 :   DLIList<CubitPoint*> boundary_points, interior_points;
                 [ #  # ]
     558 [ #  # ][ #  # ]:          0 :   DLIList<CubitFacetEdge*> boundary_edges, interior_edges;
         [ #  # ][ #  # ]
     559 [ #  # ][ #  # ]:          0 :   DLIList<PartitionPoint*> geom_points, interior_geom_points;
         [ #  # ][ #  # ]
     560                 :            :   
     561                 :            :     // Get facet data
     562                 :            :   rval = get_facet_points_and_edges( facets, boundary_points, 
     563         [ #  # ]:          0 :     interior_points, boundary_edges, interior_edges );
     564         [ #  # ]:          0 :   if (!rval)
     565                 :            :   {
     566 [ #  # ][ #  # ]:          0 :     PRINT_ERROR("Internal error at %s:%d\n", __FILE__, __LINE__ );
         [ #  # ][ #  # ]
     567                 :          0 :     return CUBIT_FAILURE;
     568                 :            :   }
     569                 :            : 
     570                 :            :     // Get real points on surface boundary
     571         [ #  # ]:          0 :   mySurface->get_points(geom_points);
     572 [ #  # ][ #  # ]:          0 :   for (i = 0; i < geom_points.size(); i++ )
     573                 :            :   {
     574 [ #  # ][ #  # ]:          0 :     if (!geom_points[i]->real_point())
                 [ #  # ]
     575         [ #  # ]:          0 :       geom_points[i] = 0;
     576                 :            :     // also process for hardpoints
     577 [ #  # ][ #  # ]:          0 :     if (geom_points[i]) 
     578                 :            :     {
     579 [ #  # ][ #  # ]:          0 :       PartitionCurve* curve = geom_points[i]->next_curve();
     580 [ #  # ][ #  # ]:          0 :       if ( curve->measure() < GEOMETRY_RESABS &&
         [ #  # ][ #  # ]
     581 [ #  # ][ #  # ]:          0 :            curve->start_point() == curve->end_point() )
     582                 :            :       {
     583         [ #  # ]:          0 :         geom_points[i] = 0;
     584                 :            :       }
     585                 :            :     }
     586                 :            :   }
     587         [ #  # ]:          0 :   geom_points.remove_all_with_value(0);
     588                 :            :   
     589                 :            :     // Group geometric points into boundary and interior sets
     590 [ #  # ][ #  # ]:          0 :   for (i = geom_points.size(); i--; )
     591                 :            :   {
     592         [ #  # ]:          0 :     PartitionPoint* point = geom_points.step_and_get();
     593                 :          0 :     bool boundary = false;
     594                 :          0 :     PartitionCurve* curve = 0;
     595 [ #  # ][ #  # ]:          0 :     while ( (curve = point->next_curve(curve)) )
     596 [ #  # ][ #  # ]:          0 :       if (curve->is_in_surface(mySurface,true))
     597                 :          0 :         boundary = true;
     598         [ #  # ]:          0 :     if (!boundary)
     599                 :            :     {
     600         [ #  # ]:          0 :       geom_points.change_to(0);
     601         [ #  # ]:          0 :       interior_geom_points.append(point);
     602                 :            :     }
     603                 :            :   }
     604         [ #  # ]:          0 :   geom_points.remove_all_with_value(0);
     605                 :            :   
     606                 :            :     // Associate each boundary geometry point with the closest
     607                 :            :     // boundary facet point.
     608 [ #  # ][ #  # ]:          0 :   if(boundary_points.size() == 0 && geom_points.size() != 0)
         [ #  # ][ #  # ]
                 [ #  # ]
     609                 :          0 :     rval = CUBIT_FAILURE;
     610                 :            :   else
     611         [ #  # ]:          0 :     rval = associate_points( boundary_points, geom_points );
     612                 :            : 
     613         [ #  # ]:          0 :   if (!rval)
     614                 :          0 :     return CUBIT_FAILURE;
     615                 :            :  
     616                 :            :     // Associate each interior geometry point with the closest 
     617                 :            :     // interior facet point.
     618         [ #  # ]:          0 :   rval = associate_points( interior_points, interior_geom_points );
     619         [ #  # ]:          0 :   if (!rval)
     620                 :          0 :     return CUBIT_FAILURE;
     621                 :            : 
     622 [ #  # ][ #  # ]:          0 :   if (DEBUG_FLAG(145))
                 [ #  # ]
     623                 :            :   {
     624         [ #  # ]:          0 :     draw_edges( boundary_edges, CUBIT_ORANGE_INDEX, true, false, CUBIT_WHITE_INDEX, true );
     625         [ #  # ]:          0 :     draw_edges( interior_edges, CUBIT_WHITE_INDEX );
     626                 :            :   }
     627                 :            :   
     628                 :            :   
     629                 :            :     // Populate sets
     630         [ #  # ]:          0 :   boundary_set.clear();
     631         [ #  # ]:          0 :   interior_set.clear();
     632 [ #  # ][ #  # ]:          0 :   for (i = boundary_edges.size(); i--; )
     633 [ #  # ][ #  # ]:          0 :     boundary_set.insert(boundary_edges.step_and_get());
     634 [ #  # ][ #  # ]:          0 :   for (i = interior_edges.size(); i--; )
     635 [ #  # ][ #  # ]:          0 :     interior_set.insert(interior_edges.step_and_get());
     636                 :            :  
     637                 :            :     // For each loop on the surface...
     638                 :          0 :   PartitionLoop* loop = 0;
     639 [ #  # ][ #  # ]:          0 :   DLIList<PartitionCurve*> curve_set;
     640 [ #  # ][ #  # ]:          0 :   DLIList<CubitFacetEdge*> point_edges, edge_set_1, edge_set_2;
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
     641 [ #  # ][ #  # ]:          0 :   DLIList<PartitionCurve*> nonmanifold_stack;
     642 [ #  # ][ #  # ]:          0 :   while ( (loop = mySurface->next_loop(loop)) )
     643                 :            :   {
     644                 :            :       // Find coedge beginning at real vertex (must be at least one)
     645         [ #  # ]:          0 :     PartitionCoEdge* coedge = loop->first_coedge();
     646 [ #  # ][ #  # ]:          0 :     while (!coedge->start_point()->real_point())
                 [ #  # ]
     647                 :            :     { 
     648         [ #  # ]:          0 :       coedge = coedge->next();
     649 [ #  # ][ #  # ]:          0 :       assert(coedge != loop->first_coedge());
     650                 :            :     }
     651                 :            :     
     652                 :          0 :     PartitionCoEdge* first_coedge = coedge; // so we know when to stop
     653                 :            :     
     654                 :            :      
     655         [ #  # ]:          0 :     do // Loop until all curves in loop have been handled (back to first_coedge)
     656                 :            :     {
     657                 :            :         // Keep track of start and end
     658         [ #  # ]:          0 :       PartitionCurve* first_curve = coedge->get_curve();
     659         [ #  # ]:          0 :       PartitionPoint* start_point = coedge->start_point();
     660         [ #  # ]:          0 :       PartitionPoint* end_point = coedge->end_point();
     661                 :            : 
     662                 :            :       // Hardpoints (meeting all cases below) are a special
     663                 :            :       // case loop that should not be handled in the partitioning.
     664 [ #  # ][ #  # ]:          0 :       if (loop->num_coedges() == 1 && 
                 [ #  # ]
     665 [ #  # ][ #  # ]:          0 :           first_curve->measure() < GEOMETRY_RESABS &&
                 [ #  # ]
     666                 :            :           start_point == end_point)
     667                 :          0 :         break;
     668                 :            : 
     669                 :            :         // Get list of curves until next real vertex
     670         [ #  # ]:          0 :       curve_set.clean_out();
     671         [ #  # ]:          0 :       curve_set.append(first_curve);
     672 [ #  # ][ #  # ]:          0 :       while (!coedge->end_point()->real_point())
                 [ #  # ]
     673                 :            :       {
     674         [ #  # ]:          0 :         coedge = coedge->next();
     675 [ #  # ][ #  # ]:          0 :         curve_set.append(coedge->get_curve());
     676         [ #  # ]:          0 :         end_point = coedge->end_point();
     677 [ #  # ][ #  # ]:          0 :         assert(&first_curve->sub_entity_set() == &coedge->get_curve()->sub_entity_set());
         [ #  # ][ #  # ]
     678                 :            :       }
     679                 :            :       
     680 [ #  # ][ #  # ]:          0 :       if (DEBUG_FLAG(145))
                 [ #  # ]
     681                 :            :       {
     682         [ #  # ]:          0 :         curve_set.reset();
     683 [ #  # ][ #  # ]:          0 :         for (i = curve_set.size(); i--; )
     684                 :            :         {
     685         [ #  # ]:          0 :           GMem gmem;
     686         [ #  # ]:          0 :           PartitionCurve* c = curve_set.get_and_step();
     687 [ #  # ][ #  # ]:          0 :           c->get_geometry_query_engine()->get_graphics( c, &gmem );
     688 [ #  # ][ #  # ]:          0 :           GfxDebug::draw_polyline(gmem.point_list(), gmem.pointListCount, CUBIT_RED_INDEX );
     689         [ #  # ]:          0 :         }
     690         [ #  # ]:          0 :         GfxDebug::flush();
     691                 :            :       }
     692                 :            : 
     693                 :            :         // Special case for non-manifold curves
     694 [ #  # ][ #  # ]:          0 :       if (first_curve->is_nonmanifold(mySurface))
     695                 :            :       {
     696                 :            :           // Don't do the same non-manifold curve twice
     697         [ #  # ]:          0 :         curve_set.reset();
     698         [ #  # ]:          0 :         nonmanifold_stack.last();
     699 [ #  # ][ #  # ]:          0 :         if (nonmanifold_stack.size() &&
         [ #  # ][ #  # ]
     700 [ #  # ][ #  # ]:          0 :             curve_set.get() == nonmanifold_stack.get())
     701                 :            :         {
     702 [ #  # ][ #  # ]:          0 :           for (i = curve_set.size(); i--; )
     703                 :            :           {
     704         [ #  # ]:          0 :             PartitionCurve* curv1 = curve_set.get_and_step();
     705         [ #  # ]:          0 :             PartitionCurve* curv2 = nonmanifold_stack.pop();
     706         [ #  # ]:          0 :             assert(curv1 == curv2);
     707         [ #  # ]:          0 :             if (curv1 != curv2) {
     708 [ #  # ][ #  # ]:          0 :               PRINT_ERROR("Internal error at %s:%d\n", __FILE__, __LINE__);
         [ #  # ][ #  # ]
     709                 :          0 :               return CUBIT_FAILURE;
     710                 :            :             }
     711                 :            :           }
     712                 :            :         }
     713                 :            :         else
     714                 :            :         {
     715 [ #  # ][ #  # ]:          0 :           for (i = curve_set.size(); i--; )
     716 [ #  # ][ #  # ]:          0 :             nonmanifold_stack.append(curve_set.get_and_step());
     717                 :            :         
     718 [ #  # ][ #  # ]:          0 :           if (!seam_nonmanifold_curves(curve_set, facets))
     719                 :            :           {
     720                 :          0 :             return CUBIT_FAILURE;
     721                 :            :           }
     722                 :            :         }
     723         [ #  # ]:          0 :         coedge = coedge->next();
     724         [ #  # ]:          0 :         if (coedge != first_coedge)
     725                 :          0 :           continue;
     726                 :            :         else
     727                 :          0 :           break;
     728                 :            :       }
     729                 :            : 
     730                 :            :         // Get facet edges adjacent to first point
     731         [ #  # ]:          0 :       point_edges.clean_out();
     732 [ #  # ][ #  # ]:          0 :       start_point->facet_point()->edges(point_edges);
     733                 :            : 
     734                 :            :         // For each boundary edge on the point, look for a chain
     735                 :            :         // of connected boundary edges.
     736         [ #  # ]:          0 :       edge_set_1.clean_out();
     737         [ #  # ]:          0 :       edge_set_2.clean_out();
     738 [ #  # ][ #  # ]:          0 :       while(point_edges.size())
     739                 :            :       {
     740         [ #  # ]:          0 :         CubitFacetEdge* edge = point_edges.pop();
     741 [ #  # ][ #  # ]:          0 :         if (boundary_set.count(edge) == 0)  // skip non-boundary edges
     742                 :          0 :           continue;
     743                 :            : 
     744         [ #  # ]:          0 :         edge_set_2.clean_out();
     745 [ #  # ][ #  # ]:          0 :         if (!get_boundary_chain(start_point->facet_point(), edge, 
     746 [ #  # ][ #  # ]:          0 :                                   end_point->facet_point(), edge_set_2))
     747                 :          0 :           continue; // skip edges that don't begin a chain that reaches the end vertex
     748                 :            : 
     749                 :            :           // If only one chain found so far, store the chain and 
     750                 :            :           // continue to the next edge around the point
     751 [ #  # ][ #  # ]:          0 :         if (!edge_set_1.size())
     752                 :            :         {
     753         [ #  # ]:          0 :           edge_set_1 = edge_set_2;
     754         [ #  # ]:          0 :           edge_set_2.clean_out();
     755                 :          0 :           continue;
     756                 :            :         }
     757                 :            : 
     758                 :            :           // If we reached this point, handle special case where
     759                 :            :           // loop is composed of two real curves and we need a 
     760                 :            :           // geometric check to determine which half of the facet edge
     761                 :            :           // loop goes with which curve.
     762         [ #  # ]:          0 :         edge_set_1.reset();
     763         [ #  # ]:          0 :         edge_set_2.reset();
     764 [ #  # ][ #  # ]:          0 :         CubitVector set_1_mid = edge_set_1.get()->center();
     765 [ #  # ][ #  # ]:          0 :         CubitVector set_2_mid = edge_set_2.get()->center();
     766 [ #  # ][ #  # ]:          0 :         CubitVector set_1_closest, set_2_closest;
     767         [ #  # ]:          0 :         first_curve->closest_point_trimmed(set_1_mid, set_1_closest);
     768         [ #  # ]:          0 :         first_curve->closest_point_trimmed(set_2_mid, set_2_closest);
     769                 :            : 
     770         [ #  # ]:          0 :         set_1_closest -= set_1_mid;
     771         [ #  # ]:          0 :         set_2_closest -= set_2_mid;
     772 [ #  # ][ #  # ]:          0 :         if (set_2_closest.length_squared() < set_1_closest.length_squared())
                 [ #  # ]
     773         [ #  # ]:          0 :           edge_set_1 = edge_set_2;
     774                 :            :       } // while(point_edges.size())
     775                 :            : 
     776                 :            :         // We have the chain of edges to associate with the curve
     777                 :            :         // set.  Seam with adjacent surface facettings (if any)
     778 [ #  # ][ #  # ]:          0 :       if (DEBUG_FLAG(145))
                 [ #  # ]
     779         [ #  # ]:          0 :         draw_edges( edge_set_1, CUBIT_RED_INDEX, true );
     780                 :            :       
     781 [ #  # ][ #  # ]:          0 :       if (!seam_curves( curve_set, edge_set_1, facets ))
     782                 :          0 :         return CUBIT_FAILURE;
     783                 :            :       
     784         [ #  # ]:          0 :       coedge = coedge->next();
     785                 :            :     } while (coedge != first_coedge);
     786                 :            :     
     787                 :            :   } // while (loop)
     788                 :            :   
     789                 :            :     // attach facets to surface
     790         [ #  # ]:          0 :   mySurface->set_facet_data(facets);
     791                 :            :   
     792         [ #  # ]:          0 :   return CUBIT_SUCCESS;
     793                 :            : }
     794                 :            : 
     795                 :            : //-------------------------------------------------------------------------
     796                 :            : // Purpose       : Helper function for curve seaming functions.
     797                 :            : //                 Check that input curve list are partitions of the
     798                 :            : //                 same real curve and are all the partitions of that curve.
     799                 :            : //                 Returns the real curve and the PartitionPoints that
     800                 :            : //                 are the start and end of the real curve.
     801                 :            : //
     802                 :            : // Special Notes : Assumes the passed curves are either in order or in
     803                 :            : //                 the reverse order.  If the reverse order, the passed
     804                 :            : //                 list will be reversed.
     805                 :            : //
     806                 :            : // Creator       : Jason Kraftcheck
     807                 :            : //
     808                 :            : // Creation Date : 09/08/03
     809                 :            : //-------------------------------------------------------------------------
     810                 :          0 : Curve* PartSurfFacetTool::get_real_curve( DLIList<PartitionCurve*>& curve_list,
     811                 :            :                                           PartitionPoint*& start_point,
     812                 :            :                                           PartitionPoint*& end_point )
     813                 :            : {
     814 [ #  # ][ #  # ]:          0 :   SubEntitySet* set = &(curve_list.get()->sub_entity_set());
     815 [ #  # ][ #  # ]:          0 :   DLIList<PartitionEntity*> tmp_set(curve_list.size());
     816         [ #  # ]:          0 :   set->get_sub_entities(tmp_set);
     817 [ #  # ][ #  # ]:          0 :   if (tmp_set.size() != curve_list.size())
                 [ #  # ]
     818                 :          0 :     return 0;
     819                 :            :   
     820         [ #  # ]:          0 :   tmp_set.reset();
     821         [ #  # ]:          0 :   curve_list.reset();
     822 [ #  # ][ #  # ]:          0 :   if (tmp_set.get() != curve_list.get())
         [ #  # ][ #  # ]
     823                 :            :   {
     824         [ #  # ]:          0 :     curve_list.reverse();
     825         [ #  # ]:          0 :     curve_list.reset();
     826                 :            :   }
     827                 :            :   
     828 [ #  # ][ #  # ]:          0 :   for (int i = curve_list.size(); i--; )
     829 [ #  # ][ #  # ]:          0 :     if (curve_list.get_and_step() != tmp_set.get_and_step())
         [ #  # ][ #  # ]
     830                 :          0 :       return 0;
     831                 :            :    
     832                 :            :     // Get real curve
     833 [ #  # ][ #  # ]:          0 :   Curve* real_curve = dynamic_cast<Curve*>(set->get_entity());
     834         [ #  # ]:          0 :   assert(!!real_curve);
     835                 :            :   
     836 [ #  # ][ #  # ]:          0 :   DLIList<TopologyBridge*> point_bridges(2);
     837 [ #  # ][ #  # ]:          0 :   real_curve->get_children(point_bridges, false, set->get_owner_layer());
     838         [ #  # ]:          0 :   point_bridges.reset();
     839 [ #  # ][ #  # ]:          0 :   start_point = dynamic_cast<PartitionPoint*>(point_bridges.get());
     840 [ #  # ][ #  # ]:          0 :   end_point = dynamic_cast<PartitionPoint*>(point_bridges.next());
     841 [ #  # ][ #  # ]:          0 :   assert(start_point && end_point);
     842                 :            :   
     843         [ #  # ]:          0 :   return real_curve;
     844                 :            : }
     845                 :            : 
     846                 :          0 : CubitStatus PartSurfFacetTool::get_boundary_chain( 
     847                 :            :                                       CubitPoint* start_point,
     848                 :            :                                       CubitFacetEdge* start_edge,
     849                 :            :                                       CubitPoint* end_point,
     850                 :            :                                       DLIList<CubitFacetEdge*>& result_list )
     851                 :            : {
     852         [ #  # ]:          0 :   DLIList<CubitFacetEdge*> point_edges;
     853                 :            :   
     854                 :            :   //assert(start_edge->marked());
     855 [ #  # ][ #  # ]:          0 :   assert(result_list.size() == 0);
     856                 :          0 :   CubitPoint* point = start_point;
     857                 :          0 :   CubitFacetEdge* edge = start_edge;
     858                 :            :   while (true)
     859                 :            :   {
     860         [ #  # ]:          0 :     result_list.append(edge);
     861         [ #  # ]:          0 :     point = edge->other_point(point);
     862 [ #  # ][ #  # ]:          0 :     if (TDVGFacetOwner::get(point))
     863         [ #  # ]:          0 :       return point == end_point ? CUBIT_SUCCESS : CUBIT_FAILURE;
     864                 :            :     
     865         [ #  # ]:          0 :     point->edges(point_edges);
     866 [ #  # ][ #  # ]:          0 :     for (int i = point_edges.size(); i--; )
     867                 :            :     {
     868         [ #  # ]:          0 :       CubitFacetEdge* point_edge = point_edges.step_and_get();
     869                 :            :       //if (point_edge->marked() != 1 || point_edge == edge)
     870 [ #  # ][ #  # ]:          0 :       if (boundary_set.count(point_edge) == 0 || point_edge == edge)
         [ #  # ][ #  # ]
     871         [ #  # ]:          0 :         point_edges.change_to(0);
     872                 :            :     }
     873         [ #  # ]:          0 :     point_edges.remove_all_with_value(0);
     874                 :            :     
     875 [ #  # ][ #  # ]:          0 :     if (point_edges.size() != 1)
     876                 :          0 :       return CUBIT_FAILURE;
     877                 :            :     
     878         [ #  # ]:          0 :     edge = point_edges.remove();
     879                 :            :   }
     880                 :            :   
     881                 :            :     // unreachable
     882         [ #  # ]:          0 :   return CUBIT_SUCCESS;
     883                 :            : }
     884                 :            :       
     885                 :            : //-------------------------------------------------------------------------
     886                 :            : // Purpose       : Associate facet edges in the interior of a surface
     887                 :            : //                 facetting with the set of curve partitions of some
     888                 :            : //                 real, non-manifold curve in the surface.
     889                 :            : //
     890                 :            : // Special Notes : Assumes edges internal to the surface facetting
     891                 :            : //                 have been marked with a '2' by the caller.  Clears
     892                 :            : //                 marks on consumed edges.
     893                 :            : //
     894                 :            : // Creator       : Jason Kraftcheck
     895                 :            : //
     896                 :            : // Creation Date : 09/08/03
     897                 :            : //-------------------------------------------------------------------------
     898                 :          0 : CubitStatus PartSurfFacetTool::seam_nonmanifold_curves(
     899                 :            :                                         DLIList<PartitionCurve*>& curve_list,
     900                 :            :                                         DLIList<CubitFacetData*>& facet_list )
     901                 :            : {
     902                 :            :     // All the curves in the attached coedge_list should belong
     903                 :            :     // to the same real curve and thus have a single continuous 
     904                 :            :     // parameterization over the entire set of curves.  Verify
     905                 :            :     // this now.
     906                 :            :   PartitionPoint *start_point, *end_point;
     907         [ #  # ]:          0 :   Curve* real_curve = get_real_curve(curve_list, start_point, end_point);
     908         [ #  # ]:          0 :   if (!real_curve)
     909                 :            :   {
     910 [ #  # ][ #  # ]:          0 :     PRINT_ERROR("Internal error at %s:%d\n", __FILE__, __LINE__ );
         [ #  # ][ #  # ]
     911                 :          0 :     assert(false);
     912                 :            :     return CUBIT_FAILURE;
     913                 :            :   }
     914                 :            :   
     915                 :            :     // Assume caller has marked all interior edges with a '2'.
     916                 :            :     // Clear marks as we go to ensure we don't loop forever.
     917                 :            :     // Find chain of curves closest to real curve and ending
     918                 :            :     // at the end facet point.
     919         [ #  # ]:          0 :   CubitPoint* const start_vtx = start_point->facet_point();
     920         [ #  # ]:          0 :   CubitPoint* const   end_vtx =   end_point->facet_point();
     921 [ #  # ][ #  # ]:          0 :   assert(start_vtx&&end_vtx);
     922 [ #  # ][ #  # ]:          0 :   DLIList<CubitFacetEdge*> vtx_edges, seam_list;
                 [ #  # ]
     923                 :          0 :   CubitPoint* vtx = start_vtx;
     924         [ #  # ]:          0 :   do
     925                 :            :   {
     926         [ #  # ]:          0 :     vtx->edges(vtx_edges);
     927                 :          0 :     CubitFacetEdge* edge = 0;
     928                 :          0 :     double shortest_dist_sqr = CUBIT_DBL_MAX;
     929 [ #  # ][ #  # ]:          0 :     while( vtx_edges.size() )
     930                 :            :     {
     931         [ #  # ]:          0 :       CubitFacetEdge* curr = vtx_edges.pop();
     932                 :            :       //if (curr->marked() != 2 )
     933 [ #  # ][ #  # ]:          0 :       if (interior_set.count(curr) == 0)
     934                 :          0 :         continue;
     935                 :            :       
     936 [ #  # ][ #  # ]:          0 :       if (curr->other_point(vtx) == end_vtx)
     937                 :            :       { 
     938                 :          0 :         edge = curr;
     939                 :          0 :         break;
     940                 :            :       }
     941                 :            :       
     942 [ #  # ][ #  # ]:          0 :       CubitVector closest, tangent;
     943         [ #  # ]:          0 :       CubitVector start(vtx->coordinates());
     944 [ #  # ][ #  # ]:          0 :       CubitVector end(curr->other_point(vtx)->coordinates());
     945 [ #  # ][ #  # ]:          0 :       real_curve->closest_point(0.5*(start+end), closest, &tangent);
                 [ #  # ]
     946 [ #  # ][ #  # ]:          0 :       if (tangent % (end-start) < 0.0)
                 [ #  # ]
     947                 :          0 :         continue;
     948                 :            :       
     949         [ #  # ]:          0 :       real_curve->closest_point(end, closest);
     950         [ #  # ]:          0 :       closest -= end;
     951         [ #  # ]:          0 :       double dist_sqr = closest.length_squared();
     952         [ #  # ]:          0 :       if (dist_sqr < shortest_dist_sqr)
     953                 :            :       {
     954                 :          0 :         edge = curr;
     955                 :          0 :         shortest_dist_sqr = dist_sqr;
     956                 :            :       }
     957                 :            :     }
     958                 :            :     
     959         [ #  # ]:          0 :     if (!edge)
     960                 :            :     {
     961 [ #  # ][ #  # ]:          0 :       PRINT_ERROR("Internal error at %s:%d:\n"
                 [ #  # ]
     962                 :            :                   "Failed to associate facet edges with non-manofold curves.\n",
     963         [ #  # ]:          0 :                   __FILE__, __LINE__ );
     964                 :          0 :       return CUBIT_FAILURE;
     965                 :            :     }
     966 [ #  # ][ #  # ]:          0 :     if (DEBUG_FLAG(145))
                 [ #  # ]
     967                 :            :     {
     968         [ #  # ]:          0 :       GfxDebug::draw_facet_edge( edge, CUBIT_MAGENTA_INDEX );
     969         [ #  # ]:          0 :       GfxDebug::flush();
     970                 :            :     }
     971                 :            :     
     972         [ #  # ]:          0 :     seam_list.append(edge);
     973                 :            :     //edge->marked(0);
     974         [ #  # ]:          0 :     vtx = edge->other_point(vtx);
     975                 :            :   } while (vtx != end_vtx);
     976                 :            :   
     977 [ #  # ][ #  # ]:          0 :   return seam_curves( curve_list, seam_list, facet_list );
     978                 :            : }
     979                 :            : 
     980                 :            : 
     981                 :          0 : CubitStatus PartSurfFacetTool::split_edge( CubitFacetEdge* old_edge,
     982                 :            :                                           const CubitVector& position,
     983                 :            :                                           CubitFacet* edge_facet,
     984                 :            :                                           CubitPoint*& new_point,
     985                 :            :                                           CubitFacetEdge*& new_edge,
     986                 :            :                                           CubitFacet*& new_facet )
     987                 :            : {
     988 [ #  # ][ #  # ]:          0 :   CubitVector v1, v2;
     989                 :          0 :   int i = 0, junk;
     990                 :          0 :   new_point = 0;
     991                 :          0 :   new_edge = 0;
     992                 :          0 :   new_facet = 0;
     993                 :            : 
     994                 :          0 :   CubitFacet* split_facet = edge_facet;
     995         [ #  # ]:          0 :   if( !split_facet )
     996         [ #  # ]:          0 :     split_facet = old_edge->adj_facet(0);
     997 [ #  # ][ #  # ]:          0 :   else if( edge_facet->edge_index(old_edge) < 0 )
     998                 :          0 :     { assert(0); return CUBIT_FAILURE; }
     999                 :            : 
    1000         [ #  # ]:          0 :   CubitPoint* pt1 = old_edge->point(0);
    1001         [ #  # ]:          0 :   CubitPoint* pt2 = old_edge->point(1);
    1002                 :            : 
    1003 [ #  # ][ #  # ]:          0 :   v1 = position - pt1->coordinates();
                 [ #  # ]
    1004 [ #  # ][ #  # ]:          0 :   v2 = pt2->coordinates() - position;
                 [ #  # ]
    1005 [ #  # ][ #  # ]:          0 :   assert( v1.length_squared() > GEOMETRY_RESABS*GEOMETRY_RESABS );
    1006 [ #  # ][ #  # ]:          0 :   assert( v2.length_squared() > GEOMETRY_RESABS*GEOMETRY_RESABS );
    1007                 :            : #ifndef NDEBUG
    1008         [ #  # ]:          0 :   double dot = v1 % v2;
    1009         [ #  # ]:          0 :   assert( dot > 0 ); // projection of new point onto line lies outside edge.
    1010                 :            : //  double cos_sqr = (dot * dot) / (v1.length_squared() * v2.length_squared());
    1011                 :            : //  assert( cos_sqr > 0.99240387650610407 ); // angle less than 5 degrees
    1012                 :            : #endif
    1013                 :            : 
    1014                 :            : 
    1015         [ #  # ]:          0 :   CubitPoint* new_pt = split_facet->split_edge( pt1, pt2, position );
    1016         [ #  # ]:          0 :   new_edge = new_pt->shared_edge(pt2);
    1017         [ #  # ]:          0 :   if( !new_edge ) { assert(0); return CUBIT_FAILURE; }
    1018                 :            : 
    1019                 :            :     // find new facet and update for other split facets
    1020                 :            :   CubitFacet *facet, *other_facet;
    1021                 :            :   PartitionEntity* facet_owner;
    1022 [ #  # ][ #  # ]:          0 :   while ( (facet = old_edge->adj_facet(i++)) ) {
    1023 [ #  # ][ #  # ]:          0 :     CubitPoint* pt3 = facet->point( facet->edge_index(pt1,new_pt,junk) );
    1024 [ #  # ][ #  # ]:          0 :     if( !pt3->shared_edge( new_pt ) )
    1025 [ #  # ][ #  # ]:          0 :       new CubitFacetEdgeData( pt3, new_pt );
    1026                 :            :       
    1027         [ #  # ]:          0 :     other_facet = facet->shared_facet( new_pt, pt3 );
    1028         [ #  # ]:          0 :     if( !other_facet ) { assert(0); continue; }
    1029         [ #  # ]:          0 :     if ( facet == edge_facet )
    1030                 :          0 :       new_facet = other_facet;
    1031 [ #  # ][ #  # ]:          0 :     else if( (facet_owner = TDVGFacetOwner::get(facet)) )
    1032         [ #  # ]:          0 :       facet_owner->notify_split( facet, other_facet );
    1033                 :            :   }
    1034 [ #  # ][ #  # ]:          0 :   if( (facet_owner = TDVGFacetOwner::get( old_edge )) )
    1035         [ #  # ]:          0 :       facet_owner->notify_split( old_edge, new_edge );
    1036                 :            : 
    1037         [ #  # ]:          0 :   if( edge_facet )
    1038         [ #  # ]:          0 :     assert(!!new_facet);
    1039                 :            :   else 
    1040                 :          0 :     new_facet = 0;
    1041                 :            :     
    1042                 :          0 :   new_point = new_pt;
    1043                 :          0 :   return CUBIT_SUCCESS;
    1044                 :            : }
    1045                 :            : 
    1046                 :          0 : CubitStatus PartSurfFacetTool::collapse_edge( CubitPoint* keep,
    1047                 :            :                                              CubitPoint* dead,
    1048                 :            :                                              DLIList<CubitFacetData*>* unowned )
    1049                 :            : {
    1050                 :            :   int i;
    1051                 :            :   
    1052         [ #  # ]:          0 :   CubitPointData* keep_pt = dynamic_cast<CubitPointData*>(keep);
    1053         [ #  # ]:          0 :   CubitPointData* dead_pt = dynamic_cast<CubitPointData*>(dead);
    1054                 :            :   CubitFacetEdge* dead_edge;
    1055 [ #  # ][ #  # ]:          0 :   assert(keep_pt&&dead_pt);
    1056                 :            :   
    1057                 :            :     // Cannot proceed if dead_pt is owned by a PartitionPoint.
    1058 [ #  # ][ #  # ]:          0 :   if ( TDVGFacetOwner::get(dead_pt) )
    1059                 :          0 :     return CUBIT_FAILURE;
    1060                 :            :   
    1061                 :            :     // Get list of facets to be destroyed when edge is collapsed
    1062         [ #  # ]:          0 :   DLIList<CubitFacet*> dead_facets;
    1063         [ #  # ]:          0 :   keep->shared_facets(dead_pt,dead_facets);
    1064 [ #  # ][ #  # ]:          0 :   DLIList<PartitionSurface*> dead_facet_owners(dead_facets.size());
                 [ #  # ]
    1065 [ #  # ][ #  # ]:          0 :   DLIList<CubitFacetData*> dead_facet_ds(dead_facets.size());
                 [ #  # ]
    1066 [ #  # ][ #  # ]:          0 :   CAST_LIST(dead_facets, dead_facet_ds, CubitFacetData);
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
                 [ #  # ]
    1067                 :            :   
    1068                 :            :     // Find other edges to be destroyed when edge is collapsed.
    1069                 :            :     // cannot proceed if any of them belong to a PartitionCurve.
    1070                 :            :     // Also, find owners of each facet to be destroyed.
    1071         [ #  # ]:          0 :   dead_facets.reset();
    1072 [ #  # ][ #  # ]:          0 :   for ( i = dead_facets.size(); i--; )
    1073                 :            :   {
    1074         [ #  # ]:          0 :     CubitFacet* facet = dead_facets.get_and_step();
    1075         [ #  # ]:          0 :     int keep_index = facet->point_index(keep);
    1076         [ #  # ]:          0 :     int dead_index = facet->point_index(dead);
    1077                 :          0 :     int othr_index = (keep_index + 1) % 3;
    1078         [ #  # ]:          0 :     if ( othr_index == dead_index )
    1079                 :          0 :       othr_index = (keep_index + 2) % 3;
    1080 [ #  # ][ #  # ]:          0 :     assert( keep_index >= 0 && dead_index >= 0 );
    1081 [ #  # ][ #  # ]:          0 :     dead_edge = dead_pt->shared_edge(facet->point(othr_index));
    1082 [ #  # ][ #  # ]:          0 :     if ( TDVGFacetOwner::get(dead_edge) )
    1083                 :          0 :       return CUBIT_FAILURE;
    1084                 :            :       
    1085 [ #  # ][ #  # ]:          0 :     PartitionSurface* surf = dynamic_cast<PartitionSurface*>(TDVGFacetOwner::get(facet));
    1086         [ #  # ]:          0 :     dead_facet_owners.append( surf );
    1087                 :            :   }
    1088                 :            : 
    1089 [ #  # ][ #  # ]:          0 : PRINT_INFO("Collapsing edge (%f,%f,%f)->(%f,%f,%f) (%f)\n",
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
                 [ #  # ]
    1090                 :            :   keep_pt->coordinates().x(), keep_pt->coordinates().y(), keep_pt->coordinates().z(),
    1091                 :            :   dead_pt->coordinates().x(), dead_pt->coordinates().y(), dead_pt->coordinates().z(),
    1092         [ #  # ]:          0 :   (keep_pt->coordinates()-dead_pt->coordinates()).length());
    1093                 :            :   
    1094                 :            :     // Get PartitionCurve to update for collapsed edge.
    1095                 :          0 :   PartitionCurve* dead_edge_owner = 0;
    1096         [ #  # ]:          0 :   dead_edge = dead_pt->shared_edge(keep_pt);
    1097         [ #  # ]:          0 :   if (dead_edge)
    1098 [ #  # ][ #  # ]:          0 :     dead_edge_owner = dynamic_cast<PartitionCurve*>(TDVGFacetOwner::get(dead_edge));
    1099                 :            :   
    1100                 :            :     // Collapse the edge
    1101 [ #  # ][ #  # ]:          0 :   if ( !keep_pt->collapse_edge(dead_pt) )
    1102                 :          0 :     return CUBIT_FAILURE;
    1103                 :            :   
    1104                 :            :     // Update owning curve
    1105         [ #  # ]:          0 :   if (dead_edge_owner)
    1106         [ #  # ]:          0 :     dead_edge_owner->remove_dead_facet( (CubitFacetEdgeData*)dead_edge );
    1107                 :            :   
    1108                 :            :     // Update facet owners for dead facets.
    1109         [ #  # ]:          0 :   dead_facet_ds.reset();
    1110         [ #  # ]:          0 :   dead_facet_owners.reset();
    1111 [ #  # ][ #  # ]:          0 :   for ( i = dead_facet_ds.size(); i--; )
    1112                 :            :   {
    1113         [ #  # ]:          0 :     CubitFacetData* facet = dead_facet_ds.get_and_step();
    1114         [ #  # ]:          0 :     PartitionSurface* facet_owner = dead_facet_owners.get_and_step();
    1115         [ #  # ]:          0 :     if (!facet_owner)
    1116         [ #  # ]:          0 :       unowned->append(facet);
    1117                 :            :     else 
    1118         [ #  # ]:          0 :       facet_owner->notify_destroyed(facet);
    1119                 :            :  }
    1120                 :            :   
    1121         [ #  # ]:          0 :   return CUBIT_SUCCESS;
    1122                 :            : }
    1123                 :            : 
    1124                 :            : 
    1125                 :            : 
    1126                 :            : 
    1127                 :            : //-------------------------------------------------------------------------
    1128                 :            : // Purpose       : Seam a list of facet edges from the boundary of a
    1129                 :            : //                 surface facetting with all the curves that are 
    1130                 :            : //                 partitions of the same real curve on the boundary of
    1131                 :            : //                 that surface.
    1132                 :            : //
    1133                 :            : // Special Notes : 
    1134                 :            : //
    1135                 :            : // Creator       : Jason Kraftcheck
    1136                 :            : //
    1137                 :            : // Creation Date : 09/08/03
    1138                 :            : //-------------------------------------------------------------------------
    1139                 :          0 : CubitStatus PartSurfFacetTool::seam_curves( DLIList<PartitionCurve*>& curve_list,
    1140                 :            :                                             DLIList<CubitFacetEdge*>& edge_list,
    1141                 :            :                                             DLIList<CubitFacetData*>& facets )
    1142                 :            : {
    1143                 :            :   int i;
    1144 [ #  # ][ #  # ]:          0 :   if (!curve_list.size() || !edge_list.size())
         [ #  # ][ #  # ]
                 [ #  # ]
    1145                 :          0 :     return CUBIT_FAILURE;
    1146                 :            :   
    1147 [ #  # ][ #  # ]:          0 :   if (DEBUG_FLAG(145))
                 [ #  # ]
    1148         [ #  # ]:          0 :     draw_edges( edge_list, CUBIT_WHITE_INDEX, true, true, CUBIT_WHITE_INDEX, false );
    1149                 :            :   
    1150 [ #  # ][ #  # ]:          0 :   DLIList<CubitFacetData*> old_facets, new_facets;
                 [ #  # ]
    1151 [ #  # ][ #  # ]:          0 :   DLIList<CubitFacetEdgeData*> dead_edge_ptrs;
    1152                 :          0 :   PartitionCurve* curve = 0;
    1153                 :            :   
    1154                 :            :     // All the curves in the attached coedge_list should belong
    1155                 :            :     // to the same real curve and thus have a single continuous 
    1156                 :            :     // parameterization over the entire set of curves.  Verify
    1157                 :            :     // this now.
    1158                 :            :   PartitionPoint *start_point, *end_point;
    1159         [ #  # ]:          0 :   Curve* real_curve = get_real_curve(curve_list, start_point, end_point);
    1160         [ #  # ]:          0 :   if (!real_curve)
    1161                 :            :   {
    1162 [ #  # ][ #  # ]:          0 :     PRINT_ERROR("Internal error at %s:%d\n", __FILE__, __LINE__ );
         [ #  # ][ #  # ]
    1163                 :          0 :     assert(false);
    1164                 :            :     return CUBIT_FAILURE;
    1165                 :            :   }
    1166                 :            :   
    1167                 :            :   double period;
    1168         [ #  # ]:          0 :   const bool periodic = real_curve->is_periodic(period);
    1169 [ #  # ][ #  # ]:          0 :   const bool fwdparam = (periodic ?  period > 0.0 : real_curve->start_param() < real_curve->end_param());
                 [ #  # ]
    1170                 :            :   
    1171         [ #  # ]:          0 :   edge_list.reset();
    1172                 :            :   CubitPoint *next_vtx, *curr_vtx;
    1173 [ #  # ][ #  # ]:          0 :   if (edge_list.size() == 1)
    1174                 :            :   {
    1175 [ #  # ][ #  # ]:          0 :     next_vtx = edge_list.get()->point(1);
    1176 [ #  # ][ #  # ]:          0 :     curr_vtx = edge_list.get()->point(0);
    1177                 :            :   }
    1178                 :            :   else
    1179                 :            :   {
    1180 [ #  # ][ #  # ]:          0 :     next_vtx = edge_list.get()->shared_point(edge_list.next());
                 [ #  # ]
    1181 [ #  # ][ #  # ]:          0 :     curr_vtx = edge_list.get()->other_point(next_vtx);
    1182                 :            :   }
    1183 [ #  # ][ #  # ]:          0 :   assert(curr_vtx&&next_vtx);
    1184                 :            :     // Special case:  If curve_list is a closed loop of curves,
    1185                 :            :     // a geometric check is required to determine if the passed
    1186                 :            :     // list of facet edges is reversed wrt the curve list.
    1187         [ #  # ]:          0 :   if (start_point == end_point)
    1188                 :            :   {
    1189 [ #  # ][ #  # ]:          0 :     CubitVector tangent, closest, start(curr_vtx->coordinates()), end(next_vtx->coordinates());
         [ #  # ][ #  # ]
    1190 [ #  # ][ #  # ]:          0 :     real_curve->closest_point( 0.5*(start+end), closest, &tangent );
                 [ #  # ]
    1191 [ #  # ][ #  # ]:          0 :     if ((end - start) % tangent < 0.0)
                 [ #  # ]
    1192         [ #  # ]:          0 :       edge_list.reverse();    
    1193                 :            :   }
    1194                 :            :     // Otherwise just compare end coordinates
    1195                 :            :   else
    1196                 :            :   {
    1197 [ #  # ][ #  # ]:          0 :     if ((start_point->coordinates() - curr_vtx->coordinates()).length_squared() >
         [ #  # ][ #  # ]
                 [ #  # ]
    1198 [ #  # ][ #  # ]:          0 :         (end_point->coordinates() - curr_vtx->coordinates()).length_squared())
         [ #  # ][ #  # ]
    1199                 :            :     {
    1200 [ #  # ][ #  # ]:          0 :       if (edge_list.size() == 1)
    1201                 :            :       {
    1202                 :          0 :         next_vtx = curr_vtx;
    1203 [ #  # ][ #  # ]:          0 :         curr_vtx = edge_list.get()->other_point(next_vtx);
    1204                 :            :       }
    1205                 :            :       else
    1206                 :            :       {
    1207         [ #  # ]:          0 :         edge_list.reverse();
    1208         [ #  # ]:          0 :         edge_list.reset();
    1209 [ #  # ][ #  # ]:          0 :         next_vtx = edge_list.get()->shared_point(edge_list.next());
                 [ #  # ]
    1210 [ #  # ][ #  # ]:          0 :         curr_vtx = edge_list.get()->other_point(next_vtx);
    1211                 :            :       }
    1212 [ #  # ][ #  # ]:          0 :       assert(next_vtx&&curr_vtx);
    1213                 :            :     }
    1214                 :            :   }
    1215                 :            : 
    1216 [ #  # ][ #  # ]:          0 :   DLIList<CubitFacetEdgeData*> edge_data_list;
    1217 [ #  # ][ #  # ]:          0 :   CAST_LIST(edge_list, edge_data_list, CubitFacetEdgeData);
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
                 [ #  # ]
    1218 [ #  # ][ #  # ]:          0 :   assert(edge_list.size() == edge_data_list.size());
                 [ #  # ]
    1219                 :            :   
    1220                 :            :     // Find the subset of edges which belong on each curve.
    1221                 :            :     // Begin with the first edge in the list, and the point
    1222                 :            :     // at the end (opposite the curve start point) of the edge.
    1223 [ #  # ][ #  # ]:          0 :   DLIList<CubitFacetEdgeData*> curve_edge_list;  // edges for current curve
    1224                 :          0 :   PartitionPoint* vertex = start_point;      // end point of current curve
    1225         [ #  # ]:          0 :   curve_list.reset(); 
    1226         [ #  # ]:          0 :   edge_data_list.reset();
    1227         [ #  # ]:          0 :   edge_data_list.reverse();
    1228         [ #  # ]:          0 :   CubitFacetEdgeData* edge = edge_data_list.pop();
    1229         [ #  # ]:          0 :   CubitPoint* point = start_point->facet_point(); // edge end point
    1230         [ #  # ]:          0 :   point = edge->other_point(point);
    1231         [ #  # ]:          0 :   if (!point)
    1232                 :            :   {
    1233 [ #  # ][ #  # ]:          0 :     PRINT_ERROR("Internal error at %s:%d\n", __FILE__, __LINE__);
         [ #  # ][ #  # ]
    1234                 :          0 :     assert(0);
    1235                 :            :     return CUBIT_FAILURE;
    1236                 :            :   }
    1237                 :            :   
    1238                 :            :     // Iterate over all but the last curve
    1239         [ #  # ]:          0 :   double prev_vtx_param = real_curve->start_param();
    1240         [ #  # ]:          0 :   double prev_pt_param = real_curve->start_param();
    1241 [ #  # ][ #  # ]:          0 :   for (i = curve_list.size() - 1; i--; )
    1242                 :            :   {
    1243         [ #  # ]:          0 :     curve_edge_list.clean_out();
    1244                 :            :     
    1245         [ #  # ]:          0 :     curve = curve_list.get_and_step();
    1246         [ #  # ]:          0 :     vertex = curve->other_point(vertex);
    1247         [ #  # ]:          0 :     const CubitVector vtx_pos(vertex->coordinates());
    1248         [ #  # ]:          0 :     double vtx_param = real_curve->u_from_position(vtx_pos);
    1249 [ #  # ][ #  # ]:          0 :     double point_param = real_curve->u_from_position(point->coordinates());
    1250         [ #  # ]:          0 :     if (periodic)
    1251                 :            :     {
    1252         [ #  # ]:          0 :       if ((vtx_param < prev_vtx_param) == fwdparam)
    1253                 :          0 :         vtx_param += period;
    1254         [ #  # ]:          0 :       if ((point_param < prev_pt_param) == fwdparam)
    1255                 :          0 :         point_param += period;
    1256                 :          0 :       prev_vtx_param = vtx_param;
    1257                 :          0 :       prev_pt_param = point_param;
    1258                 :            :     }
    1259                 :            :     
    1260                 :            :       // Iterate until the edge "containing" the vertex
    1261         [ #  # ]:          0 :     while ((vtx_param > point_param) == fwdparam)
    1262                 :            :     {
    1263                 :            :         // decrement edge count each time we add one of the
    1264                 :            :         // original, input edges to the cuve edge list.
    1265         [ #  # ]:          0 :       curve_edge_list.append(edge);
    1266                 :            :       
    1267 [ #  # ][ #  # ]:          0 :       if (!edge_data_list.size()) { assert(0); return CUBIT_FAILURE; }
    1268                 :            : 
    1269                 :            :         // Get the next edge and facet point
    1270         [ #  # ]:          0 :       edge = edge_data_list.pop();
    1271         [ #  # ]:          0 :       point = edge->other_point(point);
    1272 [ #  # ][ #  # ]:          0 :       point_param = real_curve->u_from_position(point->coordinates());
    1273         [ #  # ]:          0 :       if (periodic)
    1274                 :            :       {
    1275         [ #  # ]:          0 :         if ((point_param < prev_pt_param) == fwdparam)
    1276                 :          0 :           point_param += period;
    1277                 :          0 :         prev_pt_param = point_param;
    1278                 :            :       }
    1279                 :            :     }
    1280                 :            :   
    1281         [ #  # ]:          0 :     CubitVector edge_pos;
    1282         [ #  # ]:          0 :     edge->closest_point(vtx_pos, edge_pos);
    1283                 :            :   
    1284                 :            :     CubitFacetEdgeData* new_edge;
    1285 [ #  # ][ #  # ]:          0 :     CubitPoint* new_point = split_edge_closest( edge, edge_pos, 0.1*edge->length(), new_edge, facets );
    1286         [ #  # ]:          0 :     if (!new_point)
    1287                 :          0 :       return CUBIT_FAILURE;
    1288                 :            :     
    1289                 :            :       // If the edge was split...
    1290         [ #  # ]:          0 :     if (new_edge)
    1291                 :            :     {
    1292                 :            :         // If new_edge ends at the "end" point
    1293                 :            :         // swap the edges.
    1294 [ #  # ][ #  # ]:          0 :       if (new_edge->other_point(point))
    1295         [ #  # ]:          0 :         std::swap(edge, new_edge);
    1296                 :            :         // Put the earlier peice of the edge in the curve
    1297                 :            :         // list.  Keep the latter peice for the next curve
    1298                 :            :         // iteration.
    1299         [ #  # ]:          0 :       curve_edge_list.append(new_edge);
    1300                 :            :     }
    1301                 :            :       // If the input position was the same as the edge end point...
    1302         [ #  # ]:          0 :     else if (new_point == point)
    1303                 :            :     {
    1304                 :            :         // Add edge to list for current curve and decrement count.
    1305         [ #  # ]:          0 :       curve_edge_list.append(edge);
    1306 [ #  # ][ #  # ]:          0 :       if (!edge_data_list.size()) { assert(0); return CUBIT_FAILURE; }
    1307                 :            :       
    1308                 :            :         // Get the next edge and facet point for the next iteration.
    1309         [ #  # ]:          0 :       edge = edge_data_list.pop();
    1310         [ #  # ]:          0 :       point = edge->other_point(point);
    1311                 :            :     }
    1312                 :            :     
    1313                 :            :       // Move edge split point to location of vertex
    1314                 :            : #ifdef PART_SURF_REFACET
    1315                 :            :     double d_sqr = (vtx_pos - edge_pos).length_squared();
    1316                 :            :     bool close = d_sqr < (GEOMETRY_RESABS*GEOMETRY_RESABS);
    1317                 :            :     old_facets.clean_out();
    1318                 :            :     new_facets.clean_out();
    1319                 :            :     if (close)
    1320                 :            :       dynamic_cast<CubitPointData*>(new_point)->set(vtx_pos);
    1321                 :            :     else if (!fix_move_point( new_point, vtx_pos, facets, old_facets, new_facets ))
    1322                 :            :       return CUBIT_FAILURE;
    1323                 :            :     assert(!old_facets.size() == !new_facets.size());
    1324                 :            :     facets -= old_facets;
    1325                 :            :     facets += new_facets;
    1326                 :            : #else
    1327 [ #  # ][ #  # ]:          0 :     dynamic_cast<CubitPointData*>(new_point)->set(vtx_pos); 
    1328                 :            : #endif
    1329                 :            :       // Merge the points
    1330         [ #  # ]:          0 :     CubitPointData* vtx_pointd = vertex->facet_point();
    1331         [ #  # ]:          0 :     CubitPointData* new_pointd = dynamic_cast<CubitPointData*>(new_point);
    1332         [ #  # ]:          0 :     if (vtx_pointd)
    1333         [ #  # ]:          0 :       vtx_pointd->merge_points(new_pointd);
    1334                 :            :     else
    1335         [ #  # ]:          0 :       vertex->facet_point(new_pointd);
    1336                 :            :     
    1337 [ #  # ][ #  # ]:          0 :     if (!curve->has_facet_data())
    1338         [ #  # ]:          0 :       curve->set_facet_data(curve_edge_list);
    1339 [ #  # ][ #  # ]:          0 :     else if(!seam_curve( curve_edge_list, curve, facets, &dead_edge_ptrs ))
    1340                 :          0 :       return CUBIT_FAILURE;
    1341                 :            :       
    1342 [ #  # ][ #  # ]:          0 :     while (dead_edge_ptrs.size())
    1343                 :            :     {
    1344         [ #  # ]:          0 :       CubitFacetEdgeData* edge = dead_edge_ptrs.pop();
    1345         [ #  # ]:          0 :       boundary_set.erase(edge);
    1346         [ #  # ]:          0 :       interior_set.erase(edge);
    1347                 :            :     }
    1348                 :            : 
    1349                 :            :   } // for(curve_list)
    1350                 :            :   
    1351                 :            :     // Do last curve
    1352                 :            : 
    1353         [ #  # ]:          0 :   curve = curve_list.get();
    1354         [ #  # ]:          0 :   curve_edge_list.clean_out();
    1355         [ #  # ]:          0 :   if (edge)
    1356         [ #  # ]:          0 :     curve_edge_list.append(edge);
    1357 [ #  # ][ #  # ]:          0 :   while (edge_data_list.size())
    1358 [ #  # ][ #  # ]:          0 :     curve_edge_list.append(edge_data_list.pop());
    1359                 :            :   
    1360 [ #  # ][ #  # ]:          0 :   if(!curve_edge_list.size()) { assert(0); return CUBIT_FAILURE; }
    1361                 :            :   
    1362 [ #  # ][ #  # ]:          0 :   if (!curve->has_facet_data())
    1363         [ #  # ]:          0 :     curve->set_facet_data(curve_edge_list);
    1364 [ #  # ][ #  # ]:          0 :   else if(!seam_curve( curve_edge_list, curve, facets, &dead_edge_ptrs ))
    1365                 :          0 :     return CUBIT_FAILURE;
    1366                 :            :       
    1367 [ #  # ][ #  # ]:          0 :   while (dead_edge_ptrs.size())
    1368                 :            :   {
    1369         [ #  # ]:          0 :     CubitFacetEdgeData* edge = dead_edge_ptrs.pop();
    1370         [ #  # ]:          0 :     boundary_set.erase(edge);
    1371         [ #  # ]:          0 :     interior_set.erase(edge);
    1372                 :            :   }
    1373                 :            :     
    1374         [ #  # ]:          0 :   return CUBIT_SUCCESS;
    1375                 :            : }
    1376                 :            : 
    1377                 :            : //-------------------------------------------------------------------------
    1378                 :            : // Purpose       : Seam a new list of facet edges with the list of facet
    1379                 :            : //                 edges on a curve.
    1380                 :            : //
    1381                 :            : // Special Notes : 
    1382                 :            : //
    1383                 :            : // Creator       : Jason Kraftcheck
    1384                 :            : //
    1385                 :            : // Creation Date : 12/02/03
    1386                 :            : //-------------------------------------------------------------------------
    1387                 :          0 : CubitStatus PartSurfFacetTool::seam_curve( DLIList<CubitFacetEdgeData*>& edge_list,
    1388                 :            :                                            PartitionCurve* curve,
    1389                 :            :                                            DLIList<CubitFacetData*>& facets,
    1390                 :            :                                            DLIList<CubitFacetEdgeData*>* dead_ptrs )
    1391                 :            : {
    1392 [ #  # ][ #  # ]:          0 :   DLIList<CubitFacetData*> old_facets, new_facets;
                 [ #  # ]
    1393                 :          0 :   const double FRACT_TOL = 0.1;
    1394                 :            : 
    1395                 :          0 :   int curve_color = CUBIT_GREEN_INDEX;
    1396 [ #  # ][ #  # ]:          0 :   if (DEBUG_FLAG(145))
                 [ #  # ]
    1397                 :            :   {
    1398 [ #  # ][ #  # ]:          0 :     RefEntity* ent = dynamic_cast<RefEntity*>(curve->topology_entity());
    1399 [ #  # ][ #  # ]:          0 :     while (ent && ent->color() < 0)
         [ #  # ][ #  # ]
    1400                 :            :     {
    1401         [ #  # ]:          0 :       DLIList<RefEntity*> list;
    1402         [ #  # ]:          0 :       ent->get_parent_ref_entities(list);
    1403         [ #  # ]:          0 :       list.reset();
    1404 [ #  # ][ #  # ]:          0 :       if (!list.size()) break;
    1405 [ #  # ][ #  # ]:          0 :       ent = list.get();
                 [ #  # ]
    1406                 :          0 :     }
    1407         [ #  # ]:          0 :     if (ent)
    1408         [ #  # ]:          0 :       curve_color = ent->color();
    1409                 :            :   }
    1410                 :            :   
    1411                 :            :     // Vertices should already be "seamed".  Verify...
    1412                 :            :     
    1413         [ #  # ]:          0 :   PartitionPoint* start_vtx = curve->start_point();
    1414         [ #  # ]:          0 :   PartitionPoint* end_vtx = curve->end_point();
    1415         [ #  # ]:          0 :   CubitPointData* start_point = start_vtx->facet_point();
    1416         [ #  # ]:          0 :   CubitPointData* end_point = end_vtx->facet_point();
    1417                 :            :   
    1418         [ #  # ]:          0 :   edge_list.last();
    1419         [ #  # ]:          0 :   CubitFacetEdgeData* last_edge = edge_list.get();
    1420         [ #  # ]:          0 :   edge_list.reset();
    1421         [ #  # ]:          0 :   CubitFacetEdgeData* first_edge = edge_list.get();
    1422 [ #  # ][ #  # ]:          0 :   if (!first_edge->other_point(start_point) || 
         [ #  # ][ #  # ]
    1423         [ #  # ]:          0 :       !last_edge->other_point(end_point))
    1424                 :            :   {
    1425 [ #  # ][ #  # ]:          0 :     PRINT_ERROR("Internal error at %s:%d\n", __FILE__, __LINE__);
         [ #  # ][ #  # ]
    1426                 :          0 :     assert(0);
    1427                 :            :     return CUBIT_FAILURE;
    1428                 :            :   }
    1429                 :            :   
    1430                 :            :     // Get direction of parameter (probably always increasing...)
    1431                 :            :   double period;
    1432         [ #  # ]:          0 :   const bool fwdparam = curve->is_periodic(period) ? period > 0.0 :
    1433 [ #  # ][ #  # ]:          0 :                         curve->start_param() < curve->end_param();
                 [ #  # ]
    1434                 :            :   
    1435                 :            :     // Get list of facet edges on curve.
    1436 [ #  # ][ #  # ]:          0 :   DLIList<CubitFacetEdgeData*> curve_edges;
    1437         [ #  # ]:          0 :   curve->get_facet_data(curve_edges);
    1438 [ #  # ][ #  # ]:          0 :   if (!curve_edges.size())
    1439                 :            :   {
    1440         [ #  # ]:          0 :     curve->set_facet_data( edge_list );
    1441                 :          0 :     return CUBIT_SUCCESS;
    1442                 :            :   }
    1443                 :            :   
    1444                 :            :     // Seam edge lists
    1445         [ #  # ]:          0 :   double curve_param = curve->start_param();
    1446         [ #  # ]:          0 :   double new_param = curve->start_param();
    1447         [ #  # ]:          0 :   curve_edges.reset();
    1448         [ #  # ]:          0 :   edge_list.reset();
    1449         [ #  # ]:          0 :   CubitFacetEdgeData* curve_edge = curve_edges.get_and_step();
    1450         [ #  # ]:          0 :   CubitFacetEdgeData* new_edge = edge_list.get_and_step();
    1451                 :          0 :   CubitPoint* prev_point = start_point;
    1452         [ #  # ]:          0 :   double orig_crv_len = curve_edge->length();
    1453         [ #  # ]:          0 :   double orig_new_len = new_edge->length();
    1454         [ #  # ]:          0 :   double split_tol = FRACT_TOL * CUBIT_MIN(orig_crv_len, orig_new_len);
    1455 [ #  # ][ #  # ]:          0 :   while (curve_edge || new_edge)
    1456                 :            :   {
    1457 [ #  # ][ #  # ]:          0 :     if (!curve_edge || !new_edge)
    1458                 :            :     {
    1459 [ #  # ][ #  # ]:          0 :       PRINT_ERROR("Internal error at %s:%d\n", __FILE__, __LINE__ );
         [ #  # ][ #  # ]
    1460                 :          0 :       assert(0);
    1461                 :          0 :       return CUBIT_FAILURE;
    1462                 :            :     }
    1463                 :            :   
    1464         [ #  # ]:          0 :     CubitPoint* curve_point = curve_edge->other_point(prev_point);
    1465         [ #  # ]:          0 :     CubitPoint* new_point = new_edge->other_point(prev_point);
    1466 [ #  # ][ #  # ]:          0 :     if (DEBUG_FLAG(145)) {
                 [ #  # ]
    1467 [ #  # ][ #  # ]:          0 :       GfxDebug::draw_point(curve_point->coordinates(), curve_color);
    1468         [ #  # ]:          0 :       GfxDebug::draw_facet_edge(curve_edge, curve_color);
    1469 [ #  # ][ #  # ]:          0 :       GfxDebug::draw_point(new_point->coordinates(), curve_color + 1);
    1470         [ #  # ]:          0 :       GfxDebug::draw_facet_edge(new_edge, curve_color + 1);
    1471         [ #  # ]:          0 :       GfxDebug::flush();
    1472                 :            :     }
    1473                 :            :     
    1474                 :          0 :     double prev_curve_param = curve_param;
    1475                 :          0 :     double prev_new_param = new_param;
    1476 [ #  # ][ #  # ]:          0 :     curve_param = curve->u_from_position(curve_point->coordinates());
    1477 [ #  # ][ #  # ]:          0 :     new_param = curve->u_from_position(new_point->coordinates());
    1478 [ #  # ][ #  # ]:          0 :     if (curve->is_periodic(period))
    1479                 :            :     {
    1480         [ #  # ]:          0 :       if ((prev_curve_param > curve_param) == fwdparam)
    1481                 :          0 :         curve_param += period;
    1482         [ #  # ]:          0 :       if ((prev_new_param > new_param) == fwdparam)
    1483                 :          0 :         new_param += period;
    1484                 :            :     }
    1485                 :            :     
    1486         [ #  # ]:          0 :     if ((curve_param > new_param) == fwdparam)
    1487                 :            :     {
    1488                 :          0 :       CubitFacetEdgeData* split_edge = 0;
    1489         [ #  # ]:          0 :       CubitVector edge_pos;
    1490 [ #  # ][ #  # ]:          0 :       curve_edge->closest_point( new_point->coordinates(), edge_pos );
    1491                 :            :       CubitPoint* split = split_edge_closest( curve_edge, 
    1492                 :            :                                               edge_pos, 
    1493                 :            :                                               split_tol,
    1494                 :            :                                               split_edge, 
    1495         [ #  # ]:          0 :                                               facets );
    1496         [ #  # ]:          0 :       if(!split)
    1497                 :          0 :         return CUBIT_FAILURE;
    1498                 :            :       
    1499         [ #  # ]:          0 :       if (split == prev_point)
    1500                 :            :       {
    1501                 :            :           // new_edge is very small compared to split_edge
    1502         [ #  # ]:          0 :         assert(!split_edge);
    1503         [ #  # ]:          0 :         old_facets.clean_out();
    1504 [ #  # ][ #  # ]:          0 :         if (!collapse_edge(prev_point, new_point, &old_facets))
    1505                 :            :         {
    1506 [ #  # ][ #  # ]:          0 :           if (!collapse_edge(new_point, prev_point, &old_facets))
    1507                 :            :           {
    1508                 :          0 :             return CUBIT_FAILURE;
    1509                 :            :           }
    1510         [ #  # ]:          0 :           std::swap(prev_point, new_point);
    1511                 :            :         }
    1512         [ #  # ]:          0 :         if (dead_ptrs)
    1513         [ #  # ]:          0 :           dead_ptrs->append( new_edge );
    1514         [ #  # ]:          0 :         facets -= old_facets;
    1515                 :            :       
    1516 [ #  # ][ #  # ]:          0 :         if (edge_list.is_at_beginning())
    1517                 :          0 :           new_edge = 0;
    1518                 :            :         else
    1519                 :            :         {
    1520         [ #  # ]:          0 :           new_edge = edge_list.get_and_step();
    1521         [ #  # ]:          0 :           orig_new_len = new_edge->length();
    1522         [ #  # ]:          0 :           split_tol = FRACT_TOL * CUBIT_MIN(orig_crv_len, orig_new_len);
    1523                 :            :         }
    1524                 :            :          
    1525                 :          0 :         continue;
    1526                 :            :       }
    1527                 :            :       
    1528         [ #  # ]:          0 :       if (split_edge)
    1529                 :            :       {
    1530 [ #  # ][ #  # ]:          0 :         if (curve_edge->other_point(prev_point))
    1531         [ #  # ]:          0 :           std::swap(split_edge, curve_edge);
    1532                 :            :       }
    1533                 :            :       else
    1534                 :            :       {
    1535         [ #  # ]:          0 :         assert(split == curve_point);
    1536                 :          0 :         split_edge = curve_edge;
    1537 [ #  # ][ #  # ]:          0 :         if (curve_edges.is_at_beginning())
    1538                 :          0 :           curve_edge = 0;
    1539                 :            :         else
    1540                 :            :         {
    1541         [ #  # ]:          0 :           curve_edge = curve_edges.get_and_step();
    1542         [ #  # ]:          0 :           orig_crv_len = curve_edge->length();
    1543         [ #  # ]:          0 :           split_tol = FRACT_TOL * CUBIT_MIN(orig_crv_len, orig_new_len);
    1544                 :            :         }
    1545                 :            :       }
    1546                 :            :       
    1547                 :            :         // Move split point to position of other point (safely)
    1548                 :            : #ifdef PART_SURF_REFACET
    1549                 :            :       double d_sqr = (edge_pos - new_point->coordinates()).length_squared();
    1550                 :            :       bool close = d_sqr < (GEOMETRY_RESABS*GEOMETRY_RESABS);
    1551                 :            :       old_facets.clean_out();
    1552                 :            :       new_facets.clean_out();
    1553                 :            :       if (close)
    1554                 :            :         dynamic_cast<CubitPointData*>(split)->set(new_point->coordinates());
    1555                 :            :       else if (!fix_move_point( split, new_point->coordinates(), facets, old_facets, new_facets ))
    1556                 :            :         return CUBIT_FAILURE;
    1557                 :            :       facets -= old_facets;
    1558                 :            :       facets += new_facets;
    1559                 :            : #else
    1560 [ #  # ][ #  # ]:          0 :       dynamic_cast<CubitPointData*>(split)->set(new_point->coordinates());
                 [ #  # ]
    1561                 :            : #endif
    1562                 :            :       
    1563         [ #  # ]:          0 :       CubitStatus s1 = split->merge_points(new_point);
    1564         [ #  # ]:          0 :       CubitStatus s2 = split_edge->merge_edges(new_edge);
    1565         [ #  # ]:          0 :       if (dead_ptrs)
    1566         [ #  # ]:          0 :         dead_ptrs->append(new_edge);
    1567 [ #  # ][ #  # ]:          0 :       assert(s1 && s2);
    1568                 :          0 :       prev_point = split;
    1569                 :            :       
    1570 [ #  # ][ #  # ]:          0 :       if (edge_list.is_at_beginning())
    1571                 :          0 :         new_edge = 0;
    1572                 :            :       else
    1573                 :            :       {
    1574         [ #  # ]:          0 :         new_edge = edge_list.get_and_step();
    1575         [ #  # ]:          0 :         orig_new_len = new_edge->length();
    1576         [ #  # ]:          0 :         split_tol = FRACT_TOL * CUBIT_MIN(orig_crv_len, orig_new_len);
    1577                 :            :       }  
    1578                 :            :     }
    1579                 :            :     else
    1580                 :            :     {
    1581                 :          0 :       CubitFacetEdgeData* split_edge = 0;
    1582         [ #  # ]:          0 :       CubitVector edge_pos;
    1583 [ #  # ][ #  # ]:          0 :       new_edge->closest_point( curve_point->coordinates(), edge_pos );
    1584                 :            :       CubitPoint* split = split_edge_closest( new_edge, 
    1585                 :            :                                               edge_pos, 
    1586                 :            :                                               split_tol,
    1587                 :            :                                               split_edge,
    1588         [ #  # ]:          0 :                                               facets );
    1589         [ #  # ]:          0 :       if(!split)
    1590                 :          0 :         return CUBIT_FAILURE;
    1591                 :            :       
    1592         [ #  # ]:          0 :       if (split == prev_point)
    1593                 :            :       {
    1594                 :            :           // curve_edge is very small compared to split_edge
    1595         [ #  # ]:          0 :         assert(!split_edge);
    1596         [ #  # ]:          0 :         old_facets.clean_out();
    1597 [ #  # ][ #  # ]:          0 :         if (!collapse_edge(prev_point,curve_point,&old_facets))
    1598                 :            :         {
    1599 [ #  # ][ #  # ]:          0 :           if (!collapse_edge(curve_point, prev_point, &old_facets))
    1600                 :            :           {
    1601                 :          0 :             return CUBIT_FAILURE;
    1602                 :            :           }
    1603         [ #  # ]:          0 :           std::swap(curve_point, prev_point);
    1604                 :            :         }
    1605         [ #  # ]:          0 :         facets -= old_facets;
    1606         [ #  # ]:          0 :         if (dead_ptrs)
    1607         [ #  # ]:          0 :           dead_ptrs->append(curve_edge);
    1608                 :            :       
    1609 [ #  # ][ #  # ]:          0 :         if (curve_edges.is_at_beginning())
    1610                 :          0 :           curve_edge = 0;
    1611                 :            :         else
    1612                 :            :         {
    1613         [ #  # ]:          0 :           curve_edge = curve_edges.get_and_step();
    1614         [ #  # ]:          0 :           orig_crv_len = curve_edge->length();
    1615         [ #  # ]:          0 :           split_tol = FRACT_TOL * CUBIT_MIN(orig_crv_len, orig_new_len);
    1616                 :            :         }  
    1617                 :          0 :         continue;
    1618                 :            :       }
    1619                 :            :         
    1620         [ #  # ]:          0 :       if (split_edge)
    1621                 :            :       {
    1622 [ #  # ][ #  # ]:          0 :         if (new_edge->other_point(prev_point))
    1623         [ #  # ]:          0 :           std::swap(split_edge, new_edge);
    1624                 :            :       }
    1625                 :            :       else
    1626                 :            :       {
    1627         [ #  # ]:          0 :         assert(split == new_point);
    1628                 :          0 :         split_edge = new_edge;
    1629 [ #  # ][ #  # ]:          0 :         if (edge_list.is_at_beginning())
    1630                 :          0 :           new_edge = 0;
    1631                 :            :         else
    1632                 :            :         {
    1633         [ #  # ]:          0 :           new_edge = edge_list.get_and_step();
    1634         [ #  # ]:          0 :           orig_new_len = new_edge->length();
    1635         [ #  # ]:          0 :           split_tol = FRACT_TOL * CUBIT_MIN(orig_crv_len, orig_new_len);
    1636                 :            :         }  
    1637                 :            :       }    
    1638                 :            :       
    1639                 :            :         // Move split point to position of other point (safely)
    1640                 :            : #ifdef PART_SURF_REFACET
    1641                 :            :       double d_sqr = (edge_pos - curve_point->coordinates()).length_squared();
    1642                 :            :       bool close = d_sqr < (GEOMETRY_RESABS*GEOMETRY_RESABS);
    1643                 :            :       old_facets.clean_out();
    1644                 :            :       new_facets.clean_out();
    1645                 :            :       if (close)
    1646                 :            :         dynamic_cast<CubitPointData*>(split)->set(curve_point->coordinates());
    1647                 :            :       else if (!fix_move_point( split, curve_point->coordinates(), facets, old_facets, new_facets ))
    1648                 :            :         return CUBIT_FAILURE;
    1649                 :            :       facets -= old_facets;
    1650                 :            :       facets += new_facets;
    1651                 :            : #else
    1652 [ #  # ][ #  # ]:          0 :       dynamic_cast<CubitPointData*>(split)->set(curve_point->coordinates());
                 [ #  # ]
    1653                 :            : #endif
    1654                 :            :       
    1655                 :          0 :       CubitStatus s2, s1 = CUBIT_SUCCESS;
    1656         [ #  # ]:          0 :       if (curve_point != split)
    1657         [ #  # ]:          0 :         s1 = curve_point->merge_points(split);
    1658         [ #  # ]:          0 :       s2 = curve_edge->merge_edges(split_edge);
    1659 [ #  # ][ #  # ]:          0 :       assert(s1 && s2);
    1660 [ #  # ][ #  # ]:          0 :       if (CUBIT_SUCCESS != s1 || CUBIT_SUCCESS != s2) {
    1661 [ #  # ][ #  # ]:          0 :         PRINT_ERROR("Internal error at %s:%d\n", __FILE__, __LINE__);
         [ #  # ][ #  # ]
    1662                 :          0 :         return CUBIT_FAILURE;
    1663                 :            :       }
    1664         [ #  # ]:          0 :       if (dead_ptrs)
    1665         [ #  # ]:          0 :         dead_ptrs->append(split_edge);
    1666                 :          0 :       prev_point = curve_point;
    1667                 :            :       
    1668 [ #  # ][ #  # ]:          0 :       if (curve_edges.is_at_beginning())
    1669                 :          0 :         curve_edge = 0;
    1670                 :            :       else
    1671                 :            :       {
    1672         [ #  # ]:          0 :         curve_edge = curve_edges.get_and_step();
    1673         [ #  # ]:          0 :         orig_crv_len = curve_edge->length();
    1674         [ #  # ]:          0 :         split_tol = FRACT_TOL * CUBIT_MIN(orig_crv_len, orig_new_len);
    1675                 :            :       }  
    1676                 :            :     }
    1677                 :            :   }
    1678                 :            :   
    1679         [ #  # ]:          0 :   return CUBIT_SUCCESS;
    1680                 :            : }
    1681                 :            : 
    1682                 :            : 
    1683                 :            : //-------------------------------------------------------------------------
    1684                 :            : // Purpose       : Retriangulate if necessary for moving a boundary point
    1685                 :            : //                 into the interior of a facet patch.
    1686                 :            : //
    1687                 :            : // Special Notes : 
    1688                 :            : //
    1689                 :            : // Creator       : Jason Kraftcheck
    1690                 :            : //
    1691                 :            : // Creation Date : 12/07/03
    1692                 :            : //-------------------------------------------------------------------------
    1693                 :          0 : CubitStatus PartSurfFacetTool::fix_move_point( 
    1694                 :            :                                       CubitPoint* point,
    1695                 :            :                                       const CubitVector& new_pos,
    1696                 :            :                                       const DLIList<CubitFacetData*>& facetds,
    1697                 :            :                                       DLIList<CubitFacetData*>& old_facets,
    1698                 :            :                                       DLIList<CubitFacetData*>& new_facets,
    1699                 :            :                                       PartitionSurface* surface )
    1700                 :            : {
    1701                 :            :   int i;
    1702 [ #  # ][ #  # ]:          0 :   DLIList<CubitFacet*> facets(facetds.size());
    1703 [ #  # ][ #  # ]:          0 :   for (i = 0; i < facetds.size(); i++)
    1704 [ #  # ][ #  # ]:          0 :     facets.append(facetds.next(i));
    1705                 :            :   
    1706                 :            :     // Look for a triangle containing the passed point.
    1707 [ #  # ][ #  # ]:          0 :   CubitVector closest_pos, vect;
    1708         [ #  # ]:          0 :   CubitFacet* facet = closest_facet(new_pos, facetds, closest_pos );
    1709         [ #  # ]:          0 :   if ( facet == NULL)
    1710                 :          0 :     return CUBIT_FAILURE;
    1711                 :            : 
    1712 [ #  # ][ #  # ]:          0 :   if (facet->point_index(point) >= 0)
    1713                 :            :   {
    1714 [ #  # ][ #  # ]:          0 :     dynamic_cast<CubitPointData*>(point)->set(new_pos);
    1715                 :          0 :     return CUBIT_SUCCESS;
    1716                 :            :   }
    1717                 :            : 
    1718 [ #  # ][ #  # ]:          0 :   PRINT_WARNING("Refacetting surface near (%f,%f,%f)\n",
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
    1719         [ #  # ]:          0 :     new_pos.x(), new_pos.y(), new_pos.z());
    1720                 :            : 
    1721                 :            :     // Line direction
    1722 [ #  # ][ #  # ]:          0 :   const CubitVector dir(point->coordinates() - new_pos);
    1723                 :            : 
    1724 [ #  # ][ #  # ]:          0 :   if (DEBUG_FLAG(145)) 
                 [ #  # ]
    1725                 :            :   { 
    1726         [ #  # ]:          0 :     GfxDebug::draw_facet(facet, CUBIT_BLUE_INDEX); 
    1727 [ #  # ][ #  # ]:          0 :     GfxDebug::draw_point(point->coordinates(), CUBIT_BLUE_INDEX);
    1728         [ #  # ]:          0 :     GfxDebug::draw_point(new_pos, CUBIT_CYAN_INDEX);
    1729 [ #  # ][ #  # ]:          0 :     GfxDebug::draw_line(point->coordinates(), new_pos, CUBIT_BLUE_INDEX);
    1730         [ #  # ]:          0 :     GfxDebug::flush(); 
    1731                 :            :   }
    1732                 :            :   
    1733                 :            :     // Find where line exits first triangle
    1734                 :          0 :   CubitFacetEdge* edge = 0;
    1735                 :            :   bool leftofpoint[3];
    1736         [ #  # ]:          0 :   for ( i = 0; i < 3; i++)
    1737                 :            :   {
    1738 [ #  # ][ #  # ]:          0 :     CubitVector vect = facet->point(i)->coordinates() - new_pos;
                 [ #  # ]
    1739         [ #  # ]:          0 :     vect *= dir;
    1740 [ #  # ][ #  # ]:          0 :     leftofpoint[i] = (vect % facet->normal()) >= 0.0;
    1741                 :            :   }
    1742                 :            :   
    1743         [ #  # ]:          0 :   for ( i = 0; i < 3; ++i)
    1744 [ #  # ][ #  # ]:          0 :     if (leftofpoint[i] && !leftofpoint[(i+1)%3])
    1745                 :            :     {
    1746         [ #  # ]:          0 :       edge = facet->edge((i+2)%3);
    1747                 :          0 :       break;
    1748                 :            :     }
    1749                 :            :   
    1750         [ #  # ]:          0 :   if (!edge)
    1751                 :          0 :     return CUBIT_FAILURE;
    1752                 :            :   
    1753                 :            :     // Find the set of triangles the line from the old 
    1754                 :            :     // position to the new position crosses.
    1755 [ #  # ][ #  # ]:          0 :   DLIList<CubitFacet*> intersect_list, edge_facets;
         [ #  # ][ #  # ]
    1756 [ #  # ][ #  # ]:          0 :   while (facet->point_index(point) < 0)
    1757                 :            :   {
    1758         [ #  # ]:          0 :     intersect_list.append(facet);
    1759                 :            : 
    1760 [ #  # ][ #  # ]:          0 :     if (DEBUG_FLAG(145)) 
                 [ #  # ]
    1761                 :            :     { 
    1762         [ #  # ]:          0 :       GfxDebug::draw_facet_edge(edge, CUBIT_WHITE_INDEX); 
    1763         [ #  # ]:          0 :       GfxDebug::draw_facet(facet, CUBIT_BLUE_INDEX); 
    1764         [ #  # ]:          0 :       GfxDebug::flush(); 
    1765                 :            :     }
    1766                 :            :       
    1767                 :            :       // Find the facet on the other side of the edge
    1768         [ #  # ]:          0 :     edge_facets.clean_out();
    1769         [ #  # ]:          0 :     if (surface)
    1770         [ #  # ]:          0 :       PartSurfFacetTool::edge_facets(surface, edge, edge_facets);
    1771                 :            :     else
    1772         [ #  # ]:          0 :       PartSurfFacetTool::edge_facets( edge, facets, edge_facets );
    1773         [ #  # ]:          0 :     edge_facets.move_to(facet);
    1774 [ #  # ][ #  # ]:          0 :     assert(edge_facets.get() == facet);
    1775                 :            : 
    1776 [ #  # ][ #  # ]:          0 :     if(edge_facets.size() != 2)
    1777                 :          0 :       break;
    1778                 :            :     
    1779         [ #  # ]:          0 :     facet = edge_facets.step_and_get();
    1780                 :            :     
    1781                 :            :       // Find the edge that the line intersects exiting the facet
    1782         [ #  # ]:          0 :     i = facet->edge_index(edge);
    1783 [ #  # ][ #  # ]:          0 :     vect = facet->point(i)->coordinates() - new_pos;
         [ #  # ][ #  # ]
    1784         [ #  # ]:          0 :     vect *= dir;
    1785 [ #  # ][ #  # ]:          0 :     if (vect % facet->normal() >= 0.0)
                 [ #  # ]
    1786         [ #  # ]:          0 :       edge = facet->edge((i+1)%3);
    1787                 :            :     else
    1788         [ #  # ]:          0 :       edge = facet->edge((i+2)%3);
    1789                 :            :   }
    1790                 :            :   
    1791         [ #  # ]:          0 :   if (facet)
    1792                 :            :   {
    1793 [ #  # ][ #  # ]:          0 :     if (DEBUG_FLAG(145)) 
                 [ #  # ]
    1794                 :            :     { 
    1795         [ #  # ]:          0 :       GfxDebug::draw_facet_edge(edge, CUBIT_WHITE_INDEX); 
    1796         [ #  # ]:          0 :       GfxDebug::flush(); 
    1797                 :            :     }
    1798         [ #  # ]:          0 :     intersect_list.append_unique(facet);
    1799                 :            :   }
    1800                 :            :   
    1801                 :            :     // Get ordered boundary
    1802 [ #  # ][ #  # ]:          0 :   DLIList<CubitPoint*> boundary_list;
    1803 [ #  # ][ #  # ]:          0 :   DLIList<CubitFacetEdge*> point_edges;
    1804                 :          0 :   CubitFacetEdge* prev_edge = 0;
    1805                 :          0 :   CubitFacet* prev_facet = 0;
    1806                 :            :     // Find one boundary edge to start with
    1807 [ #  # ][ #  # ]:          0 :   for (i = intersect_list.size(); !prev_edge && i--; )
         [ #  # ][ #  # ]
    1808                 :            :   {
    1809         [ #  # ]:          0 :     CubitFacet* facet = intersect_list.get_and_step();
    1810         [ #  # ]:          0 :     for (int j = 0; j < 3; j++)
    1811                 :            :     {
    1812         [ #  # ]:          0 :       CubitFacetEdge* edge = facet->edge(j);
    1813         [ #  # ]:          0 :       edge_facets.clean_out();
    1814         [ #  # ]:          0 :      if (surface)
    1815         [ #  # ]:          0 :        PartSurfFacetTool::edge_facets( surface, edge, edge_facets);
    1816                 :            :      else
    1817         [ #  # ]:          0 :        PartSurfFacetTool::edge_facets( edge, facets, edge_facets );
    1818         [ #  # ]:          0 :       edge_facets.intersect(intersect_list);
    1819 [ #  # ][ #  # ]:          0 :       if (edge_facets.size() == 1)
    1820                 :            :       {
    1821                 :          0 :         prev_edge = edge;
    1822                 :          0 :         prev_facet = facet;
    1823                 :          0 :         break;
    1824                 :            :       }
    1825                 :            :     }
    1826                 :            :   }
    1827                 :          0 :   CubitFacetEdge* first_edge = prev_edge;
    1828                 :            :     // Traverse boundary edges in order
    1829         [ #  # ]:          0 :   do 
    1830                 :            :   {
    1831 [ #  # ][ #  # ]:          0 :     int direction = prev_facet->edge_use( prev_facet->edge_index(prev_edge) );
    1832         [ #  # ]:          0 :     CubitPoint* pt = prev_edge->point( direction == -1 ? 0 : 1 );
    1833         [ #  # ]:          0 :     point_edges.clean_out();
    1834         [ #  # ]:          0 :     pt->edges( point_edges );
    1835                 :            :     
    1836 [ #  # ][ #  # ]:          0 :     if (DEBUG_FLAG(145))
                 [ #  # ]
    1837                 :            :     {
    1838         [ #  # ]:          0 :       GfxDebug::draw_facet_edge( prev_edge, CUBIT_LIGHTBLUE_INDEX );
    1839         [ #  # ]:          0 :       GfxDebug::flush();
    1840                 :            :     }
    1841         [ #  # ]:          0 :     boundary_list.append(pt);
    1842                 :            :     
    1843         [ #  # ]:          0 :     point_edges.move_to(prev_edge);
    1844 [ #  # ][ #  # ]:          0 :     assert(point_edges.get() == prev_edge);
    1845         [ #  # ]:          0 :     point_edges.extract();
    1846                 :          0 :     prev_edge = 0;
    1847                 :            : 
    1848 [ #  # ][ #  # ]:          0 :     while (point_edges.size())
    1849                 :            :     {
    1850         [ #  # ]:          0 :       CubitFacetEdge* edge = point_edges.pop();
    1851         [ #  # ]:          0 :       edge_facets.clean_out();
    1852         [ #  # ]:          0 :       if (surface)
    1853         [ #  # ]:          0 :         PartSurfFacetTool::edge_facets( surface, edge, edge_facets);
    1854                 :            :       else
    1855         [ #  # ]:          0 :         PartSurfFacetTool::edge_facets( edge, facets, edge_facets );
    1856         [ #  # ]:          0 :       edge_facets.intersect(intersect_list);
    1857 [ #  # ][ #  # ]:          0 :       if (edge_facets.size() == 1)
    1858                 :            :       {
    1859         [ #  # ]:          0 :         if (prev_edge) {
    1860                 :          0 :           prev_edge = 0;
    1861                 :          0 :           break;
    1862                 :            :         }
    1863                 :          0 :         prev_edge = edge;
    1864         [ #  # ]:          0 :         prev_facet = edge_facets.get();
    1865                 :            :       }
    1866                 :            :     }
    1867                 :            :   
    1868         [ #  # ]:          0 :     if (!prev_edge)
    1869                 :            :     {
    1870 [ #  # ][ #  # ]:          0 :       PRINT_ERROR("Problems finding boundary to re-facet around split point.\n");
         [ #  # ][ #  # ]
    1871                 :          0 :       return CUBIT_FAILURE;
    1872                 :            :     }
    1873                 :          0 :   } while (prev_edge != first_edge);
    1874                 :            : 
    1875                 :            :  
    1876                 :            :     // Construct new facets in affected region by connecting 
    1877                 :            :     // the split point to each boundary point
    1878                 :          0 :   int junk = 0;
    1879                 :            :   //DLIList<CubitFacetData*> new_facets, old_facets(intersect_list.size());
    1880 [ #  # ][ #  # ]:          0 :   if (!boundary_list.move_to(point))
    1881                 :            :   {
    1882 [ #  # ][ #  # ]:          0 :     PRINT_ERROR("Problems finding region around split point for re-facetting.\n");
         [ #  # ][ #  # ]
    1883                 :          0 :     return CUBIT_FAILURE;
    1884                 :            :   }
    1885         [ #  # ]:          0 :   boundary_list.step();
    1886         [ #  # ]:          0 :   CubitPoint* prev_pt = boundary_list.get_and_step();
    1887 [ #  # ][ #  # ]:          0 :   for (i = boundary_list.size(); i > 2; i--)
    1888                 :            :   {
    1889         [ #  # ]:          0 :     CubitPoint* next_pt = boundary_list.get_and_step();
    1890 [ #  # ][ #  # ]:          0 :     CubitFacetData* new_facet = new CubitFacetData( point, prev_pt, next_pt, &junk);
    1891         [ #  # ]:          0 :     new_facets.append(new_facet);
    1892                 :          0 :     prev_pt = next_pt;
    1893                 :            :     
    1894 [ #  # ][ #  # ]:          0 :     if (DEBUG_FLAG(145))
                 [ #  # ]
    1895                 :            :     {
    1896         [ #  # ]:          0 :       GfxDebug::draw_facet( new_facet, CUBIT_YELLOW_INDEX );
    1897         [ #  # ]:          0 :       GfxDebug::flush();
    1898                 :            :     }
    1899                 :            :   }
    1900                 :            :   
    1901 [ #  # ][ #  # ]:          0 :   CAST_LIST( intersect_list, old_facets, CubitFacetData );
         [ #  # ][ #  # ]
         [ #  # ][ #  # ]
                 [ #  # ]
    1902 [ #  # ][ #  # ]:          0 :   assert(intersect_list.size() == old_facets.size());
                 [ #  # ]
    1903 [ #  # ][ #  # ]:          0 :   dynamic_cast<CubitPointData*>(point)->set(new_pos);
    1904                 :            :   //replace_facets( old_facets, new_facets );
    1905         [ #  # ]:          0 :   return CUBIT_SUCCESS;
    1906                 :            : }
    1907                 :            : 
    1908                 :            : //-------------------------------------------------------------------------
    1909                 :            : // Purpose       : Find closest facet and point on facet
    1910                 :            : //
    1911                 :            : // Special Notes : 
    1912                 :            : //
    1913                 :            : // Creator       : Jason Kraftcheck
    1914                 :            : //
    1915                 :            : // Creation Date : 03/28/03
    1916                 :            : //-------------------------------------------------------------------------
    1917                 :          0 : CubitFacet* PartSurfFacetTool::closest_facet(
    1918                 :            :                                    const CubitVector& input_position,
    1919                 :            :                                    const DLIList<CubitFacetData*>& facet_list,
    1920                 :            :                                    CubitVector& result_position )
    1921                 :            : {
    1922                 :          0 :   CubitFacet* return_val = 0;
    1923                 :          0 :   double closest_dist_sqr = CUBIT_DBL_MAX;
    1924         [ #  # ]:          0 :   CubitVector facet_position;
    1925                 :            :   
    1926         [ #  # ]:          0 :   const int size = facet_list.size();
    1927         [ #  # ]:          0 :   for ( int i = 0; i < size; i++ ) {
    1928         [ #  # ]:          0 :     CubitFacet* facet = facet_list.next(i);
    1929         [ #  # ]:          0 :     closest_pt_on_facet( facet, input_position, facet_position );
    1930 [ #  # ][ #  # ]:          0 :     double dist_sqr = (input_position - facet_position).length_squared();
    1931         [ #  # ]:          0 :     if ( dist_sqr < closest_dist_sqr ) {
    1932                 :          0 :       closest_dist_sqr = dist_sqr;
    1933         [ #  # ]:          0 :       result_position = facet_position;
    1934                 :          0 :       return_val = facet;
    1935                 :            :     }
    1936                 :            :   }
    1937                 :            :   
    1938                 :          0 :   return return_val;
    1939                 :            : }
    1940                 :            : 
    1941                 :            : //-------------------------------------------------------------------------
    1942                 :            : // Purpose       : Return edge start/end if input position is sufficiently
    1943                 :            : //                 close.  Otherwise split the edge and return the new
    1944                 :            : //                 point.
    1945                 :            : //
    1946                 :            : // Special Notes : For all facets modified by this operation, owning surfaces
    1947                 :            : //                 will be notified of the change.  For any un-owned facets,
    1948                 :            : //                 new facets will be appended to the passed list.
    1949                 :            : //
    1950                 :            : // Creator       : Jason Kraftcheck
    1951                 :            : //
    1952                 :            : // Creation Date : 12/01/03
    1953                 :            : //-------------------------------------------------------------------------
    1954                 :          0 : CubitPoint* PartSurfFacetTool::split_edge_closest( 
    1955                 :            :                                      CubitFacetEdgeData* old_edge,
    1956                 :            :                                      const CubitVector& pos,
    1957                 :            :                                      double tolerance,
    1958                 :            :                                      CubitFacetEdgeData*& new_edge,
    1959                 :            :                                      DLIList<CubitFacetData*>& new_facets )
    1960                 :            : {
    1961                 :            :     // square of absolute tolerance
    1962                 :          0 :   const double GEOM_TOL_SQR = GEOMETRY_RESABS*GEOMETRY_RESABS; 
    1963                 :            :     // tolerance as fraction of edge length.
    1964         [ #  # ]:          0 :   const double TOL_SQR = tolerance < GEOM_TOL_SQR ? GEOM_TOL_SQR : tolerance * tolerance;
    1965                 :            :   
    1966                 :          0 :   new_edge = 0;
    1967                 :            : 
    1968 [ #  # ][ #  # ]:          0 :   const CubitVector start(old_edge->point(0)->coordinates());
    1969 [ #  # ][ #  # ]:          0 :   const CubitVector end(old_edge->point(1)->coordinates());
    1970                 :            : //   const CubitVector dir(end - start);
    1971                 :            :   //const double fract = (dir % (pos - start)) / dir.length_squared();
    1972                 :            : 
    1973                 :            :     // If near the start/end of the edge and start/end point is
    1974                 :            :     // not already owned by some other vertex
    1975 [ #  # ][ #  # ]:          0 :   const double start_sqr = (start - pos).length_squared();
    1976 [ #  # ][ #  # ]:          0 :   const double end_sqr   = (end   - pos).length_squared();
    1977 [ #  # ][ #  # ]:          0 :   if (start_sqr < TOL_SQR && !TDVGFacetOwner::get(old_edge->point(0)))
         [ #  # ][ #  # ]
                 [ #  # ]
    1978         [ #  # ]:          0 :     return old_edge->point(0);
    1979 [ #  # ][ #  # ]:          0 :   else if (end_sqr < TOL_SQR && !TDVGFacetOwner::get(old_edge->point(1)))
         [ #  # ][ #  # ]
                 [ #  # ]
    1980         [ #  # ]:          0 :     return old_edge->point(1);
    1981                 :            : 
    1982                 :            :     // Else if start/end of edge are same position as vertex
    1983         [ #  # ]:          0 :   else if(start_sqr < GEOM_TOL_SQR)
    1984         [ #  # ]:          0 :     return old_edge->point(0);
    1985         [ #  # ]:          0 :   else if(end_sqr < GEOM_TOL_SQR)
    1986         [ #  # ]:          0 :     return old_edge->point(1);
    1987                 :            : 
    1988                 :            :     // Otherwise split the edge
    1989         [ #  # ]:          0 :   CubitFacet* a_face = old_edge->adj_facet(0);
    1990         [ #  # ]:          0 :   CubitFacetData* facet = dynamic_cast<CubitFacetData*>(a_face);
    1991         [ #  # ]:          0 :   if (!facet)
    1992                 :          0 :     return 0;
    1993                 :            : 
    1994                 :            :   //CubitVector edge_pos((1.0-edge_param)*edge_start + edge_param*edge_end);
    1995         [ #  # ]:          0 :   CubitPoint* start_pt = old_edge->point(0);
    1996         [ #  # ]:          0 :   CubitPoint*   end_pt = old_edge->point(1);
    1997         [ #  # ]:          0 :   CubitPoint*   new_pt = facet->split_edge( start_pt, end_pt, pos );
    1998         [ #  # ]:          0 :   CubitFacetEdge* temp_edge = new_pt->shared_edge(end_pt);
    1999         [ #  # ]:          0 :   new_edge = dynamic_cast<CubitFacetEdgeData*>(temp_edge);
    2000         [ #  # ]:          0 :   if (!new_edge)
    2001                 :          0 :     return 0;
    2002                 :            :   
    2003                 :            :     // Update partition curve facetting
    2004 [ #  # ][ #  # ]:          0 :   PartitionCurve* edge_owner = dynamic_cast<PartitionCurve*>(TDVGFacetOwner::get(old_edge));
    2005         [ #  # ]:          0 :   if (edge_owner)
    2006         [ #  # ]:          0 :     edge_owner->notify_split(old_edge, new_edge);
    2007                 :            : 
    2008                 :            :     // Update partition surfaces for split of adjacent facets
    2009                 :          0 :   int i, junk = -1;
    2010 [ #  # ][ #  # ]:          0 :   DLIList<CubitFacet*> facets(old_edge->num_adj_facets());
    2011         [ #  # ]:          0 :   old_edge->facets(facets);
    2012                 :            :   
    2013 [ #  # ][ #  # ]:          0 :   for ( i = facets.size(); i--;  )
    2014                 :            :   {
    2015         [ #  # ]:          0 :     a_face = facets.get_and_step();
    2016         [ #  # ]:          0 :     facet = dynamic_cast<CubitFacetData*>(a_face);
    2017         [ #  # ]:          0 :     assert(!!facet);
    2018         [ #  # ]:          0 :     int edge_index = facet->edge_index( start_pt, new_pt, junk );
    2019         [ #  # ]:          0 :     CubitPoint* other_pt = facet->point( edge_index );
    2020 [ #  # ][ #  # ]:          0 :     if (!other_pt->shared_edge( new_pt ))
    2021 [ #  # ][ #  # ]:          0 :       new CubitFacetEdgeData( other_pt, new_pt );
    2022                 :            : 
    2023         [ #  # ]:          0 :     CubitFacet* a_face = facet->shared_facet( new_pt, other_pt );
    2024         [ #  # ]:          0 :     CubitFacetData* other_facet = dynamic_cast<CubitFacetData*>(a_face);
    2025         [ #  # ]:          0 :     if (!other_facet) { assert(0); continue; }
    2026                 :            : 
    2027         [ #  # ]:          0 :     PartitionEntity* owner = TDVGFacetOwner::get(facet);
    2028                 :            : #ifndef NDEBUG
    2029         [ #  # ]:          0 :     PartitionSurface* surf = dynamic_cast<PartitionSurface*>(owner);
    2030 [ #  # ][ #  # ]:          0 :     assert(!owner || surf);
    2031                 :            : #endif
    2032                 :            :     
    2033         [ #  # ]:          0 :     if (owner)
    2034         [ #  # ]:          0 :       owner->notify_split( facet, other_facet );
    2035                 :            :     else
    2036         [ #  # ]:          0 :       new_facets.append(other_facet);
    2037                 :            :   }
    2038                 :            :   
    2039         [ #  # ]:          0 :   return new_pt;
    2040                 :            : }
    2041                 :            : 
    2042                 :            : //-------------------------------------------------------------------------
    2043                 :            : // Purpose       : Spatially match a set of geometric points one-to-one
    2044                 :            : //                 with a subset of a set of facet vertices.
    2045                 :            : //
    2046                 :            : // Special Notes : If the geometric point already has an attached facet
    2047                 :            : //                 point, the points will be merged such that the facet
    2048                 :            : //                 point originally on the geometric point survives the
    2049                 :            : //                 merge.  If the geometric point does not already have
    2050                 :            : //                 a facet point, the input facet point will be attached
    2051                 :            : //                 to the geometric point.
    2052                 :            : //
    2053                 :            : // Creator       : Jason Kraftcheck
    2054                 :            : //
    2055                 :            : // Creation Date : 09/08/03
    2056                 :            : //-------------------------------------------------------------------------
    2057                 :          0 : CubitStatus PartSurfFacetTool::associate_points( 
    2058                 :            :                                      DLIList<CubitPoint*>& facet_points,
    2059                 :            :                                      DLIList<PartitionPoint*>& geom_points )
    2060                 :            : {
    2061                 :            :   int i;
    2062 [ #  # ][ #  # ]:          0 :   DLIList<int> geom_indices(geom_points.size());
    2063                 :            :   
    2064 [ #  # ][ #  # ]:          0 :   for (i = 0; i < geom_points.size(); i++ )
    2065         [ #  # ]:          0 :     geom_indices.append(i);
    2066                 :            : 
    2067 [ #  # ][ #  # ]:          0 :   for (i = facet_points.size(); i--; )
    2068 [ #  # ][ #  # ]:          0 :     facet_points.step_and_get()->marked(-1);
    2069                 :            : 
    2070         [ #  # ]:          0 :   geom_points.reset();
    2071         [ #  # ]:          0 :   facet_points.reset();
    2072 [ #  # ][ #  # ]:          0 :   while (geom_indices.size())
    2073                 :            :   {
    2074         [ #  # ]:          0 :     int index = geom_indices.pop();
    2075         [ #  # ]:          0 :     PartitionPoint* geom_pt = geom_points.next(index);
    2076         [ #  # ]:          0 :     const CubitVector pos(geom_pt->coordinates());
    2077                 :          0 :     double shortest_dist_sqr = CUBIT_DBL_MAX;
    2078                 :          0 :     int closest_index = -1;
    2079 [ #  # ][ #  # ]:          0 :     for (i = 0; i < facet_points.size(); i++ )
    2080                 :            :     {
    2081         [ #  # ]:          0 :       CubitPoint* facet_pt = facet_points.next(i);
    2082 [ #  # ][ #  # ]:          0 :       double dist_sqr = (pos - facet_pt->coordinates()).length_squared();
                 [ #  # ]
    2083         [ #  # ]:          0 :       if (dist_sqr < shortest_dist_sqr)
    2084                 :            :       {
    2085 [ #  # ][ #  # ]:          0 :         if (facet_pt->marked() == -1)
    2086                 :            :         {
    2087                 :          0 :           shortest_dist_sqr = dist_sqr;
    2088                 :          0 :           closest_index = i;
    2089                 :            :         }
    2090                 :            :         else 
    2091                 :            :         {
    2092         [ #  # ]:          0 :           int j = facet_pt->marked();
    2093         [ #  # ]:          0 :           CubitPoint* other_point = facet_points.next(j);
    2094 [ #  # ][ #  # ]:          0 :           double other_dist_sqr = (pos - other_point->coordinates()).length_squared();
                 [ #  # ]
    2095         [ #  # ]:          0 :           if (other_dist_sqr > dist_sqr)
    2096                 :            :           {
    2097                 :          0 :             shortest_dist_sqr = dist_sqr;
    2098                 :          0 :             closest_index = i;
    2099         [ #  # ]:          0 :             facet_pt->marked(-1);
    2100         [ #  # ]:          0 :             geom_indices.append(j);
    2101                 :            :           }
    2102                 :            :         }
    2103                 :            :       }
    2104                 :            :     }
    2105                 :            :     
    2106         [ #  # ]:          0 :     if (closest_index < 0)
    2107                 :            :     {
    2108                 :          0 :       assert(false);
    2109                 :            :       for (i = facet_points.size(); i--; )
    2110                 :            :         facet_points.step_and_get()->marked(0);
    2111                 :            :       for (i = geom_points.size(); i--; )
    2112                 :            :         geom_points.step_and_get()->mark = 0;
    2113                 :            :       return CUBIT_FAILURE;
    2114                 :            :     }
    2115                 :          0 :     geom_pt->mark = closest_index;
    2116 [ #  # ][ #  # ]:          0 :     facet_points.next(closest_index)->marked(index);
    2117                 :            :   }
    2118                 :            :   
    2119 [ #  # ][ #  # ]:          0 :   for (i = facet_points.size(); i--; )
    2120 [ #  # ][ #  # ]:          0 :     facet_points.step_and_get()->marked(0);
    2121                 :            :   
    2122         [ #  # ]:          0 :   facet_points.reset();
    2123 [ #  # ][ #  # ]:          0 :   for (i = geom_points.size(); i--; )
    2124                 :            :   {
    2125         [ #  # ]:          0 :     PartitionPoint* geom_pt = geom_points.step_and_get();
    2126         [ #  # ]:          0 :     CubitPoint* facet_pt = facet_points.next(geom_pt->mark);
    2127                 :          0 :     geom_pt->mark = 0;
    2128                 :            :     
    2129 [ #  # ][ #  # ]:          0 :     assert(!TDVGFacetOwner::get(facet_pt));
    2130 [ #  # ][ #  # ]:          0 :     facet_pt->set(geom_pt->coordinates());
    2131                 :            :     
    2132         [ #  # ]:          0 :     CubitPointData* point_data = dynamic_cast<CubitPointData*>(facet_pt);
    2133         [ #  # ]:          0 :     assert(!!point_data);
    2134                 :            :     
    2135 [ #  # ][ #  # ]:          0 :     if (geom_pt->facet_point())
    2136 [ #  # ][ #  # ]:          0 :       geom_pt->facet_point()->merge_points( point_data );
    2137                 :            :     else
    2138         [ #  # ]:          0 :       geom_pt->facet_point(point_data);
    2139                 :            :   }
    2140                 :            :   
    2141         [ #  # ]:          0 :   return CUBIT_SUCCESS;
    2142                 :            : }
    2143                 :            : 
    2144                 :            : //-------------------------------------------------------------------------
    2145                 :            : // Purpose       : Get points and edges in facet patch, separated into
    2146                 :            : //                 boundary and internal sets where a boundary point is
    2147                 :            : //                 a point for which one or more adjacent edges is on the
    2148                 :            : //                 boundary of the patch.
    2149                 :            : //
    2150                 :            : // Special Notes : Aborts and returns failure if the input facets are not
    2151                 :            : //                 a manifold patch.
    2152                 :            : //
    2153                 :            : // Creator       : Jason Kraftcheck
    2154                 :            : //
    2155                 :            : // Creation Date : 09/08/03
    2156                 :            : //-------------------------------------------------------------------------
    2157                 :          0 : CubitStatus PartSurfFacetTool::get_facet_points_and_edges(
    2158                 :            :                                    const DLIList<CubitFacetData*>& facets,
    2159                 :            :                                    DLIList<CubitPoint*>& boundary_points,
    2160                 :            :                                    DLIList<CubitPoint*>& interior_points,
    2161                 :            :                                    DLIList<CubitFacetEdge*>& boundary_edges,
    2162                 :            :                                    DLIList<CubitFacetEdge*>& interior_edges )
    2163                 :            : {
    2164                 :            :   int i, j;
    2165                 :          0 :   CubitStatus result = CUBIT_SUCCESS;
    2166                 :            :   CubitFacetData* facet;
    2167         [ #  # ]:          0 :   DLIList<CubitFacetEdge*> edge_list;
    2168         [ #  # ]:          0 :   const int count = facets.size();
    2169                 :            :   
    2170                 :            :     // Initialize marks
    2171         [ #  # ]:          0 :   for (i = 0; i < count; i++ )
    2172                 :            :   {
    2173         [ #  # ]:          0 :     facet = facets.next(i);
    2174         [ #  # ]:          0 :     for (j = 0; j < 3; j++)
    2175                 :            :     {
    2176 [ #  # ][ #  # ]:          0 :       facet->edge(j)->marked(0);
    2177 [ #  # ][ #  # ]:          0 :       facet->point(j)->marked(1);
    2178                 :            :     }
    2179                 :            :   }
    2180                 :            :   
    2181                 :            :     // Mark each edge with a count of the number of
    2182                 :            :     // adjcent facets.
    2183         [ #  # ]:          0 :   for (i = 0; i < count; i++ )
    2184                 :            :   {
    2185         [ #  # ]:          0 :     facet = facets.next(i);
    2186         [ #  # ]:          0 :     for (j = 0; j < 3; j++)
    2187 [ #  # ][ #  # ]:          0 :       facet->edge(j)->marked(facet->edge(j)->marked() + 1);
         [ #  # ][ #  # ]
    2188                 :            :   }
    2189                 :            :   
    2190                 :            :     // Collect points and clear point marks
    2191         [ #  # ]:          0 :   for (i = 0; i < count; i++ )
    2192                 :            :   {
    2193         [ #  # ]:          0 :     facet = facets.next(i);
    2194         [ #  # ]:          0 :     for (j = 0; j < 3; j++)
    2195                 :            :     {
    2196         [ #  # ]:          0 :       CubitPoint* point = facet->point(j);
    2197 [ #  # ][ #  # ]:          0 :       if (!point->marked())
    2198                 :          0 :         continue;
    2199         [ #  # ]:          0 :       point->marked(0);
    2200                 :            :       
    2201         [ #  # ]:          0 :       point->edges(edge_list);
    2202                 :          0 :       bool boundary = false;
    2203 [ #  # ][ #  # ]:          0 :       while (edge_list.size())
    2204 [ #  # ][ #  # ]:          0 :         if (edge_list.pop()->marked() == 1)
                 [ #  # ]
    2205                 :          0 :           boundary = true;
    2206         [ #  # ]:          0 :       if (boundary)
    2207         [ #  # ]:          0 :         boundary_points.append(point);
    2208                 :            :       else 
    2209         [ #  # ]:          0 :         interior_points.append(point);
    2210                 :            :     }
    2211                 :            :   }
    2212                 :            :   
    2213                 :            :     // Collect edges and clear edge marks   
    2214         [ #  # ]:          0 :   for (i = 0; i < count; i++ )
    2215                 :            :   {
    2216         [ #  # ]:          0 :     facet = facets.next(i);
    2217         [ #  # ]:          0 :     for (j = 0; j < 3; j++)
    2218                 :            :     {
    2219         [ #  # ]:          0 :       CubitFacetEdge* edge = facet->edge(j);
    2220         [ #  # ]:          0 :       switch (edge->marked())
           [ #  #  #  # ]
    2221                 :            :       {
    2222                 :            :         case 0:
    2223                 :          0 :           continue;
    2224                 :            :         case 1:
    2225         [ #  # ]:          0 :           boundary_edges.append(edge);
    2226                 :          0 :           break;
    2227                 :            :         case 2:
    2228         [ #  # ]:          0 :           interior_edges.append(edge);
    2229                 :          0 :           break;
    2230                 :            :         default:
    2231                 :          0 :           result = CUBIT_FAILURE;
    2232                 :          0 :           assert(false);
    2233                 :            :       }
    2234         [ #  # ]:          0 :       edge->marked(0);
    2235                 :            :     }
    2236                 :            :   }
    2237                 :            :   
    2238         [ #  # ]:          0 :   return result;
    2239                 :            : }
    2240                 :            : 
    2241                 :            : 
    2242                 :            : //-------------------------------------------------------------------------
    2243                 :            : // Purpose       : Get facets adjacent to edge and owned by this surface.
    2244                 :            : //
    2245                 :            : // Special Notes : 
    2246                 :            : //
    2247                 :            : // Creator       : Jason Kraftcheck
    2248                 :            : //
    2249                 :            : // Creation Date : 12/07/03
    2250                 :            : //-------------------------------------------------------------------------
    2251                 :          0 : void PartSurfFacetTool::edge_facets( PartitionSurface* surf,
    2252                 :            :                                      CubitFacetEdge* edge,
    2253                 :            :                                      DLIList<CubitFacet*>& facets )
    2254                 :            : {
    2255                 :          0 :   edge->facets(facets);
    2256                 :            : 
    2257         [ #  # ]:          0 :   for (int i = facets.size(); i--; )
    2258 [ #  # ][ #  # ]:          0 :     if (TDVGFacetOwner::get(facets.step_and_get()) != surf)
    2259                 :          0 :       facets.change_to(0);
    2260                 :            :   
    2261         [ #  # ]:          0 :   facets.remove_all_with_value(0);
    2262                 :          0 : }
    2263                 :            : 
    2264                 :            : 
    2265                 :            : 
    2266                 :            : //-------------------------------------------------------------------------
    2267                 :            : // Purpose       : Get facets in passed list adjacent to passed edge
    2268                 :            : //
    2269                 :            : // Special Notes : 
    2270                 :            : //
    2271                 :            : // Creator       : Jason Kraftcheck
    2272                 :            : //
    2273                 :            : // Creation Date : 12/07/03
    2274                 :            : //-------------------------------------------------------------------------
    2275                 :          0 : void PartSurfFacetTool::edge_facets( CubitFacetEdge* edge,
    2276                 :            :                                     const DLIList<CubitFacet*>& input_facets,
    2277                 :            :                                     DLIList<CubitFacet*>& output_facets )
    2278                 :            : {
    2279                 :          0 :   edge->facets(output_facets);
    2280                 :          0 :   output_facets.intersect( input_facets );
    2281 [ +  - ][ +  - ]:       6364 : }

Generated by: LCOV version 1.11