PolyFEM
Loading...
Searching...
No Matches
StateLoad.cpp
Go to the documentation of this file.
1#include <polyfem/State.hpp>
2
4
10
12
14
15#include <igl/Timer.h>
16namespace polyfem
17{
18 using namespace basis;
19 using namespace mesh;
20 using namespace utils;
21
23 {
24 bases.clear();
25 pressure_bases.clear();
26 geom_bases_.clear();
27 boundary_nodes.clear();
28 local_boundary.clear();
30 polys.clear();
31 poly_edge_to_data.clear();
33
34 mass.resize(0, 0);
35 rhs.resize(0, 0);
36
37 n_bases = 0;
39 }
40
41 void State::load_mesh(GEO::Mesh &meshin, const std::function<int(const RowVectorNd &)> &boundary_marker, bool non_conforming, bool skip_boundary_sideset)
42 {
43 reset_mesh();
44
45 igl::Timer timer;
46 timer.start();
47 logger().info("Loading mesh...");
48 mesh = Mesh::create(meshin, non_conforming);
49 if (!mesh)
50 {
51 logger().error("Unable to load the mesh");
52 return;
53 }
54
55 RowVectorNd min, max;
56 mesh->bounding_box(min, max);
57
58 logger().info("mesh bb min [{}], max [{}]", min, max);
59
60 if (!skip_boundary_sideset)
61 mesh->compute_boundary_ids(boundary_marker);
62
63 std::vector<std::shared_ptr<assembler::Assembler>> assemblers;
64 assemblers.push_back(assembler);
65 assemblers.push_back(mass_matrix_assembler);
66 if (mixed_assembler != nullptr)
67 // TODO: assemblers.push_back(mixed_assembler);
68 mixed_assembler->set_size(mesh->dimension());
69 if (pressure_assembler != nullptr)
70 assemblers.push_back(pressure_assembler);
71 set_materials(assemblers);
72
73 timer.stop();
74 logger().info(" took {}s", timer.getElapsedTime());
75
76 timer.start();
77 logger().info("Loading obstacles...");
79 units,
80 args["geometry"],
81 utils::json_as_array(args["boundary_conditions"]["obstacle_displacements"]),
82 utils::json_as_array(args["boundary_conditions"]["dirichlet_boundary"]),
83 args["root_path"], mesh->dimension());
84
85 timer.stop();
86 logger().info(" took {}s", timer.getElapsedTime());
87
88 out_geom.init_sampler(*mesh, args["output"]["paraview"]["vismesh_rel_area"]);
89 }
90
91 void State::load_mesh(bool non_conforming,
92 const std::vector<std::string> &names,
93 const std::vector<Eigen::MatrixXi> &cells,
94 const std::vector<Eigen::MatrixXd> &vertices)
95 {
96 assert(names.size() == cells.size());
97 assert(vertices.size() == cells.size());
98
99 reset_mesh();
100
101 igl::Timer timer;
102 timer.start();
103
104 logger().info("Loading mesh ...");
105 if (mesh == nullptr)
106 {
107 assert(is_param_valid(args, "geometry"));
109 units,
110 args["geometry"], args["root_path"],
111 names, vertices, cells, non_conforming);
112 }
113
114 if (mesh == nullptr)
115 {
116 log_and_throw_error("unable to load the mesh!");
117 }
118
119 // if(!flipped_elements.empty())
120 // {
121 // mesh->compute_elements_tag();
122 // for(auto el_id : flipped_elements)
123 // mesh->set_tag(el_id, ElementType::INTERIOR_POLYTOPE);
124 // }
125
126 RowVectorNd min, max;
127 mesh->bounding_box(min, max);
128
129 logger().info("mesh bb min [{}], max [{}]", min, max);
130
131 std::vector<std::shared_ptr<assembler::Assembler>> assemblers;
132 assemblers.push_back(assembler);
133 assemblers.push_back(mass_matrix_assembler);
134 if (mixed_assembler != nullptr)
135 // TODO: assemblers.push_back(mixed_assembler);
136 mixed_assembler->set_size(mesh->dimension());
137 if (pressure_assembler != nullptr)
138 assemblers.push_back(pressure_assembler);
139 set_materials(assemblers);
140
141 timer.stop();
142 logger().info(" took {}s", timer.getElapsedTime());
143
144 out_geom.init_sampler(*mesh, args["output"]["paraview"]["vismesh_rel_area"]);
145
146 timer.start();
147 logger().info("Loading obstacles...");
149 units,
150 args["geometry"],
151 utils::json_as_array(args["boundary_conditions"]["obstacle_displacements"]),
152 utils::json_as_array(args["boundary_conditions"]["dirichlet_boundary"]),
153 args["root_path"], mesh->dimension(), names, vertices, cells);
154 timer.stop();
155 logger().info(" took {}s", timer.getElapsedTime());
156 }
157
158 void State::build_mesh_matrices(Eigen::MatrixXd &V, Eigen::MatrixXi &F)
159 {
160 assert(bases.size() == mesh->n_elements());
161 const size_t n_vertices = n_bases - obstacle.n_vertices();
162 const int dim = mesh->dimension();
163
164 V.resize(n_vertices, dim);
165 F.resize(bases.size(), dim + 1); // TODO: this only works for triangles and tetrahedra
166
167 for (int i = 0; i < bases.size(); i++)
168 {
169 const basis::ElementBases &element = bases[i];
170 for (int j = 0; j < element.bases.size(); j++)
171 {
172 const basis::Basis &basis = element.bases[j];
173 assert(basis.global().size() == 1);
174 V.row(basis.global()[0].index) = basis.global()[0].node;
175 if (j < F.cols()) // Only grab the corners of the triangles/tetrahedra
176 F(i, j) = basis.global()[0].index;
177 }
178 }
179 }
180
181 std::unordered_map<int, std::array<bool, 3>>
182 State::boundary_conditions_ids(const std::string &bc_type) const
183 {
184 assert(args["boundary_conditions"].contains(bc_type));
185 const std::vector<json> json_bcs = json_as_array(args["boundary_conditions"][bc_type]);
186 std::unordered_map<int, std::array<bool, 3>> bcs;
187 for (const json &bc : json_bcs)
188 {
189 assert(bc["dimension"].size() >= mesh->dimension());
190 std::array<bool, 3> dimension{{true, true, true}};
191 for (int d = 0; d < bc["dimension"].size(); ++d)
192 dimension[d] = bc["dimension"][d];
193
194 assert(bc.contains("id") && bc["id"].is_number_integer());
195 bcs[bc["id"].get<int>()] = dimension;
196 }
197
198 return bcs;
199 }
200} // namespace polyfem
int V
int n_bases
number of bases
Definition State.hpp:178
int n_pressure_bases
number of pressure bases
Definition State.hpp:180
mesh::Obstacle obstacle
Obstacles used in collisions.
Definition State.hpp:468
std::shared_ptr< assembler::Assembler > assembler
assemblers
Definition State.hpp:155
io::OutGeometryData out_geom
visualization stuff
Definition State.hpp:601
void load_mesh(bool non_conforming=false, const std::vector< std::string > &names=std::vector< std::string >(), const std::vector< Eigen::MatrixXi > &cells=std::vector< Eigen::MatrixXi >(), const std::vector< Eigen::MatrixXd > &vertices=std::vector< Eigen::MatrixXd >())
loads the mesh from the json arguments
Definition StateLoad.cpp:91
std::vector< basis::ElementBases > geom_bases_
Geometric mapping bases, if the elements are isoparametric, this list is empty.
Definition State.hpp:175
void set_materials(std::vector< std::shared_ptr< assembler::Assembler > > &assemblers) const
set the material and the problem dimension
std::map< int, basis::InterfaceData > poly_edge_to_data
nodes on the boundary of polygonal elements, used for harmonic bases
Definition State.hpp:441
std::vector< basis::ElementBases > pressure_bases
FE pressure bases for mixed elements, the size is #elements.
Definition State.hpp:173
std::shared_ptr< assembler::Assembler > pressure_assembler
Definition State.hpp:160
std::shared_ptr< assembler::Mass > mass_matrix_assembler
Definition State.hpp:157
std::unique_ptr< mesh::Mesh > mesh
current mesh, it can be a Mesh2D or Mesh3D
Definition State.hpp:466
void reset_mesh()
Resets the mesh.
Definition StateLoad.cpp:22
std::unordered_map< int, std::array< bool, 3 > > boundary_conditions_ids(const std::string &bc_type) const
Construct a vector of boundary conditions ids with their dimension flags.
StiffnessMatrix mass
Mass matrix, it is computed only for time dependent problems.
Definition State.hpp:202
json args
main input arguments containing all defaults
Definition State.hpp:101
std::vector< basis::ElementBases > bases
FE bases, the size is #elements.
Definition State.hpp:171
std::vector< mesh::LocalBoundary > local_boundary
mapping from elements to nodes for dirichlet boundary conditions
Definition State.hpp:433
std::vector< int > boundary_nodes
list of boundary nodes
Definition State.hpp:427
std::vector< mesh::LocalBoundary > local_neumann_boundary
mapping from elements to nodes for neumann boundary conditions
Definition State.hpp:435
void build_mesh_matrices(Eigen::MatrixXd &V, Eigen::MatrixXi &F)
Build the mesh matrices (vertices and elements) from the mesh using the bases node ordering.
std::shared_ptr< assembler::MixedAssembler > mixed_assembler
Definition State.hpp:159
std::map< int, Eigen::MatrixXd > polys
polygons, used since poly have no geom mapping
Definition State.hpp:185
Eigen::MatrixXd rhs
System right-hand side.
Definition State.hpp:207
Represents one basis function and its gradient.
Definition Basis.hpp:44
const std::vector< Local2Global > & global() const
Definition Basis.hpp:104
Stores the basis functions for a given element in a mesh (facet in 2d, cell in 3d).
std::vector< Basis > bases
one basis function per node in the element
void init_sampler(const polyfem::mesh::Mesh &mesh, const double vismesh_rel_area)
unitalize the ref element sampler
Definition OutData.cpp:2309
static std::unique_ptr< Mesh > create(const std::string &path, const bool non_conforming=false)
factory to build the proper mesh
Definition Mesh.cpp:173
Obstacle read_obstacle_geometry(const Units &units, const json &geometry, const std::vector< json > &displacements, const std::vector< json > &dirichlets, const std::string &root_path, const int dim, const std::vector< std::string > &_names, const std::vector< Eigen::MatrixXd > &_vertices, const std::vector< Eigen::MatrixXi > &_cells, const bool non_conforming)
read a FEM mesh from a geometry JSON
std::unique_ptr< Mesh > read_fem_geometry(const Units &units, const json &geometry, const std::string &root_path, const std::vector< std::string > &_names, const std::vector< Eigen::MatrixXd > &_vertices, const std::vector< Eigen::MatrixXi > &_cells, const bool non_conforming)
read FEM meshes from a geometry JSON array (or single)
std::vector< T > json_as_array(const json &j)
Return the value of a json object as an array.
Definition JSONUtils.hpp:38
bool is_param_valid(const json &params, const std::string &key)
Determine if a key exists and is non-null in a json object.
spdlog::logger & logger()
Retrieves the current logger.
Definition Logger.cpp:42
nlohmann::json json
Definition Common.hpp:9
Eigen::Matrix< double, 1, Eigen::Dynamic, Eigen::RowMajor, 1, 3 > RowVectorNd
Definition Types.hpp:11
void log_and_throw_error(const std::string &msg)
Definition Logger.cpp:71