LCOV - code coverage report
Current view: top level - src/userobjects - PerElementParticleInitializer.C (source / functions) Hit Total Coverage
Test: idaholab/salamander: d3fcc7 Lines: 30 32 93.8 %
Date: 2025-08-11 14:54:34 Functions: 3 3 100.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : //* This file is part of SALAMANDER: Software for Advanced Large-scale Analysis of MAgnetic
       2             : //* confinement for Numerical Design, Engineering & Research,
       3             : //* A multiphysics application for modeling plasma facing components
       4             : //* https://github.com/idaholab/salamander
       5             : //* https://mooseframework.inl.gov/salamander
       6             : //*
       7             : //* SALAMANDER is powered by the MOOSE Framework
       8             : //* https://www.mooseframework.inl.gov
       9             : //*
      10             : //* Licensed under LGPL 2.1, please see LICENSE for details
      11             : //* https://www.gnu.org/licenses/lgpl-2.1.html
      12             : //*
      13             : //* Copyright 2025, Battelle Energy Alliance, LLC
      14             : //* ALL RIGHTS RESERVED
      15             : //*
      16             : 
      17             : #include "PerElementParticleInitializer.h"
      18             : #include "MooseRandom.h"
      19             : #include "ElementSampler.h"
      20             : #include "VelocityInitializerBase.h"
      21             : 
      22             : registerMooseObject("SalamanderApp", PerElementParticleInitializer);
      23             : 
      24             : InputParameters
      25         552 : PerElementParticleInitializer::validParams()
      26             : {
      27         552 :   auto params = ParticleInitializerBase::validParams();
      28         552 :   params.addClassDescription(
      29             :       "Particle initializer that uniformly distributes a specified number of particles per "
      30             :       "element and calculates the corresponding particle weight based on the requested number "
      31             :       "density, particles per element, and the elements \"volume\".");
      32        1104 :   params.addRangeCheckedParam<unsigned int>(
      33             :       "particles_per_element",
      34             :       "particles_per_element != 0",
      35             :       "The number of computational particles that should be placed in each element");
      36             : 
      37        1104 :   params.addRangeCheckedParam<Real>("number_density",
      38             :                                     "number_density > 0.0",
      39             :                                     "The number density of particles you want to represent");
      40         552 :   return params;
      41           0 : }
      42             : 
      43         275 : PerElementParticleInitializer::PerElementParticleInitializer(const InputParameters & parameters)
      44             :   : ParticleInitializerBase(parameters),
      45         275 :     _number_density(getParam<Real>("number_density")),
      46         825 :     _particles_per_element(getParam<unsigned int>("particles_per_element"))
      47             : {
      48         275 : }
      49             : 
      50             : std::vector<InitialParticleData>
      51          91 : PerElementParticleInitializer::getParticleData() const
      52             : {
      53             : 
      54             :   // counting the number of elements this process is responsible for
      55             :   // this will allow us to allocated data structures of the appropriate length
      56          91 :   const auto & elem_range = *_fe_problem.mesh().getActiveLocalElementRange();
      57             :   const auto num_local_elements = std::distance(elem_range.begin(), elem_range.end());
      58             :   // if there are no elements for this processor: do nothing
      59          91 :   if (num_local_elements == 0)
      60           0 :     return {};
      61             : 
      62             :   std::vector<InitialParticleData> data =
      63          91 :       std::vector<InitialParticleData>(num_local_elements * _particles_per_element);
      64             : 
      65             :   // random number generator to be used for sampling the elements
      66             :   MooseRandom generator;
      67          91 :   SALAMANDER::ElementSampler sampler = SALAMANDER::ElementSampler(_fe_problem, _seed, generator);
      68             :   // This will store the uniformly distributed points within the reference elements
      69             :   uint elem_count = 0;
      70        4203 :   for (const auto elem : *_fe_problem.mesh().getActiveLocalElementRange())
      71             :   {
      72             : 
      73             :     // now that all of the particle locations have been placed we need to
      74             :     // set up the data they will need to be made into actual rays
      75        4113 :     const auto & physical_points = sampler.sampleElement(elem, _particles_per_element);
      76        4112 :     const auto & velocities = _velocity_initializer.getParticleVelocities(_particles_per_element);
      77        4112 :     Real weight = _number_density * elem->volume() / (_particles_per_element);
      78       45232 :     for (const auto i : make_range(_particles_per_element))
      79             :     {
      80       41120 :       uint particle_index = elem_count * _particles_per_element + i;
      81       41120 :       data[particle_index].elem = elem;
      82       41120 :       data[particle_index].weight = weight;
      83       41120 :       data[particle_index].species = _species;
      84       41120 :       data[particle_index].mass = _mass;
      85       41120 :       data[particle_index].charge = _charge;
      86       41120 :       data[particle_index].position = physical_points[i];
      87       41120 :       data[particle_index].velocity = velocities[i];
      88             :     }
      89        4112 :     elem_count++;
      90             :   }
      91             :   return data;
      92         180 : }

Generated by: LCOV version 1.14