Main Page | Modules | Namespace List | Class Hierarchy | Alphabetical List | Class List | Directories | File List | Namespace Members | Class Members | File Members | Related Pages

mesh_global.C

Go to the documentation of this file.
00001 #include "lmesh.H"
00002 #include "mesh_global.H"
00003 #include "std/config.H"
00004 
00005 // static data
00006 Bface_list MeshGlobal::_selected_faces;
00007 Bedge_list MeshGlobal::_selected_edges;
00008 Bvert_list MeshGlobal::_selected_verts;
00009 
00010 //*****************************************************************
00011 
00012 void
00013 MeshGlobal::select(Bface*f) 
00014 { 
00015    // adds the face (and its quad partner, if it has one) to the
00016    // selected list, setting the selected flags as needed
00017 
00018    if (!f || f->is_selected())
00019       return;
00020 
00021    f->set_bit(Bsimplex::SELECTED_BIT);
00022    _selected_faces += f;
00023 
00024    if (f->is_quad())
00025       select(f->quad_partner());
00026 
00027    BMESH::set_center_of_interest(f->mesh());
00028 }
00029 
00030 void
00031 MeshGlobal::deselect(Bface* f) 
00032 { 
00033    // removes the face (and its quad partner, if it has one) from the
00034    // selected list, clearing the selected flags as needed
00035    if (!(f && f->is_selected()))
00036       return;
00037 
00038    f->clear_bit(Bsimplex::SELECTED_BIT);
00039    _selected_faces -= f; // O(n) operation
00040 
00041    if (f->is_quad())
00042       deselect(f->quad_partner());
00043 }
00044 
00045 void
00046 MeshGlobal::toggle_select(Bface* f) 
00047 { 
00048    // deselects the face if it is currently selected
00049    // and selects it otherwise
00050 
00051    if (!f)
00052       return;
00053 
00054    if (f->is_selected()) {
00055       deselect(f);
00056    } else {
00057       select(f);
00058    }
00059 }
00060 
00061 void
00062 MeshGlobal::select(CBface_list& faces) 
00063 { 
00064    // selects the faces
00065 
00066    for (int i=0; i<faces.num(); i++) {
00067       select(faces[i]);
00068    }
00069 }
00070 
00071 void
00072 MeshGlobal::deselect(CBface_list& faces) 
00073 { 
00074    // deselects the faces
00075 
00076    for (int i=0; i<faces.num(); i++) {
00077       deselect(faces[i]);
00078    }
00079 }
00080 
00081 void
00082 MeshGlobal::deselect_all_faces() 
00083 { 
00084    // removes all faces from the selected list, clearing the selected
00085    // flags as needed
00086 
00087    _selected_faces.clear_bits(Bsimplex::SELECTED_BIT);
00088    _selected_faces.clear();
00089 }
00090 
00091 Bface_list 
00092 MeshGlobal::selected_faces(BMESH* mesh) 
00093 { 
00094    // returns a list of all currently selected faces from the given
00095    // mesh
00096 
00097    return _selected_faces.filter(MeshSimplexFilter(mesh));
00098 }
00099 
00100 Bface_list
00101 MeshGlobal::selected_faces_all_levels(BMESH* m)
00102 {
00103    // returns a list of all currently selected faces from the given
00104    // mesh. if the given mesh is an LMESH*, also returns selected
00105    // faces from any other meshes in its subdivision hierarchy
00106 
00107    Bface_list ret; 
00108 
00109    if (!m) 
00110       return ret;
00111 
00112   // get the control mesh (this will just be m if
00113   // m in not an LMESH)
00114    BMESH* cm = get_ctrl_mesh(m);
00115 
00116    // return the faces selected from this mesh
00117    ret += selected_faces(cm);
00118 
00119    // If this is an lmesh, also find the selected
00120    // faces for any sub mesh in the hierarchy
00121    for (LMESH* lm = LMESH::upcast(cm); lm != 0; lm = lm->subdiv_mesh()) {
00122       ret += selected_faces(lm);
00123    }
00124 
00125    return ret;
00126 }
00127 
00128 //*****************************************************************
00129 
00130 void
00131 MeshGlobal::select(Bedge* e) 
00132 { 
00133    // adds the edge to the selected list, setting the selected flag
00134    // as needed
00135 
00136    if (!e || e->is_selected())
00137       return;
00138 
00139    e->set_bit(Bsimplex::SELECTED_BIT);
00140    _selected_edges += e;
00141 
00142    BMESH::set_center_of_interest(e->mesh());
00143 }
00144 
00145 void
00146 MeshGlobal::deselect(Bedge* e) 
00147 { 
00148    // removes the edge from the selected list, clearing the selected
00149    // flag as needed
00150 
00151    if (!(e && e->is_selected()))
00152       return;
00153 
00154    e->clear_bit(Bsimplex::SELECTED_BIT);
00155    _selected_edges -= e;
00156 }
00157 
00158 void
00159 MeshGlobal::toggle_select(Bedge* e) 
00160 { 
00161    // deselects the edge if it is currently selected
00162    // and selects it otherwise
00163 
00164    if (!e)
00165       return;
00166 
00167    if (e->is_selected()) {
00168       deselect(e);
00169    } else {
00170       select(e);
00171    }
00172 }
00173 
00174 void
00175 MeshGlobal::deselect_all_edges() 
00176 { 
00177    // removes all edges from the selected list, clearing the
00178    // selected flag as needed
00179 
00180    _selected_edges.clear_bits(Bsimplex::SELECTED_BIT);
00181    _selected_edges.clear();
00182 }
00183 
00184 void
00185 MeshGlobal::select(CBedge_list& edges) 
00186 { 
00187    // selects the edges
00188 
00189    for (int i=0; i<edges.num(); i++) {
00190       select(edges[i]);
00191    }
00192 }
00193 
00194 void
00195 MeshGlobal::deselect(CBedge_list& edges) 
00196 { 
00197    // deselects the edges
00198 
00199    for (int i=0; i<edges.num(); i++) {
00200       deselect(edges[i]);
00201    }
00202 }
00203 
00204 Bedge_list 
00205 MeshGlobal::selected_edges(BMESH* mesh) 
00206 { 
00207    // returns a list of all currently selected edges from the given
00208    // mesh
00209 
00210    return _selected_edges.filter(MeshSimplexFilter(mesh));
00211 }
00212 
00213 Bedge_list
00214 MeshGlobal::selected_edges_all_levels(BMESH* m)
00215 {
00216    // returns a list of all currently selected edges from the given
00217    // mesh. if the given mesh is an LMESH*, also returns selected
00218    // edges from any other meshes in the subdivision hierarchy
00219 
00220    Bedge_list ret; 
00221 
00222    if (!m) 
00223       return ret;
00224 
00225    // get the control mesh (this will just be m if
00226    // m in not an LMESH)
00227    BMESH* cm = get_ctrl_mesh(m);
00228 
00229    // return the edges selected from this mesh
00230    ret += selected_edges(cm);
00231 
00232    // if this is an lmesh, also find the selected
00233    // edges for any sub mesh in the hierarchy
00234 
00235    if (LMESH::isa(cm)) {
00236       LMESH* lm = (LMESH*)cm;
00237       while(lm->subdiv_mesh()) {
00238          lm = lm->subdiv_mesh();
00239          ret += selected_edges(lm);
00240       }
00241    }
00242 
00243    return ret;
00244 }
00245 
00246 //*****************************************************************
00247 
00248 void
00249 MeshGlobal::select(Bvert* v) 
00250 { 
00251    // adds the vert to the selected list, setting the selected flag
00252    // as needed
00253 
00254    if (!v || v->is_selected())
00255       return;
00256 
00257    v->set_bit(Bsimplex::SELECTED_BIT);
00258    _selected_verts += v;
00259 
00260    BMESH::set_center_of_interest(v->mesh());
00261 }
00262 
00263 void
00264 MeshGlobal::deselect(Bvert* v) 
00265 { 
00266    // removes the vert from the selected list, clearing the selected
00267    // flag as needed
00268 
00269    if (!(v && v->is_selected()))
00270       return;
00271 
00272    v->clear_bit(Bsimplex::SELECTED_BIT);
00273    _selected_verts -= v;
00274 }
00275 
00276 void
00277 MeshGlobal::toggle_select(Bvert* v) 
00278 { 
00279    // deselects the vert if it is currently selected
00280    // and selects it otherwise
00281 
00282    if (!v)
00283       return;
00284 
00285    if (v->is_selected()) {
00286       deselect(v);
00287    } else {
00288       select(v);
00289    }
00290 }
00291 
00292 void
00293 MeshGlobal::deselect_all_verts() 
00294 { 
00295    // removes all verts from the selected list, clearing the
00296    // selected flag as needed
00297 
00298    _selected_verts.clear_bits(Bsimplex::SELECTED_BIT);
00299    _selected_verts.clear();
00300 }
00301 
00302 void
00303 MeshGlobal::select(CBvert_list& verts) 
00304 { 
00305    // selects the verts
00306 
00307    for (int i=0; i<verts.num(); i++) {
00308       select(verts[i]);
00309    }
00310 }
00311 
00312 void
00313 MeshGlobal::deselect(CBvert_list& verts) 
00314 { 
00315    // deselects the verts
00316 
00317    for (int i=0; i<verts.num(); i++) {
00318       deselect(verts[i]);
00319    }
00320 }
00321 
00322 Bvert_list 
00323 MeshGlobal::selected_verts(BMESH* mesh) 
00324 { 
00325    // returns a list of all currently selected verts from the given
00326    // mesh
00327 
00328    return _selected_verts.filter(MeshSimplexFilter(mesh));
00329 }
00330 
00331 Bvert_list
00332 MeshGlobal::selected_verts_all_levels(BMESH* m)
00333 {
00334    // returns a list of all currently selected verts from the given
00335    // mesh. if the given mesh is an LMESH*, also returns selected
00336    // verts from any other meshes in the subdivision hierarchy
00337 
00338    Bvert_list ret; 
00339 
00340    if (!m) 
00341       return ret;
00342 
00343    // get the control mesh (this will just be m if
00344    // m in not an LMESH)
00345    BMESH* cm = get_ctrl_mesh(m);
00346 
00347    // return the verts selected from this mesh
00348    ret += selected_verts(cm);
00349 
00350    // if this is an lmesh, also find the selected
00351    // verts for any sub mesh in the hierarchy
00352 
00353    if (LMESH::isa(cm)) {
00354       LMESH* lm = (LMESH*)cm;
00355       while(lm->subdiv_mesh()) {
00356          lm = lm->subdiv_mesh();
00357          ret += selected_verts(lm);
00358       }
00359    }
00360 
00361    return ret;
00362 }
00363 
00364 //*****************************************************************
00365 
00366 inline
00367 bool all_selected(CBface_list& faces) 
00368 {
00369    return faces.all_satisfy(BitSetSimplexFilter(Bsimplex::SELECTED_BIT));
00370 }
00371 
00372 inline
00373 bool all_selected(CBedge_list& edges) 
00374 {
00375    return edges.all_satisfy(BitSetSimplexFilter(Bsimplex::SELECTED_BIT));
00376 }
00377 
00378 void
00379 debug_sel_faces_per_level(LMESH* m)
00380 {
00381    cerr << "sel faces per level" << endl;
00382    m = (LMESH*)get_ctrl_mesh(m);
00383 
00384    while(m) {
00385       cerr << "num sel faces level: " << m->subdiv_level() << ": "
00386            << MeshGlobal::selected_faces(m).num() << endl;
00387       m = m->subdiv_mesh();
00388    }
00389    cerr << "=====================" << endl;
00390 }
00391 
00392 void              
00393 MeshGlobal::edit_level_changed(BMESH* mesh, int from, int to)
00394 {
00395    // updates the list of selected components of the given
00396    // mesh to reflect a change in edit level. 'from' is the old
00397    // edit level, 'to' is the new edit level.
00398 
00399    // we want the components at the new level to reasonably correspond
00400    // to what's selected at the old level. the policy is that if the
00401    // edit level is refined (increased), then components at the new
00402    // level should be selected if they are descendents of selected
00403    // components at the old level.  likewise, if the edit level is
00404    // unrefined (decreased), then components at the new level should
00405    // be selected only if all of their descendents at the old level
00406    // were selected.
00407 
00408    static bool debug = Config::get_var_bool("DEBUG_EDIT_LEVEL_CHANGED",false);
00409 
00410    err_adv(debug, "MeshGlobal::edit_level_changed()");
00411    err_adv(debug, "from: %d", from);
00412    err_adv(debug, "to: %d", to);
00413 
00414    if (!LMESH::isa(mesh)) {
00415       err_adv(debug, "no valid lmesh");
00416       // don't have an lmesh, so do nothing
00417       return;
00418    }
00419 
00420    if (from==to) {
00421       err_adv(debug, "level unchanged");
00422       // edit level unchanged, do nothingy
00423       return;
00424    }
00425 
00426    // get the subdiv mesh corresponding to old edit level
00427    LMESH* old_edit_mesh = get_subdiv_mesh(get_ctrl_mesh(mesh), from);
00428 
00429    if (old_edit_mesh == 0) {
00430       err_adv(debug, "null mesh for old level");
00431       return;
00432    }
00433 
00434    // get the selected components for the old edit level
00435    Bface_list selected_faces = MeshGlobal::selected_faces(old_edit_mesh);
00436    Bedge_list selected_edges = MeshGlobal::selected_edges(old_edit_mesh);
00437    Bvert_list selected_verts = MeshGlobal::selected_verts(old_edit_mesh);
00438 
00439    Bface_list new_selected_faces;
00440    Bedge_list new_selected_edges;
00441    Bvert_list new_selected_verts;
00442 
00443    // loop indices
00444    int i=0;     // faces
00445    int j=0;     // edges
00446    int k=0;     // verts
00447    
00448    int diff = to-from;  // the change in edit level
00449 
00450    err_adv(debug, "change in level %d", diff);
00451 
00452    if (diff > 0) { // edit level refined
00453 
00454       // get the children of the old selected components at the new level
00455 
00456       for (i=0; i<selected_faces.num(); ++i) {
00457          ((Lface*)selected_faces[i])->append_subdiv_faces(diff, new_selected_faces);      }
00458 
00459       for (j=0; j<selected_edges.num(); ++j) {
00460          ((Ledge*)selected_edges[j])->append_subdiv_edges(diff, new_selected_edges);
00461       }
00462       for (k=0; k<selected_verts.num(); ++k) {
00463          Lvert* v = ((Lvert*)selected_verts[k])->subdiv_vert(diff);
00464          if (v)
00465             new_selected_verts += v;
00466       }
00467 
00468    } else { // edit level unrefined
00469 
00470       // get the parents of the old selected components at the new level
00471 
00472       Bface_list parent_faces;
00473       Bedge_list parent_edges;
00474       Bvert_list parent_verts;
00475 
00476       for (i=0; i<selected_faces.num(); ++i) {
00477          Lface* parent_f = ((Lface*)selected_faces[i])->parent(-diff);
00478          if (!parent_f) {
00479             err_adv(debug, "MeshGlobal::edit_level_changed: missing parent face");
00480             continue;
00481          }
00482          parent_faces.add_uniquely(parent_f);
00483       }
00484 
00485       for (j=0; j<selected_edges.num(); ++j) {
00486          Ledge* parent_e = ((Ledge*)selected_edges[j])->parent_edge(-diff);
00487          if (!parent_e)
00488             continue;
00489          parent_edges.add_uniquely(parent_e);
00490       }
00491 
00492       for (k=0; k<selected_verts.num(); ++k) {
00493          Lvert* parent_v = ((Lvert*)selected_verts[k])->parent_vert(-diff);
00494          if (!parent_v)
00495             continue;
00496          parent_verts.add_uniquely(parent_v);
00497       }
00498 
00499       // if all descendents of a parent component were selected at the old level, 
00500       // select the parent
00501       
00502       for (i=0; i<parent_faces.num(); ++i) {
00503          // get all the parent's children at the old edit level
00504          Bface_list child_faces; 
00505          ((Lface*)parent_faces[i])->append_subdiv_faces(-diff, child_faces);
00506 
00507          if (all_selected(child_faces)) {
00508             new_selected_faces += parent_faces[i];
00509          }
00510       }
00511 
00512       for (j=0; j<parent_edges.num(); ++j) {
00513          // get all the parent's children at the old edit level
00514          Bedge_list child_edges; 
00515          ((Ledge*)parent_edges[j])->append_subdiv_edges(-diff, child_edges);
00516 
00517          if (all_selected(child_edges)) {
00518             new_selected_edges += parent_edges[j];
00519          }
00520       }
00521 
00522       // this case is simpler: verts have 1 child vert
00523       new_selected_verts = parent_verts;
00524    }
00525 
00526    // deselect components for old level
00527    deselect(selected_faces);
00528    deselect(selected_edges);
00529    deselect(selected_verts);
00530 
00531    // select components for the new level
00532    select(new_selected_faces);
00533    select(new_selected_edges);
00534    select(new_selected_verts);
00535 }
00536 
00537 /* end of file mesh_global.C */

Generated on Mon Sep 18 11:39:32 2006 for jot by  doxygen 1.4.4