slim.h 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155
  1. // This file is part of libigl, a simple c++ geometry processing library.
  2. //
  3. // Copyright (C) 2016 Michael Rabinovich
  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. #ifndef SLIM_H
  9. #define SLIM_H
  10. #include "igl_inline.h"
  11. #include "MappingEnergyType.h"
  12. #include <Eigen/Dense>
  13. #include <Eigen/Sparse>
  14. // This option makes the iterations faster (all except the first) by caching the
  15. // sparsity pattern of the matrix involved in the assembly. It should be on if
  16. // you plan to do many iterations, off if you have to change the matrix
  17. // structure at every iteration.
  18. #define SLIM_CACHED
  19. #ifdef SLIM_CACHED
  20. #include "AtA_cached.h"
  21. #endif
  22. namespace igl
  23. {
  24. /// Parameters and precomputed data for computing a SLIM map as derived in
  25. /// "Scalable Locally Injective Maps" [Rabinovich et al. 2016].
  26. ///
  27. /// \fileinfo
  28. struct SLIMData
  29. {
  30. /// #V by 3 list of mesh vertex positions
  31. Eigen::MatrixXd V;
  32. /// #F by 3/4 list of mesh faces (triangles/tets)
  33. Eigen::MatrixXi F;
  34. /// Mapping energy type
  35. MappingEnergyType slim_energy;
  36. // Optional Input
  37. /// Fixed indices
  38. Eigen::VectorXi b;
  39. /// Fixed values
  40. Eigen::MatrixXd bc;
  41. /// Weight for enforcing fixed values as soft constraint
  42. double soft_const_p;
  43. /// used for exponential energies, ignored otherwise
  44. double exp_factor;
  45. /// only supported for 3d
  46. bool mesh_improvement_3d;
  47. // Output
  48. /// #V by dim list of mesh vertex positions (dim = 2 for parametrization, 3 otherwise)
  49. Eigen::MatrixXd V_o;
  50. /// objective value
  51. double energy;
  52. // INTERNAL
  53. Eigen::VectorXd M;
  54. double mesh_area;
  55. double avg_edge_length;
  56. int v_num;
  57. int f_num;
  58. double proximal_p;
  59. Eigen::VectorXd WGL_M;
  60. Eigen::VectorXd rhs;
  61. Eigen::MatrixXd Ri,Ji;
  62. Eigen::MatrixXd W;
  63. Eigen::SparseMatrix<double> Dx,Dy,Dz;
  64. int f_n,v_n;
  65. bool first_solve;
  66. bool has_pre_calc = false;
  67. int dim;
  68. #ifdef SLIM_CACHED
  69. Eigen::SparseMatrix<double> A;
  70. Eigen::VectorXi A_data;
  71. Eigen::SparseMatrix<double> AtA;
  72. igl::AtA_cached_data AtA_data;
  73. #endif
  74. };
  75. /// Compute necessary information to start using SLIM
  76. ///
  77. /// @param[in] V #V by 3 list of mesh vertex positions
  78. /// @param[in] F #F by (3|4) list of mesh faces (triangles/tets)
  79. /// @param[in] V_init #V by 3 list of initial mesh vertex positions
  80. /// @param[in,out] data Precomputation data structure
  81. /// @param[in] slim_energy Energy to minimize
  82. /// @param[in] b list of boundary indices into V
  83. /// @param[in] bc #b by dim list of boundary conditions
  84. /// @param[in] soft_p Soft penalty factor (can be zero)
  85. ///
  86. /// \fileinfo
  87. IGL_INLINE void slim_precompute(
  88. const Eigen::MatrixXd& V,
  89. const Eigen::MatrixXi& F,
  90. const Eigen::MatrixXd& V_init,
  91. SLIMData& data,
  92. MappingEnergyType slim_energy,
  93. const Eigen::VectorXi& b,
  94. const Eigen::MatrixXd& bc,
  95. double soft_p);
  96. /// Run iter_num iterations of SLIM
  97. ///
  98. /// @param[in,out] data Precomputation data structure
  99. /// @param[in] iter_num Number of iterations to run
  100. /// @return #V by dim list of mesh vertex positions
  101. ///
  102. /// \fileinfo
  103. IGL_INLINE Eigen::MatrixXd slim_solve(
  104. SLIMData& data,
  105. int iter_num);
  106. /// Internal Routine. Exposed for Integration with SCAF
  107. ///
  108. /// @param[in] Ji ?? by ?? list of Jacobians??
  109. /// @param[in] slim_energy Energy to minimize
  110. /// @param[in] exp_factor ??? used for exponential energies, ignored otherwise
  111. /// @param[out] W ?? by ?? list of weights??
  112. /// @param[out] Ri ?? by ?? list of rotations??
  113. ///
  114. /// \fileinfo
  115. IGL_INLINE void slim_update_weights_and_closest_rotations_with_jacobians(
  116. const Eigen::MatrixXd &Ji,
  117. igl::MappingEnergyType slim_energy,
  118. double exp_factor,
  119. Eigen::MatrixXd &W,
  120. Eigen::MatrixXd &Ri);
  121. /// Undocumented function related to SLIM optimization
  122. ///
  123. /// @param[in] Dx ?? by ?? matrix to compute of x derivatives?
  124. /// @param[in] Dy ?? by ?? matrix to compute of y derivatives?
  125. /// @param[in] Dz ?? bz ?? matrix to compute of z derivatives?
  126. /// @param[in] W ?? by ?? list of weights??
  127. /// @param[out] IJV ?? by ?? list of triplets to some A matrix??
  128. IGL_INLINE void slim_buildA(
  129. const Eigen::SparseMatrix<double> &Dx,
  130. const Eigen::SparseMatrix<double> &Dy,
  131. const Eigen::SparseMatrix<double> &Dz,
  132. const Eigen::MatrixXd &W,
  133. std::vector<Eigen::Triplet<double> > & IJV);
  134. }
  135. #ifndef IGL_STATIC_LIBRARY
  136. # include "slim.cpp"
  137. #endif
  138. #endif