Arcane  4.2.1.0
Developer documentation
Loading...
Searching...
No Matches
MeshSectionService.cc
1// -*- tab-width: 2; indent-tabs-mode: nil; coding: utf-8-with-signature -*-
2//-----------------------------------------------------------------------------
3// Copyright 2000-2026 CEA (www.cea.fr) IFPEN (www.ifpenergiesnouvelles.com)
4// See the top-level COPYRIGHT file for details.
5// SPDX-License-Identifier: Apache-2.0
6//-----------------------------------------------------------------------------
7/*---------------------------------------------------------------------------*/
8/* MeshSectionService.cc (C) 2000-2026 */
9/* */
10/* Service allowing the creation of a mesh with a section of another mesh. */
11/*---------------------------------------------------------------------------*/
12/*---------------------------------------------------------------------------*/
13
14#include "arcane/core/IMesh.h"
15#include "arcane/core/IMeshFactoryMng.h"
16#include "arcane/core/IMeshMng.h"
17#include "arcane/core/IMeshModifier.h"
18#include "arcane/core/IPrimaryMesh.h"
19#include "arcane/core/MeshBuildInfo.h"
20
21#include "arcane/core/IMeshSection.h"
22#include "arcane/std/MeshSection_axl.h"
23
24/*---------------------------------------------------------------------------*/
25/*---------------------------------------------------------------------------*/
26
27namespace Arcane
28{
29
30/*---------------------------------------------------------------------------*/
31/*---------------------------------------------------------------------------*/
32
42class MeshSectionService
44{
45 public:
46
47 explicit MeshSectionService(const ServiceBuildInfo& sbi)
49 , m_creation_type(sbi.creationType())
50 {}
51
52 public:
53
54 void addPlane(const Real3& p0, const Real3& normal) override;
55
57 VariableCollection variables() override { return {}; }
58 void setServiceMeshUniqueId(Int32 unique_id) override;
59 void updateSection() override;
60
62 {
63 return m_cloned_mesh->handle();
64 }
65
66 private:
67
68 void _createMesh();
69 void _createCells(Int32& nb_cell, UniqueArray<Int64>& cells_infos, Int32& nb_face, UniqueArray<Int64>& faces_infos, std::unordered_map<Int64, Real3>& pos_node);
70 void _compute();
71
72 private:
73
74 // VariableCollection m_variables_ori;
75 IPrimaryMesh* m_cloned_mesh = nullptr;
77 Int32 m_mesh_uid = -1;
78 eServiceType m_creation_type;
79};
80
81/*---------------------------------------------------------------------------*/
82/*---------------------------------------------------------------------------*/
83
84ARCANE_REGISTER_SERVICE_MESHSECTION(MeshSection, MeshSectionService);
85
86/*---------------------------------------------------------------------------*/
87/*---------------------------------------------------------------------------*/
88
89/*---------------------------------------------------------------------------*/
90/*---------------------------------------------------------------------------*/
91
93addPlane(const Real3& p0, const Real3& normal)
94{
95 m_plans.add({ p0, math::normalizeReal3(normal) });
96}
97
98/*---------------------------------------------------------------------------*/
99/*---------------------------------------------------------------------------*/
100
103{
104 ARCANE_UNUSED(variables);
105 ARCANE_NOT_YET_IMPLEMENTED("Not supported yet");
106 // m_variables_ori = variables;
107}
108
109/*---------------------------------------------------------------------------*/
110/*---------------------------------------------------------------------------*/
111
114{
115 m_mesh_uid = unique_id;
116}
117
118/*---------------------------------------------------------------------------*/
119/*---------------------------------------------------------------------------*/
120
123{
124 _createMesh();
125 _compute();
126}
127
128/*---------------------------------------------------------------------------*/
129/*---------------------------------------------------------------------------*/
130
131void MeshSectionService::
132_createMesh()
133{
134 if (m_cloned_mesh != nullptr) {
135 m_cloned_mesh->modifier()->clearItems();
136 }
137
138 IMeshMng* mm = subDomain()->meshMng();
139
140 if (m_mesh_uid == -1) {
141 if (m_creation_type == ST_CaseOption) {
142 m_mesh_uid = options()->getUniqueIdServiceMesh();
143 }
144 else {
145 m_mesh_uid = 0;
146 }
147 }
148
149 String service_mesh_name = mesh()->name() + "_MeshSection" + m_mesh_uid;
150
151 MeshHandle* mesh_handle = mm->findMeshHandle(service_mesh_name, false);
152
153 if (mesh_handle == nullptr) {
154 IParallelMng* pm = subDomain()->parallelMng();
155 MeshBuildInfo mbi(service_mesh_name);
156 mbi.addParallelMng(makeRef(pm));
157 m_cloned_mesh = mm->meshFactoryMng()->createMesh(mbi);
158 m_cloned_mesh->modifier()->setDynamic(true);
159 m_cloned_mesh->setDimension(mesh()->dimension());
160 m_cloned_mesh->endAllocate();
161 }
162 else {
163 m_cloned_mesh = mesh_handle->mesh()->toPrimaryMesh();
164 m_cloned_mesh->modifier()->clearItems();
165 }
166}
167
168/*---------------------------------------------------------------------------*/
169/*---------------------------------------------------------------------------*/
170
171void MeshSectionService::
172_createCells(Int32& sd_nb_cell, UniqueArray<Int64>& cells_infos, Int32& sd_nb_face, UniqueArray<Int64>& faces_infos, std::unordered_map<Int64, Real3>& pos_node)
173{
174 VariableNodeReal3& node_coord = mesh()->nodesCoordinates();
175
176 VariableFaceBool is_added(VariableBuildInfo(mesh(), "IsAdded"));
177 is_added.fill(false);
178
179 ENUMERATE_ (Cell, icell, ownCells()) {
180 {
181 Real3 b{ 0 };
182 for (Node node : icell->nodes()) {
183 b += node_coord[node];
184 }
185 b /= icell->nbNode();
186
187 bool in_plan = true;
188 for (auto& [p0, normal] : m_plans) {
189 const Real dist = math::dot({ b - p0 }, normal);
190 if (dist < 0) {
191 in_plan = false;
192 break;
193 }
194 }
195
196 if (!in_plan)
197 continue;
198 }
199
200 Int16 cell_type = icell->itemTypeId();
201 cells_infos.add(cell_type);
202
203 Int64 cell_uid = icell->uniqueId().asInt64();
204 cells_infos.add(cell_uid);
205
206 for (Node node : icell->nodes()) {
207 Int64 node_uid = node.uniqueId().asInt64();
208 cells_infos.add(node_uid);
209 pos_node[node.uniqueId()] = node_coord[node];
210 }
211 ++sd_nb_cell;
212
213 for (Face face : icell->faces()) {
214 if (is_added[face]) continue;
215 is_added[face] = true;
216
217 Int16 face_type = face.itemTypeId();
218 faces_infos.add(face_type);
219
220 Int64 face_uid = face.uniqueId().asInt64();
221 faces_infos.add(face_uid);
222
223 for (Node node : face.nodes()) {
224 Int64 node_uid = node.uniqueId().asInt64();
225 faces_infos.add(node_uid);
226 pos_node[node.uniqueId()] = node_coord[node];
227 }
228 ++sd_nb_face;
229 }
230 }
231}
232
233/*---------------------------------------------------------------------------*/
234/*---------------------------------------------------------------------------*/
235
236void MeshSectionService::
237_compute()
238{
239 UniqueArray<Int64> cells_infos;
240 cells_infos.reserve(10000);
241
242 UniqueArray<Int64> faces_infos;
243 faces_infos.reserve(10000);
244
245 std::unordered_map<Int64, Real3> coord_map;
246
247 Int32 nb_cell = 0;
248 Int32 nb_face = 0;
249
250 _createCells(nb_cell, cells_infos, nb_face, faces_infos, coord_map);
251
252 m_cloned_mesh->modifier()->addFaces(nb_face, faces_infos);
253 m_cloned_mesh->modifier()->addCells(nb_cell, cells_infos);
254 m_cloned_mesh->modifier()->endUpdate();
255
256 {
257 VariableNodeReal3& node_coords(m_cloned_mesh->nodesCoordinates());
258 ENUMERATE_ (Node, inode, m_cloned_mesh->allNodes()) {
259 node_coords[inode] = coord_map[inode->uniqueId()];
260 }
261 }
262
263 info() << "New mesh -- NbNode : " << m_cloned_mesh->nbNode() << " -- NbCells : " << m_cloned_mesh->nbCell();
264}
265
266/*---------------------------------------------------------------------------*/
267/*---------------------------------------------------------------------------*/
268
269} // namespace Arcane
270
271/*---------------------------------------------------------------------------*/
272/*---------------------------------------------------------------------------*/
#define ENUMERATE_(type, name, group)
Generic enumerator for an entity group.
ArcaneMeshSectionObject(const Arcane::ServiceBuildInfo &sbi)
Constructeur.
CaseOptionsMeshSection * options() const
Options du jeu de données du service.
virtual MeshHandle * findMeshHandle(const String &name, bool throw_exception)=0
Searches for the mesh with name name.
virtual void clearItems()=0
Deletes all entities of all families in this mesh.
virtual IMeshModifier * modifier()=0
Associated modifier interface.
virtual IMeshMng * meshMng() const =0
Returns the mesh manager.
CellGroup ownCells() const
Returns the group containing all cells specific to this domain.
Handle on a mesh.
Definition MeshHandle.h:48
void addPlane(const Real3 &p0, const Real3 &normal) override
Method allowing to add a plane to the cut service. The use of these planes depends on the service.
void updateSection() override
Method allowing to update the mesh section with all planes.
MeshHandle meshSection() override
Méthod allowing to get the mesh section.
VariableCollection variables() override
Method allowing to get a set of variables copied on the new mesh.
void setVariables(VariableCollection variables) override
Method allowing to add a set of variables to copy on the new mesh.
void setServiceMeshUniqueId(Int32 unique_id) override
Method allowing to set a unique id allowing to create multiple section services for a mesh.
Class managing a 3-dimensional real vector.
eServiceType creationType() const
Type of service that can be created by this instance.
Structure containing the information to create a service.
TraceMessage info() const
Flow for an information message.
1D data vector with value semantics (STL style).
__host__ __device__ Real dot(Real2 u, Real2 v)
Dot product of u by v in .
Definition MathUtils.h:94
__host__ __device__ Real3 normalizeReal3(Real3 v)
Normalization of a Real3.
Definition MathUtils.h:778
MeshVariableScalarRefT< Face, Byte > VariableFaceBool
Quantity at the face of boolean type.
MeshVariableScalarRefT< Node, Real3 > VariableNodeReal3
Coordinate type quantity at node.
-- tab-width: 2; indent-tabs-mode: nil; coding: utf-8-with-signature --
std::int64_t Int64
Signed integer type of 64 bits.
eServiceType
Service type.
@ ST_CaseOption
The service is used at the dataset level.
std::int16_t Int16
Signed integer type of 16 bits.
double Real
Type representing a real number.
auto makeRef(InstanceType *t) -> Ref< InstanceType >
Creates a reference on a pointer.
@ Cell
The mesh is AMR by cell.
Definition MeshKind.h:53
std::int32_t Int32
Signed integer type of 32 bits.