33 #include "libmesh/parsed_function.h"
34 #include "libmesh/zero_function.h"
59 this->_fan_speed_var = system->add_variable(_fan_speed_var_name,
69 system->time_evolving(this->fan_speed_var());
78 std::string base_function =
82 if (base_function ==
"0")
83 libmesh_error_msg(
"Error! Zero AveragedTurbine specified!" <<
86 if (base_function ==
"0")
87 this->base_velocity_function.reset
88 (
new libMesh::ZeroFunction<libMesh::Number>());
90 this->base_velocity_function.reset
91 (
new libMesh::ParsedFunction<libMesh::Number>(base_function));
93 std::string vertical_function =
97 if (vertical_function ==
"0")
98 libmesh_error_msg(
"Warning! Zero LocalVertical specified!" <<
101 this->local_vertical_function.reset
102 (
new libMesh::ParsedFunction<libMesh::Number>(vertical_function));
104 std::string lift_function_string =
108 if (lift_function_string ==
"0")
109 std::cout <<
"Warning! Zero lift function specified!" << std::endl;
111 this->lift_function.reset
112 (
new libMesh::ParsedFunction<libMesh::Number>(lift_function_string));
114 std::string drag_function_string =
118 if (drag_function_string ==
"0")
119 std::cout <<
"Warning! Zero drag function specified!" << std::endl;
121 this->drag_function.reset
122 (
new libMesh::ParsedFunction<libMesh::Number>(drag_function_string));
124 std::string chord_function_string =
128 if (chord_function_string ==
"0")
129 libmesh_error_msg(
"Warning! Zero chord function specified!" <<
132 this->chord_function.reset
133 (
new libMesh::ParsedFunction<libMesh::Number>(chord_function_string));
135 std::string area_function_string =
139 if (area_function_string ==
"0")
140 libmesh_error_msg(
"Warning! Zero area_swept_function specified!" <<
143 this->area_swept_function.reset
144 (
new libMesh::ParsedFunction<libMesh::Number>(area_function_string));
146 std::string aoa_function_string =
148 std::string(
"00000"));
150 if (aoa_function_string ==
"00000")
151 libmesh_error_msg(
"Warning! No angle-of-attack specified!" <<
154 this->aoa_function.reset
155 (
new libMesh::ParsedFunction<libMesh::Number>(aoa_function_string));
157 std::string torque_function_string =
161 if (torque_function_string ==
"0")
162 std::cout <<
"Warning! Zero torque function specified!" << std::endl;
164 this->torque_function.reset
165 (
new libMesh::ParsedFunction<libMesh::Number>(torque_function_string));
168 (this->moment_of_inertia, input,
172 if (!moment_of_inertia)
174 "Error! Zero AveragedTurbine moment of inertia specified!" <<
178 (this->initial_speed, input,
182 this->_fan_speed_var_name = input(
"Physics/VariableNames/fan_speed",
189 (
const libMesh::Point& point,
190 const libMesh::Real time,
191 const libMesh::NumberVectorValue& U,
193 libMesh::NumberVectorValue& U_B_1,
194 libMesh::NumberVectorValue& F,
195 libMesh::NumberTensorValue *dFdU,
196 libMesh::NumberVectorValue *dFds)
199 libmesh_assert(base_velocity_function.get());
201 libMesh::DenseVector<libMesh::Number> output_vec(3);
203 (*base_velocity_function)(point, time,
206 U_B_1(0) = output_vec(0);
207 U_B_1(1) = output_vec(1);
208 U_B_1(2) = output_vec(2);
210 const libMesh::NumberVectorValue U_B = U_B_1 * s;
212 const libMesh::Number U_B_size = U_B.size();
219 const libMesh::NumberVectorValue N_B =
220 libMesh::NumberVectorValue(U_B/U_B_size);
222 (*local_vertical_function)(point, time,
226 const libMesh::NumberVectorValue N_V(output_vec(0),
232 const libMesh::NumberVectorValue N_R = N_B.cross(N_V);
235 const libMesh::NumberVectorValue U_P = U - (U*N_R)*N_R - U_B;
237 const libMesh::Number U_P_size = U_P.size();
246 const libMesh::NumberVectorValue N_drag =
247 libMesh::NumberVectorValue(-U_P/U_P_size);
250 const libMesh::NumberVectorValue N_lift = N_drag.cross(N_R);
253 const libMesh::Number u_fwd = -(U_P * N_B);
256 const libMesh::Number u_up = U_P * N_V;
260 libmesh_assert (u_up || u_fwd);
263 const libMesh::Number part_angle = std::atan2(u_up, u_fwd);
266 const libMesh::Number angle = part_angle +
267 (*aoa_function)(point, time);
269 const libMesh::Number C_lift = (*lift_function)(point, angle);
270 const libMesh::Number C_drag = (*drag_function)(point, angle);
272 const libMesh::Number chord = (*chord_function)(point, time);
273 const libMesh::Number area = (*area_swept_function)(point, time);
275 const libMesh::Number v_sq = U_P*U_P;
277 const libMesh::Number LDfactor = 0.5 * this->_rho * v_sq * chord / area;
278 const libMesh::Number lift = C_lift * LDfactor;
279 const libMesh::Number drag = C_drag * LDfactor;
282 F = lift * N_lift + drag * N_drag;
286 const libMesh::NumberVectorValue LDderivfactor =
287 (N_lift*C_lift+N_drag*C_drag) *
288 this->_rho * chord / area;
290 const libMesh::Number sfactor = -(U_P*U_B_1);
292 (*dFds) = LDderivfactor * sfactor;
294 for (
unsigned int i=0; i != 3; ++i)
295 for (
unsigned int j=0; j != 3; ++j)
296 (*dFdU)(i,j) = LDderivfactor(i) * U_P(j);
virtual void set_time_evolving_vars(libMesh::FEMSystem *system)
Sets turbine_speed and velocity variables to be time-evolving.
virtual void init_variables(libMesh::FEMSystem *system)
Initialization of variables.
const PhysicsName incompressible_navier_stokes
Physics class for Incompressible Navier-Stokes.
const std::string fan_speed_var_name_default
fan speed
const PhysicsName averaged_turbine
INSTANTIATE_INC_NS_SUBCLASS(AveragedTurbineBase)
virtual void init_variables(libMesh::FEMSystem *system)
Initialization of Navier-Stokes variables.
virtual void set_time_evolving_vars(libMesh::FEMSystem *system)
Sets velocity variables to be time-evolving.
bool compute_force(const libMesh::Point &point, const libMesh::Real time, const libMesh::NumberVectorValue &U, libMesh::Number s, libMesh::NumberVectorValue &U_B_1, libMesh::NumberVectorValue &F, libMesh::NumberTensorValue *dFdU=NULL, libMesh::NumberVectorValue *dFds=NULL)
virtual void read_input_options(const GetPot &input)
Read options from GetPot input file.