14#include "arcane/utils/TraceAccessor.h"
15#include "arcane/utils/NotImplementedException.h"
16#include "arcane/utils/AutoDestroyUserData.h"
17#include "arcane/utils/IUserDataList.h"
18#include "arcane/utils/Ref.h"
19#include "arcane/utils/ScopedPtr.h"
20#include "arcane/utils/PlatformUtils.h"
23#include "arcane/core/IMesh.h"
24#include "arcane/core/ItemPrinter.h"
25#include "arcane/core/IItemFamily.h"
26#include "arcane/core/IParallelMng.h"
27#include "arcane/core/VariableTypes.h"
28#include "arcane/core/Properties.h"
29#include "arcane/core/IMeshModifier.h"
30#include "arcane/core/MeshStats.h"
31#include "arcane/core/ICartesianMeshGenerationInfo.h"
32#include "arcane/core/MeshEvents.h"
33#include "arcane/core/MeshKind.h"
34#include "arcane/core/internal/IMeshInternal.h"
36#include "arcane/cartesianmesh/internal/CartesianPatchGroup.h"
37#include "arcane/cartesianmesh/ICartesianMesh.h"
38#include "arcane/cartesianmesh/AMRZonePosition.h"
39#include "arcane/cartesianmesh/CartesianConnectivity.h"
40#include "arcane/cartesianmesh/CartesianMeshRenumberingInfo.h"
41#include "arcane/cartesianmesh/CartesianMeshCoarsening.h"
42#include "arcane/cartesianmesh/CartesianMeshCoarsening2.h"
43#include "arcane/cartesianmesh/CartesianMeshPatchListView.h"
44#include "arcane/cartesianmesh/internal/CartesianMeshPatch.h"
45#include "arcane/cartesianmesh/internal/ICartesianMeshInternal.h"
47#include "arcane/cartesianmesh/internal/CartesianMeshUniqueIdRenumbering.h"
48#include "arcane/cartesianmesh/v2/CartesianMeshUniqueIdRenumberingV2.h"
49#include "arcane/cartesianmesh/CartesianMeshNumberingMng.h"
51#include "arcane/cartesianmesh/internal/CartesianMeshAMRPatchMng.h"
52#include "arcane/core/IGhostLayerMng.h"
53#include "arcane/cartesianmesh/internal/CartesianMeshNumberingMngInternal.h"
77class CartesianMeshImpl
82 :
public ICartesianMeshInternal
86 explicit InternalApi(CartesianMeshImpl* cartesian_mesh)
87 : m_cartesian_mesh(cartesian_mesh)
95 return m_cartesian_mesh->_createCartesianMeshCoarsening2();
99 m_cartesian_mesh->_addPatchFromExistingChildren(parent_cells_local_id);
101 void initCartesianMeshAMRPatchMng()
override
103 if (m_numbering_mng.
isNull()) {
104 initCartesianMeshNumberingMngInternal();
107 m_amr_mng =
makeRef(
new CartesianMeshAMRPatchMng(m_cartesian_mesh, m_numbering_mng.
get()));
114 void initCartesianMeshNumberingMngInternal()
override
116 if (m_numbering_mng.
isNull()) {
117 m_numbering_mng =
makeRef(
new CartesianMeshNumberingMngInternal(m_cartesian_mesh->
mesh()));
122 return m_numbering_mng;
124 CartesianPatchGroup& cartesianPatchGroup()
override {
return m_cartesian_mesh->_cartesianPatchGroup(); }
128 CartesianMeshImpl* m_cartesian_mesh =
nullptr;
139 void build()
override;
149 return m_all_items_direction_info->cellDirection(dir);
154 return m_all_items_direction_info->cellDirection(idir);
159 return m_all_items_direction_info->faceDirection(dir);
164 return m_all_items_direction_info->faceDirection(idir);
169 return m_all_items_direction_info->nodeDirection(dir);
174 return m_all_items_direction_info->nodeDirection(idir);
183 return m_connectivity;
208 ICartesianMeshInternal*
_internalApi()
override {
return &m_internal_api; }
210 void computeDirectionsPatchV2(
Integer index)
override;
217 CartesianPatchGroup& _cartesianPatchGroup() {
return m_patch_group; }
218 void _computeDirectionsV2();
222 InternalApi m_internal_api;
225 Int32 m_local_face_direction[3] = { -1, -1, -1 };
226 IMesh* m_mesh =
nullptr;
227 Ref<CartesianMeshPatch> m_all_items_direction_info;
228 CartesianConnectivity m_connectivity;
229 UniqueArray<CartesianConnectivity::Index> m_nodes_to_cell_storage;
230 UniqueArray<CartesianConnectivity::Index> m_cells_to_node_storage;
231 UniqueArray<CartesianConnectivity::Permutation> m_permutation_storage;
232 bool m_is_amr =
false;
234 CartesianPatchGroup m_patch_group;
235 ScopedPtrT<Properties> m_properties;
237 EventObserverPool m_event_pool;
238 bool m_is_mesh_event_added =
false;
239 Int64 m_mesh_timestamp = 0;
244 void _computeMeshDirection(CartesianMeshPatch& cdi,
eMeshDirection dir,
249 void _computeMeshDirectionV2(CartesianMeshPatch& cdi,
eMeshDirection dir,
255 void _applyRefine(
const AMRZonePosition &position);
256 void _applyCoarse(
const AMRZonePosition& zone_position);
257 void _addPatch(ConstArrayView<Int32> parent_cells);
258 void _saveInfosInProperties();
260 std::tuple<CellGroup, NodeGroup>
262 void _checkNeedComputeDirections();
263 void _checkAddObservableMeshChanged();
270arcaneCreateCartesianMesh(
IMesh* mesh)
281CartesianMeshImpl(
IMesh* mesh)
283, m_internal_api(this)
289, m_amr_type(mesh->meshKind().meshAMRKind())
292 m_internal_api.initCartesianMeshNumberingMngInternal();
293 m_internal_api.initCartesianMeshAMRPatchMng();
295 m_all_items_direction_info = m_patch_group.groundPatch();
301void CartesianMeshImpl::
304 m_properties =
new Properties(*(
mesh()->properties()),
"CartesianMesh");
306 m_internal_api.cartesianMeshNumberingMngInternal()->build();
308 m_patch_group.build();
313const Int32 SERIALIZE_VERSION = 1;
319void CartesianMeshImpl::
320_checkNeedComputeDirections()
323 if (m_mesh_timestamp!=new_timestamp){
324 info() <<
"Mesh timestamp has changed (old=" << m_mesh_timestamp <<
" new=" << new_timestamp <<
")";
332void CartesianMeshImpl::
333_saveInfosInProperties()
336 m_properties->set(
"Version",SERIALIZE_VERSION);
338 m_patch_group.saveInfosInProperties();
341 m_internal_api.cartesianMeshNumberingMngInternal()->saveInfosInProperties();
352 info() <<
"Creating 'CartesianMesh' infos from dump";
355 m_internal_api.cartesianMeshNumberingMngInternal()->recreateFromDump();
356 m_internal_api.cartesianMeshNumberingMngInternal()->printStatus();
360 Int32 v = m_properties->getInt32(
"Version");
361 if (v!=SERIALIZE_VERSION)
362 ARCANE_FATAL(
"Bad serializer version: trying to read from incompatible checkpoint v={0} expected={1}",
363 v,SERIALIZE_VERSION);
365 m_patch_group.recreateFromDump();
367 m_all_items_direction_info = m_patch_group.groundPatch();
375void CartesianMeshImpl::
376_checkAddObservableMeshChanged()
378 if (m_is_mesh_event_added)
380 m_is_mesh_event_added =
true;
383 auto f1 = [&](
const MeshEventArgs&){ this->_checkNeedComputeDirections(); };
395 m_internal_api.cartesianMeshNumberingMngInternal()->renumberingFacesLevel0FromOriginalArcaneNumbering();
396 _computeDirectionsV2();
399 info() <<
"CartesianMesh: computeDirections()";
402 _checkAddObservableMeshChanged();
404 m_is_amr = m_mesh->isAmrActivated();
414 for( NodeLocalId inode : cell.
nodeIds() )
415 center += nodes_coord[inode];
417 cells_center[icell] = center;
422 for( NodeLocalId inode : face.
nodeIds() )
423 center += nodes_coord[inode];
425 faces_center[iface] = center;
430 Int32 next_face_x = -1;
431 Int32 next_face_y = -1;
432 Int32 next_face_z = -1;
435 Cell cell0 = cell_view[0];
438 Real3 cell_center = cells_center[cell0];
445 info(4) <<
"Cartesian mesh compute directions is_amr=" << m_is_amr;
447 for(
Integer i=0; i<nb_node; ++i ){
449 info(4) <<
"Node I=" << i <<
" node=" <<
ItemPrinter(node) <<
" pos=" << nodes_coord[node];
452 bool is_3d = m_mesh->dimension() == 3;
462 for (
Integer i = 0; i < nb_face; ++i) {
465 Real3 next_center = faces_center[f];
467 Real diff_x = next_center.
x - cell_center.
x;
468 Real diff_y = next_center.
y - cell_center.
y;
469 Real diff_z = next_center.
z - cell_center.
z;
471 info(4) <<
"NEXT_FACE=" <<
ItemPrinter(f) <<
" center=" << next_center <<
" diff=" <<
Real3(diff_x, diff_y, diff_z);
473 if (diff_x > max_x) {
478 if (diff_y > max_y) {
483 if (diff_z > max_z) {
488 info(4) <<
"Advance in direction X -> " << next_face_x;
489 info(4) <<
"Advance in direction Y -> " << next_face_y;
490 info(4) <<
"Advance in direction Z -> " << next_face_z;
496 for (
Integer i = 0; i < nb_face; ++i) {
499 Real3 next_center = faces_center[f];
501 Real diff_x = next_center.
x - cell_center.
x;
502 Real diff_y = next_center.
y - cell_center.
y;
504 info(4) <<
"NEXT_FACE=" <<
ItemPrinter(f) <<
" center=" << next_center <<
" diff=" <<
Real2(diff_x, diff_y);
506 if (diff_x > max_x) {
511 if (diff_y > max_y) {
516 info(4) <<
"Advance in direction X -> " << next_face_x;
517 info(4) <<
"Advance in direction Y -> " << next_face_y;
519 m_all_items_direction_info->_internalComputeNodeCellInformations(cell0,cells_center[cell0],nodes_coord);
521 info() <<
"Informations from IMesh properties:";
523 auto* cmgi = ICartesianMeshGenerationInfo::getReference(m_mesh,
true);
525 info() <<
"GlobalNbCell = " << cmgi->globalNbCells();
526 info() <<
"OwnNbCell: " << cmgi->ownNbCells();
527 info() <<
"SubDomainOffset: " << cmgi->subDomainOffsets();
528 info() <<
"OwnCellOffset: " << cmgi->ownCellOffsets();
533 auto x = _buildPatchGroups(
mesh()->allLevelCells(0),0);
534 all_cells = std::get<0>(x);
535 all_nodes = std::get<1>(x);
538 if (next_face_x!=(-1)){
539 m_local_face_direction[
MD_DirX] = next_face_x;
540 _computeMeshDirection(*m_all_items_direction_info.get(),
MD_DirX, cells_center, faces_center, all_cells, all_nodes);
542 if (next_face_y!=(-1)){
543 m_local_face_direction[
MD_DirY] = next_face_y;
544 _computeMeshDirection(*m_all_items_direction_info.get(),
MD_DirY, cells_center, faces_center, all_cells, all_nodes);
546 if (next_face_z != (-1)) {
547 m_local_face_direction[
MD_DirZ] = next_face_z;
548 _computeMeshDirection(*m_all_items_direction_info.get(),
MD_DirZ, cells_center, faces_center, all_cells, all_nodes);
552 for(
Integer idir=0, nb_dir=
mesh()->dimension(); idir<nb_dir; ++idir ){
554 cdm._internalSetOffsetAndNbCellInfos(cmgi->globalNbCells()[idir], cmgi->ownNbCells()[idir],
555 cmgi->subDomainOffsets()[idir], cmgi->ownCellOffsets()[idir]);
558 info() <<
"Compute cartesian connectivity";
560 m_permutation_storage.resize(1);
561 m_permutation_storage[0].compute();
562 m_nodes_to_cell_storage.resize(
mesh()->nodeFamily()->maxLocalId());
563 m_cells_to_node_storage.resize(
mesh()->cellFamily()->maxLocalId());
564 m_connectivity._setStorage(m_nodes_to_cell_storage,m_cells_to_node_storage,&m_permutation_storage[0]);
565 m_connectivity._computeInfos(
mesh(),nodes_coord,cells_center);
569 for (
Integer patch_index = 1; patch_index < m_patch_group.nbPatch(); ++patch_index) {
570 CellGroup cells = m_patch_group.allCells(patch_index);
572 info() <<
"AMR Patch name=" << cells.
name() <<
" size=" << cells.
size() <<
" index=" << patch_index <<
" nbPatch=" << m_patch_group.nbPatch();
573 patch->_internalComputeNodeCellInformations(cell0, cells_center[cell0], nodes_coord);
574 auto [patch_cells, patch_nodes] = _buildPatchGroups(cells, patch_index);
575 _computeMeshDirection(*
patch.get(),
MD_DirX, cells_center, faces_center, patch_cells, patch_nodes);
576 _computeMeshDirection(*
patch.get(),
MD_DirY, cells_center, faces_center, patch_cells, patch_nodes);
578 _computeMeshDirection(*
patch.get(),
MD_DirZ, cells_center, faces_center, patch_cells, patch_nodes);
584 _saveInfosInProperties();
590std::tuple<CellGroup,NodeGroup> CartesianMeshImpl::
603 String cell_group_name =
String(
"AMRPatchCells") + patch_level;
608 String node_group_name =
String(
"AMRPatchNodes") + patch_level;
612 info(4) <<
"PATCH_CELLS name=" << patch_cells.
name() <<
" size=" << patch_cells.
size();
613 info(4) <<
"PATCH_NODES name=" << patch_nodes.
name() <<
" size=" << patch_nodes.
size();
614 return { patch_cells, patch_nodes };
620void CartesianMeshImpl::
624 IItemFamily* cell_family = m_mesh->cellFamily();
625 IItemFamily* face_family = m_mesh->faceFamily();
626 IItemFamily* node_family = m_mesh->nodeFamily();
629 Int32 max_face_id = face_family->maxLocalId();
630 Int32 max_node_id = node_family->maxLocalId();
632 CellDirectionMng& cell_dm = cdi.cellDirection(dir);
633 cell_dm._internalResizeInfos(max_cell_id);
635 FaceDirectionMng& face_dm = cdi.faceDirection(dir);
636 face_dm._internalResizeInfos(max_face_id);
638 NodeDirectionMng& node_dm = cdi.nodeDirection(dir);
639 node_dm._internalResizeInfos(max_node_id);
642 info(4) <<
"COMPUTE DIRECTION dir=" << dir;
644 Int32 prev_local_face = -1;
645 Int32 next_local_face = m_local_face_direction[dir];
646 Integer mesh_dim = m_mesh->dimension();
649 prev_local_face = (next_local_face + 2) % 4;
650 else if (mesh_dim==3)
651 prev_local_face = (next_local_face + 3) % 6;
653 cell_dm._internalSetLocalFaceIndex(next_local_face,prev_local_face);
657 std::set<Int32> cells_set;
659 cells_set.insert(icell.itemLocalId());
666 Int32 my_level = cell.level();
667 Face next_face = cell.face(next_local_face);
668 Cell next_cell = next_face.backCell()==cell ? next_face.frontCell() : next_face.backCell();
669 if (cells_set.find(next_cell.localId()) == cells_set.end())
671 else if (next_cell.level() != my_level)
674 Face prev_face = cell.face(prev_local_face);
675 Cell prev_cell = prev_face.backCell()==cell ? prev_face.frontCell() : prev_face.backCell();
676 if (cells_set.find(prev_cell.localId()) == cells_set.end())
678 else if (prev_cell.level() != my_level)
680 cell_dm.m_infos_view[icell.itemLocalId()] = CellDirectionMng::ItemDirectionInfo(next_cell, prev_cell);
682 cell_dm._internalComputeInnerAndOuterItems(all_cells);
683 face_dm._internalComputeInfos(cell_dm,cells_center,faces_center);
684 node_dm._internalComputeInfos(cell_dm,all_nodes,cells_center);
690void CartesianMeshImpl::
691_computeDirectionsV2()
693 info() <<
"CartesianMesh: computeDirectionsV2()";
696 _checkAddObservableMeshChanged();
698 m_is_amr = m_mesh->isAmrActivated();
700 if (m_mesh->dimension() == 3) {
701 m_local_face_direction[
MD_DirX] = 4;
702 m_local_face_direction[
MD_DirY] = 5;
703 m_local_face_direction[
MD_DirZ] = 3;
706 m_local_face_direction[
MD_DirX] = 1;
707 m_local_face_direction[
MD_DirY] = 2;
710 info() <<
"Compute cartesian connectivity";
712 m_permutation_storage.resize(1);
713 m_permutation_storage[0].compute();
714 m_nodes_to_cell_storage.resize(
mesh()->nodeFamily()->maxLocalId());
715 m_cells_to_node_storage.resize(
mesh()->cellFamily()->maxLocalId());
716 m_connectivity._setStorage(m_nodes_to_cell_storage, m_cells_to_node_storage, &m_permutation_storage[0]);
717 m_connectivity._computeInfos(
this);
720 for (
Integer patch_index = 0; patch_index < m_patch_group.nbPatch(); ++patch_index) {
721 computeDirectionsPatchV2(patch_index);
727 _saveInfosInProperties();
733void CartesianMeshImpl::
734computeDirectionsPatchV2(
Integer patch_index)
736 bool is_3d = m_mesh->dimension() == 3;
738 CellGroup cells = m_patch_group.allCells(patch_index);
739 Ref<CartesianMeshPatch>
patch = m_patch_group.patch(patch_index);
741 if (
patch->index() == -1) {
742 auto* cmgi = ICartesianMeshGenerationInfo::getReference(m_mesh,
true);
743 info() <<
"Informations from IMesh properties:";
744 info() <<
"GlobalNbCell = " << cmgi->globalNbCells();
745 info() <<
"OwnNbCell: " << cmgi->ownNbCells();
746 info() <<
"SubDomainOffset: " << cmgi->subDomainOffsets();
747 info() <<
"OwnCellOffset: " << cmgi->ownCellOffsets();
749 for (
Integer idir = 0, nb_dir =
mesh()->dimension(); idir < nb_dir; ++idir) {
750 CellDirectionMng& cdm = m_all_items_direction_info->cellDirection(idir);
751 cdm._internalSetOffsetAndNbCellInfos(cmgi->globalNbCells()[idir], cmgi->ownNbCells()[idir],
752 cmgi->subDomainOffsets()[idir], cmgi->ownCellOffsets()[idir]);
756 info() <<
"AMR Patch name=" << cells.name() <<
" size=" << cells.size() <<
" index=" << patch_index <<
" trueindex=" <<
patch->index() <<
" nbPatch=" << m_patch_group.nbPatch();
758 const AMRPatchPosition position =
patch->position();
759 info() <<
" position min=" << position.minPoint() <<
" max=" << position.maxPoint() <<
" level=" << position.level() <<
" overlapLayerSize=" << position.overlapLayerSize();
761 patch->_internalComputeNodeCellInformations();
762 auto [patch_cells, patch_nodes] = _buildPatchGroups(cells, patch_index);
763 _computeMeshDirectionV2(*
patch.get(),
MD_DirX, m_patch_group.allCells(patch_index), m_patch_group.inPatchCells(patch_index), m_patch_group.overlapCells(patch_index), patch_nodes);
764 _computeMeshDirectionV2(*
patch.get(),
MD_DirY, m_patch_group.allCells(patch_index), m_patch_group.inPatchCells(patch_index), m_patch_group.overlapCells(patch_index), patch_nodes);
766 _computeMeshDirectionV2(*
patch.get(),
MD_DirZ, m_patch_group.allCells(patch_index), m_patch_group.inPatchCells(patch_index), m_patch_group.overlapCells(patch_index), patch_nodes);
772void CartesianMeshImpl::
775 IItemFamily* cell_family = m_mesh->cellFamily();
776 IItemFamily* face_family = m_mesh->faceFamily();
777 IItemFamily* node_family = m_mesh->nodeFamily();
779 Int32 max_cell_id = cell_family->maxLocalId();
780 Int32 max_face_id = face_family->maxLocalId();
781 Int32 max_node_id = node_family->maxLocalId();
783 CellDirectionMng& cell_dm = cdi.cellDirection(dir);
784 cell_dm._internalResizeInfos(max_cell_id);
786 FaceDirectionMng& face_dm = cdi.faceDirection(dir);
787 face_dm._internalResizeInfos(max_face_id);
789 NodeDirectionMng& node_dm = cdi.nodeDirection(dir);
790 node_dm._internalResizeInfos(max_node_id);
793 info(4) <<
"COMPUTE DIRECTION dir=" << dir;
795 Int32 prev_local_face = -1;
796 Int32 next_local_face = m_local_face_direction[dir];
797 Integer mesh_dim = m_mesh->dimension();
800 prev_local_face = (next_local_face + 2) % 4;
801 else if (mesh_dim == 3)
802 prev_local_face = (next_local_face + 3) % 6;
804 cell_dm._internalSetLocalFaceIndex(next_local_face, prev_local_face);
808 std::set<Int32> cells_set;
810 cells_set.insert(icell.itemLocalId());
817 Int32 my_level = cell.level();
818 Face next_face = cell.face(next_local_face);
819 Cell next_cell = next_face.backCell() == cell ? next_face.frontCell() : next_face.backCell();
820 if (!cells_set.contains(next_cell.localId()) || next_cell.level() != my_level) {
824 Face prev_face = cell.face(prev_local_face);
825 Cell prev_cell = prev_face.backCell() == cell ? prev_face.frontCell() : prev_face.backCell();
826 if (!cells_set.contains(prev_cell.localId()) || prev_cell.level() != my_level) {
830 cell_dm.m_infos_view[icell.itemLocalId()] = CellDirectionMng::ItemDirectionInfo(next_cell, prev_cell);
832 cell_dm._internalComputeCellGroups(all_cells, in_patch_cells, overlap_cells);
833 face_dm._internalComputeInfos(cell_dm);
834 node_dm._internalComputeInfos(cell_dm, all_nodes);
843 info() <<
"REFINEMENT 2D position=" << position <<
" length=" << length;
853 info() <<
"REFINEMENT 3D position=" << position <<
" length=" << length;
863 _applyRefine(position);
864 _saveInfosInProperties();
873 info() <<
"COARSEN 2D position=" << position <<
" length=" << length;
883 info() <<
"COARSEN 3D position=" << position <<
" length=" << length;
893 _applyCoarse(position);
894 _saveInfosInProperties();
904 ARCANE_FATAL(
"You cannot reduce number of ghost layer of level 0 with this method");
908 const Int32 max_nb_layer = 128;
912 level_max = std::max(level_max, icell->level());
920 Integer level_0_nb_ghost_layer = m_mesh->ghostLayerMng()->nbGhostLayer();
923 if (level_0_nb_ghost_layer == 0) {
932 if (target_nb_ghost_layers % 2 != 0) {
933 target_nb_ghost_layers++;
936 if (target_nb_ghost_layers == nb_ghost_layer) {
937 return nb_ghost_layer;
942 Integer parent_level = level - 1;
943 Integer parent_target_nb_ghost_layer = target_nb_ghost_layers / 2;
949 std::function<void(
Cell)> children_list;
951 children_list = [&cell_lid2, &children_list](
Cell cell) ->
void {
952 for (
Integer i = 0; i < cell.nbHChildren(); ++i) {
954 cell_lid2[cell.level()].
add(cell.hChild(i).localId());
955 children_list(cell.hChild(i));
968 Cell front_cell = iface->frontCell();
969 Cell back_cell = iface->backCell();
971 ((front_cell.
null() || (!front_cell.
isOwn() && front_cell.
level() == parent_level)) && ((!back_cell.
null()) && (back_cell.
isOwn() && back_cell.
level() == parent_level))) ||
972 ((back_cell.
null() || (!back_cell.
isOwn() && back_cell.
level() == parent_level)) && ((!front_cell.
null()) && (front_cell.
isOwn() && front_cell.
level() == parent_level)))) {
973 for (
Node node : iface->nodes()) {
974 level_node[node] = 0;
980 bool is_modif =
true;
981 Int32 current_layer = 0;
986 if (icell->isOwn() || icell->level() != parent_level || level_cell[icell] != -1) {
990 Int32 min = max_nb_layer;
993 for (
Node node : icell->nodes()) {
994 Int32 nlevel = level_node[node];
996 min = std::min(min, nlevel);
997 max = std::max(max, nlevel);
1002 if (min != current_layer) {
1007 if (min == max_nb_layer && max == -1) {
1011 Integer new_level = ((min == max) ? min + 1 : max);
1013 for (
Node node : icell->nodes()) {
1014 Int32 nlevel = level_node[node];
1016 level_node[node] = new_level;
1022 level_cell[icell] = min;
1027 if (min >= parent_target_nb_ghost_layer) {
1028 children_list(*icell);
1032 if (current_layer >= max_nb_layer) {
1033 ARCANE_FATAL(
"Error in ghost layer counter algo. Report it plz.");
1038 for (
Integer i = level_max - 1; i >= 0; --i) {
1045 m_mesh->modifier()->flagCellToCoarsen(cell_lid2[i]);
1046 m_mesh->modifier()->coarsenItemsV2(
false);
1049 info() <<
"Nb ghost layer for level " << level <<
" : " << target_nb_ghost_layers;
1051 return target_nb_ghost_layers;
1057void CartesianMeshImpl::
1060 _addPatch(parent_cells_local_id);
1068void CartesianMeshImpl::
1069_addPatch(ConstArrayView<Int32> parent_cells)
1074 UniqueArray<Int32> children_local_id;
1075 CellInfoListView cells(m_mesh->
cellFamily());
1076 for (Int32 cell_local_id : parent_cells) {
1077 Cell c = cells[cell_local_id];
1078 for (
Integer k = 0; k < c.nbHChildren(); ++k) {
1079 Cell child = c.hChild(k);
1080 children_local_id.add(child.localId());
1084 m_patch_group.addPatch(children_local_id);
1090void CartesianMeshImpl::
1094 UniqueArray<Int32> cells_local_id;
1095 position.cellsInPatch(
mesh(), cells_local_id);
1097 Integer nb_cell = cells_local_id.size();
1098 info(4) <<
"Local_NbCellToRefine = " << nb_cell;
1100 IParallelMng* pm = m_mesh->parallelMng();
1102 info(4) <<
"Global_NbCellToRefine = " << total_nb_cell;
1103 if (total_nb_cell == 0)
1106 debug() <<
"Refine with modifier() (for all mesh types)";
1107 m_mesh->modifier()->flagCellToRefine(cells_local_id);
1108 m_mesh->modifier()->adapt();
1110 _addPatch(cells_local_id);
1114 debug() <<
"Refine with specific refiner (for cartesian mesh only)";
1115 m_patch_group.addPatch(position);
1119 ARCANE_FATAL(
"General patch AMR is not implemented. Please use PatchCartesianMeshOnly (3)");
1126 MeshStats ms(
traceMng(),m_mesh,m_mesh->parallelMng());
1134void CartesianMeshImpl::
1138 UniqueArray<Int32> cells_local_id;
1140 zone_position.cellsInPatch(
mesh(), cells_local_id);
1142 Integer nb_cell = cells_local_id.size();
1143 info(4) <<
"Local_NbCellToCoarsen = " << nb_cell;
1145 IParallelMng* pm = m_mesh->parallelMng();
1147 info(4) <<
"Global_NbCellToCoarsen = " << total_nb_cell;
1148 if (total_nb_cell == 0)
1151 debug() <<
"Coarse with modifier() (for all mesh types)";
1152 m_patch_group.removeCellsInAllPatches(cells_local_id);
1153 m_patch_group.applyPatchEdit(
true,
false);
1155 m_mesh->modifier()->flagCellToCoarsen(cells_local_id);
1156 m_mesh->modifier()->coarsenItemsV2(
true);
1160 debug() <<
"Coarsen with specific coarser (for cartesian mesh only)";
1161 m_patch_group.removeCellsInZone(zone_position);
1165 ARCANE_FATAL(
"General patch AMR is not implemented. Please use PatchCartesianMeshOnly (3)");
1172 MeshStats ms(
traceMng(), m_mesh, m_mesh->parallelMng());
1183 info(4) <<
"Check valid CartesianMesh";
1185 for(
Integer i=0; i<nb_patch; ++i ){
1197 auto* cmgi = ICartesianMeshGenerationInfo::getReference(m_mesh,
true);
1200 Int32 face_method = v.renumberFaceMethod();
1201 if (face_method!=0 && face_method!=1)
1202 ARCANE_FATAL(
"Invalid value '{0}' for renumberFaceMethod(). Valid values are 0 or 1",
1208 Int32 patch_method = v.renumberPatchMethod();
1209 if (patch_method < 0 || patch_method > 4) {
1210 ARCANE_FATAL(
"Invalid value '{0}' for renumberPatchMethod(). Valid values are 0, 1, 2, 3 or 4",
1214 ARCANE_FATAL(
"Mesh items renumbering is not compatible with this type of AMR");
1217 if (patch_method == 1 || patch_method == 3 || patch_method == 4) {
1218 CartesianMeshUniqueIdRenumbering renumberer(
this, cmgi, v.parentPatch(), patch_method);
1219 renumberer.renumber();
1221 else if (patch_method == 2) {
1222 warning() <<
"The patch method 2 is experimental!";
1223 CartesianMeshUniqueIdRenumberingV2 renumberer(
this, cmgi);
1224 renumberer.renumber();
1228 if (v.isSortAfterRenumbering()){
1229 info() <<
"Compacting and Sorting after renumbering";
1230 m_mesh->nodeFamily()->compactItems(
true);
1231 m_mesh->faceFamily()->compactItems(
true);
1232 m_mesh->cellFamily()->compactItems(
true);
1250_createCartesianMeshCoarsening2()
1266 const char* name =
"CartesianMesh";
1275 ARCANE_FATAL(
"The mesh {0} is not yet created",h.meshName());
1282 mesh->_internalApi()->setMeshKind(mk);
1289 return adud->data();
#define ARCANE_THROW(exception_class,...)
Macro pour envoyer une exception avec formattage.
#define ARCANE_FATAL(...)
Macro envoyant une exception FatalErrorException.
Fichier contenant les mécanismes de gestion des évènements.
Classe permettant de définir une zone d'un maillage.
Integer size() const
Nombre d'éléments du vecteur.
void add(ConstReferenceType val)
Ajoute l'élément val à la fin du tableau.
UserData s'auto-détruisant une fois détaché.
Informations de connectivité d'un maillage cartésien.
Déraffine un maillage cartésien par 2.
Déraffine un maillage cartésien par 2.
Infos spécifiques à un maillage cartésien.
void refinePatch3D(Real3 position, Real3 length) override
Raffine en 3D un bloc du maillage cartésien.
Int32 nbPatch() const override
Nombre de patchs du maillage.
Integer reduceNbGhostLayers(Integer level, Integer target_nb_ghost_layers) override
Méthode permettant de supprimer une ou plusieurs couches de mailles fantômes sur un niveau de raffine...
void refinePatch(const AMRZonePosition &position) override
Raffine un bloc du maillage cartésien.
ITraceMng * traceMng() const override
Gestionnaire de trace associé.
CellDirectionMng cellDirection(Integer idir) override
Liste des mailles dans la direction dir (0, 1 ou 2)
void recreateFromDump() override
Recalcule les informations de cartésiennes après une reprise.
void computeDirections() override
Calcule les infos pour les accès par direction.
FaceDirectionMng faceDirection(Integer idir) override
Liste des faces dans la direction dir (0, 1 ou 2)
void coarseZone(const AMRZonePosition &position) override
Dé-raffine un bloc du maillage cartésien.
NodeDirectionMng nodeDirection(Integer idir) override
Liste des noeuds dans la direction dir (0, 1 ou 2)
void checkValid() const override
Effectue des vérifications sur la validité de l'instance.
IMesh * mesh() const override
Maillage associé à ce maillage cartésien.
FaceDirectionMng faceDirection(eMeshDirection dir) override
Liste des faces dans la direction dir.
NodeDirectionMng nodeDirection(eMeshDirection dir) override
Liste des noeuds dans la direction dir.
void refinePatch2D(Real2 position, Real2 length) override
Raffine en 2D un bloc du maillage cartésien.
ICartesianMeshPatch * patch(Int32 index) const override
Retourne le index-ième patch du maillage.
void coarseZone2D(Real2 position, Real2 length) override
Dé-raffine en 2D un bloc du maillage cartésien.
void renumberItemsUniqueId(const CartesianMeshRenumberingInfo &v) override
Renumérote les uniqueId() des entités.
ICartesianMeshInternal * _internalApi() override
API interne à Arcane.
void coarseZone3D(Real3 position, Real3 length) override
Dé-raffine en 3D un bloc du maillage cartésien.
Ref< CartesianMeshCoarsening > createCartesianMeshCoarsening() override
Créé une instance pour gérer le déraffinement du maillage.
CartesianPatch amrPatch(Int32 index) const override
Retourne le index-ième patch du maillage.
CellDirectionMng cellDirection(eMeshDirection dir) override
Liste des mailles dans la direction dir.
CartesianMeshPatchListView patches() const override
Vue sur la liste des patchs.
CartesianConnectivity connectivity() override
Informations sur la connectivité
Vue sur une liste de patchs.
Informations pour la renumérotation.
Patch AMR d'un maillage cartésien.
Infos sur les mailles d'une direction spécifique X,Y ou Z d'un maillage structuré.
Vue sur les informations des mailles.
Face face(Int32 i) const
i-ème face de la maille
Int32 nbFace() const
Nombre de faces de la maille.
Vue constante d'un tableau de type T.
Infos sur les face d'une direction spécifique X,Y ou Z d'un maillage structuré.
Interface d'un patch AMR d'un maillage cartésien.
virtual void checkValid() const =0
Effectue des vérifications sur la validité de l'instance.
Interface d'un maillage cartésien.
static ICartesianMesh * getReference(const MeshHandleOrMesh &mesh, bool create=true)
Récupère ou créé la référence associée à mesh.
virtual IMesh * mesh() const =0
Maillage associé à ce maillage cartésien.
Interface d'une famille d'entités.
virtual ItemGroup allItems() const =0
Groupe de toutes les entités.
virtual ItemGroup createGroup(const String &name, Int32ConstArrayView local_ids, bool do_override=false)=0
Créé un groupe d'entités de nom name contenant les entités local_ids.
virtual Int32 maxLocalId() const =0
virtual IItemFamily * cellFamily()=0
Retourne la famille des mailles.
virtual Int64 timestamp()=0
Compteur indiquant le temps de dernière modification du maillage.
virtual EventObservable< const MeshEventArgs & > & eventObservable(eMeshEventType type)=0
Observable pour un évènement.
Interface du gestionnaire de traces.
Interface d'une liste qui gère des données utilisateurs.
virtual void setData(const String &name, IUserData *ud)=0
Positionne le user-data associé au nom name.
virtual IUserData * data(const String &name, bool allow_null=false) const =0
Donnée associée à name.
Interface pour une donnée utilisateur attachée à un autre objet.
Classe de base d'une vue sur une connectivité non structurée.
NodeGroup nodeGroup() const
Groupe des noeuds des éléments de ce groupe.
const String & name() const
Nom du groupe.
ItemVectorView view() const
Vue sur les entités du groupe.
Integer size() const
Nombre d'éléments du groupe.
IItemFamily * itemFamily() const
Famille d'entité à laquelle appartient ce groupe (0 pour le group nul)
void setItems(Int32ConstArrayView items_local_id)
Positionne les entités du groupe.
Classe utilitaire pour imprimer les infos sur une entité.
Int32ConstArrayView localIds() const
Tableau des numéros locaux des entités.
Node node(Int32 i) const
i-ème noeud de l'entité
Int32 nbNode() const
Nombre de noeuds de l'entité
NodeLocalIdView nodeIds() const
Liste des noeuds de l'entité
constexpr bool null() const
true si l'entité est nul (i.e. non connecté au maillage)
constexpr bool isOwn() const
true si l'entité est appartient au sous-domaine
Arguments des évènements sur le maillage.
Classe de compatibilité pour contenir un MeshHandle ou un IMesh*.
const MeshHandle & handle() const
handle associé.
IMesh * meshOrNull() const
Retourne le maillage associé à cette instance.
IUserDataList * meshUserDataList() const
Données utilisateurs associées.
Caractéristiques d'un maillage.
Infos sur les noeuds d'une direction spécifique X,Y ou Z d'un maillage structuré.
Classe gérant un vecteur de réel de dimension 2.
Classe gérant un vecteur de réel de dimension 3.
Référence à une instance.
Chaîne de caractères unicode.
Classe d'accès aux traces.
TraceAccessor(ITraceMng *m)
Construit un accesseur via le gestionnaire de trace m.
TraceMessageDbg debug(Trace::eDebugLevel=Trace::Medium) const
Flot pour un message de debug.
TraceMessage info() const
Flot pour un message d'information.
TraceMessage warning() const
Flot pour un message d'avertissement.
ITraceMng * traceMng() const
Gestionnaire de trace.
Vecteur 1D de données avec sémantique par valeur (style STL).
Paramètres nécessaires à la construction d'une variable.
bool isNull() const
Indique si le compteur référence une instance non nulle.
InstanceType * get() const
Instance associée ou nullptr si aucune.
ItemGroupT< Cell > CellGroup
Groupe de mailles.
ItemVectorViewT< Cell > CellVectorView
Vue sur un vecteur de mailles.
ItemGroupT< Node > NodeGroup
Groupe de noeuds.
MeshVariableScalarRefT< Cell, Real3 > VariableCellReal3
Grandeur au centre des mailles de type coordonnées.
MeshVariableScalarRefT< Node, Real3 > VariableNodeReal3
Grandeur au noeud de type coordonnées.
MeshVariableScalarRefT< Node, Int32 > VariableNodeInt32
Grandeur au noeud de type entier 32 bits.
MeshVariableScalarRefT< Face, Real3 > VariableFaceReal3
Grandeur aux faces de type coordonnées.
MeshVariableScalarRefT< Cell, Int32 > VariableCellInt32
Grandeur au centre des mailles de type entier 32 bits.
Int32 toInt32(Real r)
Converti un Real en Int32.
@ ReduceSum
Somme des valeurs.
@ ReduceMax
Maximum des valeurs.
-*- tab-width: 2; indent-tabs-mode: nil; coding: utf-8-with-signature -*-
bool arcaneIsCheck()
Vrai si on est en mode vérification.
std::int64_t Int64
Type entier signé sur 64 bits.
Int32 Integer
Type représentant un entier.
ConstArrayView< Int32 > Int32ConstArrayView
Equivalent C d'un tableau à une dimension d'entiers 32 bits.
@ Cartesian
Maillage cartésien.
eMeshDirection
Type de la direction pour un maillage structuré
@ EndPrepareDump
Evènement envoyé à la fin de prepareForDump()
double Real
Type représentant un réel.
auto makeRef(InstanceType *t) -> Ref< InstanceType >
Créé une référence sur un pointeur.
eMeshAMRKind
Type de maillage AMR.
@ Patch
Le maillage est AMR par patch.
@ Cell
Le maillage est AMR par maille.
@ PatchCartesianMeshOnly
Le maillage est AMR par patch cartésien (rectangulaire)
std::int32_t Int32
Type entier signé sur 32 bits.
Real y
deuxième composante du triplet
Real z
troisième composante du triplet
Real x
première composante du triplet