Skip to content

Commit 04fcfd4

Browse files
committed
Updated explicit time integration (idaholab#30335)
1 parent face47a commit 04fcfd4

17 files changed

+785
-293
lines changed

modules/contact/test/tests/explicit_dynamics/deep_impact.i

+1
Original file line numberDiff line numberDiff line change
@@ -257,6 +257,7 @@
257257
type = DirectCentralDifference
258258
mass_matrix_tag = 'mass'
259259
use_constant_mass = true
260+
second_order_vars = 'disp_x disp_y disp_z'
260261
[]
261262
skip_exception_check = true
262263
[]

modules/contact/test/tests/explicit_dynamics/highvel.i

+1
Original file line numberDiff line numberDiff line change
@@ -345,6 +345,7 @@
345345
[TimeIntegrator]
346346
type = DirectCentralDifference
347347
mass_matrix_tag = mass
348+
second_order_vars = 'disp_x disp_y disp_z'
348349
[]
349350
[]
350351

modules/contact/test/tests/explicit_dynamics/settlement.i

+1
Original file line numberDiff line numberDiff line change
@@ -345,6 +345,7 @@
345345
[TimeIntegrator]
346346
type = DirectCentralDifference
347347
mass_matrix_tag = 'mass'
348+
second_order_vars = 'disp_x disp_y disp_z'
348349
[]
349350
[]
350351

modules/contact/test/tests/explicit_dynamics/test_balance.i

+1
Original file line numberDiff line numberDiff line change
@@ -305,6 +305,7 @@
305305
[TimeIntegrator]
306306
type = DirectCentralDifference
307307
mass_matrix_tag = 'mass'
308+
second_order_vars = 'disp_x disp_y disp_z'
308309
[]
309310
[]
310311

modules/contact/test/tests/explicit_dynamics/test_balance_optimized.i

+1
Original file line numberDiff line numberDiff line change
@@ -263,6 +263,7 @@
263263
type = DirectCentralDifference
264264
mass_matrix_tag = 'mass'
265265
use_constant_mass = true
266+
second_order_vars = 'disp_x disp_y disp_z'
266267
[]
267268
[]
268269
[Outputs]

modules/solid_mechanics/include/bcs/DirectDirichletBCBase.h

+8-1
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99

1010
#pragma once
1111

12+
#include "DirectCentralDifference.h"
1213
#include "NodalBC.h"
1314
#include "libmesh/numeric_vector.h"
1415

@@ -30,7 +31,7 @@ class DirectDirichletBCBase : public NodalBC
3031

3132
protected:
3233
virtual Real computeQpResidual() override;
33-
34+
virtual void timestepSetup() override;
3435
/**
3536
* Compute the value of the DirichletBC at the current quadrature point
3637
*/
@@ -41,4 +42,10 @@ class DirectDirichletBCBase : public NodalBC
4142

4243
const Real & _u_old;
4344
const Real & _u_dot_old;
45+
46+
/// explicit time integrator
47+
const DirectCentralDifference * _exp_integrator;
48+
49+
/// variable time order need for computing BC
50+
DirectCentralDifference::TimeOrder _var_time_order;
4451
};

modules/solid_mechanics/include/timeintegrators/DirectCentralDifference.h

+27
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010
#pragma once
1111

1212
#include "ExplicitTimeIntegrator.h"
13+
#include "libmesh/string_to_enum.h"
1314

1415
// Forward declarations
1516
namespace libMesh
@@ -42,6 +43,19 @@ class DirectCentralDifference : public ExplicitTimeIntegrator
4243
{
4344
mooseError("NOT SUPPORTED");
4445
}
46+
virtual void init() override;
47+
48+
enum TimeOrder
49+
{
50+
FIRST,
51+
SECOND
52+
};
53+
54+
/**
55+
* Retrieve the order of the highest time derivative of a variable.
56+
* @return Returns the time order enum of this variable.
57+
*/
58+
virtual TimeOrder findVariableTimeOrder(unsigned int var_num) const;
4559

4660
protected:
4761
virtual TagID massMatrixTagID() const override;
@@ -52,6 +66,19 @@ class DirectCentralDifference : public ExplicitTimeIntegrator
5266

5367
/// The older solution
5468
const NumericVector<Number> & _solution_older;
69+
70+
// Variables that forward euler time integration will be used
71+
std::unordered_set<unsigned int> & _vars_first;
72+
73+
// local dofs that will have forward euler time integration
74+
std::vector<dof_id_type> & _local_first_order_indicies;
75+
76+
// Variables that central difference time integration will be used
77+
std::unordered_set<unsigned int> & _vars_second;
78+
79+
// local dofs that will have central difference time integration
80+
std::vector<dof_id_type> & _local_second_order_indicies;
81+
5582
/**
5683
* Helper function that actually does the math for computing the time derivative
5784
*/

modules/solid_mechanics/src/bcs/DirectDirichletBCBase.C

+30-7
Original file line numberDiff line numberDiff line change
@@ -7,8 +7,12 @@
77
//* Licensed under LGPL 2.1, please see LICENSE for details
88
//* https://www.gnu.org/licenses/lgpl-2.1.html
99

10+
#include "DirectCentralDifference.h"
1011
#include "DirectDirichletBCBase.h"
12+
#include "MooseError.h"
1113
#include "NonlinearSystemBase.h"
14+
#include <iostream>
15+
#include <ostream>
1216

1317
InputParameters
1418
DirectDirichletBCBase::validParams()
@@ -21,21 +25,40 @@ DirectDirichletBCBase::DirectDirichletBCBase(const InputParameters & parameters)
2125
: NodalBC(parameters),
2226
_mass_diag(_sys.getVector("mass_matrix_diag_inverted")),
2327
_u_old(_var.nodalValueOld()),
24-
_u_dot_old(_var.nodalValueDotOld())
28+
_u_dot_old(_var.nodalValueDotOld()),
29+
_exp_integrator(
30+
dynamic_cast<const DirectCentralDifference *>(&_sys.getTimeIntegrator(_var.number())))
2531
{
32+
if (!_exp_integrator)
33+
mooseError("Time integrator for the variable is not of the right type.");
2634
}
2735

2836
Real
2937
DirectDirichletBCBase::computeQpResidual()
3038
{
3139
// Get dof for current var
3240
const auto dofnum = _variable->nodalDofIndex();
41+
Real resid = 0;
42+
// Compute residual to enforce BC based on time order
43+
switch (_var_time_order)
44+
{
45+
case DirectCentralDifference::FIRST:
46+
resid = (computeQpValue() - _u_old) / _dt;
47+
resid /= -_mass_diag(dofnum);
48+
break;
3349

34-
// Compute residual to enforce BC
35-
// This is the force required to enforce the BC in a central difference scheme
36-
Real avg_dt = (_dt + _dt_old) / 2;
37-
Real resid = (computeQpValue() - _u_old) / (avg_dt * _dt) - (_u_dot_old) / avg_dt;
38-
resid /= -_mass_diag(dofnum);
39-
50+
case DirectCentralDifference::SECOND:
51+
Real avg_dt = (_dt + _dt_old) / 2;
52+
resid = (computeQpValue() - _u_old) / (avg_dt * _dt) - (_u_dot_old) / avg_dt;
53+
resid /= -_mass_diag(dofnum);
54+
break;
55+
}
4056
return resid;
4157
}
58+
59+
void
60+
DirectDirichletBCBase::timestepSetup()
61+
{
62+
// Now is the point that the time integrator has the variable time orders setup
63+
_var_time_order = _exp_integrator->findVariableTimeOrder(_var.number());
64+
}

0 commit comments

Comments
 (0)