circulation.cpp 1.7 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071
  1. // This file is part of libigl, a simple c++ geometry processing library.
  2. //
  3. // Copyright (C) 2015 Alec Jacobson <alecjacobson@gmail.com>
  4. //
  5. // This Source Code Form is subject to the terms of the Mozilla Public License
  6. // v. 2.0. If a copy of the MPL was not distributed with this file, You can
  7. // obtain one at http://mozilla.org/MPL/2.0/.
  8. #include "circulation.h"
  9. #include "list_to_matrix.h"
  10. IGL_INLINE std::vector<int> igl::circulation(
  11. const int e,
  12. const bool ccw,
  13. const Eigen::MatrixXi & F,
  14. const Eigen::MatrixXi & E,
  15. const Eigen::VectorXi & EMAP,
  16. const Eigen::MatrixXi & EF,
  17. const Eigen::MatrixXi & EI)
  18. {
  19. // prepare output
  20. std::vector<int> N;
  21. N.reserve(6);
  22. const int m = F.rows();
  23. const auto & step = [&](
  24. const int e,
  25. const int ff,
  26. int & ne,
  27. int & nf)
  28. {
  29. assert((EF(e,1) == ff || EF(e,0) == ff) && "e should touch ff");
  30. //const int fside = EF(e,1)==ff?1:0;
  31. const int nside = EF(e,0)==ff?1:0;
  32. const int nv = EI(e,nside);
  33. // get next face
  34. nf = EF(e,nside);
  35. // get next edge
  36. const int dir = ccw?-1:1;
  37. ne = EMAP(nf+m*((nv+dir+3)%3));
  38. };
  39. // Always start with first face (ccw in step will be sure to turn right
  40. // direction)
  41. const int f0 = EF(e,0);
  42. int fi = f0;
  43. int ei = e;
  44. while(true)
  45. {
  46. step(ei,fi,ei,fi);
  47. N.push_back(fi);
  48. // back to start?
  49. if(fi == f0)
  50. {
  51. assert(ei == e);
  52. break;
  53. }
  54. }
  55. return N;
  56. }
  57. IGL_INLINE void igl::circulation(
  58. const int e,
  59. const bool ccw,
  60. const Eigen::MatrixXi & F,
  61. const Eigen::MatrixXi & E,
  62. const Eigen::VectorXi & EMAP,
  63. const Eigen::MatrixXi & EF,
  64. const Eigen::MatrixXi & EI,
  65. Eigen::VectorXi & vN)
  66. {
  67. std::vector<int> N = circulation(e,ccw,F,E,EMAP,EF,EI);
  68. igl::list_to_matrix(N,vN);
  69. }