Line data Source code
1 : /********************************************************************/ 2 : /* SOFTWARE COPYRIGHT NOTIFICATION */ 3 : /* Cardinal */ 4 : /* */ 5 : /* (c) 2021 UChicago Argonne, LLC */ 6 : /* ALL RIGHTS RESERVED */ 7 : /* */ 8 : /* Prepared by UChicago Argonne, LLC */ 9 : /* Under Contract No. DE-AC02-06CH11357 */ 10 : /* With the U. S. Department of Energy */ 11 : /* */ 12 : /* Prepared by Battelle Energy Alliance, LLC */ 13 : /* Under Contract No. DE-AC07-05ID14517 */ 14 : /* With the U. S. Department of Energy */ 15 : /* */ 16 : /* See LICENSE for full restrictions */ 17 : /********************************************************************/ 18 : 19 : #include "BulkEnergyConservationICAction.h" 20 : #include "IntegralPreservingFunctionIC.h" 21 : #include "FEProblem.h" 22 : 23 : registerMooseAction("CardinalApp", BulkEnergyConservationICAction, "add_bulk_fluid_temperature_ic"); 24 : registerMooseAction("CardinalApp", 25 : BulkEnergyConservationICAction, 26 : "add_bulk_fluid_temperature_user_object"); 27 : 28 : InputParameters 29 3 : BulkEnergyConservationICAction::validParams() 30 : { 31 3 : InputParameters params = CardinalAction::validParams(); 32 6 : params.addRequiredParam<std::vector<VariableName>>( 33 : "variable", "Name(s) of the fluid temperature variable(s)"); 34 6 : params.addRequiredParam<unsigned int>("num_layers", 35 : "Number of layers to use for integrating the heat source"); 36 : 37 6 : MooseEnum directions("x y z"); 38 6 : params.addRequiredParam<MooseEnum>( 39 : "flow_direction", directions, "The flow direction along which to integrate the heat source"); 40 6 : params.addParam<bool>( 41 : "positive_flow_direction", 42 6 : true, 43 : "Whether the flow is along the positive 'direction' or negative 'direction'"); 44 6 : params.addParam<Real>("direction_min", 45 : "Minimum coordinate along 'direction' that bounds the layers"); 46 6 : params.addParam<Real>("direction_max", 47 : "Maximum coordinate along 'direction' that bounds the layers"); 48 : 49 6 : params.addRequiredParam<Real>("mass_flowrate", "Mass flowrate of the fluid"); 50 6 : params.addRequiredParam<Real>("cp", "Fluid isobaric specific heat capacity"); 51 6 : params.addRequiredRangeCheckedParam<Real>("inlet_T", "inlet_T >= 0.0", "Inlet temperature"); 52 3 : return params; 53 3 : } 54 : 55 3 : BulkEnergyConservationICAction::BulkEnergyConservationICAction(const InputParameters & parameters) 56 : : CardinalAction(parameters), 57 3 : _variable(getParam<std::vector<VariableName>>("variable")), 58 6 : _mdot(getParam<Real>("mass_flowrate")), 59 6 : _cp(getParam<Real>("cp")), 60 6 : _inlet_T(getParam<Real>("inlet_T")), 61 6 : _num_layers(getParam<unsigned int>("num_layers")), 62 3 : _direction(parameters.get<MooseEnum>("flow_direction")), 63 3 : _positive_flow_direction(parameters.get<bool>("positive_flow_direction")), 64 6 : _has_direction_min(isParamValid("direction_min")), 65 6 : _has_direction_max(isParamValid("direction_max")), 66 3 : _direction_min(_has_direction_min ? &getParam<Real>("direction_min") : nullptr), 67 6 : _direction_max(_has_direction_max ? &getParam<Real>("direction_max") : nullptr) 68 : { 69 3 : } 70 : 71 : void 72 3 : BulkEnergyConservationICAction::act() 73 : { 74 : // by the nature of the task dependencies we set, we can get the function name 75 : // from the prerequisite task IC 76 3 : const auto & ic_warehouse = _problem->getInitialConditionWarehouse(); 77 : 78 6 : if (!ic_warehouse.hasActiveObject("cardinal_heat_source_ic")) 79 3 : mooseError( 80 : "To use the 'BulkEnergyConservation' action syntax, you must also have " 81 : "a 'VolumetricHeatSource' action!\nYour input file should contain a section like:\n\n" 82 : " [Cardinal]\n" 83 : " [ICs]\n" 84 : " type = VolumetricHeatSource\n" 85 : " ...\n" 86 : " []\n" 87 : " []"); 88 : 89 0 : std::shared_ptr<InitialConditionBase> prereq = ic_warehouse.getObject("cardinal_heat_source_ic"); 90 : std::shared_ptr<IntegralPreservingFunctionIC> ic = 91 0 : std::dynamic_pointer_cast<IntegralPreservingFunctionIC>(prereq); 92 0 : const auto & heat_source_blocks = ic->blocks(); 93 : 94 0 : if (_current_task == "add_bulk_fluid_temperature_ic") 95 : { 96 : int i = 0; 97 0 : for (const auto & v : _variable) 98 : { 99 0 : const std::string ic_type = "BulkEnergyConservationIC"; 100 0 : InputParameters params = _factory.getValidParams(ic_type); 101 0 : params.set<VariableName>("variable") = v; 102 0 : params.set<UserObjectName>("layered_integral") = "cardinal_heat_source_layered_integral"; 103 0 : params.set<Real>("mass_flowrate") = _mdot; 104 0 : params.set<Real>("cp") = _cp; 105 0 : params.set<Real>("inlet_T") = _inlet_T; 106 0 : params.set<PostprocessorName>("integral") = "cardinal_heat_source_integral"; 107 0 : params.set<Real>("magnitude") = ic->magnitude(); 108 : 109 0 : setObjectBlocks(params, _blocks); 110 : 111 0 : _problem->addInitialCondition( 112 0 : ic_type, "cardinal_fluid_temp_ic_" + Moose::stringify(i), params); 113 0 : } 114 : } 115 : 116 0 : if (_current_task == "add_bulk_fluid_temperature_user_object") 117 : { 118 0 : const std::string uo_type = "FunctionLayeredIntegral"; 119 0 : InputParameters params = _factory.getValidParams(uo_type); 120 0 : params.set<FunctionName>("function") = ic->functionName(); 121 0 : params.set<MooseEnum>("direction") = _direction; 122 0 : params.set<bool>("cumulative") = true; 123 0 : params.set<bool>("positive_cumulative_direction") = _positive_flow_direction; 124 0 : params.set<unsigned int>("num_layers") = _num_layers; 125 : 126 0 : if (_has_direction_min) 127 0 : params.set<Real>("direction_min") = *_direction_min; 128 : 129 0 : if (_has_direction_max) 130 0 : params.set<Real>("direction_max") = *_direction_max; 131 : 132 : // we need to set the blocks of the heat source for integrating the heat source, 133 : // not the blocks that the initial condition is applied for the fluid 134 0 : setObjectBlocks(params, heat_source_blocks); 135 : 136 0 : params.set<ExecFlagEnum>("execute_on") = EXEC_INITIAL; 137 0 : _problem->addUserObject(uo_type, "cardinal_heat_source_layered_integral", params); 138 0 : } 139 0 : }