|
1 | 1 | #ifndef PUMIPIC_ADJACENCY_NEW_HPP
|
2 | 2 | #define PUMIPIC_ADJACENCY_NEW_HPP
|
3 |
| - |
| 3 | +#include <Omega_h_array.hpp> |
| 4 | +#include <Omega_h_defines.hpp> |
4 | 5 | #include <Omega_h_macros.h>
|
5 | 6 | #include <iostream>
|
6 | 7 | #include "Omega_h_for.hpp"
|
@@ -423,16 +424,55 @@ namespace pumipic {
|
423 | 424 | printf("Min area is: %.15f, Planned tol is %.15f\n", min_area, tol);
|
424 | 425 | return tol;
|
425 | 426 | }
|
426 |
| - |
427 |
| - template <class ParticleType, typename Segment3d, typename SegmentInt> |
428 |
| - bool search_mesh(o::Mesh& mesh, ParticleStructure<ParticleType>* ptcls, |
| 427 | + |
| 428 | + /** |
| 429 | + * @brief Particle tracing through mesh |
| 430 | + * |
| 431 | + * Starting at the initial position, the particles are traced through the mesh (both 2D and 3D) |
| 432 | + * until they are all marked "done" by the particle handler "func" at element boundary or destination. |
| 433 | + * It gives back the parent element ids for the new positions of the particles, |
| 434 | + * the exit face ids for the particles that leave the domain, and the last intersection point for |
| 435 | + * the particles. |
| 436 | + * |
| 437 | + * Note: Particle trajectories are considered as rays (not line segments). |
| 438 | + * |
| 439 | + * |
| 440 | + * @tparam ParticleType Particle type |
| 441 | + * @tparam Segment3d Segment type for particle position |
| 442 | + * @tparam SegmentInt Segment type for particle ids |
| 443 | + * @tparam Func Callable type object |
| 444 | + * @param mesh Omega_h mesh to search on |
| 445 | + * @param ptcls Particle structure |
| 446 | + * @param x_ps_orig Particle starting position |
| 447 | + * @param x_ps_tgt Particle target position |
| 448 | + * @param pids Particle ids |
| 449 | + * @param elem_ids Paricle parent element ids |
| 450 | + * @param requireIntersection True if intersection is required |
| 451 | + * @param inter_faces Exit faces for particles at domain boundary |
| 452 | + * @param inter_points Stores intersection points for particles at each face |
| 453 | + * @param looplimit Maximum number of iterations |
| 454 | + * @param debug True if debug information is printed |
| 455 | + * @param func Callable object to handle particles at element sides or destination |
| 456 | + * @return True if all particles are found at destination or left domain |
| 457 | + */ |
| 458 | + template <class ParticleType, typename Segment3d, typename SegmentInt, typename Func> |
| 459 | + bool trace_particle_through_mesh(o::Mesh& mesh, ParticleStructure<ParticleType>* ptcls, |
429 | 460 | Segment3d x_ps_orig, Segment3d x_ps_tgt, SegmentInt pids,
|
430 | 461 | o::Write<o::LO>& elem_ids,
|
431 | 462 | bool requireIntersection,
|
432 | 463 | o::Write<o::LO>& inter_faces,
|
433 | 464 | o::Write<o::Real>& inter_points,
|
434 | 465 | int looplimit,
|
435 |
| - int debug) { |
| 466 | + bool debug, |
| 467 | + Func& func) { |
| 468 | + static_assert( |
| 469 | + std::is_invocable_r_v< |
| 470 | + void, Func, o::Mesh &, ParticleStructure<ParticleType> *, |
| 471 | + o::Write<o::LO> &, o::Write<o::LO> &, o::Write<o::LO> &, |
| 472 | + o::Write<o::Real> &, o::Write<o::LO> &, |
| 473 | + Segment3d, Segment3d>, |
| 474 | + "Functional must accept <mesh> <ps> <elem_ids> <inter_faces> <lastExit> <inter_points> <ptcl_done> <x_ps_orig> <x_ps_tgt>\n"); |
| 475 | + |
436 | 476 | //Initialize timer
|
437 | 477 | const auto btime = pumipic_prebarrier();
|
438 | 478 | Kokkos::Profiling::pushRegion("pumipic_search_mesh");
|
@@ -517,10 +557,9 @@ namespace pumipic {
|
517 | 557 | //Find intersection face
|
518 | 558 | find_exit_face(mesh, ptcls, x_ps_orig, x_ps_tgt, elem_ids, ptcl_done, elmArea, useBcc, lastExit, inter_points, tol);
|
519 | 559 | //Check if intersection face is exposed
|
520 |
| - check_model_intersection(mesh, ptcls, x_ps_orig, x_ps_tgt, elem_ids, ptcl_done, lastExit, side_is_exposed, |
521 |
| - requireIntersection, inter_faces); |
| 560 | + func(mesh, ptcls, elem_ids, inter_faces, lastExit, inter_points, ptcl_done, x_ps_orig, x_ps_tgt); |
522 | 561 |
|
523 |
| - //Move to next element |
| 562 | + // Move to next element |
524 | 563 | set_new_element(mesh, ptcls, elem_ids, ptcl_done, lastExit);
|
525 | 564 |
|
526 | 565 | //Check if all particles are found
|
@@ -572,5 +611,44 @@ namespace pumipic {
|
572 | 611 | Kokkos::Profiling::popRegion();
|
573 | 612 | return found;
|
574 | 613 | }
|
| 614 | + |
| 615 | + template <typename ParticleType, typename Segment3d> |
| 616 | + struct RemoveParticleOnGeometricModelExit { |
| 617 | + RemoveParticleOnGeometricModelExit(o::Mesh &mesh, bool requireIntersection) |
| 618 | + : requireIntersection_(requireIntersection) { |
| 619 | + side_is_exposed_ = mark_exposed_sides(&mesh); |
| 620 | + } |
| 621 | + |
| 622 | + void operator()(o::Mesh& mesh, ParticleStructure<ParticleType>* ptcls, |
| 623 | + o::Write<o::LO>& elem_ids, o::Write<o::LO>& inter_faces, |
| 624 | + o::Write<o::LO>& lastExit, o::Write<o::Real>& inter_points, |
| 625 | + o::Write<o::LO>& ptcl_done, |
| 626 | + Segment3d x_ps_orig, |
| 627 | + Segment3d x_ps_tgt) const { |
| 628 | + // Check if intersection face is exposed |
| 629 | + check_model_intersection(mesh, ptcls, x_ps_orig, x_ps_tgt, elem_ids, |
| 630 | + ptcl_done, lastExit, side_is_exposed_, |
| 631 | + requireIntersection_, inter_faces); |
| 632 | + } |
| 633 | + |
| 634 | + private: |
| 635 | + bool requireIntersection_; |
| 636 | + o::Bytes side_is_exposed_; |
| 637 | + }; |
| 638 | + |
| 639 | + template <class ParticleType, typename Segment3d, typename SegmentInt> |
| 640 | + bool search_mesh(o::Mesh& mesh, ParticleStructure<ParticleType>* ptcls, |
| 641 | + Segment3d x_ps_orig, Segment3d x_ps_tgt, SegmentInt pids, |
| 642 | + o::Write<o::LO>& elem_ids, |
| 643 | + bool requireIntersection, |
| 644 | + o::Write<o::LO>& inter_faces, |
| 645 | + o::Write<o::Real>& inter_points, |
| 646 | + int looplimit, |
| 647 | + int debug) { |
| 648 | + RemoveParticleOnGeometricModelExit<ParticleType, Segment3d> native_handler(mesh, requireIntersection); |
| 649 | + |
| 650 | + return trace_particle_through_mesh(mesh, ptcls, x_ps_orig, x_ps_tgt, pids, elem_ids, requireIntersection, |
| 651 | + inter_faces, inter_points, looplimit, debug, native_handler); |
| 652 | + } |
575 | 653 | }
|
576 | 654 | #endif
|
0 commit comments