33 #include "libmesh/getpot.h"
34 #include "libmesh/elem.h"
35 #include "libmesh/fe_interface.h"
36 #include "libmesh/mesh_base.h"
37 #include "libmesh/parallel.h"
43 const std::string& physics_name )
44 : _pinned_elem_id(
libMesh::DofObject::invalid_id)
46 _pin_value = input(
"Physics/"+physics_name+
"/pin_value", 0.0 );
48 unsigned int pin_loc_dim = input.vector_variable_size(
"Physics/"+physics_name+
"/pin_location");
51 if( pin_loc_dim > 0 && pin_loc_dim < 2 )
53 std::cerr <<
"Error: pressure pin location must be at least 2 dimensional"
58 _pin_location(0) = input(
"Physics/"+physics_name+
"/pin_location", 0.0, 0 );
61 _pin_location(1) = input(
"Physics/"+physics_name+
"/pin_location", 0.0, 1 );
63 if( pin_loc_dim == 3 )
64 _pin_location(2) = input(
"Physics/"+physics_name+
"/pin_location", 0.0, 2 );
79 libMesh::MeshBase::const_element_iterator el = mesh.active_local_elements_begin();
80 const libMesh::MeshBase::const_element_iterator end_el = mesh.active_local_elements_end();
82 for ( ; el != end_el; ++el)
84 const libMesh::Elem* elem = *el;
100 libMesh::err <<
"ERROR: Could not locate point " <<
_pin_location
101 <<
" in mesh!" << std::endl;
107 const bool request_jacobian,
109 const double penalty )
113 libmesh_assert_not_equal_to(
_pinned_elem_id, libMesh::DofObject::invalid_id );
125 libmesh_error_msg(
"ERROR: _pin_location not in the current element!");
128 libMesh::DenseSubVector<libMesh::Number> &F_var = c.get_elem_residual(var);
129 libMesh::DenseSubMatrix<libMesh::Number> &K_var = c.get_elem_jacobian(var, var);
132 const unsigned int n_var_dofs = c.get_dof_indices(var).size();
134 libMesh::Number var_value = c.point_value(var,
_pin_location);
136 libMesh::FEType fe_type = c.get_element_fe(var)->get_fe_type();
138 libMesh::Point point_loc_in_masterelem =
139 libMesh::FEInterface::inverse_map(c.get_dim(), fe_type, &c.get_elem(),
_pin_location);
141 std::vector<libMesh::Real> phi(n_var_dofs);
143 for (
unsigned int i=0; i != n_var_dofs; i++)
144 phi[i] = libMesh::FEInterface::shape( c.get_dim(), fe_type, &c.get_elem(), i,
145 point_loc_in_masterelem );
147 for (
unsigned int i=0; i != n_var_dofs; i++)
149 F_var(i) += penalty*(var_value -
_pin_value)*phi[i];
152 if (request_jacobian && c.get_elem_solution_derivative())
154 libmesh_assert (c.get_elem_solution_derivative() == 1.0);
156 for (
unsigned int j=0; j != n_var_dofs; j++)
157 K_var(i,j) += penalty*phi[i]*phi[j];
unsigned int VariableIndex
More descriptive name of the type used for variable indices.
libMesh::Point _pin_location
Location we want to pin the pressure.
void check_pin_location(const libMesh::MeshBase &mesh)
Check the mesh to ensure pin location is found.
libMesh::dof_id_type _pinned_elem_id
Cache element id for element that contains _pin_location.
void pin_value(libMesh::DiffContext &context, const bool request_jacobian, const GRINS::VariableIndex var, const double penalty=1.0)
The idea here is to pin a variable to a particular value if there is a null space - e...
libMesh::Number _pin_value
Value of pressure we wish to pin.
PressurePinning(const GetPot &input, const std::string &physics_name)