/home/runner/work/amr-wind/amr-wind/amr-wind/wind_energy/actuator/turbine/kynema/kynema_types.H Source File

AMR-Wind API: /home/runner/work/amr-wind/amr-wind/amr-wind/wind_energy/actuator/turbine/kynema/kynema_types.H Source File
AMR-Wind API v0.1.0
CFD solver for wind plant simulations
Loading...
Searching...
No Matches
kynema_types.H
Go to the documentation of this file.
1#ifndef KYNEMA_TYPES_H
2#define KYNEMA_TYPES_H
3
4#include <string>
7#include "AMReX_REAL.H"
8
9using namespace amrex::literals;
10
11namespace ext_turb {
12
16{
19 std::unique_ptr<kynema::interfaces::TurbineInterface> interface;
20
21 // Need buffers to make data contiguous to fit into coupling
49
51 {
52 // Get hub information for nacelle force
53 // Chord is not used, set it to zero
54 buffer_cf[0] = 0.;
55 // Force is calculated by AMR-Wind, passed to Kynema
56 // Get position directly from node information
57 buffer_pf[0] = interface->Turbine().hub_node.position[0];
58 buffer_pf[length_force(0)] = interface->Turbine().hub_node.position[1];
59 buffer_pf[2 * length_force(0)] =
60 interface->Turbine().hub_node.position[2];
61 buffer_pv[0] = buffer_pf[0];
64 // Get solid velocity as well, not used at the moment though
65 buffer_sv[0] = interface->Turbine().hub_node.velocity[0];
66 buffer_sv[length_force(0)] = interface->Turbine().hub_node.velocity[1];
67 buffer_sv[2 * length_force(0)] =
68 interface->Turbine().hub_node.velocity[2];
69
70 // Get blade information
71 int idx = 0;
72 for (int dir = 0; dir < AMREX_SPACEDIM; ++dir) {
73 // Skip hub node
74 ++idx;
75 // Fluid velocity (fv) is not populated here, it comes from the
76 // CFD solver. Need to add step to pass it from buffer to Kynema
77 for (int n = 1; n < length_force(0); ++n) {
78 if (dir == 0) {
79 buffer_cf[n] = (float)interface->Aerodynamics()
80 .bodies[body_index(n)]
81 .chord[node_index(n)];
82 }
83 buffer_f[idx] = (float)interface->Aerodynamics()
84 .bodies[body_index(n)]
85 .loads[node_index(n)][dir];
86 buffer_pf[idx] = (float)interface->Aerodynamics()
87 .bodies[body_index(n)]
88 .x_motion[node_index(n)][dir];
89 buffer_pv[idx] = buffer_pf[idx];
90 buffer_sv[idx] = (float)interface->Aerodynamics()
91 .bodies[body_index(n)]
92 .v_motion[node_index(n)][dir];
93 ++idx;
94 }
95 }
96 // Orientation stores a 3x3 tensor (9 elements) for every point
97 std::array<float, 4> q;
98 for (int n = 0; n < length_force(0); ++n) {
99 // convert quaternions to rotation matrix
100 for (int iq = 0; iq < 4; ++iq) {
101 if (n == 0) {
102 q[iq] =
103 (float)interface->Turbine().hub_node.position[iq + 3];
104 } else {
105 q[iq] = (float)interface->Aerodynamics()
106 .bodies[body_index(n)]
107 .qqr_motion_map[node_index(n)][iq];
108 }
109 }
110 const int idx = n * 9;
111 buffer_ori[idx + 0] =
112 q[0] * q[0] + q[1] * q[1] - q[2] * q[2] - q[3] * q[3];
113 buffer_ori[idx + 1] = 2. * (q[1] * q[2] - q[0] * q[3]);
114 buffer_ori[idx + 2] = 2. * (q[1] * q[3] + q[0] * q[2]);
115 buffer_ori[idx + 3] = 2. * (q[1] * q[2] + q[0] * q[3]);
116 buffer_ori[idx + 4] =
117 (q[0] * q[0] - q[1] * q[1] + q[2] * q[2] - q[3] * q[3]);
118 buffer_ori[idx + 5] = 2. * (q[2] * q[3] - q[0] * q[1]);
119 buffer_ori[idx + 6] = 2. * (q[1] * q[3] - q[0] * q[2]);
120 buffer_ori[idx + 7] = 2. * (q[2] * q[3] + q[0] * q[1]);
121 buffer_ori[idx + 8] =
122 (q[0] * q[0] - q[1] * q[1] - q[2] * q[2] + q[3] * q[3]);
123 }
124 }
125
127 {
128 // Fluid velocity at hub does not need to be passed, loads computed
129 // internally in AMR-Wind
130 int idx = 0;
131 for (int dir = 0; dir < AMREX_SPACEDIM; ++dir) {
132 // Skip hub node
133 ++idx;
134 for (int n = 1; n < length_fluid_velocity(0); ++n) {
135 interface->Aerodynamics()
136 .bodies[body_index(n)]
137 .v_inflow[node_index(n)][dir] = buffer_fv[idx];
138 ++idx;
139 }
140 }
141 // Hub load (also called nacelle_force) does need to be passed
142 interface->Turbine().hub_node.loads[0] = buffer_f[0];
143 interface->Turbine().hub_node.loads[1] = buffer_f[length_force(0)];
144 interface->Turbine().hub_node.loads[2] =
146 // Fluid velocity at hub is passed separately for the sake of controller
147 std::array<amrex::Real, 3> hub_inflow{
150 interface->SetHubInflow(hub_inflow);
151 }
152
154 int body_index(int id) const
155 {
156 // Considering hub, which is 1 node, subtract
157 id -= 1;
158 int b_id = 0;
159 int id_diff = id;
160 for (int b = 0; b < (int)interface->Aerodynamics().bodies.size(); ++b) {
161 id_diff -= static_cast<int>(
162 interface->Aerodynamics().bodies[b].loads.size());
163 if (id_diff < 0) {
164 b_id = b;
165 break;
166 }
167 }
168 return b_id;
169 }
170
171 int node_index(int id) const
172 {
173 // Considering hub, which is 1 node, subtract
174 id -= 1;
175 int n_id = 0;
176 int id_diff = id;
177 for (int b = 0; b < (int)interface->Aerodynamics().bodies.size(); ++b) {
178 id_diff -= (int)interface->Aerodynamics().bodies[b].loads.size();
179 if (id_diff < 0) {
180 n_id = id_diff +
181 (int)interface->Aerodynamics().bodies[b].loads.size();
182 break;
183 }
184 }
185 return n_id;
186 }
187
189
190 float* position_at_vel(int dir) const override
191 {
192 return ptr_pv + dir * length_fluid_velocity(0);
193 }
194
195 float* solid_velocity(int dir) const override
196 {
197 return ptr_sv + dir * length_fluid_velocity(0);
198 }
199
200 float* fluid_velocity(int dir) const override
201 {
202 return ptr_fv + dir * length_fluid_velocity(0);
203 }
204
205 float* force(int dir) const override
206 {
207 return ptr_f + dir * length_force(0);
208 }
209
210 float* position_at_force(int dir) const override
211 {
212 return ptr_pf + dir * length_position_at_force(0);
213 }
214
215 float* chord_at_force() const override { return ptr_cf; }
216
217 float* orientation() const override { return ptr_ori; }
218
219 int length_fluid_velocity(int dir) const override
220 {
221 return length_force(dir);
222 }
223
224 int length_force(int dir) const override
225 {
226 unsigned int n_sect{1};
227 for (unsigned int n = 0; n < interface->Aerodynamics().bodies.size();
228 ++n) {
229 n_sect += interface->Aerodynamics().bodies[n].loads.size();
230 }
231 return static_cast<int>(n_sect);
232 }
233
234 int length_position_at_force(int dir) const override
235 {
236 return length_force(dir);
237 }
238
239 int length_orientation() const override
240 {
241 return length_force(0) * AMREX_SPACEDIM * AMREX_SPACEDIM;
242 }
243
244 int num_vel_pts_blade() const override { return num_pts_blade; }
245
246 amrex::Real fluid_density{1.0_rt};
247 amrex::Real rotational_speed{0.0_rt};
248 amrex::Real generator_power{0.0_rt};
249 amrex::Real wind_speed{0.0_rt};
250 amrex::Real yaw{0.0_rt};
251 amrex::Real generator_efficiency{1.0_rt};
253
255 std::string controller_input_file{""};
256
257 std::vector<float> buffer_cf;
258 std::vector<float> buffer_pv;
259 std::vector<float> buffer_sv;
260 std::vector<float> buffer_fv;
261 std::vector<float> buffer_f;
262 std::vector<float> buffer_pf;
263 std::vector<float> buffer_ori;
264 float* ptr_cf{nullptr};
265 float* ptr_pv{nullptr};
266 float* ptr_sv{nullptr};
267 float* ptr_fv{nullptr};
268 float* ptr_f{nullptr};
269 float* ptr_pf{nullptr};
270 float* ptr_ori{nullptr};
271};
272
274{
275 std::string output_dir{"kynema_velocity_data"};
276
277 amrex::Real damping_factor{0.0_rt};
278 int nl_iter_max{12};
279 amrex::Real abs_err_tol{1.0e-5_rt};
280 amrex::Real rel_err_tol{1.0e-4_rt};
281 amrex::Vector<amrex::Real> gravity{0.0_rt, 0.0_rt, -9.81_rt};
282};
283
284} // namespace ext_turb
285
286#endif /* KYNEMA_TYPES_H */
Definition external_base_types.H:9
Definition external_base_types.H:23
int num_pts_blade
Number of actuator points per blade.
Definition external_base_types.H:36
Definition kynema_types.H:274
amrex::Real damping_factor
Definition kynema_types.H:277
amrex::Vector< amrex::Real > gravity
Definition kynema_types.H:281
amrex::Real abs_err_tol
Definition kynema_types.H:279
amrex::Real rel_err_tol
Definition kynema_types.H:280
int nl_iter_max
Definition kynema_types.H:278
std::string output_dir
Definition kynema_types.H:275
Definition kynema_types.H:16
float * position_at_vel(int dir) const override
Definition kynema_types.H:190
std::vector< float > buffer_ori
Definition kynema_types.H:263
float * ptr_pf
Definition kynema_types.H:269
float * orientation() const override
Definition kynema_types.H:217
std::vector< float > buffer_fv
Definition kynema_types.H:260
float * ptr_sv
Definition kynema_types.H:266
float * ptr_fv
Definition kynema_types.H:267
int node_index(int id) const
Definition kynema_types.H:171
int length_fluid_velocity(int dir) const override
Definition kynema_types.H:219
std::vector< float > buffer_f
Definition kynema_types.H:261
float * position_at_force(int dir) const override
Definition kynema_types.H:210
float * solid_velocity(int dir) const override
Definition kynema_types.H:195
std::vector< float > buffer_cf
Definition kynema_types.H:257
std::string controller_input_file
Definition kynema_types.H:255
float * ptr_pv
Definition kynema_types.H:265
float * chord_at_force() const override
Definition kynema_types.H:215
std::string controller_shared_lib_path
Definition kynema_types.H:254
int body_index(int id) const
Definition kynema_types.H:154
float * ptr_f
Definition kynema_types.H:268
void pass_fluid_velocity_and_hub_load()
Definition kynema_types.H:126
amrex::Real yaw
Definition kynema_types.H:250
void allocate_buffers()
Definition kynema_types.H:22
int substep_counter
Definition kynema_types.H:252
float * ptr_cf
Definition kynema_types.H:264
int length_force(int dir) const override
Definition kynema_types.H:224
std::unique_ptr< kynema::interfaces::TurbineInterface > interface
Definition kynema_types.H:19
int num_vel_pts_blade() const override
Definition kynema_types.H:244
void populate_buffers()
Definition kynema_types.H:50
int length_orientation() const override
Definition kynema_types.H:239
amrex::Real rotational_speed
Definition kynema_types.H:247
amrex::Real generator_efficiency
Definition kynema_types.H:251
std::vector< float > buffer_pf
Definition kynema_types.H:262
int length_position_at_force(int dir) const override
Definition kynema_types.H:234
float * ptr_ori
Definition kynema_types.H:270
float * force(int dir) const override
Definition kynema_types.H:205
std::vector< float > buffer_pv
Definition kynema_types.H:258
amrex::Real generator_power
Definition kynema_types.H:248
amrex::Real wind_speed
Definition kynema_types.H:249
float * fluid_velocity(int dir) const override
Definition kynema_types.H:200
std::vector< float > buffer_sv
Definition kynema_types.H:259
amrex::Real fluid_density
Definition kynema_types.H:246