diff --git a/.gitignore b/.gitignore index 8876bf76..778c3458 100644 --- a/.gitignore +++ b/.gitignore @@ -12,9 +12,12 @@ new* *COMPILED* *.out *.h5 +*h5* *.mat *.png *.gif +*.pdf +*.csv *.mp4 -*turbsimfiles/ +*turbsim*/ *animation/ \ No newline at end of file diff --git a/Project.toml b/Project.toml index 396b4063..827f268f 100644 --- a/Project.toml +++ b/Project.toml @@ -1,7 +1,7 @@ name = "OWENS" uuid = "51d15398-4eaf-40f9-a029-79ae1c4a3867" authors = ["Kevin R. Moore and contributors"] -version = "1.0.2" +version = "1.0.3" [deps] Composites = "d0d699f6-c662-11e8-0fb1-1b30104ab829" @@ -29,10 +29,10 @@ YAML = "ddb6d928-2868-570f-bddf-ab3f9cf99eb6" [sources] Composites = {url = "https://github.com/byuflowlab/Composites.jl.git"} -OWENSAero = {url = "https://github.com/sandialabs/OWENSAero.jl"} -OWENSFEA = {url = "https://github.com/sandialabs/OWENSFEA.jl"} OWENSOpenFAST_jll = {url = "https://github.com/sandialabs/OWENSOpenFAST_jll.jl"} OWENSOpenFASTWrappers = {url = "https://github.com/sandialabs/OWENSOpenFASTWrappers.jl"} +OWENSAero = {url = "https://github.com/sandialabs/OWENSAero.jl"} +OWENSFEA = {url = "https://github.com/sandialabs/OWENSFEA.jl"} [compat] DelimitedFiles = "1" diff --git a/app/OWENS_APP/src/sampleOWENS.yml b/app/OWENS_APP/src/sampleOWENS.yml index 657c60f4..bcfdce9b 100644 --- a/app/OWENS_APP/src/sampleOWENS.yml +++ b/app/OWENS_APP/src/sampleOWENS.yml @@ -31,7 +31,7 @@ controlParameters: AeroParameters: Nslices: 30 # number of OWENSAero discritizations #TODO: AD parameters ntheta: 30 # number of OWENSAero azimuthal discretizations - AModel: AD # AD, DMS, AC + AeroModel: AD # AD, DMS, AC adi_lib: /Users/kevmoor/Documents/coderepos/openfast/build/modules/aerodyn/libaerodyn_inflow_c_binding adi_rootname: "/ExampleB" diff --git a/docs/src/OWENS_Dev_Guide.md b/docs/src/OWENS_Dev_Guide.md index 0a7f8903..c26138ce 100644 --- a/docs/src/OWENS_Dev_Guide.md +++ b/docs/src/OWENS_Dev_Guide.md @@ -62,6 +62,13 @@ displacements$_\text{guess}$ with the calculated displacements []{#alg:Transient label="alg:Transient"} ::: +# WindIO Usage +The majority of the WindIO standard can be used for the structural and aerodynamic design. Airfoil polars are forthcoming. However, there are the following additional and limitations: + - Gravity single value or array of 3, is in the global frame of reference, so positive gravity would be pulling the structure up. + - Start and end nd_arc values are the only input supported. Otherwise, there are as many as 12 different ways to specify this input. + - Grids must be defined from end to end, set number of plies to 1e-6 at unused spanwise sections. + - The blade object is reused for the tower, struts, cables, etc. since these elements can be modeled at the same fidelity as the blade and can be simplified via simpler inputs, but the other WindIO definitions don't allow for the more complex inputs. + # Global Frame of Reference Thanks to some legacy VAWT frames of reference where wind was originally diff --git a/docs/src/VAWTGenUserGuide.md b/docs/src/VAWTGenUserGuide.md index 29b8819e..038d36e2 100644 --- a/docs/src/VAWTGenUserGuide.md +++ b/docs/src/VAWTGenUserGuide.md @@ -872,7 +872,7 @@ height="3.3866666666666667in"} > A similar capability exists for generating animated mode shapes. The > vizAnimateModal function is utilized in the following manner: > -> vizAnimateModal(meshFile,resultsFile,selectedMode,sf,outFileName); +> vizAnimateModal(meshFile,resultsFile,selectedMode,sf,dataOutputFilename); > > All the input parameters are the same as those for viz, however, the > last parameter specifies a file name for a AVI movie file. @@ -884,12 +884,12 @@ height="3.3866666666666667in"} > vizAnimateTransient function. The command line argument is executed > as: > -> vizAnimateTransient(meshFile,uData,sf,outFileName); +> vizAnimateTransient(meshFile,uData,sf,dataOutputFilename); > > Such that mesh file is the mesh filename (.mesh), uData is an n x m > array holding displacement data for n degrees of freedom at m time > steps, and sf is the deformation scale factor for the structural mesh. -> The AVI movie file is generated using outFileName. +> The AVI movie file is generated using dataOutputFilename. # VAWTGen Output Files diff --git a/docs/src/indepth_installation.md b/docs/src/indepth_installation.md index 908e337f..409650da 100644 --- a/docs/src/indepth_installation.md +++ b/docs/src/indepth_installation.md @@ -233,7 +233,7 @@ Pkg.add(PackageSpec(url="https://github.com/sandialabs/OWENS.jl.git")) Note that there are many packages used in the examples. While they are installed within the OWENS.jl environment, if you want to additionally install them in your 1.11+ environment where you will likely be running from: ```julia using Pkg -Pkg.add(["Statistics","Dierckx","QuadGK","FLOWMath","HDF5","ImplicitAD","GXBeam","DelimitedFiles","Statistics","FFTW"]) +Pkg.add(["Statistics","Dierckx","QuadGK","FLOWMath","HDF5","ImplicitAD","GXBeam","DelimitedFiles","FFTW","YAML","OrderedCollections"]) ``` If you want to show any of the plots in the examples, they currently use the PyPlot interface, which means that julia has to install its own conda in the back end, which can take some time. Alternatively, you can point to your own python if desired. @@ -257,9 +257,10 @@ println("\n#####################") println("Install OWENS") println("#####################") -Pkg.add(["Statistics","Dierckx","QuadGK","FLOWMath","HDF5","ImplicitAD","GXBeam","DelimitedFiles","Statistics","FFTW", +Pkg.add(["Statistics","Dierckx","QuadGK","FLOWMath","HDF5","ImplicitAD","GXBeam","DelimitedFiles","FFTW","YAML","OrderedCollections"]) + +Pkg.add([ PackageSpec(url="https://github.com/byuflowlab/Composites.jl.git"), -PackageSpec(url="https://github.com/sandialabs/OWENSPreComp.jl.git"), PackageSpec(url="https://github.com/sandialabs/OWENSOpenFAST_jll.jl.git"), PackageSpec(url="https://github.com/sandialabs/OWENSOpenFASTWrappers.jl.git"), PackageSpec(url="https://github.com/sandialabs/OWENSAero.jl.git"), diff --git a/examples/AddedMass_Buoyancy/300mx300m12msETM_Coarse.bts b/examples/AddedMass_Buoyancy/300mx300m12msETM_Coarse.bts index 91d82b0c..8d076513 100644 Binary files a/examples/AddedMass_Buoyancy/300mx300m12msETM_Coarse.bts and b/examples/AddedMass_Buoyancy/300mx300m12msETM_Coarse.bts differ diff --git a/examples/AddedMass_Buoyancy/Buoyancy.jl b/examples/AddedMass_Buoyancy/Buoyancy.jl index 2ffb76b8..65335534 100644 --- a/examples/AddedMass_Buoyancy/Buoyancy.jl +++ b/examples/AddedMass_Buoyancy/Buoyancy.jl @@ -43,7 +43,7 @@ nbelem = 60 ncelem = 10 nselem = 10 ifw = false -AModel = "DMS" +AeroModel = "DMS" windINPfilename = "$path/300mx300m12msETM_Coarse.bts" ifw_libfile = nothing#"$path/../../openfast/build/modules/inflowwind/libifw_c_binding" Blade_Height = 20.0 @@ -130,8 +130,8 @@ mass_breakout_blds,mass_breakout_twr,system,assembly,sections,AD15bldNdIdxRng,AD c_mount_ratio = 0.05, strut_twr_mountpoint = [0.5], strut_bld_mountpoint = [0.5], - AModel, #AD, DMS, AC - DSModel="BV", + AeroModel, #AD, DMS, AC + DynamicStallModel="BV", Aero_AddedMass_Active, AddedMass_Coeff_Ca=0.0, Aero_RotAccel_Active, @@ -209,13 +209,13 @@ nothing # There are inputs for the overall coupled simulation, please see the api reference for specifics on all the options -if AModel=="AD" +if AeroModel=="AD" AD15On = true else AD15On = false end -inputs = OWENS.Inputs(;analysisType = structuralModel, +inputs = OWENS.Inputs(;verbosity,analysisType = structuralModel, tocp, Omegaocp, tocp_Vinf, @@ -312,7 +312,7 @@ initTopConditions[length(displace_y)+1:end,2] .= 5 initTopConditions[length(displace_y)+1:end,3] = curve_y feamodel = OWENS.FEAModel(;analysisType = structuralModel, -outFilename = "none", +dataOutputFilename = "none", joint = myjoint, platformTurbineConnectionNodeNumber = 1, pBC, @@ -332,7 +332,7 @@ nothing println("Running Unsteady") topdata = OWENS.Unsteady_Land(inputs;system,assembly,returnold=false, -topModel=feamodel,topMesh=mymesh,topEl=myel,aero=flappingForces,deformAero,verbosity) +topModel=feamodel,topMesh=mymesh,topEl=myel,aero=flappingForces,deformAero) t = topdata.t aziHist = topdata.aziHist OmegaHist = topdata.OmegaHist @@ -409,9 +409,9 @@ println("Percent Diff = $percentdiff%") # for example, strain, or reaction force, etc. This is described in more detail in the api reference for the function and: TODO -# saveName = "$path/vtk/flapping_buoyancy" +# VTKsaveName = "$path/vtk/flapping_buoyancy" # tsave_idx=1:1:numTS-1 -# OWENS.OWENSVTK(saveName,t,uHist,system,assembly,sections,aziHist,mymesh,myel, +# OWENS.OWENSVTK(VTKsaveName,t,uHist,system,assembly,sections,aziHist,mymesh,myel, # epsilon_x_hist,epsilon_y_hist,epsilon_z_hist,kappa_x_hist,kappa_y_hist,kappa_z_hist, # FReactionHist,topFexternal_hist;tsave_idx) diff --git a/examples/AddedMass_Buoyancy/Flapping_Added_Mass.jl b/examples/AddedMass_Buoyancy/Flapping_Added_Mass.jl index ea69cce1..be2a70af 100644 --- a/examples/AddedMass_Buoyancy/Flapping_Added_Mass.jl +++ b/examples/AddedMass_Buoyancy/Flapping_Added_Mass.jl @@ -43,7 +43,7 @@ nbelem = 60 ncelem = 10 nselem = 10 ifw = false -AModel = "DMS" +AeroModel = "DMS" windINPfilename = "$path/300mx300m12msETM_Coarse.bts" ifw_libfile = nothing#"$path/../../openfast/build/modules/inflowwind/libifw_c_binding" Blade_Height = 20.0 @@ -131,8 +131,8 @@ mass_breakout_blds,mass_breakout_twr,system,assembly,sections,AD15bldNdIdxRng,AD c_mount_ratio = 0.05, strut_twr_mountpoint = [0.5], strut_bld_mountpoint = [0.5], - AModel, #AD, DMS, AC - DSModel="BV", + AeroModel, #AD, DMS, AC + DynamicStallModel="BV", Aero_AddedMass_Active, AddedMass_Coeff_Ca, Aero_RotAccel_Active, @@ -227,13 +227,13 @@ nothing # There are inputs for the overall coupled simulation, please see the api reference for specifics on all the options -if AModel=="AD" +if AeroModel=="AD" AD15On = true else AD15On = false end -inputs = OWENS.Inputs(;analysisType = structuralModel, +inputs = OWENS.Inputs(;verbosity,analysisType = structuralModel, tocp, Omegaocp, tocp_Vinf, @@ -327,7 +327,7 @@ initTopConditions[length(displace_y)+1:end,2] .= 5 initTopConditions[length(displace_y)+1:end,3] = curve_y feamodel = OWENS.FEAModel(;analysisType = structuralModel, -outFilename = "none", +dataOutputFilename = "none", joint = myjoint, platformTurbineConnectionNodeNumber = 1, pBC, @@ -348,7 +348,7 @@ nothing println("Running Unsteady") topdata = OWENS.Unsteady_Land(inputs;system,assembly,returnold=false, -topModel=feamodel,topMesh=mymesh,topEl=myel,aero=flappingForces,deformAero,verbosity) +topModel=feamodel,topMesh=mymesh,topEl=myel,aero=flappingForces,deformAero) t = topdata.t aziHist = topdata.aziHist OmegaHist = topdata.OmegaHist @@ -449,9 +449,9 @@ println("percent_diff: $percentdiff%") # for example, strain, or reaction force, etc. This is described in more detail in the api reference for the function and: TODO # azi=aziHist#./aziHist*1e-6 -# saveName = "$path/vtk/flapping_added_mass" +# VTKsaveName = "$path/vtk/flapping_added_mass" # tsave_idx=1:1:numTS-1 -# OWENS.OWENSVTK(saveName,t,uHist,system,assembly,sections,aziHist,mymesh,myel, +# OWENS.OWENSVTK(VTKsaveName,t,uHist,system,assembly,sections,aziHist,mymesh,myel, # epsilon_x_hist,epsilon_y_hist,epsilon_z_hist,kappa_x_hist,kappa_y_hist,kappa_z_hist, # FReactionHist,topFexternal_hist;tsave_idx) diff --git a/examples/AddedMass_Buoyancy/modeling_options_OWENS_RM2.yml b/examples/AddedMass_Buoyancy/modeling_options_OWENS_RM2.yml index 0eb95e43..1f86157e 100644 --- a/examples/AddedMass_Buoyancy/modeling_options_OWENS_RM2.yml +++ b/examples/AddedMass_Buoyancy/modeling_options_OWENS_RM2.yml @@ -19,7 +19,7 @@ controlParameters: AeroParameters: Nslices: 30 # number of OWENSAero discritizations #TODO: AD parameters ntheta: 30 # number of OWENSAero azimuthal discretizations - AModel: AD # AD, DMS, AC + AeroModel: AD # AD, DMS, AC adi_lib: nothing adi_rootname: "/RM2" diff --git a/examples/Optimization/InitialDataOutputs_UNIT.h5 b/examples/Optimization/InitialDataOutputs_UNIT.h5 new file mode 100644 index 00000000..dbb0b337 Binary files /dev/null and b/examples/Optimization/InitialDataOutputs_UNIT.h5 differ diff --git a/examples/Optimization/OWENS_Opt.yml b/examples/Optimization/OWENS_Opt.yml new file mode 100644 index 00000000..b4f3d34d --- /dev/null +++ b/examples/Optimization/OWENS_Opt.yml @@ -0,0 +1,63 @@ +OWENS_Options: + analysisType: "Unsteady" # Unsteady, DLC, Campbell, todo: steady, flutter may be re-activated in the future. + AeroModel: "DMS" # OWENSAero model "DMS" for double multiple streamtube or "AC" for actuator cylinder, or "AD" for aerodyn + structuralModel: "TNB" #Structural models available: TNB full timoshenko beam elements with time newmark beta time stepping, ROM reduced order modal model of the timoshenko elements, GX with GXBeam's methods for geometrically exact beam theory and more efficient methods and time stepping + controlStrategy: "prescribedRPM" # should be in WindIO?- yes, + numTS: 20 # number of time steps TODO: change to sim time and make this derived + delta_t: 0.01 # time step in seconds + dataOutputFilename: "./InitialDataOutputs.out" # data output filename with path, set to nothing or don't specify to not output anything + TOL: 1e-4 # gauss-seidel iteration tolerance - i.e. the two-way iteration tolerance + MAXITER: 300 # gauss-seidel max iterations - i.e. the two-way iterations + verbosity: 2 # verbosity where 0 is nothing, 1 is warnings, 2 is summary outputs, 3 is detailed outputs, and 4 is everything + VTKsaveName: "./vtk/windio" # Path and name of the VTK outputs, recommended to put it in its own folder (which it will automatically create if needed) + aeroLoadsOn: 2 # Level of aero coupling 0 structures only, 1 no deformation passed to the aero, 2 two-way coupling, 1.5 last time step's deformations passed to this timesteps aero and no internal iteration. + Prescribed_RPM_time_controlpoints: [0.0,100000.1] + Prescribed_RPM_RPM_controlpoints: [17.2,17.2] + Prescribed_Vinf_time_controlpoints: [0.0,100000.1] + Prescribed_Vinf_Vinf_controlpoints: [17.2,17.2] + +DLC_Options: + DLCs: ["1_1","2_1"] # name of DLC + Vinf_range: [17.2] # inflow Cutin to cutout and discretization + IEC_std: "\"1-ED3\"" # turbsim input file IEC standard + WindChar: "\"A\"" # turbsim wind charasteric + WindClass: 1 # turbsim wind class + turbsimsavepath: "./turbsimfiles" # path where the turbsim files are saved + pathtoturbsim: nothing # path to the turbsim executable + NumGrid_Z: 38 # turbsim vertical discretizations + NumGrid_Y: 26 # turbsim horizontal discretizations + Vref: 17.2 # reference/nominal wind speed m/s for turbsim or other inflow wind input file (depending on which DLC is selected) + Vdesign: 11.0 # Design or rated speed of turbine, used for certain DLC cases + grid_oversize: 1.1 # amount that the turbsim inflow is oversized compared to the turbine to allow for deflection + regenWindFiles: false #, force regeneration of turbsim files even if they already exist + delta_t_turbsim: 0.05 # turbsim timestep + simtime_turbsim: 600.0 # turbsim total time, which loops if simtime exceeds turbsim time + +OWENSAero_Options: + Nslices: 30 # number of 3-D slices for the strip method to go from 2D to 3D considering curved deforming blades + ntheta: 30 # number of azimuthal discretizations + ifw: false # use the OpenFASTWrappers inflow wind coupling to get inflow velocities + DynamicStallModel: "BV" # dynamic stall model, should be under an OWENSAero options + RPI: true # rotating point iterative method (i.e. it just calculates at the blade positions and is much faster) + Aero_Buoyancy_Active: false # flag to turn buoyancy on for the blades. This is likely to be replaced by a different model + +OWENSFEA_Options: + nlOn: true #nonlinear effects + RayleighAlpha: 0.05 #damping coefficient scalar on the stiffness matrix + RayleighBeta: 0.05 #damping coefficient scalar on the mass matrix + iterationType: "DI" #internal iteration type DI direct iteration, NR newton rhapson (which is less stable than DI) + numModes: 20 #if ROM model, number of modes used in the analysis type. Less is faster but less accurate + tolerance: 1.0e-06 #total mesh unsteady analysis convergence tolerance for a timestep within the structural model + maxIterations: 50 #total mesh unsteady analysis convergence max iterations for a timestep + AddedMass_Coeff_Ca: 0.0 #added mass coefficient, scaling factor (typically 0-1) on the cones of water mass applied to each structural element in the 22 and 33 diagonal terms. 0 turns this off + +Mesh_Options: + ntelem: 10 # number of tower elements in each blade, plus nodes wherever there is a component overlap + nbelem: 60 # number of blade elements in each blade, plus nodes wherever there is a component overlap + nselem: 5 # number of elements in each strut + angularOffset: -1.5707963267948966 + AD15hubR: 0.1 # parameter, used in aerodyn coupling for the hub radius so that the vortex sheets don't go within the hub + turbineType: Darrieus + +OWENSOpenFASTWrappers_Options: + windINPfilename: /data/turbsim/115mx115m_30x30_20.0msETM.bts #OWENSOpenFASTWrappers If ifw or AeroDyn is being used, gets overwritten if using the DLC analysis type, the moordyn file location, like in the unit test \ No newline at end of file diff --git a/examples/Optimization/WINDIO_example.yaml b/examples/Optimization/WINDIO_example.yaml index 4578331f..2a90ed62 100644 --- a/examples/Optimization/WINDIO_example.yaml +++ b/examples/Optimization/WINDIO_example.yaml @@ -1,10 +1,11 @@ name: WINDIO Example assembly: {turbine_class: I, turbulence_class: B, drivetrain: geared, rotor_orientation: upwind, number_of_blades: 3, hub_height: -25.2, rotor_diameter: 20.0, rated_power: 500000, lifetime: 25.0, marine_hydro: true} components: + hub: {diameter: 2.0} tower: outer_shape_bem: airfoil_position: - grid: &id000 [0, 6.607421057, 13.21484211, 19.82226317, 26.42968423, 33.03710529, 39.64452634, 46.2519474, 52.85936846, 59.46678951, 66.07421057, 72.68163163, 79.28905268, 85.89647374, 92.5038948, 99.11131586, 105.7187369, 112.326158, 118.933579, 125.5410001, 132.1484211] + grid: &id000 [0.0, 0.050000000015134494, 0.09999999999999999, 0.15000000003783623, 0.20000000007567248, 0.2500000001135087, 0.30000000007567246, 0.3500000001135087, 0.40000000015134496, 0.4500000001135087, 0.5000000001513449, 0.5500000001891812, 0.6000000001513449, 0.6500000001891812, 0.7000000002270174, 0.7500000002648537, 0.8000000001513449, 0.8500000004918712, 0.9000000000756724, 0.9500000004161987, 1.0] labels: [circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular] chord: grid: *id000 @@ -85,7 +86,7 @@ components: blade: outer_shape_bem: airfoil_position: - grid: &id001 [0, 6.607, 13.215, 19.822, 26.43, 33.037, 39.645, 46.252, 52.859, 59.467, 66.074, 72.682, 79.289, 85.896, 92.504, 99.111, 105.719, 112.326, 118.934, 125.541, 132.148] + grid: &id001 [0.0, 0.04999697309077701, 0.1000015134546115, 0.1499984865453885, 0.200003026909223, 0.25, 0.3000045403638345, 0.3500015134546115, 0.39999848654538855, 0.450003026909223, 0.5, 0.5500045403638345, 0.6000015134546115, 0.6499984865453885, 0.700003026909223, 0.75, 0.8000045403638345, 0.8500015134546115, 0.900006053818446, 0.950003026909223, 1.0] labels: [NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021] chord: grid: *id001 @@ -312,9 +313,11 @@ components: joint: {position: 0.0, mass: 0.0, cost: 0.0, bolt: M30, nonmaterial_cost: 0.0, reinforcement_layer_ss: joint_reinf_ss, reinforcement_layer_ps: joint_reinf_ps} struts: - name: strut1 + mountfraction_tower: [0.25,0.75] + mountfraction_blade: [0.25,0.75] outer_shape_bem: airfoil_position: - grid: &id002 [0, 6.607, 13.215, 19.822] + grid: &id002 [0, 0.333, 0.6667, 1.0] labels: [NACA_0021, NACA_0021, NACA_0021, NACA_0021] chord: grid: *id002 @@ -331,7 +334,7 @@ components: values: [-0.0, -0.0, -0.0, -0.0] y: grid: *id002 - values: [0.0, 0.0, 0.0, 0.0, 0.0] + values: [0.0, 0.0, 0.0, 0.0] z: grid: *id002 values: [0.0, 0.15, 0.45, 0.75] @@ -538,52 +541,6 @@ components: grid: *id002 root: {d_f: 0.03, sigma_max: 675000000.0} joint: {position: 0.0, mass: 0.0, cost: 0.0, bolt: M30, nonmaterial_cost: 0.0, reinforcement_layer_ss: joint_reinf_ss, reinforcement_layer_ps: joint_reinf_ps} - hub: {diameter: 2.0, cone_angle: 0.0, drag_coefficient: 0.0, flange_t2shell_t: 6.0, flange_OD2hub_D: 0.6, flange_ID2OD: 0.8, hub_blade_spacing_margin: 1.2, hub_stress_concentration: 3.0, n_front_brackets: 5, n_rear_brackets: 5, clearance_hub_spinner: 0.5, spin_hole_incr: 1.2, pitch_system_scaling_factor: 0.75, spinner_gust_ws: 70.0, hub_material: cast_iron, spinner_material: glass_uni} - nacelle: - drivetrain: - uptilt: -0.0 - distance_tt_hub: 1.2 - distance_hub_mb: 2.0 - distance_mb_mb: 1.0 - overhang: 4.91 - generator_length: 2.0 - generator_radius_user: 0.25 - generator_mass_user: 8928.0 - generator_rpm_efficiency_user: - grid: [0.0,1.0] - values: [1.0,1.0] - gear_ratio: 53.0 - gearbox_length_user: 0.0 - gearbox_radius_user: 0.0 - gearbox_mass_user: 0.0 - gearbox_efficiency: 0.92 - damping_ratio: 0.01 - lss_diameter: [0.577, 0.577] - lss_wall_thickness: [0.288, 0.288] - lss_material: steel - hss_length: 1.5 - hss_diameter: [0.288, 0.288] - hss_wall_thickness: [0.144, 0.144] - hss_material: steel - nose_diameter: [0.3, 0.3] - nose_wall_thickness: [0.1, 0.1] - bedplate_wall_thickness: - grid: [0.0, 1.0] - values: [0.05, 0.05] - bedplate_flange_width: 1.0 - bedplate_flange_thickness: 0.05 - bedplate_web_thickness: 0.05 - bedplate_material: steel - mb1Type: CARB - mb2Type: SRB - uptower: true - gear_configuration: eep - planet_numbers: [3, 3, 0] - brake_mass_user: 0.0 - hvac_mass_coefficient: 0.025 - converter_mass_user: 0.0 - transformer_mass_user: 0.0 - # generator: {generator_type: DFIG, rho_Fe: 7700.0, rho_Fes: 7850.0, rho_Copper: 8900.0, rho_PM: 7450.0, B_r: 1.2, P_Fe0e: 1.0, P_Fe0h: 4.0, S_N: -0.002, alpha_p: 1.0995574287564276, b_r_tau_r: 0.45, b_ro: 0.004, b_s_tau_s: 0.45, b_so: 0.004, freq: 60, h_i: 0.001, h_sy0: 0.0, h_w: 0.005, k_fes: 0.9, k_s: 0.2, m: 3, mu_0: 1.2566370614359173e-06, mu_r: 1.06, p: 3.0, phi: 1.5707963267948966, ratio_mw2pp: 0.7, resist_Cu: 2.52e-08, y_tau_pr: 0.8333333, rated_rpm: 1200.0, cofi: 0.9, y_tau_p: 0.8, sigma: 21500.0, rad_ag: 0.61, len_s: 0.49, h_s: 0.08, I_0: 40.0, B_symax: 1.3, S_Nmax: -0.2, h_0: 0.01, k_fillr: 0.55, k_fills: 0.65, q1: 5, q2: 4, C_Cu: 4.786, C_Fe: 0.556, C_Fes: 0.50139, C_PM: 50.0, mass_coefficient: 0.0, q3: 4, d_r: 0.0, h_m: 0.0, n_r: 0.0, t_wr: 0.0, n_s: 0.0, b_st: 0.0, d_s: 0.0, t_ws: 0.0} airfoils: - name: NACA6_1000 coordinates: @@ -660,12 +617,4 @@ materials: unit_cost: 0.10 A: [50.0,45.0,40.0,35.0,20.0,0.0] m: [0.0,1.0,2.0,4.0,6.0,20.0] -control: - supervisory: {Vin: 0.5, Vout: 4.0, maxTS: 60} - pitch: {PC_zeta: !!null '', PC_omega: !!null '', ps_percent: !!null '', max_pitch: !!null '', max_pitch_rate: 0.1745, min_pitch: 0.00088} - torque: {control_type: !!null '', tsr: 7.64, VS_zeta: !!null '', VS_omega: !!null '', max_torque_rate: 1500000.0, VS_minspd: 0.0, VS_maxspd: 1.26711} - setpoint_smooth: {ss_vsgain: !!null '', ss_pcgain: !!null ''} - shutdown: {limit_type: !!null '', limit_value: !!null ''} -environment: {air_density: 1.225, air_dyn_viscosity: 1.7894e-5, air_speed_sound: 1500.0, shear_exp: 0.0, gravity: 9.80665, weib_shape_parameter: 2.0, water_density: 1025.0, water_dyn_viscosity: 0.0013351, soil_shear_modulus: 140000000.0, soil_poisson: 0.4, water_depth: 50.0, air_pressure: 101325.0, air_vapor_pressure: 2500.0, significant_wave_height: 1.0, significant_wave_period: 5.0} -bos: {plant_turbine_spacing: 7, plant_row_spacing: 7, commissioning_pct: 0.01, decommissioning_pct: 0.15, distance_to_substation: 1.0, distance_to_interconnection: 8.5, interconnect_voltage: 130.0, distance_to_site: 115.0, distance_to_landfall: 50.0, port_cost_per_month: 2000000.0, site_auction_price: 100000000.0, site_assessment_plan_cost: 1000000.0, site_assessment_cost: 25000000.0, construction_operations_plan_cost: 2500000.0, boem_review_cost: 0.0, design_install_plan_cost: 2500000.0} -costs: {wake_loss_factor: 0.15, fixed_charge_rate: 0.056, bos_per_kW: 4053.0, opex_per_kW: 137.0, turbine_number: 40.0, labor_rate: 58.8, painting_rate: 30.0, blade_mass_cost_coeff: 14.6, hub_mass_cost_coeff: 3.9, pitch_system_mass_cost_coeff: 22.1, spinner_mass_cost_coeff: 11.1, lss_mass_cost_coeff: 11.9, bearing_mass_cost_coeff: 4.5, gearbox_mass_cost_coeff: 12.9, hss_mass_cost_coeff: 6.8, generator_mass_cost_coeff: 12.4, bedplate_mass_cost_coeff: 2.9, yaw_mass_cost_coeff: 8.3, converter_mass_cost_coeff: 18.8, transformer_mass_cost_coeff: 18.8, hvac_mass_cost_coeff: 124.0, cover_mass_cost_coeff: 5.7, elec_connec_machine_rating_cost_coeff: 41.85, platforms_mass_cost_coeff: 17.1, tower_mass_cost_coeff: 2.9, controls_machine_rating_cost_coeff: 21.15, crane_cost: 12000.0, electricity_price: 0.04, reserve_margin_price: 120.0, capacity_credit: 0.0, benchmark_price: 0.071} +environment: {air_density: 1.225, air_dyn_viscosity: 1.7894e-5, air_speed_sound: 1500.0, shear_exp: 0.0, gravity: [0,0,-9.81], weib_shape_parameter: 2.0, water_density: 1025.0, water_dyn_viscosity: 0.0013351, soil_shear_modulus: 140000000.0, soil_poisson: 0.4, water_depth: 50.0, air_pressure: 101325.0, air_vapor_pressure: 2500.0, significant_wave_height: 1.0, significant_wave_period: 5.0} \ No newline at end of file diff --git a/examples/Optimization/modeling_options_OWENS_windioExample.yml b/examples/Optimization/modeling_options_OWENS_windioExample.yml index 44a007f7..e659b23d 100644 --- a/examples/Optimization/modeling_options_OWENS_windioExample.yml +++ b/examples/Optimization/modeling_options_OWENS_windioExample.yml @@ -19,12 +19,12 @@ controlParameters: AeroParameters: Nslices: 30 # number of OWENSAero discritizations #TODO: AD parameters ntheta: 30 # number of OWENSAero azimuthal discretizations - AModel: DMS # AD, DMS, AC + AeroModel: DMS # AD, DMS, AC adi_lib: nothing adi_rootname: "/ExampleB" structuralParameters: - structuralModel: GX #GX, TNB, ROM + structuralModel: TNB #GX, TNB, ROM nonlinear: false #TODO: propogate ntelem: 10 #tower elements in each nbelem: 60 #blade elements in each diff --git a/examples/Optimization/optimizationExample.jl b/examples/Optimization/optimizationExample.jl index 4a340b83..bce11fb7 100644 --- a/examples/Optimization/optimizationExample.jl +++ b/examples/Optimization/optimizationExample.jl @@ -31,7 +31,7 @@ # nselem: int, number of strut elements, in the automatically generated mesh # ifw: true or false, tells the AC or DMS models to use constant inflow or to read the specified windINPfilename # WindType: Inflow wind wind type (1 2 3), this is automatically handled by the DLC processor when it is used -# AModel: Aero model, "AC" actuator cylinder (slower but slightly more accurate with array capability at the planar aero only level) "DMS" (faster and nearly as accurate) or "AD" (aerodyn interface, specifically OLAF, which is a relatively slow but higher fidelity vortex line wake model. This includes strut drag and tip losses.) +# AeroModel: Aero model, "AC" actuator cylinder (slower but slightly more accurate with array capability at the planar aero only level) "DMS" (faster and nearly as accurate) or "AD" (aerodyn interface, specifically OLAF, which is a relatively slow but higher fidelity vortex line wake model. This includes strut drag and tip losses.) # windINPfilename: .bts or .inp files, see inflow wind documentation. If running with the DLC script, it will automatically generate these and run with them, and not generate them if they already exist unless told to do so. # ifw_libfile: path to the inflow wind interface library, "nothing" if you are using the one that is automatically build (on mac/linux) with OWENSOpenFASTWrappers.jl # numTS: total number of time steps diff --git a/examples/Optimization/windio_example.jl b/examples/Optimization/windio_example.jl index f29d16ae..99c0fdcb 100644 --- a/examples/Optimization/windio_example.jl +++ b/examples/Optimization/windio_example.jl @@ -16,7 +16,7 @@ # #- #md # !!! tip -#md # This example is also available as a Jupyter notebook todo: get link working: +#md # This example is also available as a Jupyter notebook #- import OWENS @@ -27,11 +27,11 @@ using OrderedCollections runpath = splitdir(@__FILE__)[1] -OWENS_Options = "$runpath/modeling_options_OWENS_windioExample.yml" +OWENS_Options = "$runpath/OWENS_Opt.yml" WINDIO_filename = "$runpath/WINDIO_example.yaml" -OWENS.runOWENSWINDIO(WINDIO_filename,OWENS_Options,runpath) +OWENS.runOWENSWINDIO(OWENS_Options,WINDIO_filename,runpath) # Alternatively OWENS.runOWENSWINDIO(WINDIO_filename,OWENS_Options,runpath) @@ -79,7 +79,7 @@ topDamage_tower_U_UNIT = HDF5.h5read(file,"topDamage_tower_U") topDamage_tower_L_UNIT = HDF5.h5read(file,"topDamage_tower_L") -file = "$runpath/InitialDataOutputs.h5" +file = "./InitialDataOutputs.h5" t = HDF5.h5read(file,"t") aziHist = HDF5.h5read(file,"aziHist") OmegaHist = HDF5.h5read(file,"OmegaHist") @@ -122,11 +122,11 @@ topDamage_blade_L = HDF5.h5read(file,"topDamage_blade_L") topDamage_tower_U = HDF5.h5read(file,"topDamage_tower_U") topDamage_tower_L = HDF5.h5read(file,"topDamage_tower_L") -import PyPlot -PyPlot.pygui(true) -PyPlot.figure() -PyPlot.plot(t_UNIT,FReactionHist_UNIT[:,6]) -PyPlot.plot(t,FReactionHist[:,6]) +# import PyPlot +# PyPlot.pygui(true) +# PyPlot.figure() +# PyPlot.plot(t_UNIT,FReactionHist_UNIT[:,3]) +# PyPlot.plot(t,FReactionHist[:,3]) frac = 1e-5 @test isapprox(t_UNIT,t;atol=maximum(abs.(t_UNIT))*frac) @@ -158,22 +158,22 @@ for i = 1:length(stress_U_UNIT) end end println("Percent Stress Pass: $(ipass/length(stress_U_UNIT)*100)%") -# @test isapprox(SF_ult_U_UNIT,SF_ult_U;atol=maximum(abs.(SF_ult_U_UNIT))*frac) -# @test isapprox(SF_buck_U_UNIT,SF_buck_U;atol=maximum(abs.(SF_buck_U_UNIT))*frac) -# @test isapprox(stress_L_UNIT,stress_L;atol=maximum(abs.(stress_L_UNIT))*frac) -# @test isapprox(SF_ult_L_UNIT,SF_ult_L;atol=maximum(abs.(SF_ult_L_UNIT))*frac) -# @test isapprox(SF_buck_L_UNIT,SF_buck_L;atol=maximum(abs.(SF_buck_L_UNIT))*frac) -# @test isapprox(stress_TU_UNIT,stress_TU;atol=maximum(abs.(stress_TU_UNIT))*frac) -# @test isapprox(SF_ult_TU_UNIT,SF_ult_TU;atol=maximum(abs.(SF_ult_TU_UNIT))*frac) -# @test isapprox(SF_buck_TU_UNIT,SF_buck_TU;atol=maximum(abs.(SF_buck_TU_UNIT))*frac) -# @test isapprox(stress_TL_UNIT,stress_TL;atol=maximum(abs.(stress_TL_UNIT))*frac) -# @test isapprox(SF_ult_TL_UNIT,SF_ult_TL;atol=maximum(abs.(SF_ult_TL_UNIT))*frac) -# @test isapprox(SF_buck_TL_UNIT,SF_buck_TL;atol=maximum(abs.(SF_buck_TL_UNIT))*frac) -# @test isapprox(topstrainout_blade_U_UNIT,topstrainout_blade_U;atol=maximum(abs.(topstrainout_blade_U_UNIT))*frac) -# @test isapprox(topstrainout_blade_L_UNIT,topstrainout_blade_L;atol=maximum(abs.(topstrainout_blade_L_UNIT))*frac) -# @test isapprox(topstrainout_tower_U_UNIT,topstrainout_tower_U;atol=maximum(abs.(topstrainout_tower_U_UNIT))*frac) -# @test isapprox(topstrainout_tower_L_UNIT,topstrainout_tower_L;atol=maximum(abs.(topstrainout_tower_L_UNIT))*frac) -# @test isapprox(topDamage_blade_U_UNIT,topDamage_blade_U;atol=maximum(abs.(topDamage_blade_U_UNIT))*frac) -# @test isapprox(topDamage_blade_L_UNIT,topDamage_blade_L;atol=maximum(abs.(topDamage_blade_L_UNIT))*frac) -# @test isapprox(topDamage_tower_U_UNIT,topDamage_tower_U;atol=maximum(abs.(topDamage_tower_U_UNIT))*frac) -# @test isapprox(topDamage_tower_L_UNIT,topDamage_tower_L;atol=maximum(abs.(topDamage_tower_L_UNIT))*frac) \ No newline at end of file +@test isapprox(SF_ult_U_UNIT,SF_ult_U;atol=maximum(abs.(SF_ult_U_UNIT))*frac) +@test isapprox(SF_buck_U_UNIT,SF_buck_U;atol=maximum(abs.(SF_buck_U_UNIT))*frac) +@test isapprox(stress_L_UNIT,stress_L;atol=maximum(abs.(stress_L_UNIT))*frac) +@test isapprox(SF_ult_L_UNIT,SF_ult_L;atol=maximum(abs.(SF_ult_L_UNIT))*frac) +@test isapprox(SF_buck_L_UNIT,SF_buck_L;atol=maximum(abs.(SF_buck_L_UNIT))*frac) +@test isapprox(stress_TU_UNIT,stress_TU;atol=maximum(abs.(stress_TU_UNIT))*frac) +@test isapprox(SF_ult_TU_UNIT,SF_ult_TU;atol=maximum(abs.(SF_ult_TU_UNIT))*frac) +@test isapprox(SF_buck_TU_UNIT,SF_buck_TU;atol=maximum(abs.(SF_buck_TU_UNIT))*frac) +@test isapprox(stress_TL_UNIT,stress_TL;atol=maximum(abs.(stress_TL_UNIT))*frac) +@test isapprox(SF_ult_TL_UNIT,SF_ult_TL;atol=maximum(abs.(SF_ult_TL_UNIT))*frac) +@test isapprox(SF_buck_TL_UNIT,SF_buck_TL;atol=maximum(abs.(SF_buck_TL_UNIT))*frac) +@test isapprox(topstrainout_blade_U_UNIT,topstrainout_blade_U;atol=maximum(abs.(topstrainout_blade_U_UNIT))*frac) +@test isapprox(topstrainout_blade_L_UNIT,topstrainout_blade_L;atol=maximum(abs.(topstrainout_blade_L_UNIT))*frac) +@test isapprox(topstrainout_tower_U_UNIT,topstrainout_tower_U;atol=maximum(abs.(topstrainout_tower_U_UNIT))*frac) +@test isapprox(topstrainout_tower_L_UNIT,topstrainout_tower_L;atol=maximum(abs.(topstrainout_tower_L_UNIT))*frac) +@test isapprox(topDamage_blade_U_UNIT,topDamage_blade_U;atol=maximum(abs.(topDamage_blade_U_UNIT))*frac) +@test isapprox(topDamage_blade_L_UNIT,topDamage_blade_L;atol=maximum(abs.(topDamage_blade_L_UNIT))*frac) +@test isapprox(topDamage_tower_U_UNIT,topDamage_tower_U;atol=maximum(abs.(topDamage_tower_U_UNIT))*frac) +@test isapprox(topDamage_tower_L_UNIT,topDamage_tower_L;atol=maximum(abs.(topDamage_tower_L_UNIT))*frac) \ No newline at end of file diff --git a/examples/RM2/RM2_Medium.jl b/examples/RM2/RM2_Medium.jl index 7e248a11..2b84a7ed 100644 --- a/examples/RM2/RM2_Medium.jl +++ b/examples/RM2/RM2_Medium.jl @@ -18,6 +18,9 @@ PyPlot.rc("figure",max_open_warning=500) # PyPlot.rc("axes", prop_cycle=["348ABD", "A60628", "009E73", "7A68A6", "D55E00", "CC79A7"]) plot_cycle=["#348ABD", "#A60628", "#009E73", "#7A68A6", "#D55E00", "#CC79A7"] +PyPlot.figure() +PyPlot.plot(LinRange(0,1,10),LinRange(0,1,10)) + # function runprofilefunction() path = runpath = splitdir(@__FILE__)[1] @@ -41,7 +44,7 @@ nbelem = 30 ncelem = 10 nselem = 10 ifw = false -AModel = "DMS" +AeroModel = "DMS" windINPfilename = "$path/300mx300m12msETM_Coarse.bts" ifw_libfile = nothing#"$path/../../openfast/build/modules/inflowwind/libifw_c_binding" Blade_Height = 0.807 @@ -126,8 +129,8 @@ mass_breakout_blds,mass_breakout_twr,system,assembly,sections,AD15bldNdIdxRng, A c_mount_ratio = 0.05, strut_twr_mountpoint = [0.5], strut_bld_mountpoint = [0.5], - AModel, #AD, DMS, AC - DSModel="BV", + AeroModel, #AD, DMS, AC + DynamicStallModel="BV", Aero_AddedMass_Active = false, Aero_RotAccel_Active = false, AddedMass_Coeff_Ca, @@ -184,13 +187,13 @@ nothing # There are inputs for the overall coupled simulation, please see the api reference for specifics on all the options -if AModel=="AD" +if AeroModel=="AD" AD15On = true else AD15On = false end -inputs = OWENS.Inputs(;analysisType = structuralModel, +inputs = OWENS.Inputs(;verbosity,analysisType = structuralModel, tocp, Omegaocp, tocp_Vinf, @@ -204,8 +207,8 @@ nothing # Then there are inputs for the finite element models, also, please see the api reference for specifics on the options (TODO: ensure that this is propogated to the docs) -feamodel = OWENS.FEAModel(;analysisType = structuralModel, -outFilename = "none", +FEAinputs = OWENS.FEAModel(;analysisType = structuralModel, +dataOutputFilename = "none", joint = myjoint, platformTurbineConnectionNodeNumber = 1, pBC, @@ -227,7 +230,7 @@ t, aziHist,OmegaHist,OmegaDotHist,gbHist,gbDotHist,gbDotDotHist,FReactionHist, FTwrBsHist,genTorque,genPower,torqueDriveShaft,uHist,uHist_prp,epsilon_x_hist,epsilon_y_hist, epsilon_z_hist,kappa_x_hist,kappa_y_hist,kappa_z_hist,FPtfmHist,FHydroHist,FMooringHist, topFexternal_hist,rbDataHist = OWENS.Unsteady_Land(inputs;system,assembly, -topModel=feamodel,topMesh=mymesh,topEl=myel,aero=aeroForces,deformAero) +topModel=FEAinputs,topMesh=mymesh,topEl=myel,aero=aeroForces,deformAero) CP = mean(FReactionHist[:,6].*OmegaHist*2*pi)/(0.5*fluid_density*mean(Vinfocp)^3*area) TSR = mean(OmegaHist*2*pi*Blade_Radius/mean(Vinfocp)) @@ -239,9 +242,9 @@ nothing # for example, strain, or reaction force, etc. This is described in more detail in the api reference for the function and: TODO azi=aziHist#./aziHist*1e-6 -saveName = "$path/vtk/RM2_medium" +VTKsaveName = "$path/vtk/RM2_medium" tsave_idx=1:1:numTS-1 -OWENS.OWENSVTK(saveName,t,uHist,system,assembly,sections,aziHist,mymesh,myel, +OWENS.OWENSVTK(VTKsaveName,t,uHist,system,assembly,sections,aziHist,mymesh,myel, epsilon_x_hist,epsilon_y_hist,epsilon_z_hist,kappa_x_hist,kappa_y_hist,kappa_z_hist, FReactionHist,topFexternal_hist;tsave_idx) @@ -271,4 +274,67 @@ AD15bldNdIdxRng,AD15bldElIdxRng,strut_precompoutput=nothing) #TODO: add in abili # ffmpeg -i smallerhelical.%04d.png -vf palettegen=reserve_transparent=1 palette.png # ffmpeg -framerate 30 -i smallerhelical.%04d.png -i palette.png -lavfi paletteuse=alpha_threshold=30 -gifflags -offsetting smallerhelical.gif -nothing \ No newline at end of file +nothing + + + +starttime2 = time() +FEAinputs.analysisType = "GX" +freq2 = OWENS.AutoCampbellDiagram(FEAinputs,mymesh,myel,system,assembly,sections; + minRPM = 0.0, + maxRPM = 42.6, + NRPM = 2, # int + VTKsavename="$path/campbellVTK/SNL34m", + saveModes = [1,2,3,4,5], #must be int + saveRPM = [2], #must be int + mode_scaling = 500.0, + ) +freqGX = [freq2[:,i] for i=1:2:FEAinputs.numModes-6-2] +elapsedtime2 = time() - starttime2 + + +# import PyPlot +# PyPlot.close("all") +# PyPlot.pygui(true) +# PyPlot.rc("figure", figsize=(4.5, 3)) +# PyPlot.rc("font", size=10.0) +# PyPlot.rc("lines", linewidth=1.5) +# PyPlot.rc("lines", markersize=4.0) +# PyPlot.rc("legend", frameon=true) +# PyPlot.rc("axes.spines", right=false, top=false) +# PyPlot.rc("figure.subplot", left=.18, bottom=.17, top=0.9, right=.9) +# PyPlot.rc("figure",max_open_warning=500) +# # PyPlot.rc("axes", prop_cycle=["348ABD", "A60628", "009E73", "7A68A6", "D55E00", "CC79A7"]) +# plot_cycle=["#348ABD", "#A60628", "#009E73", "#7A68A6", "#D55E00", "#CC79A7"] + +# NperRevLines = 8 +# rotSpdArrayRPM = LinRange(0.0, 40.0, 9) # int +# PyPlot.figure() +# for i=1:1:FEAinputs.numModes-2 +# PyPlot.plot(rotSpdArrayRPM,freq[:,i],color=plot_cycle[1],"-") #plot mode i at various rotor speeds +# end + +# #plot per rev lines +# for i=1:NperRevLines +# linex=[rotSpdArrayRPM[1], rotSpdArrayRPM[end]+5] +# liney=[rotSpdArrayRPM[1], rotSpdArrayRPM[end]+5].*i./60.0 +# PyPlot.plot(linex,liney,"--k",linewidth=0.5) +# PyPlot.annotate("$i P",xy=(0.95*linex[2],liney[2]+.05+(i-1)*.01)) +# end +# PyPlot.grid() +# PyPlot.xlabel("Rotor Speed (RPM)") +# PyPlot.ylabel("Frequency (Hz)") +# PyPlot.plot(0,0,"k-",label="Experimental") +# PyPlot.plot(0,0,color=plot_cycle[1],"-",label="OWENS") +# PyPlot.legend() +# # PyPlot.ylim([0.0,0.8]) +# # PyPlot.savefig("$(path)/../figs/34mCampbell.pdf",transparent = true) + +# # Add to figure +# for i=1:2:FEAinputs.numModes-6-2 +# PyPlot.plot(rotSpdArrayRPM,freq2[:,i],color=plot_cycle[2],"-") #plot mode i at various rotor speeds +# end +# PyPlot.plot(0,0,color=plot_cycle[2],"-",label="GXBeam") +# PyPlot.legend(fontsize=8.5,loc = (0.09,0.8),ncol=2,handleheight=1.8, labelspacing=0.03) +# PyPlot.ylim([0,6.01]) +# # PyPlot.savefig("$(path)/../figs/34mCampbellWGX.pdf",transparent = true) diff --git a/examples/RM2/modeling_options_OWENS_RM2.yml b/examples/RM2/modeling_options_OWENS_RM2.yml index 0eb95e43..1f86157e 100644 --- a/examples/RM2/modeling_options_OWENS_RM2.yml +++ b/examples/RM2/modeling_options_OWENS_RM2.yml @@ -19,7 +19,7 @@ controlParameters: AeroParameters: Nslices: 30 # number of OWENSAero discritizations #TODO: AD parameters ntheta: 30 # number of OWENSAero azimuthal discretizations - AModel: AD # AD, DMS, AC + AeroModel: AD # AD, DMS, AC adi_lib: nothing adi_rootname: "/RM2" diff --git a/examples/SNL34m/Example34mHVAWTConfiguration.jl b/examples/SNL34m/Example34mHVAWTConfiguration.jl index 7b36db74..64cef1af 100644 --- a/examples/SNL34m/Example34mHVAWTConfiguration.jl +++ b/examples/SNL34m/Example34mHVAWTConfiguration.jl @@ -49,7 +49,7 @@ nbelem = Inp.nbelem ncelem = Inp.ncelem nselem = Inp.nselem ifw = Inp.ifw -AModel = Inp.AModel +AeroModel = Inp.AeroModel windINPfilename = "$(path)$(Inp.windINPfilename)" ifw_libfile = Inp.ifw_libfile if ifw_libfile == "nothing" @@ -148,8 +148,8 @@ mass_breakout_blds,mass_breakout_twr,system, assembly, sections,AD15bldNdIdxRng, joint_type = 0, strut_twr_mountpoint = [0.25,0.75], strut_bld_mountpoint = [0.26,0.74], - AModel, #AD, DMS, AC - DSModel="BV", + AeroModel, #AD, DMS, AC + DynamicStallModel="BV", RPI=true, cables_connected_to_blade_base = true, angularOffset = pi/2, @@ -168,13 +168,13 @@ top_idx 3 0 top_idx 4 0 top_idx 5 0] -if AModel=="AD" +if AeroModel=="AD" AD15On = true else AD15On = false end -inputs = OWENS.Inputs(;analysisType = structuralModel, +inputs = OWENS.Inputs(;verbosity,analysisType = structuralModel, tocp, Omegaocp, tocp_Vinf, @@ -462,5 +462,5 @@ for it = 1:length(t) end azi=aziHist#./aziHist*1e-6 -saveName = "$path/vtk/SNL34mVAWTNormalOperation" -OWENS.OWENSFEA_VTK(saveName,t,uHist,system,assembly,sections;scaling=1,azi,userPointNames,userPointData) +VTKsaveName = "$path/vtk/SNL34mVAWTNormalOperation" +OWENS.OWENSFEA_VTK(VTKsaveName,t,uHist,system,assembly,sections;scaling=1,azi,userPointNames,userPointData) diff --git a/examples/SNL34m/Fig4.1Gravity_Fig4.4_Steady40RPMCentrifugalGX.jl b/examples/SNL34m/Fig4.1Gravity_Fig4.4_Steady40RPMCentrifugalGX.jl index c7bc0e86..02b2a30c 100644 --- a/examples/SNL34m/Fig4.1Gravity_Fig4.4_Steady40RPMCentrifugalGX.jl +++ b/examples/SNL34m/Fig4.1Gravity_Fig4.4_Steady40RPMCentrifugalGX.jl @@ -32,7 +32,7 @@ nbelem = 60 ncelem = 10 nselem = 5 ifw = false -AModel = "DMS" +AeroModel = "DMS" windINPfilename = nothing ifw_libfile = nothing Blade_Height = 41.9 @@ -104,8 +104,8 @@ mass_breakout_blds,mass_breakout_twr,system, assembly, sections,AD15bldNdIdxRng, joint_type = 0, strut_twr_mountpoint = [0.03,0.97], strut_bld_mountpoint = [0.03,0.97], - AModel, #AD, DMS, AC - DSModel="BV", + AeroModel, #AD, DMS, AC + DynamicStallModel="BV", RPI=true, cables_connected_to_blade_base = true, angularOffset = pi/2, @@ -157,8 +157,8 @@ top_idx 3 0 top_idx 4 0 top_idx 5 0] -model = OWENS.Inputs(;analysisType = "TNB", -outFilename = "none", +model = OWENS.Inputs(;verbosity,analysisType = "TNB", +dataOutputFilename = "none", tocp = [0.0, 1e6],#SNL34m_5_3_RPM[:,1],#[0.0,10.0,100000.1], Omegaocp = [0.0, 0.0]./60,#SNL34m_5_3_RPM[:,2]./ 60,#[RPM,RPM,RPM] ./ 60, tocp_Vinf = [0.0, 1e6], @@ -313,8 +313,8 @@ for it = 1:length(t) end azi=aziHist#./aziHist*1e-6 -saveName = "$path/vtk/two_blade" -OWENS.OWENSFEA_VTK(saveName,t,uHist,system,assembly,sections;scaling=1,azi,userPointNames,userPointData) +VTKsaveName = "$path/vtk/two_blade" +OWENS.OWENSFEA_VTK(VTKsaveName,t,uHist,system,assembly,sections;scaling=1,azi,userPointNames,userPointData) ################################################################## ########### FIG 4.4 40RPM with Gravity Loads Tared out ########## @@ -388,8 +388,8 @@ PyPlot.plot(t,FReactionHist[:,6]) # Nslices, # ifw = false, # RPI = true, -# DSModel = "BV", -# AModel = "DMS", +# DynamicStallModel = "BV", +# AeroModel = "DMS", # tau = [1e-5,1e-5], # afname = airfoils) @@ -399,7 +399,7 @@ PyPlot.plot(t,FReactionHist[:,6]) # deformTurb(azi_j;newOmega=0,newVinf=0,bld_x=0,bld_z=0,bld_twist=0) = 0 model = OWENS.Inputs(;analysisType = "GX", -outFilename = "none", +dataOutputFilename = "none", tocp = [0.0, 1e6],#SNL34m_5_3_RPM[:,1],#[0.0,10.0,100000.1], Omegaocp = [0.0, 0.0]./60,#SNL34m_5_3_RPM[:,2]./ 60,#[RPM,RPM,RPM] ./ 60, tocp_Vinf = [0.0, 1e6], diff --git a/examples/SNL34m/Fig5_11_EmergStop_torque_flatwise.jl b/examples/SNL34m/Fig5_11_EmergStop_torque_flatwise.jl index 7fb2291a..0c155101 100644 --- a/examples/SNL34m/Fig5_11_EmergStop_torque_flatwise.jl +++ b/examples/SNL34m/Fig5_11_EmergStop_torque_flatwise.jl @@ -48,7 +48,7 @@ nbelem = 60 ncelem = 10 nselem = 5 ifw = false -AModel = "DMS" +AeroModel = "DMS" windINPfilename = nothing ifw_libfile = nothing Blade_Height = 41.9 @@ -174,8 +174,8 @@ mass_breakout_blds,mass_breakout_twr,system, assembly, sections,AD15bldNdIdxRng, joint_type = 0, strut_twr_mountpoint = [0.03,0.97], strut_bld_mountpoint = [0.03,0.97], - AModel, #AD, DMS, AC - DSModel="BV", + AeroModel, #AD, DMS, AC + DynamicStallModel="BV", RPI=true, cables_connected_to_blade_base = true, angularOffset = pi/2, @@ -229,8 +229,8 @@ top_idx 5 0] Omegaocp = [new_RPM[1]; new_RPM; new_RPM[end]]./60 -model = OWENS.Inputs(;analysisType = "ROM", - outFilename = "none", +model = OWENS.Inputs(;verbosity,analysisType = "ROM", + dataOutputFilename = "none", tocp = [0.0; new_t.+offsetTime; 1e6],#SNL34m_5_11_RPM[:,1],#[0.0,10.0,100000.1], Omegaocp,#SNL34m_5_11_RPM[:,2]./ 60,#[RPM,RPM,RPM] ./ 60, tocp_Vinf = t_Vinf, diff --git a/examples/SNL34m/Fig5_4_Fig5_3_normaloperation_torque_flatwise_generatorControl.jl b/examples/SNL34m/Fig5_4_Fig5_3_normaloperation_torque_flatwise_generatorControl.jl index f6eeaa4d..1ba8edc4 100644 --- a/examples/SNL34m/Fig5_4_Fig5_3_normaloperation_torque_flatwise_generatorControl.jl +++ b/examples/SNL34m/Fig5_4_Fig5_3_normaloperation_torque_flatwise_generatorControl.jl @@ -43,7 +43,7 @@ nbelem = 60 ncelem = 10 nselem = 5 ifw = false -AModel = "DMS" +AeroModel = "DMS" windINPfilename = nothing ifw_libfile = nothing Blade_Height = 41.9 @@ -169,8 +169,8 @@ mass_breakout_blds,mass_breakout_twr,system, assembly, sections,AD15bldNdIdxRng, joint_type = 0, strut_twr_mountpoint = [0.03,0.97], strut_bld_mountpoint = [0.03,0.97], - AModel, #AD, DMS, AC - DSModel="BV", + AeroModel, #AD, DMS, AC + DynamicStallModel="BV", RPI=true, cables_connected_to_blade_base = true, angularOffset = pi/2, @@ -218,8 +218,8 @@ Omegaocp = [new_RPM[1]; new_RPM; new_RPM[end]]./60 .*0 .+33.92871/60 tocp_Vinf = [0.0;t_Vinf.+offsetTime; 1e6] Vinfocp = [Vinf_spec[1];Vinf_spec;Vinf_spec[end]].*1e-6 -model = OWENS.Inputs(;analysisType = "ROM", - outFilename = "none", +model = OWENS.Inputs(;verbosity,analysisType = "ROM", + dataOutputFilename = "none", tocp = [0.0;new_t.+offsetTime; 1e6],#SNL34m_5_3_RPM[:,1],#[0.0,10.0,100000.1], Omegaocp,#SNL34m_5_3_RPM[:,2]./ 60,#[RPM,RPM,RPM] ./ 60, tocp_Vinf, diff --git a/examples/SNL34m/SNL34mVAWTNormalOperation.jl b/examples/SNL34m/SNL34mVAWTNormalOperation.jl index 3c8ad510..e899b5dc 100644 --- a/examples/SNL34m/SNL34mVAWTNormalOperation.jl +++ b/examples/SNL34m/SNL34mVAWTNormalOperation.jl @@ -49,7 +49,7 @@ nbelem = Inp.nbelem ncelem = Inp.ncelem nselem = Inp.nselem ifw = Inp.ifw -AModel = Inp.AModel +AeroModel = Inp.AeroModel windINPfilename = "$(path)$(Inp.windINPfilename)" ifw_libfile = Inp.ifw_libfile if ifw_libfile == "nothing" @@ -153,8 +153,8 @@ mass_breakout_blds,mass_breakout_twr,system, assembly, sections,AD15bldNdIdxRng, joint_type = 0, strut_twr_mountpoint = [0.03,0.97], strut_bld_mountpoint = [0.03,0.97], - AModel, #AD, DMS, AC - DSModel="BV", + AeroModel, #AD, DMS, AC + DynamicStallModel="BV", RPI=true, cables_connected_to_blade_base = true, angularOffset = pi/2, @@ -308,13 +308,13 @@ top_idx 3 0 top_idx 4 0 top_idx 5 0] -if AModel=="AD" +if AeroModel=="AD" AD15On = true else AD15On = false end -inputs = OWENS.Inputs(;analysisType = structuralModel, +inputs = OWENS.Inputs(;verbosity,analysisType = structuralModel, tocp, Omegaocp, tocp_Vinf, @@ -603,5 +603,5 @@ for it = 1:length(t) end azi=aziHist#./aziHist*1e-6 -saveName = "$path/vtk/SNL34mVAWTNormalOperation" -# OWENS.OWENSFEA_VTK(saveName,t,uHist,system,assembly,sections;scaling=1,azi,userPointNames,userPointData) +VTKsaveName = "$path/vtk/SNL34mVAWTNormalOperation" +# OWENS.OWENSFEA_VTK(VTKsaveName,t,uHist,system,assembly,sections;scaling=1,azi,userPointNames,userPointData) diff --git a/examples/SNL34m/SNL34m_Inputs.yml b/examples/SNL34m/SNL34m_Inputs.yml index 770c0ac6..b9752779 100644 --- a/examples/SNL34m/SNL34m_Inputs.yml +++ b/examples/SNL34m/SNL34m_Inputs.yml @@ -30,7 +30,7 @@ controlParameters: AeroParameters: Nslices: 35 # number of OWENSAero discritizations #TODO: AD parameters ntheta: 30 # number of OWENSAero azimuthal discretizations - AModel: DMS # AD, DMS, AC + AeroModel: DMS # AD, DMS, AC adi_lib: nothing adi_rootname: "/SNL34m" diff --git a/examples/SNL34m/SNL34m_InputsAeroDyn.yml b/examples/SNL34m/SNL34m_InputsAeroDyn.yml index d27d6571..6af1f20d 100644 --- a/examples/SNL34m/SNL34m_InputsAeroDyn.yml +++ b/examples/SNL34m/SNL34m_InputsAeroDyn.yml @@ -30,7 +30,7 @@ controlParameters: AeroParameters: Nslices: 35 # number of OWENSAero discritizations #TODO: AD parameters ntheta: 30 # number of OWENSAero azimuthal discretizations - AModel: AD # AD, DMS, AC + AeroModel: AD # AD, DMS, AC adi_lib: nothing adi_rootname: "/SNL34m" diff --git a/examples/SNL34m/TSR_CP_2way_Aerostructural.jl b/examples/SNL34m/TSR_CP_2way_Aerostructural.jl index 559efa54..c38b2248 100644 --- a/examples/SNL34m/TSR_CP_2way_Aerostructural.jl +++ b/examples/SNL34m/TSR_CP_2way_Aerostructural.jl @@ -48,7 +48,7 @@ nbelem = 60 ncelem = 10 nselem = 5 ifw = false -AModel = "DMS" +AeroModel = "DMS" windINPfilename = "$(path)/data/turbsim/115mx115m_30x30_20.0msETM.bts" ifw_libfile = nothing Blade_Height = 41.9 @@ -146,8 +146,8 @@ mass_breakout_blds,mass_breakout_twr,system, assembly, sections,AD15bldNdIdxRng, joint_type = 0, strut_twr_mountpoint = [0.03,0.97], strut_bld_mountpoint = [0.03,0.97], - AModel, #AD, DMS, AC - DSModel="BV", + AeroModel, #AD, DMS, AC + DynamicStallModel="BV", RPI=true, cables_connected_to_blade_base = true, angularOffset = pi/2, @@ -170,13 +170,13 @@ top_idx 3 0 top_idx 4 0 top_idx 5 0] -if AModel=="AD" +if AeroModel=="AD" AD15On = true else AD15On = false end -inputs = OWENS.Inputs(;analysisType = structuralModel, +inputs = OWENS.Inputs(;verbosity,analysisType = structuralModel, tocp, Omegaocp, tocp_Vinf, @@ -238,8 +238,8 @@ topModel=feamodel,topMesh=mymesh,topEl=myel,aero=aeroForces,deformAero,system,as # Nslices, # RPI=true, # ifw = false, -# DSModel = "BV", -# AModel = "DMS", +# DynamicStallModel = "BV", +# AeroModel = "DMS", # tau = [1e-5,1e-5], # afname = airfoils) diff --git a/examples/SNL5MW/ExampleSNL5MW_turbulent.jl b/examples/SNL5MW/ExampleSNL5MW_turbulent.jl index bf307520..a4882155 100644 --- a/examples/SNL5MW/ExampleSNL5MW_turbulent.jl +++ b/examples/SNL5MW/ExampleSNL5MW_turbulent.jl @@ -27,6 +27,7 @@ import Composites path,_ = splitdir(@__FILE__) println("Set up Macro Geometry/Inputs") +verbosity=2 rho = 1.225 Nslices = 30 ntheta = 30 @@ -47,10 +48,10 @@ delta_t = 0.05 simtime = 6.0 numTS = simtime/delta_t -AModel = "AD" +AeroModel = "AD" turbineType = "Darrieus" -if AModel=="AD" #TODO: unify flag +if AeroModel=="AD" #TODO: unify flag AD15On=true #AD for AeroDyn, DMS for double multiple streamtube, AC for actuator cylinder else AD15On=false @@ -90,7 +91,7 @@ delta3D = atan.(delta_xs./delta_zs) # ### Set up aero forces # ######################################### # println("Initialize Aerodynamics") -# OWENSAero.setupTurb(shapeX,shapeZ,B,chord,tsr,Vinf;AModel="DMS",DSModel="BV", +# OWENSAero.setupTurb(shapeX,shapeZ,B,chord,tsr,Vinf;AeroModel="DMS",DynamicStallModel="BV", # afname = "$(path)/airfoils/NACA_0021.dat", # ifw=false, # ifw_libfile = nothing, @@ -258,13 +259,13 @@ mass_breakout_blds,mass_breakout_twr,system, assembly, sections,AD15bldNdIdxRng, joint_type = 0, strut_twr_mountpoint = [0.1,0.9], strut_bld_mountpoint = [0.1,0.9], - AModel, #AD, DMS, AC - DSModel="BV", + AeroModel, #AD, DMS, AC + DynamicStallModel="BV", RPI=true, cables_connected_to_blade_base = true, angularOffset = pi/2, meshtype = turbineType, - verbosity=2) + verbosity) ###################################### @@ -278,7 +279,7 @@ pBC = [1 1 0 1 5 0 1 6 0] -model = OWENS.Inputs(;analysisType = "GX", +model = OWENS.Inputs(;verbosity,analysisType = "GX", tocp = [0.0,100000.1], Omegaocp = [RPM,RPM] ./ 60, tocp_Vinf = [0.0,100000.1], @@ -289,7 +290,7 @@ delta_t, aeroLoadsOn = 2) feamodel = OWENSFEA.FEAModel(;analysisType = "GX", -outFilename = "none", +dataOutputFilename = "none", joint = myjoint, platformTurbineConnectionNodeNumber = 1, pBC, @@ -308,8 +309,8 @@ epsilon_z_hist,kappa_x_hist,kappa_y_hist,kappa_z_hist,FPtfmHist,FHydroHist,FMoor topFexternal_hist,rbDataHist = OWENS.Unsteady_Land(model; topModel=feamodel,topMesh=mymesh,topEl=myel,aero=aeroForces,deformAero,system,assembly) -saveName = "$path/vtk/SNL5MW_timedomain" -OWENS.OWENSVTK(saveName,t,uHist,system,assembly,sections,aziHist,mymesh,myel,epsilon_x_hist,epsilon_y_hist,epsilon_z_hist,kappa_x_hist,kappa_y_hist,kappa_z_hist,FReactionHist,topFexternal_hist) +VTKsaveName = "$path/vtk/SNL5MW_timedomain" +OWENS.OWENSVTK(VTKsaveName,t,uHist,system,assembly,sections,aziHist,mymesh,myel,epsilon_x_hist,epsilon_y_hist,epsilon_z_hist,kappa_x_hist,kappa_y_hist,kappa_z_hist,FReactionHist,topFexternal_hist) ########################################## #### Get strain values at the blades ##### diff --git a/examples/dev/OptimizationExample.jl b/examples/dev/OptimizationExample.jl index 4978b05f..0cfcd357 100644 --- a/examples/dev/OptimizationExample.jl +++ b/examples/dev/OptimizationExample.jl @@ -74,7 +74,7 @@ nbelem = Inp.nbelem ncelem = Inp.ncelem nselem = Inp.nselem ifw = Inp.ifw -AModel = Inp.AModel +AeroModel = Inp.AeroModel windINPfilename = Inp.windINPfilename ifw_libfile = Inp.ifw_libfile Blade_Height = Inp.Blade_Height @@ -156,8 +156,8 @@ mass_breakout_blds,mass_breakout_twr,system, assembly, sections = OWENS.setupOWE joint_type = 0, strut_twr_mountpoint = [0.1,0.9], strut_bld_mountpoint = [0.05,0.95], - AModel, #AD, DMS, AC - DSModel="BV", + AeroModel, #AD, DMS, AC + DynamicStallModel="BV", RPI=true, cables_connected_to_blade_base = true, angularOffset = pi/2, @@ -176,13 +176,13 @@ top_idx 3 0 top_idx 4 0 top_idx 5 0] -if AModel=="AD" +if AeroModel=="AD" AD15On = true else AD15On = false end -inputs = OWENS.Inputs(;analysisType = structuralModel, +inputs = OWENS.Inputs(;verbosity,analysisType = structuralModel, tocp, Omegaocp, tocp_Vinf, diff --git a/examples/dev/RM2.jl b/examples/dev/RM2.jl index 3eea4ed7..2017569a 100644 --- a/examples/dev/RM2.jl +++ b/examples/dev/RM2.jl @@ -71,7 +71,7 @@ nbelem = Inp.nbelem ncelem = Inp.ncelem nselem = Inp.nselem ifw = Inp.ifw -AModel = Inp.AModel +AeroModel = Inp.AeroModel windINPfilename = Inp.windINPfilename ifw_libfile = Inp.ifw_libfile Blade_Height = Inp.Blade_Height @@ -154,8 +154,8 @@ mass_breakout_blds,mass_breakout_twr,system, assembly, sections,AD15bldNdIdxRng, joint_type = 0, strut_twr_mountpoint = [0.1,0.9], strut_bld_mountpoint = [0.05,0.95], - AModel, #AD, DMS, AC - DSModel="BV", + AeroModel, #AD, DMS, AC + DynamicStallModel="BV", RPI=true, Aero_AddedMass_Active = true, Aero_RotAccel_Active = true, @@ -177,13 +177,13 @@ top_idx 3 0 top_idx 4 0 top_idx 5 0] -if AModel=="AD" +if AeroModel=="AD" AD15On = true else AD15On = false end -inputs = OWENS.Inputs(;analysisType = structuralModel, +inputs = OWENS.Inputs(;verbosity,analysisType = structuralModel, tocp, Omegaocp, tocp_Vinf, @@ -287,8 +287,8 @@ for it = 1:length(t) end azi=aziHist#./aziHist*1e-6 -saveName = "$path/vtk/RM2" -OWENS.OWENSFEA_VTK(saveName,t,uHist,system,assembly,sections;scaling=1,azi,userPointNames,userPointData) +VTKsaveName = "$path/vtk/RM2" +OWENS.OWENSFEA_VTK(VTKsaveName,t,uHist,system,assembly,sections;scaling=1,azi,userPointNames,userPointData) # Open Paraview, open animation pane, adjust as desired, export animation (which exports frames) # ffmpeg -i Ux.%04d.png -vcodec libx264 -vf "pad=ceil(iw/2)*2:ceil(ih/2)*2" -r 24 -y -an -pix_fmt yuv420p video34m34RPM_Ux.mp4 diff --git a/examples/dev/RM2_OWENS_modeling_options.yaml b/examples/dev/RM2_OWENS_modeling_options.yaml index b9efe61e..bf320d55 100644 --- a/examples/dev/RM2_OWENS_modeling_options.yaml +++ b/examples/dev/RM2_OWENS_modeling_options.yaml @@ -29,7 +29,7 @@ controlParameters: AeroParameters: Nslices: 35 # number of OWENSAero discritizations #TODO: AD parameters ntheta: 30 # number of OWENSAero azimuthal discretizations - AModel: DMS # AD, DMS, AC + AeroModel: DMS # AD, DMS, AC adi_lib: "/Users/kevmoor/Documents/coderepos/openfast/build/modules/aerodyn/libaerodyn_inflow_c_binding" adi_rootname: "./SNL34m" diff --git a/examples/helical_riverine/helical_riverine_driver.jl b/examples/helical_riverine/helical_riverine_driver.jl index 76b477c2..d5390756 100644 --- a/examples/helical_riverine/helical_riverine_driver.jl +++ b/examples/helical_riverine/helical_riverine_driver.jl @@ -8,8 +8,6 @@ using Statistics:mean using Test import HDF5 import YAML -using StructTypes -import OrderedCollections import PyPlot PyPlot.pygui(true) @@ -48,7 +46,7 @@ nbelem = 60 ncelem = 10 nselem = 5 ifw = false -AModel = "AD" +AeroModel = "AD" windINPfilename = "$path/300mx300m12msETM_Coarse.bts" ifw_libfile = nothing#"$path/../../openfast/build/modules/inflowwind/libifw_c_binding" Blade_Height = 41.9 @@ -116,8 +114,8 @@ mass_breakout_blds,mass_breakout_twr,system, assembly, sections,AD15bldNdIdxRng, joint_type = 0, strut_twr_mountpoint = [0.1,0.5,0.9], strut_bld_mountpoint = [0.05,0.5,0.95], - AModel, #AD, DMS, AC - DSModel="BV", + AeroModel, #AD, DMS, AC + DynamicStallModel="BV", RPI=true, cables_connected_to_blade_base = true, angularOffset = 0.0,#pi/2, @@ -154,13 +152,13 @@ top_idx 3 0 top_idx 4 0 top_idx 5 0] -if AModel=="AD" +if AeroModel=="AD" AD15On = true else AD15On = false end -inputs = OWENS.Inputs(;analysisType = structuralModel, +inputs = OWENS.Inputs(;verbosity,analysisType = structuralModel, tocp, Omegaocp, tocp_Vinf, @@ -264,8 +262,8 @@ for it = 1:length(t) end azi=aziHist#./aziHist*1e-6 -saveName = "$path/vtk/helical" -OWENS.OWENSFEA_VTK(saveName,t,uHist,system,assembly,sections;scaling=1,azi,userPointNames,userPointData) +VTKsaveName = "$path/vtk/helical" +OWENS.OWENSFEA_VTK(VTKsaveName,t,uHist,system,assembly,sections;scaling=1,azi,userPointNames,userPointData) # Open Paraview, open animation pane, adjust as desired, export animation (which exports frames) # ffmpeg -i Ux.%04d.png -vcodec libx264 -vf "pad=ceil(iw/2)*2:ceil(ih/2)*2" -r 24 -y -an -pix_fmt yuv420p video34m34RPM_Ux.mp4 diff --git a/examples/literate/A_simplyRunningOWENS.jl b/examples/literate/A_simplyRunningOWENS.jl index 51a13901..c9109195 100644 --- a/examples/literate/A_simplyRunningOWENS.jl +++ b/examples/literate/A_simplyRunningOWENS.jl @@ -10,13 +10,12 @@ # common use cases for which helper functions have been developed, such as for meshing certain standard architectures # and calculating and applying sectional properties to these architectures. The figure below summarizes this at a high # level. -# TODO: yml file definition and inputs expanded # # ![](../assets/OWENS_Example_Figure_Building_Blocks.png) # #- #md # !!! tip -#md # This example is also available as a Jupyter notebook todo: get link working: +#md # This example is also available as a Jupyter notebook #- import OWENS @@ -24,45 +23,18 @@ import OWENS runpath = path = "/home/runner/work/OWENS.jl/OWENS.jl/examples/literate" # to run locally, change to splitdir(@__FILE__)[1] ##runpath = path = splitdir(@__FILE__)[1] -Inp = OWENS.MasterInput("$runpath/sampleOWENS.yml") +modelopt = OWENS.ModelingOptions("$(path)/OWENS_Opt.yml") +designparams = OWENS.Design_Data("$path/WINDIO_example.yaml") -OWENS.runOWENS(Inp,runpath) +OWENS.runOWENSWINDIO(modelopt,designparams,runpath) # Here is an example of using the same model against the automated DLC run script. TODO: memory issue with running DLC with AeroDyn multiple times. # Note that for a setup cutom to a specific design, you'll want to go to the B level to get all of the detailed inputs correct # One of these is the controller where a discon controller library can be coupled instead of the specified RPM control. -DLCs = ["1_1"] #"normal" -#### DLCs = ["1_3"] #"normal" -#### DLCs = ["1_4"] #"normal" -#### DLCs = ["1_5"] #"normal" -#### DLCs = ["2_1"] #"freewheelatNormalOperatingRPM" -#### DLCs = ["2_3"] #"freewheelatNormalOperatingRPM" -#### DLCs = ["3_1"] #"startup" -#### DLCs = ["3_2"] #"startup" -#### DLCs = ["3_3"] #"startup" -#### DLCs = ["4_1"] #"shutdown" -#### DLCs = ["4_2"] #"shutdown" -#### DLCs = ["5_1"] #"emergencyshutdown" -#### DLCs = ["6_1"] #"parked" -#### DLCs = ["6_2"] #"parked_idle" -#### DLCs = ["6_4"] #"parked" -#### DLCs = ["7_1"] #"parked" -#### DLCs = ["2_3","3_1","3_2","3_3","4_1","4_2","5_1"] +modelopt.DLC_Options.DLCs = ["1_1"] #"normal" +#### modelopt.DLC_Options.DLCs = ["1_3","6_1"] #"normal" -OWENS.runDLC(DLCs,Inp,runpath; - IEC_std="\"1-ED3\"", - WindChar="\"A\"", - WindClass=1, - NumGrid_Z=38, - NumGrid_Y=26, - Vdesign=11.0, - grid_oversize=1.25, - Vinf_range=[10.0,15.0],#LinRange(4,24,21), - regenWindFiles=true, - delta_t_turbsim=0.05, - simtime_turbsim=30.0, - pathtoturbsim=nothing, - runScript=OWENS.runOWENS) +OWENS.runDLC(modelopt,designparams,runpath) nothing \ No newline at end of file diff --git a/examples/literate/B_detailedInputs.jl b/examples/literate/B_detailedInputs.jl index 0e1078ec..ab0a55a4 100644 --- a/examples/literate/B_detailedInputs.jl +++ b/examples/literate/B_detailedInputs.jl @@ -5,7 +5,7 @@ # input file currently allows, but your design still fits within the setupOWENS helper function etc. #- #md # !!! tip -#md # This example is also available as a Jupyter notebook todo: get link working: +#md # This example is also available as a Jupyter notebook #- # First we import the packages. If "using" was employed, then all of the functions of the packages @@ -45,7 +45,7 @@ ncelem = Inp.ncelem nselem = Inp.nselem ifw = Inp.ifw WindType = Inp.WindType -AModel = Inp.AModel +AeroModel = Inp.AeroModel windINPfilename = "$(path)$(Inp.windINPfilename)" ifw_libfile = Inp.ifw_libfile if ifw_libfile == "nothing" @@ -118,8 +118,8 @@ mass_breakout_blds,mass_breakout_twr,system,assembly,sections,AD15bldNdIdxRng, A nselem, joint_type = 0, c_mount_ratio = 0.05, - AModel, #AD, DMS, AC - DSModel="BV", + AeroModel, #AD, DMS, AC + DynamicStallModel="BV", RPI=true, cables_connected_to_blade_base = true, meshtype = turbineType) @@ -171,13 +171,13 @@ nothing # There are inputs for the overall coupled simulation, please see the api reference for specifics on all the options -if AModel=="AD" +if AeroModel=="AD" AD15On = true else AD15On = false end -inputs = OWENS.Inputs(;analysisType = structuralModel, +inputs = OWENS.Inputs(;verbosity,analysisType = structuralModel, tocp = [0.0,100000.1], Omegaocp = [RPM,RPM] ./ 60, tocp_Vinf = [0.0,100000.1], @@ -192,7 +192,7 @@ nothing # Then there are inputs for the finite element models, also, please see the api reference for specifics on the options (TODO: ensure that this is propogated to the docs) feamodel = OWENS.FEAModel(;analysisType = structuralModel, -outFilename = "none", +dataOutputFilename = "none", joint = myjoint, platformTurbineConnectionNodeNumber = 1, pBC, diff --git a/examples/literate/C_customizablePreprocessing.jl b/examples/literate/C_customizablePreprocessing.jl index 12bf2d85..5d8b80f7 100644 --- a/examples/literate/C_customizablePreprocessing.jl +++ b/examples/literate/C_customizablePreprocessing.jl @@ -7,7 +7,7 @@ # an properly map the sectional properties to each element and apply unique boundary conditions, etc. #- #md # !!! tip -#md # This example is also available as a Jupyter notebook todo: get link working: +#md # This example is also available as a Jupyter notebook #- # This example is the same as example B except that the setupOWENS function is broken out and each step defined @@ -17,8 +17,8 @@ import OWENSFEA import OWENSAero import QuadGK import FLOWMath -import PyPlot -#### PyPlot.pygui(true) +## import PyPlot +## PyPlot.pygui(true) import OWENSOpenFASTWrappers @@ -51,7 +51,7 @@ ncelem = Inp.ncelem nselem = Inp.nselem ifw = Inp.ifw WindType = Inp.WindType -AModel = Inp.AModel +AeroModel = Inp.AeroModel windINPfilename = "$(path)$(Inp.windINPfilename)" ifw_libfile = Inp.ifw_libfile if ifw_libfile == "nothing" @@ -96,12 +96,12 @@ joint_type = 0 c_mount_ratio = 0.05 angularOffset = -pi/2 custommesh = nothing -if AModel=="AD" #TODO: unify flag +if AeroModel=="AD" #TODO: unify flag AD15On=true #AD for AeroDyn, DMS for double multiple streamtube, AC for actuator cylinder else AD15On=false end -DSModel="BV" +DynamicStallModel="BV" RPI=true cables_connected_to_blade_base = true meshtype = "Darrieus" @@ -207,27 +207,25 @@ end nothing # Here is a way that you can visualize the nodal numbers of the mesh - -PyPlot.figure() -for icon = 1:length(mymesh.conn[:,1]) - idx1 = mymesh.conn[icon,1] - idx2 = mymesh.conn[icon,2] - PyPlot.plot3D([mymesh.x[idx1],mymesh.x[idx2]],[mymesh.y[idx1],mymesh.y[idx2]],[mymesh.z[idx1],mymesh.z[idx2]],"k.-") - PyPlot.text3D(mymesh.x[idx1].+rand()/30,mymesh.y[idx1].+rand()/30,mymesh.z[idx1].+rand()/30,"$idx1",ha="center",va="center") - #### sleep(0.1) -end - -for ijoint = 1:length(myjoint[:,1]) - idx2 = Int(myjoint[ijoint,2]) - idx1 = Int(myjoint[ijoint,3]) - PyPlot.plot3D([mymesh.x[idx1],mymesh.x[idx2]],[mymesh.y[idx1],mymesh.y[idx2]],[mymesh.z[idx1],mymesh.z[idx2]],"r.-") - PyPlot.text3D(mymesh.x[idx1].+rand()/30,mymesh.y[idx1].+rand()/30,mymesh.z[idx1].+rand()/30,"$idx1",color="r",ha="center",va="center") - PyPlot.text3D(mymesh.x[idx2].+rand()/30,mymesh.y[idx2].+rand()/30,mymesh.z[idx2].+rand()/30,"$idx2",color="r",ha="center",va="center") - #### sleep(0.1) -end -PyPlot.xlabel("x") -PyPlot.ylabel("y") -PyPlot.zlabel("z") +# PyPlot.figure() +# for icon = 1:length(mymesh.conn[:,1]) +# idx1 = mymesh.conn[icon,1] +# idx2 = mymesh.conn[icon,2] +# PyPlot.plot3D([mymesh.x[idx1],mymesh.x[idx2]],[mymesh.y[idx1],mymesh.y[idx2]],[mymesh.z[idx1],mymesh.z[idx2]],"k.-") +# PyPlot.text3D(mymesh.x[idx1].+rand()/30,mymesh.y[idx1].+rand()/30,mymesh.z[idx1].+rand()/30,"$idx1",ha="center",va="center") +# #### sleep(0.1) +# end +# for ijoint = 1:length(myjoint[:,1]) +# idx2 = Int(myjoint[ijoint,2]) +# idx1 = Int(myjoint[ijoint,3]) +# PyPlot.plot3D([mymesh.x[idx1],mymesh.x[idx2]],[mymesh.y[idx1],mymesh.y[idx2]],[mymesh.z[idx1],mymesh.z[idx2]],"r.-") +# PyPlot.text3D(mymesh.x[idx1].+rand()/30,mymesh.y[idx1].+rand()/30,mymesh.z[idx1].+rand()/30,"$idx1",color="r",ha="center",va="center") +# PyPlot.text3D(mymesh.x[idx2].+rand()/30,mymesh.y[idx2].+rand()/30,mymesh.z[idx2].+rand()/30,"$idx2",color="r",ha="center",va="center") +# #### sleep(0.1) +# end +# PyPlot.xlabel("x") +# PyPlot.ylabel("y") +# PyPlot.zlabel("z") # This is where the sectional properties for the tower are either read in from the file, or are directly input and could be manuplated here in the script @@ -508,7 +506,7 @@ if !AD15On end end - OWENSAero.setupTurb(shapeX,shapeZ,B,chord,tsr,Vinf;AModel,DSModel, + OWENSAero.setupTurb(shapeX,shapeZ,B,chord,tsr,Vinf;AeroModel,DynamicStallModel, afname = airfoils, bld_y = shapeY, rho, @@ -723,7 +721,7 @@ pBC = [1 1 0 1 5 0 1 6 0] -inputs = OWENS.Inputs(;analysisType = structuralModel, +inputs = OWENS.Inputs(;verbosity,analysisType = structuralModel, tocp = [0.0,100000.1], Omegaocp = [RPM,RPM] ./ 60, tocp_Vinf = [0.0,100000.1], @@ -734,7 +732,7 @@ AD15On, aeroLoadsOn = 2) feamodel = OWENS.FEAModel(;analysisType = structuralModel, -outFilename = "none", +dataOutputFilename = "none", joint = myjoint, platformTurbineConnectionNodeNumber = 1, pBC, diff --git a/examples/literate/D_simulatingFloatingPlatforms.jl b/examples/literate/D_simulatingFloatingPlatforms.jl index 37801b30..9ca93420 100644 --- a/examples/literate/D_simulatingFloatingPlatforms.jl +++ b/examples/literate/D_simulatingFloatingPlatforms.jl @@ -11,7 +11,7 @@ # available to users, which is helpful for explaining how the floating platform mesh # (or "bottom side") is defined and differs from the topside. -import PyPlot +## import PyPlot import OWENS import OWENSFEA @@ -43,7 +43,7 @@ ncelem = Inp.ncelem nselem = Inp.nselem ifw = Inp.ifw WindType = Inp.WindType -AModel = "DMS"#Inp.AModel +AeroModel = "DMS"#Inp.AeroModel windINPfilename = "$(path)$(Inp.windINPfilename)" ifw_libfile = Inp.ifw_libfile if ifw_libfile == "nothing" @@ -104,8 +104,8 @@ aeroForces, deformAero, _, _,topSystem,topAssembly, sections, _, _ = OWENS.setup nselem, joint_type = 0, c_mount_ratio = 0.05, - AModel, #AD, DMS, AC - DSModel="BV", + AeroModel, #AD, DMS, AC + DynamicStallModel="BV", RPI=true, cables_connected_to_blade_base = true, meshtype = turbineType) @@ -190,7 +190,7 @@ end nothing # We also want to provide some additional general inputs to enable floating simulation. -# `hydroOn` being the principal and obvious one, but also the input files needed by +# `platformActive` being the principal and obvious one, but also the input files needed by # HydroDyn and MoorDyn, which are the external libraries that calculate the hydrodynamic # and mooring loads to send to the bottom side mesh. These input files include: # - interpOrder: the degree of interpolation used to predict the future states within @@ -208,12 +208,12 @@ nothing # use predefined input files for the OC4 semisubmersible platform, which comes with # OpenFAST and is copied to the `data` folder here. -if AModel=="AD" +if AeroModel=="AD" AD15On = true else AD15On = false end -hydroOn = true +platformActive = true interpOrder = 2 hd_input_file = "$(path)/data/HydroDyn.dat" md_input_file = "$(path)/data/MoorDyn.dat" @@ -229,7 +229,7 @@ numTS, delta_t, AD15On, aeroLoadsOn = 2, -hydroOn, +platformActive, interpOrder, hd_input_file, md_input_file, @@ -255,7 +255,7 @@ nothing topFEAModel = OWENS.FEAModel(; analysisType = analysisType, - outFilename = "none", + dataOutputFilename = "none", joint = topJoint, platformTurbineConnectionNodeNumber = 1, nlOn = true, @@ -338,7 +338,7 @@ bottomConcTerms = OWENSFEA.applyConcentratedTerms( jointData=[]) bottomFEAModel = OWENS.FEAModel(; analysisType = analysisType, - outFilename = "none", + dataOutputFilename = "none", joint = [], platformTurbineConnectionNodeNumber = 1, nlOn = true, @@ -395,15 +395,13 @@ nothing # see how the floating VAWT responds over time. # Note that the platform modeled here is not necessarily design for the Darrieus VAWT it # is supporting, so your mileage may vary on the simulation results. - -PyPlot.plot(t, uHist_prp[:, 1]) -PyPlot.title("Platform Surge Response") -PyPlot.xlabel("Time [s]") -PyPlot.ylabel("Force [N]") - -PyPlot.plot(t, FHydroHist[:, 1]) -PyPlot.xlabel("Time [s]") -PyPlot.ylabel("Force [N]") -PyPlot.title("Hydrodynamic Surge Loading") +# PyPlot.plot(t, uHist_prp[:, 1]) +# PyPlot.title("Platform Surge Response") +# PyPlot.xlabel("Time [s]") +# PyPlot.ylabel("Force [N]") +# PyPlot.plot(t, FHydroHist[:, 1]) +# PyPlot.xlabel("Time [s]") +# PyPlot.ylabel("Force [N]") +# PyPlot.title("Hydrodynamic Surge Loading") nothing \ No newline at end of file diff --git a/examples/literate/OWENS_Opt.yml b/examples/literate/OWENS_Opt.yml new file mode 100644 index 00000000..ea668078 --- /dev/null +++ b/examples/literate/OWENS_Opt.yml @@ -0,0 +1,62 @@ +OWENS_Options: + analysisType: "Unsteady" # Unsteady, DLC, Campbell, todo: steady, flutter may be re-activated in the future. + AeroModel: "AD" # OWENSAero model "DMS" for double multiple streamtube or "AC" for actuator cylinder, or "AD" for aerodyn + structuralModel: "TNB" #Structural models available: TNB full timoshenko beam elements with time newmark beta time stepping, ROM reduced order modal model of the timoshenko elements, GX with GXBeam's methods for geometrically exact beam theory and more efficient methods and time stepping + controlStrategy: "prescribedRPM" # should be in WindIO?- yes, + numTS: 20 # number of time steps TODO: change to sim time and make this derived + delta_t: 0.01 # time step in seconds + dataOutputFilename: nothing # data output filename with path, set to nothing or don't specify to not output anything + TOL: 1e-4 # gauss-seidel iteration tolerance - i.e. the two-way iteration tolerance + MAXITER: 300 # gauss-seidel max iterations - i.e. the two-way iterations + verbosity: 2 # verbosity where 0 is nothing, 1 is warnings, 2 is summary outputs, 3 is detailed outputs, and 4 is everything + VTKsaveName: "./vtk/windio" # Path and name of the VTK outputs, recommended to put it in its own folder (which it will automatically create if needed) + aeroLoadsOn: 2 # Level of aero coupling 0 structures only, 1 no deformation passed to the aero, 2 two-way coupling, 1.5 last time step's deformations passed to this timesteps aero and no internal iteration. + Prescribed_RPM_time_controlpoints: [0.0,100000.1] + Prescribed_RPM_RPM_controlpoints: [17.2,17.2] + Prescribed_Vinf_time_controlpoints: [0.0,100000.1] + Prescribed_Vinf_Vinf_controlpoints: [17.2,17.2] + +DLC_Options: + DLCs: ["1_1","2_1"] # name of DLC + Vinf_range: [5.0,10.0] # inflow Cutin to cutout and discretization + IEC_std: "\"1-ED3\"" # turbsim input file IEC standard + WindChar: "\"A\"" # turbsim wind charasteric + WindClass: 1 # turbsim wind class + turbsimsavepath: "./turbsimfiles" # path where the turbsim files are saved + pathtoturbsim: nothing # path to the turbsim executable + NumGrid_Z: 38 # turbsim vertical discretizations + NumGrid_Y: 26 # turbsim horizontal discretizations + Vref: 10.0 # reference/nominal wind speed m/s for turbsim or other inflow wind input file (depending on which DLC is selected) + Vdesign: 11.0 # Design or rated speed of turbine, used for certain DLC cases + grid_oversize: 1.1 # amount that the turbsim inflow is oversized compared to the turbine to allow for deflection + regenWindFiles: false #, force regeneration of turbsim files even if they already exist + delta_t_turbsim: 0.05 # turbsim timestep + simtime_turbsim: 600.0 # turbsim total time, which loops if simtime exceeds turbsim time + +OWENSAero_Options: + Nslices: 20 # number of 3-D slices for the strip method to go from 2D to 3D considering curved deforming blades + ntheta: 30 # number of azimuthal discretizations + ifw: false # use the OpenFASTWrappers inflow wind coupling to get inflow velocities + DynamicStallModel: "BV" # dynamic stall model, should be under an OWENSAero options + RPI: true # rotating point iterative method (i.e. it just calculates at the blade positions and is much faster) + Aero_Buoyancy_Active: false # flag to turn buoyancy on for the blades. This is likely to be replaced by a different model + +OWENSFEA_Options: + nlOn: true #nonlinear effects + RayleighAlpha: 0.05 #damping coefficient scalar on the stiffness matrix + RayleighBeta: 0.05 #damping coefficient scalar on the mass matrix + iterationType: "DI" #internal iteration type DI direct iteration, NR newton rhapson (which is less stable than DI) + numModes: 20 #if ROM model, number of modes used in the analysis type. Less is faster but less accurate + tolerance: 1.0e-06 #total mesh unsteady analysis convergence tolerance for a timestep within the structural model + maxIterations: 50 #total mesh unsteady analysis convergence max iterations for a timestep + AddedMass_Coeff_Ca: 0.0 #added mass coefficient, scaling factor (typically 0-1) on the cones of water mass applied to each structural element in the 22 and 33 diagonal terms. 0 turns this off + +Mesh_Options: + ntelem: 20 # number of tower elements in each blade, plus nodes wherever there is a component overlap + nbelem: 30 # number of blade elements in each blade, plus nodes wherever there is a component overlap + nselem: 10 # number of elements in each strut + angularOffset: -1.5707963267948966 + AD15hubR: 0.1 # parameter, used in aerodyn coupling for the hub radius so that the vortex sheets don't go within the hub + +OWENSOpenFASTWrappers_Options: + windINPfilename: /data/turbsim/115mx115m_30x30_20.0msETM.bts #OWENSOpenFASTWrappers If ifw or AeroDyn is being used, gets overwritten if using the DLC analysis type, the moordyn file location, like in the unit test \ No newline at end of file diff --git a/examples/literate/WINDIO_example.yaml b/examples/literate/WINDIO_example.yaml new file mode 100644 index 00000000..673d7db6 --- /dev/null +++ b/examples/literate/WINDIO_example.yaml @@ -0,0 +1,620 @@ +name: WINDIO Example +assembly: {number_of_blades: 3, hub_height: 75.0} +components: + hub: {diameter: 2.0} + tower: + outer_shape_bem: + airfoil_position: + grid: &id000 [0.0, 0.050000000015134494, 0.09999999999999999, 0.15000000003783623, 0.20000000007567248, 0.2500000001135087, 0.30000000007567246, 0.3500000001135087, 0.40000000015134496, 0.4500000001135087, 0.5000000001513449, 0.5500000001891812, 0.6000000001513449, 0.6500000001891812, 0.7000000002270174, 0.7500000002648537, 0.8000000001513449, 0.8500000004918712, 0.9000000000756724, 0.9500000004161987, 1.0] + labels: [circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular] + chord: + grid: *id000 + values: [5.888066637, 5.788249614, 5.684865834, 5.577578504, 5.465996871, 5.349663569, 5.22803793, 5.100473576, 4.966187737, 4.824218239, 4.673361587, 4.512081003, 4.338364592, 4.149496455, 3.941665819, 3.70924955, 3.443362258, 3.128502234, 2.732998436, 2.169182296, 2.0] + twist: + grid: *id000 + values: [0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0] + pitch_axis: + grid: *id000 + values: [0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5] + reference_axis: + x: + grid: *id000 + values: [0.0,0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0] + y: + grid: *id000 + values: [0.0,0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0] + z: + grid: *id000 + values: [0.0, 6.607421057, 13.21484211, 19.82226317, 26.42968423, 33.03710529, 39.64452634, 46.2519474, 52.85936846, 59.46678951, 66.07421057, 72.68163163, 79.28905268, 85.89647374, 92.5038948, 99.11131586, 105.7187369, 112.326158, 118.933579, 125.5410001, 132.1484211] + internal_structure_2d_fem: + reference_axis: + x: + grid: [0.0] + values: [0.0] + y: + grid: [0.0] + values: [0.0] + z: + grid: [0.0] + values: [0.0] + webs: + layers: + - name: Panel_Face_outer + material: Generic_Skin + n_plies: + grid: *id000 + values: [8.921, 8.770, 8.613, 8.451, 8.282, 8.106, 7.921, 7.728, 7.525, 7.309, 7.081, 6.836, 6.573, 6.287, 5.972, 5.620, 5.217, 4.740, 4.141, 3.287, 3.030] + start_nd_arc: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id000 + end_nd_arc: + values: [1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0] + grid: *id000 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id000 + - name: Center + material: Generic_Pultrusion + n_plies: + grid: *id000 + values: [89.213, 87.701, 86.134, 84.509, 82.818, 81.056, 79.213, 77.280, 75.245, 73.094, 70.809, 68.365, 65.733, 62.871, 59.722, 56.201, 52.172, 47.402, 41.409, 32.866, 30.303] + start_nd_arc: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id000 + end_nd_arc: + values: [1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0] + grid: *id000 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id000 + - name: Panel_Face_inner + material: Generic_Skin + n_plies: + grid: *id000 + values: [8.921, 8.770, 8.613, 8.451, 8.282, 8.106, 7.921, 7.728, 7.525, 7.309, 7.081, 6.836, 6.573, 6.287, 5.972, 5.620, 5.217, 4.740, 4.141, 3.287, 3.030] + start_nd_arc: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id000 + end_nd_arc: + values: [1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0] + grid: *id000 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id000 + root: {d_f: 0.03, sigma_max: 675000000.0} + joint: {position: 0.0, mass: 0.0, cost: 0.0, bolt: M30, nonmaterial_cost: 0.0, reinforcement_layer_ss: joint_reinf_ss, reinforcement_layer_ps: joint_reinf_ps} + blade: + outer_shape_bem: + airfoil_position: + grid: &id001 [0.0, 0.04999697309077701, 0.1000015134546115, 0.1499984865453885, 0.200003026909223, 0.25, 0.3000045403638345, 0.3500015134546115, 0.39999848654538855, 0.450003026909223, 0.5, 0.5500045403638345, 0.6000015134546115, 0.6499984865453885, 0.700003026909223, 0.75, 0.8000045403638345, 0.8500015134546115, 0.900006053818446, 0.950003026909223, 1.0] + labels: [NACA_0018, NACA_0018, NACA_0018, NACA_0018, NACA_0018, NACA_0018, NACA_0018, NACA_0018, NACA_0018, NACA_0018, NACA_0018, NACA_0018, NACA_0018, NACA_0018, NACA_0018, NACA_0018, NACA_0018, NACA_0018, NACA_0018, NACA_0018, NACA_0018] + chord: + grid: *id001 + values: [6, 6, 6, 5.498, 4.431, 3.806, 3.435, 3.205, 3.068, 3.003, 3, 3.056, 3.176, 3.377, 3.688, 4.18, 4.924, 6, 6, 6, 6] + twist: + grid: *id001 + values: [0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0] + blade_mountpoint: 0.5 + pitch_axis: + grid: *id001 + values: [0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3] + reference_axis: + x: + grid: &id022 [0.0, 0.03333333333333333, 0.06666666666666667, 0.1, 0.13333333333333333, 0.16666666666666666, 0.2, 0.23333333333333334, 0.26666666666666666, 0.3, 0.3333333333333333, 0.36666666666666664, 0.4, 0.43333333333333335, 0.4666666666666667, 0.5, 0.5333333333333333, 0.5666666666666667, 0.6, 0.6333333333333333, 0.6666666666666666, 0.7, 0.7333333333333333, 0.7666666666666667, 0.8, 0.8333333333333334, 0.8666666666666667, 0.9, 0.9333333333333333, 0.9666666666666667, 1.0] + values: &id02x [0.0, 6.961447494399997, 13.442795161599998, 19.444043001599994, 24.965191014399995, 30.006239199999996, 34.5671875584, 38.6480360896, 42.248784793599995, 45.3694336704, 48.00998272, 50.1704319424, 51.8507813376, 53.0510309056, 53.7711806464, 54.01123056, 53.7711806464, 53.0510309056, 51.8507813376, 50.1704319424, 48.009982720000004, 45.36943367040001, 42.24878479360001, 38.6480360896, 34.56718755839999, 30.006239199999996, 24.965191014399995, 19.444043001599994, 13.442795161599998, 6.961447494399997, 0.0] + y: + grid: *id022 + values: &id02y [0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0] + z: + grid: *id022 + values: &id02z [0.0, 3.67276364, 7.34552728, 11.01829092, 14.69105456, 18.363818199999997, 22.03658184, 25.70934548, 29.38210912, 33.054872759999995, 36.727636399999994, 40.400400039999994, 44.07316368, 47.74592732, 51.41869096, 55.0914546, 58.76421824, 62.43698188, 66.10974551999999, 69.78250915999999, 73.45527279999999, 77.12803643999999, 80.80080007999999, 84.47356372, 88.14632736, 91.819091, 95.49185464, 99.16461828, 102.83738192, 106.51014556, 110.1829092] + internal_structure_2d_fem: + reference_axis: + x: + grid: *id022 + values: *id02x + y: + grid: *id022 + values: *id02y + z: + grid: *id022 + values: *id02z + webs: + - name: web0 + start_nd_arc: + grid: *id001 + values: [0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35] + end_nd_arc: + grid: *id001 + values: [0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65] + layers: + - name: Panel_Face_outer + material: Generic_Skin + n_plies: + grid: *id001 + values: [1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1] + start_nd_arc: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + end_nd_arc: + values: [1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: Leading_Edge + material: Generic_Pultrusion + n_plies: + grid: *id001 + values: [12,12,12,11,9,8,7,6,6,6,6,6,6,7,7,8,10,12,12,12,12] + start_nd_arc: + values: [0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525] + grid: *id001 + end_nd_arc: + values: [0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: HP_Aft_Panel_foam + material: Foam + n_plies: + grid: *id001 + values: [8,9,9,8,7,6,5,5,5,4,4,4,5,5,5,6,7,9,9,9,9] + start_nd_arc: + values: [0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75] + grid: *id001 + end_nd_arc: + values: [0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: HP_Fore_Panel_foam + material: Foam + n_plies: + grid: *id001 + values: [8,9,9,8,7,6,5,5,5,4,4,4,5,5,5,6,7,9,9,9,9] + start_nd_arc: + values: [0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475] + grid: *id001 + end_nd_arc: + values: [0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: LP_Fore_Panel_foam + material: Foam + n_plies: + grid: *id001 + values: [8,9,9,8,7,6,5,5,5,4,4,4,5,5,5,6,7,9,9,9,9] + start_nd_arc: + values: [0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45] + grid: *id001 + end_nd_arc: + values: [0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: LP_Aft_Panel_foam + material: Foam + n_plies: + grid: *id001 + values: [8,9,9,8,7,6,5,5,5,4,4,4,5,5,5,6,7,9,9,9,9] + start_nd_arc: + values: [0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025] + grid: *id001 + end_nd_arc: + values: [0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: HP_Spar + material: Generic_Pultrusion + n_plies: + grid: *id001 + values: [12,13,13,12,10,8,8,7,7,7,7,7,7,8,8,9,11,13,13,13,13] + start_nd_arc: + values: [0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55] + grid: *id001 + end_nd_arc: + values: [0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: LP_Spar + material: Generic_Pultrusion + n_plies: + grid: *id001 + values: [12,13,13,12,10,8,8,7,7,7,7,7,7,8,8,9,11,13,13,13,13] + start_nd_arc: + values: [0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25] + grid: *id001 + end_nd_arc: + values: [0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: HP_TE + material: Generic_Pultrusion + n_plies: + grid: *id001 + values: [12,12,12,11,9,8,7,6,6,6,6,6,6,7,7,8,10,12,12,12,12] + start_nd_arc: + values: [0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975] + grid: *id001 + end_nd_arc: + values: [1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: LP_TE + material: Generic_Pultrusion + n_plies: + grid: *id001 + values: [12,12,12,11,9,8,7,6,6,6,6,6,6,7,7,8,10,12,12,12,12] + start_nd_arc: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + end_nd_arc: + values: [0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: Panel_Face_inner + material: Generic_Skin + n_plies: + grid: *id001 + values: [1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1] + start_nd_arc: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + end_nd_arc: + values: [1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: web0_face + material: Generic_Skin + web: web0 + n_plies: + grid: *id001 + values: [1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1] + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: web0_core + material: Foam + web: web0 + n_plies: + grid: *id001 + values: [8,9,9,8,7,6,5,5,5,4,4,4,5,5,5,6,7,9,9,9,9] + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: web0_face + material: Generic_Skin + web: web0 + n_plies: + grid: *id001 + values: [1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1] + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + root: {d_f: 0.03, sigma_max: 675000000.0} + joint: {position: 0.0, mass: 0.0, cost: 0.0, bolt: M30, nonmaterial_cost: 0.0, reinforcement_layer_ss: joint_reinf_ss, reinforcement_layer_ps: joint_reinf_ps} + struts: + - name: strut1 + mountfraction_tower: [0.25,0.75] + mountfraction_blade: [0.25,0.75] + outer_shape_bem: + airfoil_position: + grid: &id002 [0, 0.333, 0.6667, 1.0] + labels: [NACA_0018, NACA_0018, NACA_0018, NACA_0018] + chord: + grid: *id002 + values: [6.0, 6.0, 6.0, 6.0] + twist: + grid: *id002 + values: [0.0, 0.0, 0.0, 0.0] + pitch_axis: + grid: *id002 + values: [0.3, 0.3, 0.3, 0.3] + reference_axis: + x: + grid: *id002 + values: [-0.0, -0.0, -0.0, -0.0] + y: + grid: *id002 + values: [0.0, 0.0, 0.0, 0.0] + z: + grid: *id002 + values: [0.0, 0.15, 0.45, 0.75] + internal_structure_2d_fem: + reference_axis: + x: + grid: [0.0] + values: [0.0] + y: + grid: [0.0] + values: [0.0] + z: + grid: [0.0] + values: [0.0] + webs: + - name: web0 + start_nd_arc: + grid: *id002 + values: [0.35,0.35,0.35,0.35] + end_nd_arc: + grid: *id002 + values: [0.65,0.65,0.65,0.65] + layers: + - name: Panel_Face_outer + material: Generic_Skin + n_plies: + grid: *id002 + values: [1,1,1,1] + start_nd_arc: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + end_nd_arc: + values: [1.0,1.0,1.0,1.0] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: Leading_Edge + material: Generic_Pultrusion + n_plies: + grid: *id002 + values: [12,12,12,12] + start_nd_arc: + values: [0.4525,0.4525,0.4525,0.4525] + grid: *id002 + end_nd_arc: + values: [0.5475,0.5475,0.5475,0.5475] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: HP_Aft_Panel_foam + material: Foam + n_plies: + grid: *id002 + values: [8,8,8,8] + start_nd_arc: + values: [0.75,0.75,0.75,0.75] + grid: *id002 + end_nd_arc: + values: [0.975,0.975,0.975,0.975] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: HP_Fore_Panel_foam + material: Foam + n_plies: + grid: *id002 + values: [8,8,8,8] + start_nd_arc: + values: [0.5475,0.5475,0.5475,0.5475] + grid: *id002 + end_nd_arc: + values: [0.55,0.55,0.55,0.55] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: LP_Fore_Panel_foam + material: Foam + n_plies: + grid: *id002 + values: [8,8,8,8] + start_nd_arc: + values: [0.45,0.45,0.45,0.45] + grid: *id002 + end_nd_arc: + values: [0.4525,0.4525,0.4525,0.4525] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: LP_Aft_Panel_foam + material: Foam + n_plies: + grid: *id002 + values: [8,8,8,8] + start_nd_arc: + values: [0.025,0.025,0.025,0.025] + grid: *id002 + end_nd_arc: + values: [0.25,0.25,0.25,0.25] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: HP_Spar + material: Generic_Pultrusion + n_plies: + grid: *id002 + values: [12,12,12,12] + start_nd_arc: + values: [0.55,0.55,0.55,0.55] + grid: *id002 + end_nd_arc: + values: [0.75,0.75,0.75,0.75] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: LP_Spar + material: Generic_Pultrusion + n_plies: + grid: *id002 + values: [12,12,12,12] + start_nd_arc: + values: [0.25,0.25,0.25,0.25] + grid: *id002 + end_nd_arc: + values: [0.45,0.45,0.45,0.45] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: HP_TE + material: Generic_Pultrusion + n_plies: + grid: *id002 + values: [12,12,12,12] + start_nd_arc: + values: [0.975,0.975,0.975,0.975] + grid: *id002 + end_nd_arc: + values: [1.0,1.0,1.0,1.0] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: LP_TE + material: Generic_Pultrusion + n_plies: + grid: *id002 + values: [12,12,12,12] + start_nd_arc: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + end_nd_arc: + values: [0.025,0.025,0.025,0.025] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: Panel_Face_inner + material: Generic_Skin + n_plies: + grid: *id002 + values: [1,1,1,1] + start_nd_arc: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + end_nd_arc: + values: [1.0,1.0,1.0,1.0] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: web0_face + material: Generic_Pultrusion + web: web0 + n_plies: + grid: *id002 + values: [1,1,1,1] + fiber_orientation: + values: [0.0, 0.0, 0.0, 0.0] + grid: *id002 + - name: web0_core + material: Foam + web: web0 + n_plies: + grid: *id002 + values: [8,8,8,8] + fiber_orientation: + values: [0.0, 0.0, 0.0, 0.0] + grid: *id002 + - name: web0_face + material: Generic_Pultrusion + web: web0 + n_plies: + grid: *id002 + values: [1,1,1,1] + fiber_orientation: + values: [0.0, 0.0, 0.0, 0.0] + grid: *id002 + root: {d_f: 0.03, sigma_max: 675000000.0} + joint: {position: 0.0, mass: 0.0, cost: 0.0, bolt: M30, nonmaterial_cost: 0.0, reinforcement_layer_ss: joint_reinf_ss, reinforcement_layer_ps: joint_reinf_ps} +airfoils: + - name: NACA6_1000 + coordinates: + x: [1.0, 0.993181, 0.972909, 0.939737, 0.89457, 0.838641, 0.773474, 0.700848, 0.622743, 0.54129, 0.45870999999999995, 0.37725699999999995, 0.299152, 0.226526, 0.16135900000000003, 0.10543000000000002, 0.060262999999999955, 0.027090999999999976, 0.0068190000000000195, 0.0, 0.0068190000000000195, 0.027090999999999976, 0.060262999999999955, 0.10543000000000002, 0.16135900000000003, 0.226526, 0.299152, 0.37725699999999995, 0.45870999999999995, 0.54129, 0.622743, 0.700848, 0.773474, 0.838641, 0.89457, 0.939737, 0.972909, 0.993181, 1.0] + y: [0.0, 0.082442, 0.162359, 0.237976, 0.307106, 0.367865, 0.418583, 0.457883, 0.484712, 0.498283, 0.498283, 0.484712, 0.457883, 0.418583, 0.367865, 0.307106, 0.237976, 0.162359, 0.082442, 0.0, -0.082442, -0.162359, -0.237976, -0.307106, -0.367865, -0.418583, -0.457883, -0.484712, -0.498283, -0.498283, -0.484712, -0.457883, -0.418583, -0.367865, -0.307106, -0.237976, -0.162359, -0.082442, 0.0] + relative_thickness: 1.0 + aerodynamic_center: 0.25 + polars: + - configuration: '' + re: 2000000.0 + c_l: + grid: [-3.141592653589793, 0.0, 3.141592653589793] + values: [0.0, 0.0, 0.0] + c_d: + grid: [-3.141592653589793, 0.0, 3.141592653589793] + values: [0.3, 0.3, 0.3] + c_m: + grid: [-3.141592653589793, 0.0, 3.141592653589793] + values: [0.0, 0.0, 0.0] +materials: + - name: Generic_Pultrusion + description: a description of the material + source: source link + ply_t: 0.001 + E: [27000000000.0, 6000000000.0, 6000000000.0] + G: [3000000000.0, 3000000000.0, 3000000000.0] + nu: [0.26, 0.36, 0.26] + rho: 1850.0 + Xt: [400000000.0, 100000000.0, 100000000.0] + Xc: [200000000.0, 200000000.0, 200000000.0] + S: [100000000.0, 100000000.0, 100000000.0] + unit_cost: 3.00 + A: [400.0,350.0,325.0,275.0,200.0,0.0] + m: [0.0,1.0,2.0,4.0,6.0,20.0] + - name: Generic_Skin + description: a description of the material + source: source link + ply_t: 0.001 + E: [27000000000.0, 6000000000.0, 6000000000.0] + G: [3000000000.0, 3000000000.0, 3000000000.0] + nu: [0.26, 0.36, 0.26] + rho: 1850.0 + Xt: [400000000.0, 100000000.0, 100000000.0] + Xc: [200000000.0, 200000000.0, 200000000.0] + S: [100000000.0, 100000000.0, 100000000.0] + unit_cost: 3.00 + A: [400.0,350.0,325.0,275.0,200.0,0.0] + m: [0.0,1.0,2.0,4.0,6.0,20.0] + - name: steel + description: a description of the material + source: source link + ply_t: 0.001 + E: [199948000000.0, 199948000000.0, 199948000000.0] + G: [76877000000.0, 76877000000.0, 76877000000.0] + nu: [0.3, 0.3, 0.3] + rho: 7861.092935 + Xt: [420000000.0, 420000000.0, 420000000.0] + Xc: [250000000.0, 250000000.0, 250000000.0] + S: [100000000.0, 100000000.0, 100000000.0] + unit_cost: 1.00 + A: [420.0,415.0,375.0,275.0,190.0,0.0] + m: [0.0,1.0,2.0,4.0,6.0,20.0] + - name: Foam + description: a description of the material + source: source link + ply_t: 0.001 + E: [1000000000.0, 1000000000.0, 1000000000.0] + G: [100000000.0, 100000000.0, 100000000.0] + nu: [0.3, 0.3, 0.3] + rho: 100.0 + Xt: [50000000.0, 50000000.0, 50000000.0] + Xc: [50000000.0, 50000000.0, 50000000.0] + S: [100000000.0, 100000000.0, 100000000.0] + unit_cost: 0.10 + A: [50.0,45.0,40.0,35.0,20.0,0.0] + m: [0.0,1.0,2.0,4.0,6.0,20.0] +environment: {air_density: 1.225, air_dyn_viscosity: 1.7894e-5, air_speed_sound: 1500.0, shear_exp: 0.0, gravity: [0,0,-9.81], weib_shape_parameter: 2.0, water_density: 1025.0, water_dyn_viscosity: 0.0013351, soil_shear_modulus: 140000000.0, soil_poisson: 0.4, water_depth: 50.0, air_pressure: 101325.0, air_vapor_pressure: 2500.0, significant_wave_height: 1.0, significant_wave_period: 5.0} \ No newline at end of file diff --git a/examples/literate/sampleOWENS.yml b/examples/literate/sampleOWENS.yml index d79d0428..55373e44 100644 --- a/examples/literate/sampleOWENS.yml +++ b/examples/literate/sampleOWENS.yml @@ -30,7 +30,7 @@ controlParameters: AeroParameters: Nslices: 30 # number of OWENSAero discritizations #TODO: AD parameters ntheta: 30 # number of OWENSAero azimuthal discretizations - AModel: AD # AD, DMS, AC + AeroModel: AD # AD, DMS, AC adi_lib: nothing adi_rootname: "/ExampleB" diff --git a/src/AeroMapping.jl b/src/AeroMapping.jl index 72ab369a..ce4f563d 100644 --- a/src/AeroMapping.jl +++ b/src/AeroMapping.jl @@ -130,7 +130,7 @@ function mapACDMS(t,azi_j,mesh,el,advanceTurb;numAeroTS = 1,alwaysrecalc=true,ou #integrate over elements #read element aero_data in - numDofPerNode = 6 + numDOFPerNode = 6 # [~,~,timeLen] = size(aeroDistLoadsArrayTime) Fg = zeros(Int(mesh.numNodes*6),numAeroTS) Fg_global = zeros(Int(mesh.numNodes*6),numAeroTS) @@ -143,7 +143,7 @@ function mapACDMS(t,azi_j,mesh,el,advanceTurb;numAeroTS = 1,alwaysrecalc=true,ou #get dof map node1 = Int(structuralNodeNumbers[j,k]) node2 = Int(structuralNodeNumbers[j,k+1]) - dofList = [(node1-1)*numDofPerNode.+(1:6) (node2-1)*numDofPerNode.+(1:6)] + dofList = [(node1-1)*numDOFPerNode.+(1:6) (node2-1)*numDOFPerNode.+(1:6)] elementOrder = 1 x = [mesh.x[node1], mesh.x[node2]] @@ -381,7 +381,7 @@ end # #integrate over elements # # #read element aero_data in -# numDofPerNode = 6 +# numDOFPerNode = 6 # # [~,~,timeLen] = size(aeroDistLoadsArrayTime) # Fg = zeros(Int(max(maximum(structuralNodeNumbers))*6),numAeroTS) # for i=1:numAeroTS @@ -393,7 +393,7 @@ end # #get dof map # node1 = Int(structuralNodeNumbers[j,k]) # node2 = Int(structuralNodeNumbers[j,k+1]) -# dofList = [(node1-1)*numDofPerNode.+(1:6) (node2-1)*numDofPerNode.+(1:6)] +# dofList = [(node1-1)*numDOFPerNode.+(1:6) (node2-1)*numDOFPerNode.+(1:6)] # # elementOrder = 1 # x = [mesh.x[node1], mesh.x[node2]] diff --git a/src/SetupTurbine.jl b/src/SetupTurbine.jl index 583c9375..1c351f32 100644 --- a/src/SetupTurbine.jl +++ b/src/SetupTurbine.jl @@ -45,8 +45,8 @@ function setupOWENS(OWENSAero,path; joint_type = 2, c_mount_ratio = 0.05, angularOffset = -pi/2, - AModel="DMS", - DSModel="BV", + AeroModel="DMS", + DynamicStallModel="BV", RPI=true, Aero_AddedMass_Active = false, Aero_RotAccel_Active = false, @@ -59,7 +59,7 @@ function setupOWENS(OWENSAero,path; custom_mesh_outputs = [] - if AModel=="AD" + if AeroModel=="AD" AD15On = true else AD15On = false @@ -153,7 +153,7 @@ function setupOWENS(OWENSAero,path; bshapey = shapeY, # but magnitude for this is relevant angularOffset, #Blade shape, magnitude is irrelevant, scaled based on height and radius above AD15_ccw = true, - verbosity=0, # 0 nothing, 1 basic, 2 lots: amount of printed information) + verbosity, # 0 nothing, 1 basic, 2 lots: amount of printed information) ) else #TODO unify with HAWT error("please choose a valid mesh type (Darrieus, H-VAWT, ARCUS)") @@ -456,7 +456,7 @@ function setupOWENS(OWENSAero,path; rhoA_in = [mass_bld[i][1,1] for i = 1:length(mass_bld)] - OWENSAero.setupTurb(shapeX,shapeZ,B,chord,tsr,Vinf;AModel,DSModel, + OWENSAero.setupTurb(shapeX,shapeZ,B,chord,tsr,Vinf;AeroModel,DynamicStallModel, afname = airfoils, bld_y = shapeY, rho, @@ -634,7 +634,7 @@ function setupOWENS(OWENSAero,path; isHAWT = false # true for HAWT, false for crossflow or VAWT ) - aeroForcesAD(t,azi) = OWENS.mapAD15(t,azi,[mymesh],OWENSOpenFASTWrappers.advanceAD15;alwaysrecalc=true,verbosity=1) + aeroForcesAD(t,azi) = OWENS.mapAD15(t,azi,[mymesh],OWENSOpenFASTWrappers.advanceAD15;alwaysrecalc=true,verbosity) deformAeroAD=OWENSOpenFASTWrappers.deformAD15 end @@ -645,6 +645,28 @@ function setupOWENS(OWENSAero,path; mass_breakout_blds = mass_breakout_bld.*length(mymesh.structuralNodeNumbers[:,1]) mass_breakout_twr = OWENS.get_material_mass(plyprops_twr,numadIn_twr;int_start=0.0,int_stop=Htwr_base) + + # If the sectional properties material files includes cost information, that is combined with the density + # to estimate the overall material cost of of materials in the blades + + if verbosity>0 + + println("\nBlades' Mass Breakout") + for (i,name) in enumerate(plyprops_bld.names) + println("$name $(mass_breakout_blds[i]) kg, $(plyprops_bld.costs[i]) \$/kg: \$$(mass_breakout_blds[i]*plyprops_bld.costs[i])") + end + + println("\nTower Mass Breakout") + for (i,name) in enumerate(plyprops_twr.names) + println("$name $(mass_breakout_twr[i]) kg, $(plyprops_twr.costs[i]) \$/kg: \$$(mass_breakout_twr[i]*plyprops_twr.costs[i])") + end + + println("Total Material Cost Blades: \$$(sum(mass_breakout_blds.*plyprops_bld.costs))") + println("Total Material Cost Tower: \$$(sum(mass_breakout_twr.*plyprops_twr.costs))") + println("Total Material Cost: \$$(sum(mass_breakout_blds.*plyprops_bld.costs)+ sum(mass_breakout_twr.*plyprops_twr.costs))") + + end + if AD15On return mymesh,myel,myort,myjoint,sectionPropsArray,mass_twr, mass_bld, stiff_twr, stiff_bld,bld_precompinput, @@ -729,8 +751,8 @@ function setupOWENShawt(OWENSAero,path; ncelem = 10, joint_type = 2, c_mount_ratio = 0.05, - AModel="DMS", - DSModel="BV", + AeroModel="DMS", + DynamicStallModel="BV", RPI=true, biwing=false, hub_depth = 15.0, #Hub Beam Depth @@ -956,7 +978,7 @@ function setupOWENShawt(OWENSAero,path; ######################################### # println("Initialize Aerodynamics") # chord_spl = safeakima(numadIn_bld.span./maximum(numadIn_bld.span), numadIn_bld.chord,LinRange(0,1,Nslices)) - # OWENSAero.setupTurb(shapeX,shapeZ,B,chord_spl,tsr,Vinf;AModel,DSModel, + # OWENSAero.setupTurb(shapeX,shapeZ,B,chord_spl,tsr,Vinf;AeroModel,DynamicStallModel, # afname = "$path/Airfoils/NACA_0021.dat", #TODO: map to the numad input # ifw, # windINPfilename, diff --git a/src/Unsteady.jl b/src/Unsteady.jl index 3651dc14..159eb944 100644 --- a/src/Unsteady.jl +++ b/src/Unsteady.jl @@ -49,7 +49,7 @@ function Unsteady(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, # INITIALIZATION #.......................................................................... - if (!inputs.topsideOn) && (!inputs.hydroOn) + if (!inputs.topsideOn) && (!inputs.platformActive) error("No structure is being simulated!") end @@ -76,7 +76,7 @@ function Unsteady(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, torqueDriveShaft_s,topFexternal,topFexternal_hist = allocate_topside(inputs,topMesh,topEl,topModel,numDOFPerNode,u_s,assembly) end ## Hydrodynamics/mooring module initialization and coupling variables - if inputs.hydroOn + if inputs.platformActive bottom_totalNumDOF,u_s_ptfm_n,udot_s_ptfm_n,uddot_s_ptfm_n,u_sm1_ptfm_n,bottomDispData,prpDOFs,u_s_prp_n, udot_s_prp_n,uddot_s_prp_n,jac,numMooringLines,FHydro_n,FMooring_n,outVals, mooringTensions = allocate_bottom(t,numTS,delta_t,inputs,bottomMesh,bottomEl,bottomModel,bin,numDOFPerNode) @@ -89,7 +89,7 @@ function Unsteady(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, if isnothing(topElStorage) && inputs.topsideOn topElStorage = OWENSFEA.initialElementCalculations(topModel,topEl,topMesh) #perform initial element calculations for conventional structural dynamics analysis end - if isnothing(bottomElStorage) && inputs.hydroOn + if isnothing(bottomElStorage) && inputs.platformActive bottomElStorage = OWENSFEA.initialElementCalculations(bottomModel,bottomEl,bottomMesh) #perform initial element calculations for conventional structural dynamics analysis end if inputs.analysisType=="ROM" @@ -106,7 +106,7 @@ function Unsteady(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, topDispData2.etaddot_s = etaddot_s end - if inputs.hydroOn + if inputs.platformActive bottom_rom,bottomJointTransformTrans,u_sRed_ptfm_n, udot_sRed_ptfm_n,uddot_sRed_ptfm_n,bottomBC,u_s2_ptfm_n,udot_s2_ptfm_n, @@ -123,9 +123,9 @@ function Unsteady(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, topsideMass, topsideMOI, topsideCG = OWENSFEA.calculateStructureMassProps(topElStorage) topModel.jointTransform, topModel.reducedDOFList = OWENSFEA.createJointTransform(topModel.joint,topMesh.numNodes,6) #creates a joint transform to constrain model degrees of freedom (DOF) consistent with joint constraints - if inputs.hydroOn + if inputs.platformActive hydro_topside_nodal_coupling!(bottomModel,bottomMesh,topsideMass,topModel,topsideCG,topsideMOI,numDOFPerNode) - end # if inputs.hydroOn + end # if inputs.platformActive end # if inputs.topsideOn if inputs.topsideOn @@ -145,7 +145,7 @@ function Unsteady(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, torqueDriveShaft[1] = torqueDriveShaft_s end - if inputs.hydroOn + if inputs.platformActive uHist_prp[1,:] = u_s_prp_n end @@ -153,7 +153,7 @@ function Unsteady(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, # INITIAL SOLVE #.................................................................. ## Evaluate mooring and hydrodynamics at t=0 based on initial conditions - if inputs.hydroOn + if inputs.platformActive # function initial_solve_hydro(inputs,bottom_totalNumDOF,numDOFPerNode,FHydro_n,FMooring_n,t,delta_t) # Initial coupled bottomside solve using reaction force from topside bottomFexternal = zeros(6) @@ -245,7 +245,7 @@ function Unsteady(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, torqueDriveShaft_j = torqueDriveShaft_s end ## Extrapolate platform motions at t+dt to send to HydroDyn/MoorDyn #TODO: use Adams-Bashforth method if i > 4? - if inputs.hydroOn + if inputs.platformActive top_grav_setting = copy(topModel.gravityOn) topModel.gravityOn = false u_s_prp_n = extrap_pred_vals(recent_u_prp, recent_times, t[i+1], inputs.interpOrder) @@ -351,7 +351,7 @@ function Unsteady(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, # Calculate new aerodynamic loading # Update reference frame transformation and convert aerodynamic loads to hub reference frame - if inputs.hydroOn + if inputs.platformActive CN2H = calcHubRotMat(u_s_prp_predState[4:6], azi_j) CN2H_no_azi = calcHubRotMat(u_s_prp_predState[4:6], 0.0) # CN2H = LinearAlgebra.I(3) @@ -473,7 +473,7 @@ function Unsteady(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, # println("$(numIterations) uNorm: $(uNorm) ") if numIterations==MAXITER - if inputs.iteration_parameters.iterwarnings + if inputs.verbosity > 0 @warn "Maximum Iterations Met Breaking Iteration Loop" end break @@ -500,7 +500,7 @@ function Unsteady(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, #------------------------------------ # COUPLED BOTTOMSIDE STRUCTURAL/HYDRO/MOORING MODULES #------------------------------------ - if inputs.hydroOn + if inputs.platformActive if inputs.topsideOn bottomFexternal = frame_convert(-1*topFReaction_j[1:6], LinearAlgebra.transpose(CN2H)) # in hub frame already # bottomFexternal = zeros(6) @@ -631,7 +631,7 @@ function Unsteady(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, numIterations = numIterations + 1 if numIterations==MAXITER - if inputs.iteration_parameters.iterwarnings + if inputs.verbosity > 0 @warn "Maximum Iterations Met Breaking Iteration Loop" end break @@ -650,7 +650,7 @@ function Unsteady(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, end # if inputs.topsideOn - end # if inputs.hydroOn + end # if inputs.platformActive ## update timestepping variables and other states, store in history arrays if inputs.topsideOn @@ -727,7 +727,7 @@ function Unsteady(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, end - if inputs.hydroOn + if inputs.platformActive uHist_prp[i+1,:] = u_s_prp_n FPtfmHist[i+1,:] = FPtfm_n FHydroHist[i+1,:] = FHydro_n @@ -746,15 +746,14 @@ function Unsteady(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, println("Simulation Complete.") # End FAST module links - if inputs.hydroOn + if inputs.platformActive OWENSOpenFASTWrappers.HD_End() OWENSOpenFASTWrappers.MD_End() end - outputData(topMesh,inputs,t[1:i],aziHist[1:i],OmegaHist[1:i],OmegaDotHist[1:i],gbHist[1:i],gbDotHist[1:i],gbDotDotHist[1:i], - FReactionHist[1:i,:],genTorque[1:i],genPower[1:i],torqueDriveShaft[1:i],uHist[1:i,:],uHist_prp[1:i,:], - epsilon_x_hist[:,:,1:i],epsilon_y_hist[:,:,1:i],epsilon_z_hist[:,:,1:i],kappa_x_hist[:,:,1:i],kappa_y_hist[:,:,1:i], - kappa_z_hist[:,:,1:i]) + if inputs.AD15On + OWENSOpenFASTWrappers.endTurb() + end return t[1:i], aziHist[1:i],OmegaHist[1:i],OmegaDotHist[1:i],gbHist[1:i],gbDotHist[1:i],gbDotDotHist[1:i], FReactionHist[1:i,:],FTwrBsHist[1:i,:],genTorque[1:i],genPower[1:i],torqueDriveShaft[1:i],uHist[1:i,:], @@ -890,7 +889,7 @@ function run_aero_with_deform(aero,deformAero,mesh,el,u_j,uddot_j,inputs,numIter if inputs.aeroLoadsOn > 1 # Transform Global Displacements to Local - numDofPerNode = 6 + numDOFPerNode = 6 u_j_local = zeros(Int(max(maximum(mesh.structuralNodeNumbers))*6)) uddot_j_local = zeros(Int(max(maximum(mesh.structuralNodeNumbers))*6)) @@ -901,7 +900,7 @@ function run_aero_with_deform(aero,deformAero,mesh,el,u_j,uddot_j,inputs,numIter #get dof map node1 = Int(mesh.structuralNodeNumbers[jbld,kel]) node2 = Int(mesh.structuralNodeNumbers[jbld,kel+1]) - dofList = [(node1-1)*numDofPerNode.+(1:6);(node2-1)*numDofPerNode.+(1:6)] + dofList = [(node1-1)*numDOFPerNode.+(1:6);(node2-1)*numDOFPerNode.+(1:6)] globaldisp = u_j[dofList] globaldispddot = uddot_j[dofList] @@ -1027,80 +1026,6 @@ function run_aero_with_deformAD15(aero,deformAero,mesh,el,topdata,inputs,t_i) return aeroVals,aeroDOFs #last 4 are experimental for "GX" solve (not yet working) end -function outputData(mymesh,inputs,t,aziHist,OmegaHist,OmegaDotHist,gbHist,gbDotHist,gbDotDotHist,FReactionHist,genTorque,genPower,torqueDriveShaft,uHist,uHist_prp,epsilon_x_hist,epsilon_y_hist,epsilon_z_hist,kappa_x_hist,kappa_y_hist,kappa_z_hist) - - #Writefile - if inputs.outFilename!="none" - println("WRITING Output File to $(inputs.outFilename)") - - filename = string(inputs.outFilename[1:end-3], "h5") - HDF5.h5open(filename, "w") do file - # HDF5.write(file,"model",model) - HDF5.write(file,"t",collect(t)) - HDF5.write(file,"aziHist",aziHist) - HDF5.write(file,"OmegaHist",OmegaHist) - HDF5.write(file,"OmegaDotHist",OmegaDotHist) - HDF5.write(file,"gbHist",gbHist) - HDF5.write(file,"gbDotHist",gbDotHist) - HDF5.write(file,"gbDotDotHist",gbDotDotHist) - HDF5.write(file,"FReactionHist",FReactionHist) - HDF5.write(file,"genTorque",genTorque) - HDF5.write(file,"genPower",genPower) - HDF5.write(file,"torqueDriveShaft",torqueDriveShaft) - HDF5.write(file,"uHist",uHist) - HDF5.write(file,"uHist_prp",uHist_prp) - HDF5.write(file,"epsilon_x_hist",epsilon_x_hist) - HDF5.write(file,"epsilon_y_hist",epsilon_y_hist) - HDF5.write(file,"epsilon_z_hist",epsilon_z_hist) - HDF5.write(file,"kappa_x_hist",kappa_x_hist) - HDF5.write(file,"kappa_y_hist",kappa_y_hist) - HDF5.write(file,"kappa_z_hist",kappa_z_hist) - end - - filename = string(inputs.outFilename[1:end-3], "out") - DelimitedFiles.open(filename, "w") do io - - header1 = ["t"]# "VinfX_hub" "VinfY_hub" "VinfZ_hub" "Fx1" "Fy1" "Fz1" "Mx1" "My1" "Mz1"] - header2 = ["(s)"]# "(m/s)" "(m/s)" "(m/s)" "(N)" "(N)" "(N)" "(N-m)" "(N-m)" "(N-m)"] - # for i = 2:mymesh.numEl - # header1 = [header1 "Fx$i" "Fy$i" "Fz$i" "Mx$i" "My$i" "Mz$i"] - # header2 = [header2 "(N)" "(N)" "(N)" "(N-m)" "(N-m)" "(N-m)"] - # end - - for ibld = 1:length(mymesh.meshSeg) - for ibldel = 1:mymesh.meshSeg[ibld] - formattedelNum = lpad(ibldel,3,'0')#mymesh.structuralElNumbers[ibld,ibldel] - header1 = [header1 "B$(ibld)N$(formattedelNum)Fx" "B$(ibld)N$(formattedelNum)Fy" "B$(ibld)N$(formattedelNum)Fz" "B$(ibld)N$(formattedelNum)Mx" "B$(ibld)N$(formattedelNum)My" "B$(ibld)N$(formattedelNum)Mz"] - header2 = [header2 "(N)" "(N)" "(N)" "(N-m)" "(N-m)" "(N-m)"] - end - end - - DelimitedFiles.writedlm(io, header1, '\t') - DelimitedFiles.writedlm(io, header2, '\t') - - for i_t = 1:length(FReactionHist[:,1]) - velocity = [1,2,3]#OWENSOpenFASTWrappers.ifwcalcoutput(hub_loc,t[i_t]) - data = [t[i_t]]# velocity[1] velocity[2] velocity[3] FReactionHist[i_t,1] FReactionHist[i_t,2] FReactionHist[i_t,3] FReactionHist[i_t,4] FReactionHist[i_t,5] FReactionHist[i_t,6]] - # for i = 2:mymesh.numEl - # data = [data FReactionHist[i_t,((i-1)*6)+1] FReactionHist[i_t,((i-1)*6)+2] FReactionHist[i_t,((i-1)*6)+3] FReactionHist[i_t,((i-1)*6)+4] FReactionHist[i_t,((i-1)*6)+5] FReactionHist[i_t,((i-1)*6)+6]] - # end - - for ibld = 1:length(mymesh.meshSeg) - for ibldel = 1:mymesh.meshSeg[ibld] - if mymesh.structuralElNumbers!=0 #TODO: this is due to cactus run option with legacy files, but should we get rid of it all? - elidx = Int(mymesh.structuralElNumbers[ibld,ibldel]) - data = [data FReactionHist[i_t,((elidx-1)*6)+1] FReactionHist[i_t,((elidx-1)*6)+2] FReactionHist[i_t,((elidx-1)*6)+3] FReactionHist[i_t,((elidx-1)*6)+4] FReactionHist[i_t,((elidx-1)*6)+5] FReactionHist[i_t,((elidx-1)*6)+6]] - end - end - end - - DelimitedFiles.writedlm(io, data, '\t') - end - end - - end -end - function allocate_topside(inputs,topMesh,topEl,topModel,numDOFPerNode,u_s,assembly) if isnothing(topModel) error("topMesh must be specified if OWENS.Inputs.topsideOn") @@ -1143,13 +1068,13 @@ end function allocate_bottom(t,numTS,delta_t,inputs,bottomMesh,bottomEl,bottomModel,bin,numDOFPerNode) if isnothing(bottomModel) - error("bottomMesh must be specified if OWENS.Inputs.hydroOn") + error("bottomMesh must be specified if OWENS.Inputs.platformActive") elseif isnothing(bottomMesh) - error("bottomMesh must be specified if OWENS.Inputs.hydroOn") + error("bottomMesh must be specified if OWENS.Inputs.platformActive") elseif isnothing(bottomEl) - error("bottomEl must be specified if OWENS.Inputs.hydroOn") + error("bottomEl must be specified if OWENS.Inputs.platformActive") elseif isnothing(bin) - error("bin must be specified if OWENS.Inputs.hydroOn") + error("bin must be specified if OWENS.Inputs.platformActive") end bottom_totalNumDOF = bottomMesh.numNodes*numDOFPerNode @@ -1168,10 +1093,10 @@ function allocate_bottom(t,numTS,delta_t,inputs,bottomMesh,bottomEl,bottomModel, jac = Array{Float32}(undef, numDOFPerNode*2, numDOFPerNode*2) numMooringLines = 3 - if inputs.outFilename == "none" - hd_outFilename = "hydrodyn_temp.out" + if inputs.dataOutputFilename == "none" + hd_dataOutputFilename = "hydrodyn_temp.out" else - hd_outFilename = inputs.outFilename + hd_dataOutputFilename = inputs.dataOutputFilename end FHydro_n = zeros(Float32, numDOFPerNode) #Vector{Float32}(undef, numDOFPerNode) @@ -1179,7 +1104,7 @@ function allocate_bottom(t,numTS,delta_t,inputs,bottomMesh,bottomEl,bottomModel, outVals = Vector{Float32}(undef, numDOFPerNode+1) # Rigid body displacement in 6DOF + wave elevation mooringTensions = Vector{Float32}(undef, numMooringLines*2) # Fairlead + anchor tension for each line - OWENSOpenFASTWrappers.HD_Init(;hdlib_filename=bin.hydrodynLibPath, output_root_name=hd_outFilename, hd_input_file=inputs.hd_input_file, ss_input_file=inputs.ss_input_file,PotFile=inputs.potflowfile, t_initial=t[1], dt=delta_t, t_max=t[1]+(numTS-1)*delta_t, interp_order=inputs.interpOrder) + OWENSOpenFASTWrappers.HD_Init(;hdlib_filename=bin.hydrodynLibPath, output_root_name=hd_dataOutputFilename, hd_input_file=inputs.hd_input_file, ss_input_file=inputs.ss_input_file,PotFile=inputs.potflowfile, t_initial=t[1], dt=delta_t, t_max=t[1]+(numTS-1)*delta_t, interp_order=inputs.interpOrder) OWENSOpenFASTWrappers.MD_Init(;mdlib_filename=bin.moordynLibPath, md_input_file=inputs.md_input_file, init_ptfm_pos=u_s_prp_n, interp_order=inputs.interpOrder, WtrDpth=200) return bottom_totalNumDOF,u_s_ptfm_n,udot_s_ptfm_n,uddot_s_ptfm_n,u_sm1_ptfm_n,bottomDispData,prpDOFs,u_s_prp_n,udot_s_prp_n,uddot_s_prp_n,jac,numMooringLines,FHydro_n,FMooring_n,outVals,mooringTensions diff --git a/src/Unsteady_Land.jl b/src/Unsteady_Land.jl index dfdf1934..a7aa3149 100644 --- a/src/Unsteady_Land.jl +++ b/src/Unsteady_Land.jl @@ -124,7 +124,7 @@ Executable function for transient analysis. Provides the interface of various function Unsteady_Land(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, aeroVals=nothing,aeroDOFs=nothing,aero=nothing,deformAero=nothing, bottomModel=nothing,bottomMesh=nothing,bottomEl=nothing,bin=nothing, - getLinearizedMatrices=false, verbosity=0, + getLinearizedMatrices=false, system=nothing,assembly=nothing,returnold=true, #TODO: should we initialize them in here? Unify the interface for ease? topElStorage = nothing,bottomElStorage = nothing, u_s = nothing, meshcontrolfunction = nothing,userDefinedGenerator=nothing,turbsimfile=nothing) @@ -132,7 +132,7 @@ function Unsteady_Land(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, # INITIALIZATION #.......................................................................... - if (!inputs.topsideOn) && (!inputs.hydroOn) + if (!inputs.topsideOn) && (!inputs.platformActive) error("No structure is being simulated!") end @@ -320,7 +320,7 @@ function Unsteady_Land(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, # genTorqueAppliedToTurbineRotor0 = -genTorque0 # genTorqueAppliedToPlatform0 = genTorqueHSS0 else - if !isnothing(turbsimfile) && verbosity >=1#&& inputs.AD15On + if !isnothing(turbsimfile) && inputs.verbosity > 0#&& inputs.AD15On velocity = OWENSOpenFASTWrappers.ifwcalcoutput([0.0,0.0,maximum(topMesh.z)],t[i]) newVinf = velocity[1] end @@ -492,12 +492,12 @@ function Unsteady_Land(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, OWENSFEA.structuralDynamicsTransient(topModel,topMesh,topEl,topdata.topDispData2,topdata.Omega_s,topdata.OmegaDot_s,t[i+1],topdata.delta_t,topElStorage,topdata.topFexternal,Int.(full_aeroDOFs),topdata.CN2H,topdata.rbData;predef = topModel.nlParams.predef) end - if verbosity>4 + if inputs.verbosity>3 println("$(numIterations) uNorm: $(uNorm) aziNorm: $(aziNorm) gbNorm: $(gbNorm) \n") end if numIterations==MAXITER - if inputs.iteration_parameters.iterwarnings + if inputs.inputs.verbosity>0 @warn "Maximum Iterations Met Breaking Iteration Loop" end break @@ -505,7 +505,7 @@ function Unsteady_Land(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, end #end iteration while loop - if verbosity >=7 + if inputs.verbosity >=3 println("Gen Torque: $(topdata.genTorque_j)\n") println("RPM: $(topdata.Omega_j*60)\n") println("Vinf: $(newVinf)\n") @@ -601,12 +601,11 @@ function Unsteady_Land(inputs;topModel=nothing,topMesh=nothing,topEl=nothing, end #end timestep loop println("Simulation Complete.") - - outputData(topMesh,inputs,t[1:i],topdata.aziHist[1:i],topdata.OmegaHist[1:i],topdata.OmegaDotHist[1:i],topdata.gbHist[1:i],topdata.gbDotHist[1:i],topdata.gbDotDotHist[1:i], - topdata.FReactionHist[1:i,:],topdata.genTorque[1:i],topdata.genPower[1:i],topdata.torqueDriveShaft[1:i],topdata.uHist[1:i,:],topdata.uHist_prp[1:i,:], - topdata.epsilon_x_hist[:,:,1:i],topdata.epsilon_y_hist[:,:,1:i],topdata.epsilon_z_hist[:,:,1:i],topdata.kappa_x_hist[:,:,1:i],topdata.kappa_y_hist[:,:,1:i], - topdata.kappa_z_hist[:,:,1:i]) + if inputs.AD15On + OWENSOpenFASTWrappers.endTurb() + end + if returnold return t[1:i], topdata.aziHist[1:i],topdata.OmegaHist[1:i],topdata.OmegaDotHist[1:i],topdata.gbHist[1:i],topdata.gbDotHist[1:i],topdata.gbDotDotHist[1:i], topdata.FReactionHist[1:i,:],topdata.FTwrBsHist[1:i,:],topdata.genTorque[1:i],topdata.genPower[1:i],topdata.torqueDriveShaft[1:i],topdata.uHist[1:i,:], diff --git a/src/fileio.jl b/src/fileio.jl index 570efec4..5367834c 100644 --- a/src/fileio.jl +++ b/src/fileio.jl @@ -36,18 +36,18 @@ function readNuMadGeomCSV(WindIO_Dict::OrderedCollections.OrderedDict{Symbol, An ref_z = sec_Dict[:outer_shape_bem][:reference_axis][:z][:values] if sec_Dict[:outer_shape_bem][:reference_axis][:x][:grid] != airfoil_grid - @error "The windio grids must all be the same at this time" + @error "The windio grids must all be the same for a given component at this time" end if isnothing(span) span = sqrt.(ref_x.^2 .+ ref_y.^2 .+ ref_z.^2) - println("Custom span is not specified in OWENS input, using WindIO airfoil grid as common span that all the other values are splined to") + println("Custom span is not specified in OWENS input, using WindIO outer_shape_bem sqrt.(reference_axis_x.^2 .+ reference_axis_y.^2 .+ reference_axis_z.^2) as common span that all the other values are splined to") end norm_span = span./maximum(span) - if norm_span[1]!=0.0 && norm_span[end]!=1.0 - @error "Span definition must encompass the entire blade from root 0, to tip 1" + if airfoil_grid[1]!=0.0 && airfoil_grid[end]!=1.0 + @error "ALL grid definitions must extend from root 0, to tip 1" end airfoil = Array{String,1}(undef,length(span)) @@ -814,7 +814,7 @@ end """ - readBCdata(bcfilename,numNodes,numDofPerNode) + readBCdata(bcfilename,numNodes,numDOFPerNode) This function reads the boundray condition file and stores data in the boundary condition object. @@ -822,12 +822,12 @@ boundary condition object. #Input * `bcfilename::string`: string containing boundary condition filename * `numNodes::int`: number of nodes in structural model -* `numDofPerNode::int`: number of degrees of freedom per node +* `numDOFPerNode::int`: number of degrees of freedom per node #Output * `BC::OWENSFEA.BC_struct`: see OWENSFEA.BC_struct, object containing boundary condition data """ -function readBCdata(bcfilename,numNodes,numDofPerNode) +function readBCdata(bcfilename,numNodes,numDOFPerNode) fid = open(bcfilename) #open boundary condition file numpBC = parse(Int,readline(fid)) #read in number of boundary conditions (displacement boundary conditions) @@ -847,7 +847,7 @@ function readBCdata(bcfilename,numNodes,numDofPerNode) end - totalNumDof = numNodes*numDofPerNode + totalNumDof = numNodes*numDOFPerNode numsBC = 0 nummBC = 0 @@ -860,11 +860,11 @@ function readBCdata(bcfilename,numNodes,numDofPerNode) #calculate constrained dof vector isConstrained = zeros(totalNumDof,1) - constDof = (pBC[:,1].-1)*numDofPerNode + pBC[:,2] + constDof = (pBC[:,1].-1)*numDOFPerNode + pBC[:,2] index = 1 for i=1:numNodes - for j=1:numDofPerNode - if ((i-1)*numDofPerNode + j in constDof) + for j=1:numDOFPerNode + if ((i-1)*numDOFPerNode + j in constDof) isConstrained[index] = 1 end index = index + 1 @@ -1229,3 +1229,145 @@ function readResultsModalOut(resultsFile,numNodes) end return freq,damp,U_x_0,U_y_0,U_z_0,theta_x_0,theta_y_0,theta_z_0,U_x_90,U_y_90,U_z_90,theta_x_90,theta_y_90,theta_z_90 end + + +function outputData(;mymesh="not saved", + inputs="not saved", + t="not saved", + aziHist="not saved", + OmegaHist="not saved", + OmegaDotHist="not saved", + gbHist="not saved", + gbDotHist="not saved", + gbDotDotHist="not saved", + FReactionHist="not saved", + genTorque="not saved", + genPower="not saved", + torqueDriveShaft="not saved", + uHist="not saved", + uHist_prp="not saved", + epsilon_x_hist="not saved", + epsilon_y_hist="not saved", + epsilon_z_hist="not saved", + kappa_x_hist="not saved", + kappa_y_hist="not saved", + kappa_z_hist="not saved", + FTwrBsHist="not saved", + massOwens="not saved", + stress_U="not saved", + SF_ult_U="not saved", + SF_buck_U="not saved", + stress_L="not saved", + SF_ult_L="not saved", + SF_buck_L="not saved", + stress_TU="not saved", + SF_ult_TU="not saved", + SF_buck_TU="not saved", + stress_TL="not saved", + SF_ult_TL="not saved", + SF_buck_TL="not saved", + topstrainout_blade_U="not saved", + topstrainout_blade_L="not saved", + topstrainout_tower_U="not saved", + topstrainout_tower_L="not saved", + topDamage_blade_U="not saved", + topDamage_blade_L="not saved", + topDamage_tower_U="not saved", + topDamage_tower_L="not saved", + ofastformat=false) + + #Writefile + if inputs.dataOutputFilename!="none" + println("WRITING Output File to $(inputs.dataOutputFilename)") + + filename = string(inputs.dataOutputFilename[1:end-3], "h5") + + HDF5.h5open(filename, "w") do file + HDF5.write(file,"t",collect(t)) + HDF5.write(file,"aziHist",aziHist) + HDF5.write(file,"OmegaHist",OmegaHist) + HDF5.write(file,"OmegaDotHist",OmegaDotHist) + HDF5.write(file,"gbHist",gbHist) + HDF5.write(file,"gbDotHist",gbDotHist) + HDF5.write(file,"gbDotDotHist",gbDotDotHist) + HDF5.write(file,"FReactionHist",FReactionHist) + HDF5.write(file,"FTwrBsHist",FTwrBsHist) # + HDF5.write(file,"genTorque",genTorque) + HDF5.write(file,"genPower",genPower) + HDF5.write(file,"torqueDriveShaft",torqueDriveShaft) + HDF5.write(file,"uHist",uHist) + HDF5.write(file,"uHist_prp",uHist_prp) + HDF5.write(file,"epsilon_x_hist",epsilon_x_hist) + HDF5.write(file,"epsilon_y_hist",epsilon_y_hist) + HDF5.write(file,"epsilon_z_hist",epsilon_z_hist) + HDF5.write(file,"kappa_x_hist",kappa_x_hist) + HDF5.write(file,"kappa_y_hist",kappa_y_hist) + HDF5.write(file,"kappa_z_hist",kappa_z_hist) + HDF5.write(file,"massOwens",massOwens) + HDF5.write(file,"stress_U",stress_U) + HDF5.write(file,"SF_ult_U",SF_ult_U) + HDF5.write(file,"SF_buck_U",SF_buck_U) + HDF5.write(file,"stress_L",stress_L) + HDF5.write(file,"SF_ult_L",SF_ult_L) + HDF5.write(file,"SF_buck_L",SF_buck_L) + HDF5.write(file,"stress_TU",stress_TU) + HDF5.write(file,"SF_ult_TU",SF_ult_TU) + HDF5.write(file,"SF_buck_TU",SF_buck_TU) + HDF5.write(file,"stress_TL",stress_TL) + HDF5.write(file,"SF_ult_TL",SF_ult_TL) + HDF5.write(file,"SF_buck_TL",SF_buck_TL) + HDF5.write(file,"topstrainout_blade_U",topstrainout_blade_U) + HDF5.write(file,"topstrainout_blade_L",topstrainout_blade_L) + HDF5.write(file,"topstrainout_tower_U",topstrainout_tower_U) + HDF5.write(file,"topstrainout_tower_L",topstrainout_tower_L) + HDF5.write(file,"topDamage_blade_U",topDamage_blade_U) + HDF5.write(file,"topDamage_blade_L",topDamage_blade_L) + HDF5.write(file,"topDamage_tower_U",topDamage_tower_U) + HDF5.write(file,"topDamage_tower_L",topDamage_tower_L) + end + + if ofastformat + filename = string(inputs.dataOutputFilename[1:end-3], "out") + DelimitedFiles.open(filename, "w") do io + + header1 = ["t"]# "VinfX_hub" "VinfY_hub" "VinfZ_hub" "Fx1" "Fy1" "Fz1" "Mx1" "My1" "Mz1"] + header2 = ["(s)"]# "(m/s)" "(m/s)" "(m/s)" "(N)" "(N)" "(N)" "(N-m)" "(N-m)" "(N-m)"] + # for i = 2:mymesh.numEl + # header1 = [header1 "Fx$i" "Fy$i" "Fz$i" "Mx$i" "My$i" "Mz$i"] + # header2 = [header2 "(N)" "(N)" "(N)" "(N-m)" "(N-m)" "(N-m)"] + # end + + for ibld = 1:length(mymesh.meshSeg) + for ibldel = 1:mymesh.meshSeg[ibld] + formattedelNum = lpad(ibldel,3,'0')#mymesh.structuralElNumbers[ibld,ibldel] + header1 = [header1 "B$(ibld)N$(formattedelNum)Fx" "B$(ibld)N$(formattedelNum)Fy" "B$(ibld)N$(formattedelNum)Fz" "B$(ibld)N$(formattedelNum)Mx" "B$(ibld)N$(formattedelNum)My" "B$(ibld)N$(formattedelNum)Mz"] + header2 = [header2 "(N)" "(N)" "(N)" "(N-m)" "(N-m)" "(N-m)"] + end + end + + DelimitedFiles.writedlm(io, header1, '\t') + DelimitedFiles.writedlm(io, header2, '\t') + + for i_t = 1:length(FReactionHist[:,1]) + velocity = [1,2,3]#OWENSOpenFASTWrappers.ifwcalcoutput(hub_loc,t[i_t]) + data = [t[i_t]]# velocity[1] velocity[2] velocity[3] FReactionHist[i_t,1] FReactionHist[i_t,2] FReactionHist[i_t,3] FReactionHist[i_t,4] FReactionHist[i_t,5] FReactionHist[i_t,6]] + # for i = 2:mymesh.numEl + # data = [data FReactionHist[i_t,((i-1)*6)+1] FReactionHist[i_t,((i-1)*6)+2] FReactionHist[i_t,((i-1)*6)+3] FReactionHist[i_t,((i-1)*6)+4] FReactionHist[i_t,((i-1)*6)+5] FReactionHist[i_t,((i-1)*6)+6]] + # end + + for ibld = 1:length(mymesh.meshSeg) + for ibldel = 1:mymesh.meshSeg[ibld] + if mymesh.structuralElNumbers!=0 #TODO: this is due to cactus run option with legacy files, but should we get rid of it all? + elidx = Int(mymesh.structuralElNumbers[ibld,ibldel]) + data = [data FReactionHist[i_t,((elidx-1)*6)+1] FReactionHist[i_t,((elidx-1)*6)+2] FReactionHist[i_t,((elidx-1)*6)+3] FReactionHist[i_t,((elidx-1)*6)+4] FReactionHist[i_t,((elidx-1)*6)+5] FReactionHist[i_t,((elidx-1)*6)+6]] + end + end + end + + DelimitedFiles.writedlm(io, data, '\t') + end + end + end + + end +end \ No newline at end of file diff --git a/src/gxbeam_conversion.jl b/src/gxbeam_conversion.jl index 007143a8..363c7589 100644 --- a/src/gxbeam_conversion.jl +++ b/src/gxbeam_conversion.jl @@ -156,7 +156,7 @@ Formats and outputs OWENS data into VTK format * `none`: """ -function OWENSVTK(saveName,t,uHist,system,assembly,sections,aziHist,mymesh,myel, +function OWENSVTK(VTKsaveName,t,uHist,system,assembly,sections,aziHist,mymesh,myel, epsilon_x_hist,epsilon_y_hist,epsilon_z_hist,kappa_x_hist,kappa_y_hist,kappa_z_hist, FReactionHist,topFexternal_hist;tsave_idx=1:length(t)) @@ -222,8 +222,8 @@ function OWENSVTK(saveName,t,uHist,system,assembly,sections,aziHist,mymesh,myel, end azi=aziHist#./aziHist*1e-6 - # saveName = "$path/vtk/$(windINPfilename[1:end-4])" - OWENS.OWENSFEA_VTK(saveName,t[tsave_idx],uHist[tsave_idx,:],system,assembly,sections;scaling=1,azi=azi[tsave_idx],userPointNames,userPointData) + # VTKsaveName = "$path/vtk/$(windINPfilename[1:end-4])" + OWENS.OWENSFEA_VTK(VTKsaveName,t[tsave_idx],uHist[tsave_idx,:],system,assembly,sections;scaling=1,azi=azi[tsave_idx],userPointNames,userPointData) end diff --git a/src/structs.jl b/src/structs.jl index e728e42b..a2a3a106 100644 --- a/src/structs.jl +++ b/src/structs.jl @@ -7,6 +7,7 @@ struct Bin end mutable struct Inputs + verbosity analysisType turbineStartup usingRotorSpeedFunction @@ -20,7 +21,7 @@ mutable struct Inputs generatorOn aeroLoadsOn AD15On - hydroOn + platformActive topsideOn interpOrder hd_input_file @@ -41,7 +42,7 @@ mutable struct Inputs aeroloadfile owensfile potflowfile - outFilename + dataOutputFilename bladeData driveShaftProps iteration_parameters @@ -51,7 +52,8 @@ end # this way you can use defaults and pass in what is different, and it's mapped # by keyword so it doesn't have to be in order. """ -Inputs(;analysisType = "TNB", +Inputs(;verbosity=2, + analysisType = "TNB", turbineStartup = 0, usingRotorSpeedFunction = false, tocp = [0.0,1.1], @@ -64,7 +66,7 @@ Inputs(;analysisType = "TNB", AD15On = false, driveTrainOn = false, generatorOn = false, - hydroOn = false, + platformActive = false, topsideOn = true, interpOrder = 2, hd_input_file = "none", @@ -84,18 +86,18 @@ Inputs(;analysisType = "TNB", rigid = false, #turn off structural dynamics aeroloadfile = "module_path/../test/data/input_files_test/DVAWT_2B_LCDT_ElementData.csv", owensfile = "module_path/../test/data/input_files_test/_15mTower_transient_dvawt_c_2_lcdt.owens", - outFilename = "none", - numDofPerNode = 6, + dataOutputFilename = "none", + numDOFPerNode = 6, bladeData = [], driveShaftProps = DriveShaftProps(0.0,0.0) - TOl = 1e-4, + TOL = 1e-4, MAXITER = 300, - iterwarnings = true, ) Model inputs for OWENS coupled analysis, struct # Inputs +* `verbosity::int`: output verbosity where 0 is nothing, 1 is warnings, 2 is summary outputs, 3 is detailed outputs, and 4 is everything * `analysisType::string`: Newmark Beta time stepping "TNB", Dean time stepping "TD", modal "M" * `turbineStartup::int`: 1 forced start-up using generator as motor, 2 self-starting mode, 0 specified rotor speed mode") * `usingRotorSpeedFunction::bool`: use user specified rotor speed profile function @@ -109,7 +111,7 @@ Model inputs for OWENS coupled analysis, struct * `AD15On::bool`: flag to use AD15 for aero * `driveTrainOn::bool`: flag to include drivetrain effects * `generatorOn::bool`: flag to include generator effects -* `hydroOn::bool`: flag to include platform coupling +* `platformActive::bool`: flag to include platform coupling * `interpOrder::int`: order used for extrapolating inputs and states, 0 flat, 1 linear, 2 quadratic * `hd_input_file::string`: file path to the HydroDyn .dat input file * `ss_input_file::string`: file path to the HydroDyn sea states input file @@ -129,19 +131,19 @@ Model inputs for OWENS coupled analysis, struct * `aeroloadfile::string`: string of the name and path for the cactus aeroloads if using the old serial owens call * `owensfile::string`: string of the name and path for the owens input file if using the old serial owens call * `potflowfile::string`: string of the prefix and path for the directory containing the potential flow files from WAMIT (required by HydroDyn) -* `outFilename::string`: path and name of output file, will be overwritten if already exists -* `numDofPerNode::int`: number of degrees of freedom per node +* `dataOutputFilename::string`: path and name of output file, will be overwritten if already exists +* `numDOFPerNode::int`: number of degrees of freedom per node * `bladeData::BladeData`: see ?BladeData, only used if calling the old serial owens function * `driveShaftProps::DriveShaftProps`: see ?DriveShaftProps -* `TOl::float`: gauss-seidel iteration tolerance +* `TOL::float`: gauss-seidel iteration tolerance * `MAXITER::int`: gauss-seidel maximum iterations -* `iterwarnings::bool`: iteration warnings flag # Outputs: * `OWENS.Inputs`: """ -function Inputs(;analysisType = "TNB", +function Inputs(;verbosity=2, + analysisType = "TNB", turbineStartup = 0, usingRotorSpeedFunction = false, tocp = [0.0,1.1], @@ -154,7 +156,7 @@ function Inputs(;analysisType = "TNB", generatorOn = false, aeroLoadsOn = false, #this need to get cleaned up in the code AD15On = false, - hydroOn = false, + platformActive = false, topsideOn = true, interpOrder = 2, hd_input_file = "none", @@ -175,21 +177,20 @@ function Inputs(;analysisType = "TNB", aeroloadfile = "$module_path/../test/data/input_files_test/DVAWT_2B_LCDT_ElementData.csv", owensfile = "$module_path/../test/data/input_files_test/_15mTower_transient_dvawt_c_2_lcdt.owens", potflowfile = "$module_path/../test/data/potential_flow_data", - outFilename = "none", - numDofPerNode = 6, + dataOutputFilename = "none", + numDOFPerNode = 6, bladeData = [], rigid = false, driveShaftProps = DriveShaftProps(0.0,0.0), - TOl = 1e-4, + TOL = 1e-4, MAXITER = 300, - iterwarnings = true, ) - return Inputs(analysisType,turbineStartup,usingRotorSpeedFunction,tocp,tocp_Vinf,numTS,delta_t,Omegaocp,Vinfocp, - driveTrainOn,generatorOn,aeroLoadsOn,AD15On,hydroOn,topsideOn,interpOrder,hd_input_file,md_input_file, + return Inputs(verbosity,analysisType,turbineStartup,usingRotorSpeedFunction,tocp,tocp_Vinf,numTS,delta_t,Omegaocp,Vinfocp, + driveTrainOn,generatorOn,aeroLoadsOn,AD15On,platformActive,topsideOn,interpOrder,hd_input_file,md_input_file, JgearBox,gearRatio,gearBoxEfficiency,useGeneratorFunction,generatorProps,ratedTorque, zeroTorqueGenSpeed,pulloutRatio,ratedGenSlipPerc,OmegaGenStart,omegaControl,OmegaInit,rigid, - aeroloadfile,owensfile,potflowfile,outFilename,bladeData,driveShaftProps,Iteration_Parameters(TOl,MAXITER,iterwarnings),ss_input_file) + aeroloadfile,owensfile,potflowfile,dataOutputFilename,bladeData,driveShaftProps,Iteration_Parameters(TOL,MAXITER),ss_input_file) end """ @@ -206,7 +207,6 @@ Internal, gauss-seidel iteration parameters mutable struct Iteration_Parameters TOL # = 1e-4 #gauss-seidel iteration tolerance for various modules MAXITER # = 2 #max iteration for various modules - iterwarnings end # Cactus Related Structs diff --git a/src/template_files/design_defaults.yml b/src/template_files/design_defaults.yml new file mode 100644 index 00000000..2a90ed62 --- /dev/null +++ b/src/template_files/design_defaults.yml @@ -0,0 +1,620 @@ +name: WINDIO Example +assembly: {turbine_class: I, turbulence_class: B, drivetrain: geared, rotor_orientation: upwind, number_of_blades: 3, hub_height: -25.2, rotor_diameter: 20.0, rated_power: 500000, lifetime: 25.0, marine_hydro: true} +components: + hub: {diameter: 2.0} + tower: + outer_shape_bem: + airfoil_position: + grid: &id000 [0.0, 0.050000000015134494, 0.09999999999999999, 0.15000000003783623, 0.20000000007567248, 0.2500000001135087, 0.30000000007567246, 0.3500000001135087, 0.40000000015134496, 0.4500000001135087, 0.5000000001513449, 0.5500000001891812, 0.6000000001513449, 0.6500000001891812, 0.7000000002270174, 0.7500000002648537, 0.8000000001513449, 0.8500000004918712, 0.9000000000756724, 0.9500000004161987, 1.0] + labels: [circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular, circular] + chord: + grid: *id000 + values: [5.888066637, 5.788249614, 5.684865834, 5.577578504, 5.465996871, 5.349663569, 5.22803793, 5.100473576, 4.966187737, 4.824218239, 4.673361587, 4.512081003, 4.338364592, 4.149496455, 3.941665819, 3.70924955, 3.443362258, 3.128502234, 2.732998436, 2.169182296, 2.0] + twist: + grid: *id000 + values: [0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0] + pitch_axis: + grid: *id000 + values: [0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5, 0.5] + reference_axis: + x: + grid: *id000 + values: [0.0,0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0] + y: + grid: *id000 + values: [0.0,0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0] + z: + grid: *id000 + values: [0.0, 6.607421057, 13.21484211, 19.82226317, 26.42968423, 33.03710529, 39.64452634, 46.2519474, 52.85936846, 59.46678951, 66.07421057, 72.68163163, 79.28905268, 85.89647374, 92.5038948, 99.11131586, 105.7187369, 112.326158, 118.933579, 125.5410001, 132.1484211] + internal_structure_2d_fem: + reference_axis: + x: + grid: [0.0] + values: [0.0] + y: + grid: [0.0] + values: [0.0] + z: + grid: [0.0] + values: [0.0] + webs: + layers: + - name: Panel_Face_outer + material: Generic_Skin + n_plies: + grid: *id000 + values: [8.921, 8.770, 8.613, 8.451, 8.282, 8.106, 7.921, 7.728, 7.525, 7.309, 7.081, 6.836, 6.573, 6.287, 5.972, 5.620, 5.217, 4.740, 4.141, 3.287, 3.030] + start_nd_arc: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id000 + end_nd_arc: + values: [1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0] + grid: *id000 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id000 + - name: Center + material: Generic_Pultrusion + n_plies: + grid: *id000 + values: [89.213, 87.701, 86.134, 84.509, 82.818, 81.056, 79.213, 77.280, 75.245, 73.094, 70.809, 68.365, 65.733, 62.871, 59.722, 56.201, 52.172, 47.402, 41.409, 32.866, 30.303] + start_nd_arc: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id000 + end_nd_arc: + values: [1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0] + grid: *id000 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id000 + - name: Panel_Face_inner + material: Generic_Skin + n_plies: + grid: *id000 + values: [8.921, 8.770, 8.613, 8.451, 8.282, 8.106, 7.921, 7.728, 7.525, 7.309, 7.081, 6.836, 6.573, 6.287, 5.972, 5.620, 5.217, 4.740, 4.141, 3.287, 3.030] + start_nd_arc: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id000 + end_nd_arc: + values: [1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0] + grid: *id000 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id000 + root: {d_f: 0.03, sigma_max: 675000000.0} + joint: {position: 0.0, mass: 0.0, cost: 0.0, bolt: M30, nonmaterial_cost: 0.0, reinforcement_layer_ss: joint_reinf_ss, reinforcement_layer_ps: joint_reinf_ps} + blade: + outer_shape_bem: + airfoil_position: + grid: &id001 [0.0, 0.04999697309077701, 0.1000015134546115, 0.1499984865453885, 0.200003026909223, 0.25, 0.3000045403638345, 0.3500015134546115, 0.39999848654538855, 0.450003026909223, 0.5, 0.5500045403638345, 0.6000015134546115, 0.6499984865453885, 0.700003026909223, 0.75, 0.8000045403638345, 0.8500015134546115, 0.900006053818446, 0.950003026909223, 1.0] + labels: [NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021, NACA_0021] + chord: + grid: *id001 + values: [6, 6, 6, 5.498, 4.431, 3.806, 3.435, 3.205, 3.068, 3.003, 3, 3.056, 3.176, 3.377, 3.688, 4.18, 4.924, 6, 6, 6, 6] + twist: + grid: *id001 + values: [0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0] + blade_mountpoint: 0.5 + pitch_axis: + grid: *id001 + values: [0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3, 0.3] + reference_axis: + x: + grid: &id022 [0.0, 0.03333333333333333, 0.06666666666666667, 0.1, 0.13333333333333333, 0.16666666666666666, 0.2, 0.23333333333333334, 0.26666666666666666, 0.3, 0.3333333333333333, 0.36666666666666664, 0.4, 0.43333333333333335, 0.4666666666666667, 0.5, 0.5333333333333333, 0.5666666666666667, 0.6, 0.6333333333333333, 0.6666666666666666, 0.7, 0.7333333333333333, 0.7666666666666667, 0.8, 0.8333333333333334, 0.8666666666666667, 0.9, 0.9333333333333333, 0.9666666666666667, 1.0] + values: [0.0, 6.961447494399997, 13.442795161599998, 19.444043001599994, 24.965191014399995, 30.006239199999996, 34.5671875584, 38.6480360896, 42.248784793599995, 45.3694336704, 48.00998272, 50.1704319424, 51.8507813376, 53.0510309056, 53.7711806464, 54.01123056, 53.7711806464, 53.0510309056, 51.8507813376, 50.1704319424, 48.009982720000004, 45.36943367040001, 42.24878479360001, 38.6480360896, 34.56718755839999, 30.006239199999996, 24.965191014399995, 19.444043001599994, 13.442795161599998, 6.961447494399997, 0.0] + y: + grid: *id022 + values: [0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0] + z: + grid: *id022 + values: [0.0, 3.67276364, 7.34552728, 11.01829092, 14.69105456, 18.363818199999997, 22.03658184, 25.70934548, 29.38210912, 33.054872759999995, 36.727636399999994, 40.400400039999994, 44.07316368, 47.74592732, 51.41869096, 55.0914546, 58.76421824, 62.43698188, 66.10974551999999, 69.78250915999999, 73.45527279999999, 77.12803643999999, 80.80080007999999, 84.47356372, 88.14632736, 91.819091, 95.49185464, 99.16461828, 102.83738192, 106.51014556, 110.1829092] + internal_structure_2d_fem: + reference_axis: + x: + grid: [0.0, 0.03333333333333333, 0.06666666666666667, 0.1, 0.13333333333333333, 0.16666666666666666, 0.2, 0.23333333333333334, 0.26666666666666666, 0.3, 0.3333333333333333, 0.36666666666666664, 0.4, 0.43333333333333335, 0.4666666666666667, 0.5, 0.5333333333333333, 0.5666666666666667, 0.6, 0.6333333333333333, 0.6666666666666666, 0.7, 0.7333333333333333, 0.7666666666666667, 0.8, 0.8333333333333334, 0.8666666666666667, 0.9, 0.9333333333333333, 0.9666666666666667, 1.0] + values: [0.0, 6.961447494399997, 13.442795161599998, 19.444043001599994, 24.965191014399995, 30.006239199999996, 34.5671875584, 38.6480360896, 42.248784793599995, 45.3694336704, 48.00998272, 50.1704319424, 51.8507813376, 53.0510309056, 53.7711806464, 54.01123056, 53.7711806464, 53.0510309056, 51.8507813376, 50.1704319424, 48.009982720000004, 45.36943367040001, 42.24878479360001, 38.6480360896, 34.56718755839999, 30.006239199999996, 24.965191014399995, 19.444043001599994, 13.442795161599998, 6.961447494399997, 0.0] + y: + grid: [0.0, 0.03333333333333333, 0.06666666666666667, 0.1, 0.13333333333333333, 0.16666666666666666, 0.2, 0.23333333333333334, 0.26666666666666666, 0.3, 0.3333333333333333, 0.36666666666666664, 0.4, 0.43333333333333335, 0.4666666666666667, 0.5, 0.5333333333333333, 0.5666666666666667, 0.6, 0.6333333333333333, 0.6666666666666666, 0.7, 0.7333333333333333, 0.7666666666666667, 0.8, 0.8333333333333334, 0.8666666666666667, 0.9, 0.9333333333333333, 0.9666666666666667, 1.0] + values: [0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0] + z: + grid: [0.0, 0.03333333333333333, 0.06666666666666667, 0.1, 0.13333333333333333, 0.16666666666666666, 0.2, 0.23333333333333334, 0.26666666666666666, 0.3, 0.3333333333333333, 0.36666666666666664, 0.4, 0.43333333333333335, 0.4666666666666667, 0.5, 0.5333333333333333, 0.5666666666666667, 0.6, 0.6333333333333333, 0.6666666666666666, 0.7, 0.7333333333333333, 0.7666666666666667, 0.8, 0.8333333333333334, 0.8666666666666667, 0.9, 0.9333333333333333, 0.9666666666666667, 1.0] + values: [0.0, 3.67276364, 7.34552728, 11.01829092, 14.69105456, 18.363818199999997, 22.03658184, 25.70934548, 29.38210912, 33.054872759999995, 36.727636399999994, 40.400400039999994, 44.07316368, 47.74592732, 51.41869096, 55.0914546, 58.76421824, 62.43698188, 66.10974551999999, 69.78250915999999, 73.45527279999999, 77.12803643999999, 80.80080007999999, 84.47356372, 88.14632736, 91.819091, 95.49185464, 99.16461828, 102.83738192, 106.51014556, 110.1829092] + webs: + - name: web0 + start_nd_arc: + grid: *id001 + values: [0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35,0.35] + end_nd_arc: + grid: *id001 + values: [0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65,0.65] + layers: + - name: Panel_Face_outer + material: Generic_Skin + n_plies: + grid: *id001 + values: [1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1] + start_nd_arc: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + end_nd_arc: + values: [1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: Leading_Edge + material: Generic_Pultrusion + n_plies: + grid: *id001 + values: [12,12,12,11,9,8,7,6,6,6,6,6,6,7,7,8,10,12,12,12,12] + start_nd_arc: + values: [0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525] + grid: *id001 + end_nd_arc: + values: [0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: HP_Aft_Panel_foam + material: Foam + n_plies: + grid: *id001 + values: [8,9,9,8,7,6,5,5,5,4,4,4,5,5,5,6,7,9,9,9,9] + start_nd_arc: + values: [0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75] + grid: *id001 + end_nd_arc: + values: [0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: HP_Fore_Panel_foam + material: Foam + n_plies: + grid: *id001 + values: [8,9,9,8,7,6,5,5,5,4,4,4,5,5,5,6,7,9,9,9,9] + start_nd_arc: + values: [0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475,0.5475] + grid: *id001 + end_nd_arc: + values: [0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: LP_Fore_Panel_foam + material: Foam + n_plies: + grid: *id001 + values: [8,9,9,8,7,6,5,5,5,4,4,4,5,5,5,6,7,9,9,9,9] + start_nd_arc: + values: [0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45] + grid: *id001 + end_nd_arc: + values: [0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525,0.4525] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: LP_Aft_Panel_foam + material: Foam + n_plies: + grid: *id001 + values: [8,9,9,8,7,6,5,5,5,4,4,4,5,5,5,6,7,9,9,9,9] + start_nd_arc: + values: [0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025] + grid: *id001 + end_nd_arc: + values: [0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: HP_Spar + material: Generic_Pultrusion + n_plies: + grid: *id001 + values: [12,13,13,12,10,8,8,7,7,7,7,7,7,8,8,9,11,13,13,13,13] + start_nd_arc: + values: [0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55,0.55] + grid: *id001 + end_nd_arc: + values: [0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75,0.75] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: LP_Spar + material: Generic_Pultrusion + n_plies: + grid: *id001 + values: [12,13,13,12,10,8,8,7,7,7,7,7,7,8,8,9,11,13,13,13,13] + start_nd_arc: + values: [0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25,0.25] + grid: *id001 + end_nd_arc: + values: [0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45,0.45] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: HP_TE + material: Generic_Pultrusion + n_plies: + grid: *id001 + values: [12,12,12,11,9,8,7,6,6,6,6,6,6,7,7,8,10,12,12,12,12] + start_nd_arc: + values: [0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975,0.975] + grid: *id001 + end_nd_arc: + values: [1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: LP_TE + material: Generic_Pultrusion + n_plies: + grid: *id001 + values: [12,12,12,11,9,8,7,6,6,6,6,6,6,7,7,8,10,12,12,12,12] + start_nd_arc: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + end_nd_arc: + values: [0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025,0.025] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: Panel_Face_inner + material: Generic_Skin + n_plies: + grid: *id001 + values: [1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1] + start_nd_arc: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + end_nd_arc: + values: [1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0] + grid: *id001 + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: web0_face + material: Generic_Skin + web: web0 + n_plies: + grid: *id001 + values: [1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1] + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: web0_core + material: Foam + web: web0 + n_plies: + grid: *id001 + values: [8,9,9,8,7,6,5,5,5,4,4,4,5,5,5,6,7,9,9,9,9] + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + - name: web0_face + material: Generic_Skin + web: web0 + n_plies: + grid: *id001 + values: [1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1] + fiber_orientation: + values: [0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0,0.0] + grid: *id001 + root: {d_f: 0.03, sigma_max: 675000000.0} + joint: {position: 0.0, mass: 0.0, cost: 0.0, bolt: M30, nonmaterial_cost: 0.0, reinforcement_layer_ss: joint_reinf_ss, reinforcement_layer_ps: joint_reinf_ps} + struts: + - name: strut1 + mountfraction_tower: [0.25,0.75] + mountfraction_blade: [0.25,0.75] + outer_shape_bem: + airfoil_position: + grid: &id002 [0, 0.333, 0.6667, 1.0] + labels: [NACA_0021, NACA_0021, NACA_0021, NACA_0021] + chord: + grid: *id002 + values: [6.0, 6.0, 6.0, 6.0] + twist: + grid: *id002 + values: [0.0, 0.0, 0.0, 0.0] + pitch_axis: + grid: *id002 + values: [0.3, 0.3, 0.3, 0.3] + reference_axis: + x: + grid: *id002 + values: [-0.0, -0.0, -0.0, -0.0] + y: + grid: *id002 + values: [0.0, 0.0, 0.0, 0.0] + z: + grid: *id002 + values: [0.0, 0.15, 0.45, 0.75] + internal_structure_2d_fem: + reference_axis: + x: + grid: [0.0] + values: [0.0] + y: + grid: [0.0] + values: [0.0] + z: + grid: [0.0] + values: [0.0] + webs: + - name: web0 + start_nd_arc: + grid: *id002 + values: [0.35,0.35,0.35,0.35] + end_nd_arc: + grid: *id002 + values: [0.65,0.65,0.65,0.65] + layers: + - name: Panel_Face_outer + material: Generic_Skin + n_plies: + grid: *id002 + values: [1,1,1,1] + start_nd_arc: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + end_nd_arc: + values: [1.0,1.0,1.0,1.0] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: Leading_Edge + material: Generic_Pultrusion + n_plies: + grid: *id002 + values: [12,12,12,12] + start_nd_arc: + values: [0.4525,0.4525,0.4525,0.4525] + grid: *id002 + end_nd_arc: + values: [0.5475,0.5475,0.5475,0.5475] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: HP_Aft_Panel_foam + material: Foam + n_plies: + grid: *id002 + values: [8,8,8,8] + start_nd_arc: + values: [0.75,0.75,0.75,0.75] + grid: *id002 + end_nd_arc: + values: [0.975,0.975,0.975,0.975] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: HP_Fore_Panel_foam + material: Foam + n_plies: + grid: *id002 + values: [8,8,8,8] + start_nd_arc: + values: [0.5475,0.5475,0.5475,0.5475] + grid: *id002 + end_nd_arc: + values: [0.55,0.55,0.55,0.55] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: LP_Fore_Panel_foam + material: Foam + n_plies: + grid: *id002 + values: [8,8,8,8] + start_nd_arc: + values: [0.45,0.45,0.45,0.45] + grid: *id002 + end_nd_arc: + values: [0.4525,0.4525,0.4525,0.4525] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: LP_Aft_Panel_foam + material: Foam + n_plies: + grid: *id002 + values: [8,8,8,8] + start_nd_arc: + values: [0.025,0.025,0.025,0.025] + grid: *id002 + end_nd_arc: + values: [0.25,0.25,0.25,0.25] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: HP_Spar + material: Generic_Pultrusion + n_plies: + grid: *id002 + values: [12,12,12,12] + start_nd_arc: + values: [0.55,0.55,0.55,0.55] + grid: *id002 + end_nd_arc: + values: [0.75,0.75,0.75,0.75] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: LP_Spar + material: Generic_Pultrusion + n_plies: + grid: *id002 + values: [12,12,12,12] + start_nd_arc: + values: [0.25,0.25,0.25,0.25] + grid: *id002 + end_nd_arc: + values: [0.45,0.45,0.45,0.45] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: HP_TE + material: Generic_Pultrusion + n_plies: + grid: *id002 + values: [12,12,12,12] + start_nd_arc: + values: [0.975,0.975,0.975,0.975] + grid: *id002 + end_nd_arc: + values: [1.0,1.0,1.0,1.0] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: LP_TE + material: Generic_Pultrusion + n_plies: + grid: *id002 + values: [12,12,12,12] + start_nd_arc: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + end_nd_arc: + values: [0.025,0.025,0.025,0.025] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: Panel_Face_inner + material: Generic_Skin + n_plies: + grid: *id002 + values: [1,1,1,1] + start_nd_arc: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + end_nd_arc: + values: [1.0,1.0,1.0,1.0] + grid: *id002 + fiber_orientation: + values: [0.0,0.0,0.0,0.0] + grid: *id002 + - name: web0_face + material: Generic_Pultrusion + web: web0 + n_plies: + grid: *id002 + values: [1,1,1,1] + fiber_orientation: + values: [0.0, 0.0, 0.0, 0.0] + grid: *id002 + - name: web0_core + material: Foam + web: web0 + n_plies: + grid: *id002 + values: [8,8,8,8] + fiber_orientation: + values: [0.0, 0.0, 0.0, 0.0] + grid: *id002 + - name: web0_face + material: Generic_Pultrusion + web: web0 + n_plies: + grid: *id002 + values: [1,1,1,1] + fiber_orientation: + values: [0.0, 0.0, 0.0, 0.0] + grid: *id002 + root: {d_f: 0.03, sigma_max: 675000000.0} + joint: {position: 0.0, mass: 0.0, cost: 0.0, bolt: M30, nonmaterial_cost: 0.0, reinforcement_layer_ss: joint_reinf_ss, reinforcement_layer_ps: joint_reinf_ps} +airfoils: + - name: NACA6_1000 + coordinates: + x: [1.0, 0.993181, 0.972909, 0.939737, 0.89457, 0.838641, 0.773474, 0.700848, 0.622743, 0.54129, 0.45870999999999995, 0.37725699999999995, 0.299152, 0.226526, 0.16135900000000003, 0.10543000000000002, 0.060262999999999955, 0.027090999999999976, 0.0068190000000000195, 0.0, 0.0068190000000000195, 0.027090999999999976, 0.060262999999999955, 0.10543000000000002, 0.16135900000000003, 0.226526, 0.299152, 0.37725699999999995, 0.45870999999999995, 0.54129, 0.622743, 0.700848, 0.773474, 0.838641, 0.89457, 0.939737, 0.972909, 0.993181, 1.0] + y: [0.0, 0.082442, 0.162359, 0.237976, 0.307106, 0.367865, 0.418583, 0.457883, 0.484712, 0.498283, 0.498283, 0.484712, 0.457883, 0.418583, 0.367865, 0.307106, 0.237976, 0.162359, 0.082442, 0.0, -0.082442, -0.162359, -0.237976, -0.307106, -0.367865, -0.418583, -0.457883, -0.484712, -0.498283, -0.498283, -0.484712, -0.457883, -0.418583, -0.367865, -0.307106, -0.237976, -0.162359, -0.082442, 0.0] + relative_thickness: 1.0 + aerodynamic_center: 0.25 + polars: + - configuration: '' + re: 2000000.0 + c_l: + grid: [-3.141592653589793, 0.0, 3.141592653589793] + values: [0.0, 0.0, 0.0] + c_d: + grid: [-3.141592653589793, 0.0, 3.141592653589793] + values: [0.3, 0.3, 0.3] + c_m: + grid: [-3.141592653589793, 0.0, 3.141592653589793] + values: [0.0, 0.0, 0.0] +materials: + - name: Generic_Pultrusion + description: a description of the material + source: source link + ply_t: 0.001 + E: [27000000000.0, 6000000000.0, 6000000000.0] + G: [3000000000.0, 3000000000.0, 3000000000.0] + nu: [0.26, 0.36, 0.26] + rho: 1850.0 + Xt: [400000000.0, 100000000.0, 100000000.0] + Xc: [200000000.0, 200000000.0, 200000000.0] + S: [100000000.0, 100000000.0, 100000000.0] + unit_cost: 3.00 + A: [400.0,350.0,325.0,275.0,200.0,0.0] + m: [0.0,1.0,2.0,4.0,6.0,20.0] + - name: Generic_Skin + description: a description of the material + source: source link + ply_t: 0.001 + E: [27000000000.0, 6000000000.0, 6000000000.0] + G: [3000000000.0, 3000000000.0, 3000000000.0] + nu: [0.26, 0.36, 0.26] + rho: 1850.0 + Xt: [400000000.0, 100000000.0, 100000000.0] + Xc: [200000000.0, 200000000.0, 200000000.0] + S: [100000000.0, 100000000.0, 100000000.0] + unit_cost: 3.00 + A: [400.0,350.0,325.0,275.0,200.0,0.0] + m: [0.0,1.0,2.0,4.0,6.0,20.0] + - name: steel + description: a description of the material + source: source link + ply_t: 0.001 + E: [199948000000.0, 199948000000.0, 199948000000.0] + G: [76877000000.0, 76877000000.0, 76877000000.0] + nu: [0.3, 0.3, 0.3] + rho: 7861.092935 + Xt: [420000000.0, 420000000.0, 420000000.0] + Xc: [250000000.0, 250000000.0, 250000000.0] + S: [100000000.0, 100000000.0, 100000000.0] + unit_cost: 1.00 + A: [420.0,415.0,375.0,275.0,190.0,0.0] + m: [0.0,1.0,2.0,4.0,6.0,20.0] + - name: Foam + description: a description of the material + source: source link + ply_t: 0.001 + E: [1000000000.0, 1000000000.0, 1000000000.0] + G: [100000000.0, 100000000.0, 100000000.0] + nu: [0.3, 0.3, 0.3] + rho: 100.0 + Xt: [50000000.0, 50000000.0, 50000000.0] + Xc: [50000000.0, 50000000.0, 50000000.0] + S: [100000000.0, 100000000.0, 100000000.0] + unit_cost: 0.10 + A: [50.0,45.0,40.0,35.0,20.0,0.0] + m: [0.0,1.0,2.0,4.0,6.0,20.0] +environment: {air_density: 1.225, air_dyn_viscosity: 1.7894e-5, air_speed_sound: 1500.0, shear_exp: 0.0, gravity: [0,0,-9.81], weib_shape_parameter: 2.0, water_density: 1025.0, water_dyn_viscosity: 0.0013351, soil_shear_modulus: 140000000.0, soil_poisson: 0.4, water_depth: 50.0, air_pressure: 101325.0, air_vapor_pressure: 2500.0, significant_wave_height: 1.0, significant_wave_period: 5.0} \ No newline at end of file diff --git a/src/topRunDLC.jl b/src/topRunDLC.jl index a1f6334a..11761fdd 100644 --- a/src/topRunDLC.jl +++ b/src/topRunDLC.jl @@ -16,7 +16,7 @@ mutable struct MasterInput nbelem ncelem nselem - AModel + AeroModel ifw WindType windINPfilename @@ -54,7 +54,7 @@ function MasterInput(; nbelem = 60, #blade elements in each ncelem = 10, #central cable elements in each if turbineType is ARCUS nselem = 5, #strut elements in each if turbineType has struts - AModel = "AD", + AeroModel = "AD", ifw = false, WindType = 1, ifw_libfile = "./../openfast/build/modules/inflowwind/libifw_c_binding", @@ -72,59 +72,565 @@ function MasterInput(; ) return MasterInput(analysisType,turbineType,eta,Nbld,towerHeight,rho,Vinf,controlStrategy, - RPM,Nslices,ntheta,structuralModel,ntelem,nbelem,ncelem,nselem,AModel,ifw,WindType,windINPfilename,ifw_libfile,adi_lib,adi_rootname, + RPM,Nslices,ntheta,structuralModel,ntelem,nbelem,ncelem,nselem,AeroModel,ifw,WindType,windINPfilename,ifw_libfile,adi_lib,adi_rootname, Blade_Height,Blade_Radius,numTS,delta_t,NuMad_geom_xlscsv_file_twr,NuMad_mat_xlscsv_file_twr, NuMad_geom_xlscsv_file_bld,NuMad_mat_xlscsv_file_bld,NuMad_geom_xlscsv_file_strut,NuMad_mat_xlscsv_file_strut) end +""" + +OWENS_Options(dict_in::OrderedCollections.OrderedDict{Symbol,Any}) + + # Input + * `analysisType`: default "Unsteady", Unsteady, DLC, Campbell, todo: steady, flutter may be re-activated in the future. + * `AeroModel`: default "DMS", OWENSAero model "DMS" for double multiple streamtube or "AC" for actuator cylinder, or "AD" for aerodyn + * `structuralModel`: default "TNB", Structural models available: TNB full timoshenko beam elements with time newmark beta time stepping, ROM reduced order modal model of the timoshenko elements, GX with GXBeam's methods for geometrically exact beam theory and more efficient methods and time stepping + * `controlStrategy`: default "normal", should be in WindIO?- yes, + * `numTS`: default 10, number of time steps TODO: change to sim time and make this derived + * `delta_t`: default 0.05, time step in seconds + * `platformActive`: default false, flag to indicate if the floating platform model is active. + * `topsideOn`: default true, flat to be able to turn off the rotor and just run the floating portions + * `interpOrder`: default 2, if platformActive, order used for extrapolating inputs and states, 0 flat, 1 linear, 2 quadratic + * `dataOutputFilename`: default nothing, data output filename with path, set to nothing or don't specify to not output anything + * `rigid`: default false, this bypasses the structural solve and just mapps the applied loads as the reaction loads, and the deflections remain 0 + * `TOL`: default 1e-4, gauss-seidel iteration tolerance - i.e. the two-way iteration tolerance + * `MAXITER`: default 300, gauss-seidel max iterations - i.e. the two-way iterations + * `verbosity`: default 2, verbosity where 0 is nothing, 1 is warnings, 2 is summary outputs, 3 is detailed outputs, and 4 is everything + * `VTKsaveName`: default "./vtk/windio", Path and name of the VTK outputs, recommended to put it in its own folder (which it will automatically create if needed) + * `aeroLoadsOn`: default 2, Level of aero coupling 0 structures only, 1 no deformation passed to the aero, 2 two-way coupling, 1.5 last time step's deformations passed to this timesteps aero and no internal iteration. + * `Prescribed_RPM_time_controlpoints`: default [0.0,100000.1], If controlStrategy is "fixedRPM", array of time control points for the internal spline + * `Prescribed_RPM_RPM_controlpoints`: default [17.2,17.2], If controlStrategy is "fixedRPM", array of RPM control points for the internal spline + * `Prescribed_Vinf_time_controlpoints`: default [0.0,100000.1], If AeroModel is "DMS" or "AC, and ifw is false, array of time control points for the internal spline + * `Prescribed_Vinf_Vinf_controlpoints`: default [17.2,17.2], If AeroModel is "DMS" or "AC, and ifw is false, array of Vinf control points for the internal spline + + + # Output + * `OWENS_Options`: +""" +mutable struct OWENS_Options + analysisType + AeroModel + structuralModel + controlStrategy + numTS + delta_t + platformActive + topsideOn + interpOrder + dataOutputFilename + rigid + TOL + MAXITER + verbosity + VTKsaveName + aeroLoadsOn + Prescribed_RPM_time_controlpoints + Prescribed_RPM_RPM_controlpoints + Prescribed_Vinf_time_controlpoints + Prescribed_Vinf_Vinf_controlpoints + + # Constructor that takes a dictionary + function OWENS_Options(dict_in::OrderedCollections.OrderedDict{Symbol,Any}) + # Use get to provide default values for missing fields + new( + get(dict_in,:analysisType, "Unsteady"), # Unsteady, DLC, Campbell, todo: steady, flutter may be re-activated in the future. + get(dict_in,:AeroModel, "DMS"), # OWENSAero model "DMS" for double multiple streamtube or "AC" for actuator cylinder, or "AD" for aerodyn + get(dict_in,:structuralModel, "TNB"), # Structural models available: TNB full timoshenko beam elements with time newmark beta time stepping, ROM reduced order modal model of the timoshenko elements, GX with GXBeam's methods for geometrically exact beam theory and more efficient methods and time stepping + get(dict_in,:controlStrategy, "normal"), # should be in WindIO?- yes, + get(dict_in,:numTS, 10), # number of time steps TODO: change to sim time and make this derived + get(dict_in,:delta_t, 0.05), # time step in seconds + get(dict_in,:platformActive, false), # flag to indicate if the floating platform model is active. + get(dict_in,:topsideOn, true), # flat to be able to turn off the rotor and just run the floating portions + get(dict_in,:interpOrder, 2), # if platformActive, order used for extrapolating inputs and states, 0 flat, 1 linear, 2 quadratic + get(dict_in,:dataOutputFilename, "./default_savename"), # data output filename with path, set to nothing or don't specify to not output anything + get(dict_in,:rigid, false), # this bypasses the structural solve and just mapps the applied loads as the reaction loads, and the deflections remain 0 + get(dict_in,:TOL, 1e-4), # gauss-seidel iteration tolerance - i.e. the two-way iteration tolerance + get(dict_in,:MAXITER, 300), # gauss-seidel max iterations - i.e. the two-way iterations + get(dict_in,:verbosity, 2), # verbosity where 0 is nothing, 1 is warnings, 2 is summary outputs, 3 is detailed outputs, and 4 is everything + get(dict_in,:VTKsaveName, "./vtk/windio"), # Path and name of the VTK outputs, recommended to put it in its own folder (which it will automatically create if needed) + get(dict_in,:aeroLoadsOn, 2), # Level of aero coupling 0 structures only, 1 no deformation passed to the aero, 2 two-way coupling, 1.5 last time step's deformations passed to this timesteps aero and no internal iteration. + get(dict_in,:Prescribed_RPM_time_controlpoints, [0.0,100000.1]), # If controlStrategy is "fixedRPM", array of time control points for the internal spline + get(dict_in,:Prescribed_RPM_RPM_controlpoints, [17.2,17.2]), # If controlStrategy is "fixedRPM", array of RPM control points for the internal spline + get(dict_in,:Prescribed_Vinf_time_controlpoints, [0.0,100000.1]), # If AeroModel is "DMS" or "AC, and ifw is false, array of time control points for the internal spline + get(dict_in,:Prescribed_Vinf_Vinf_controlpoints, [17.2,17.2]), # If AeroModel is "DMS" or "AC, and ifw is false, array of Vinf control points for the internal spline + ) + end +end + +""" + +DLC_Options(dict_in::OrderedCollections.OrderedDict{Symbol,Any}) + + # Input + * `DLCs`: default ["none"], name of DLC + * `Vinf_range`: default inRange(5,20,16), inflow Cutin to cutout and discretization + * `IEC_std`: default "\"1-ED3\"", turbsim input file IEC standard + * `WindChar`: default "\"A\"", turbsim wind charasteric + * `WindClass`: default , DLC turbsim wind class + * `turbsimsavepath`: default "./turbsimfiles", path where the turbsim files are saved + * `pathtoturbsim`: default othing, path to the turbsim executable + * `NumGrid_Z`: default 8, turbsim vertical discretizations + * `NumGrid_Y`: default 6, turbsim horizontal discretizations + * `Vref`: default 0.0, reference/nominal wind speed m/s for turbsim or other inflow wind input file (depending on which DLC is selected) + * `Vdesign`: default 1.0, Design or rated speed of turbine, used for certain DLC cases + * `grid_oversize`: default .1, amount that the turbsim inflow is oversized compared to the turbine to allow for deflection + * `regenWindFiles`: default false, force regeneration of turbsim files even if they already exist + * `delta_t_turbsim`: default .05, turbsim timestep + * `simtime_turbsim`: default 00.0, turbsim total time, which loops if simtime exceeds turbsim time + * `RandSeed1`: default 0071, turbsim random seed number + + + # Output + * `DLC_Options`: +""" +mutable struct DLC_Options + DLCs + Vinf_range + IEC_std + WindChar + WindClass + turbsimsavepath + pathtoturbsim + NumGrid_Z + NumGrid_Y + Vref + Vdesign + grid_oversize + regenWindFiles + delta_t_turbsim + simtime_turbsim + RandSeed1 + + # Constructor that takes a dictionary + function DLC_Options(dict_in::OrderedCollections.OrderedDict{Symbol,Any}) + # Use get to provide default values for missing fields + new( + get(dict_in,:DLCs,["none"]), # name of DLC + get(dict_in,:Vinf_range,LinRange(5,20,16)), # inflow Cutin to cutout and discretization + get(dict_in,:IEC_std,"\"1-ED3\""), # turbsim input file IEC standard + get(dict_in,:WindChar,"\"A\""), # turbsim wind charasteric + get(dict_in,:WindClass,1), # DLC turbsim wind class + get(dict_in,:turbsimsavepath,"./turbsimfiles"), # path where the turbsim files are saved + get(dict_in,:pathtoturbsim,nothing), # path to the turbsim executable + get(dict_in,:NumGrid_Z,38), # turbsim vertical discretizations + get(dict_in,:NumGrid_Y,26), # turbsim horizontal discretizations + get(dict_in,:Vref,10.0), # reference/nominal wind speed m/s for turbsim or other inflow wind input file (depending on which DLC is selected) + get(dict_in,:Vdesign,11.0), # Design or rated speed of turbine, used for certain DLC cases + get(dict_in,:grid_oversize,1.1), # amount that the turbsim inflow is oversized compared to the turbine to allow for deflection + get(dict_in,:regenWindFiles,false), #, force regeneration of turbsim files even if they already exist + get(dict_in,:delta_t_turbsim,0.05), # turbsim timestep + get(dict_in,:simtime_turbsim,600.0), # turbsim total time, which loops if simtime exceeds turbsim time + get(dict_in,:RandSeed1,40071), # turbsim random seed number + + ) + end +end + +""" + +OWENSAero_Options(dict_in::OrderedCollections.OrderedDict{Symbol,Any}) + + # Input + * `Nslices`: default 20, number of 3-D slices for the strip method to go from 2D to 3D considering curved deforming blades + * `ntheta`: default 30, number of azimuthal discretizations + * `ifw`: default false, use the inflow wind coupling to get inflow velocities TODO: change ifw to inflowwind inflowwind_active etc everywhere + * `DynamicStallModel`: defaultBV", dynamic stall model, should be under an OWENSAero options + * `RPI`: default true, rotating point iterative method (i.e. it just calculates at the blade positions and is much faster) + * `Aero_Buoyancy_Active`: default false, flag to turn buoyancy on for the blades. This is likely to be replaced by a different model + * `Aero_AddedMass_Active`: default false, flag to turn added mass forces on, don't turn on if the added mass in the structures are on + * `Aero_RotAccel_Active`: default false, flag to turn added mass forces on, don't turn on if the added mass in the structures are on + + + # Output + * `OWENSAero_Options`: +""" +mutable struct OWENSAero_Options #TODO: move these downstream to their respective packages and unify the options with those + Nslices + ntheta + ifw + DynamicStallModel + RPI + Aero_Buoyancy_Active + Aero_AddedMass_Active + Aero_RotAccel_Active + + # Constructor that takes a dictionary + function OWENSAero_Options(dict_in::OrderedCollections.OrderedDict{Symbol,Any}) + # Use get to provide default values for missing fields + new( + get(dict_in,:Nslices, 20), # number of 3-D slices for the strip method to go from 2D to 3D considering curved deforming blades + get(dict_in,:ntheta, 30), # number of azimuthal discretizations + get(dict_in,:ifw, false), # use the inflow wind coupling to get inflow velocities TODO: change ifw to inflowwind inflowwind_active etc everywhere + get(dict_in,:DynamicStallModel,"BV"), # dynamic stall model, should be under an OWENSAero options + get(dict_in,:RPI, true), # rotating point iterative method (i.e. it just calculates at the blade positions and is much faster) + get(dict_in,:Aero_Buoyancy_Active, false), # flag to turn buoyancy on for the blades. This is likely to be replaced by a different model + get(dict_in,:Aero_AddedMass_Active, false), # flag to turn added mass forces on, don't turn on if the added mass in the structures are on + get(dict_in,:Aero_RotAccel_Active, false), # flag to turn added mass forces on, don't turn on if the added mass in the structures are on + ) + end +end + +""" + +OWENSFEA_Options(dict_in::OrderedCollections.OrderedDict{Symbol,Any}) + + # Input + * `nlOn`: default true, nonlinear effects + * `RayleighAlpha`: default 0.05, damping coefficient scalar on the stiffness matrix + * `RayleighBeta`: default 0.05, damping coefficient scalar on the mass matrix + * `iterationType`: default "DI", internal iteration type DI direct iteration, NR newton rhapson (which is less stable than DI) + * `guessFreq`: default 0.0, for the built in flutter model frequency guessed for the flutter frequency + * `numModes`: default 20, ROM model, number of modes used in the analysis type. Less is faster but less accurate + * `adaptiveLoadSteppingFlag`: default true, for steady analysis if convergence fails, it will reduce the load and retry then increase the load + * `minLoadStepDelta`: default 0.0500, minimum change in load step + * `minLoadStep`: default 0.0500, minimum value of reduced load + * `prescribedLoadStep`: default 0.0, optional prescribed load fraction + * `maxNumLoadSteps`: default 20, used in static (steady state) analysis, max load steps for adaptive load stepping + * `tolerance`: default 1.0000e-06, total mesh unsteady analysis convergence tolerance for a timestep within the structural model + * `maxIterations`: default 50, total mesh unsteady analysis convergence max iterations for a timestep + * `elementOrder`: default 1, Element order, 1st order, 2nd order etc; determines the number of nodes per element (order +1). Orders above 1 have not been tested in a long time + * `alpha`: default 0.5, newmark time integration alpha parameter + * `gamma`: default 0.5, newmark time integration gamma parameter + * `AddedMass_Coeff_Ca`: default 0.0, added mass coefficient, scaling factor (typically 0-1) on the cones of water mass applied to each structural element in the 22 and 33 diagonal terms. 0 turns this off + * `platformTurbineConnectionNodeNumber`: default 1, TODO: reconnect this + * `aeroElasticOn`: default false, OWENSFEA for the built in flutter model + * `spinUpOn`: default true, TODO: remove this since it should always be true since that is how its used. To turn it off, just set RPM and gravity to 0. OWENSFEA modal analysis, calculates steady centrifugal strain stiffening and then passes that model to the modal analysis + * `predef`: default false, Predeformation flag for two state analysis where a portion of the blade is deformed and the nonlinear strain stiffening terms are "update"-d, then "use"-d in two different analysis + + # Output + * `OWENSFEA_Options`: +""" +mutable struct OWENSFEA_Options + nlOn + RayleighAlpha + RayleighBeta + iterationType + guessFreq + numModes + adaptiveLoadSteppingFlag + minLoadStepDelta + minLoadStep + prescribedLoadStep + maxNumLoadSteps + tolerance + maxIterations + elementOrder + alpha + gamma + AddedMass_Coeff_Ca + platformTurbineConnectionNodeNumber + aeroElasticOn + spinUpOn + predef + + # Constructor that takes a dictionary + function OWENSFEA_Options(dict_in::OrderedCollections.OrderedDict{Symbol,Any}) + # Use get to provide default values for missing fields + new( + get(dict_in,:nlOn, true), # nonlinear effects + get(dict_in,:RayleighAlpha, 0.05), # damping coefficient scalar on the stiffness matrix + get(dict_in,:RayleighBeta, 0.05), # damping coefficient scalar on the mass matrix + get(dict_in,:iterationType, "DI"), # internal iteration type DI direct iteration, NR newton rhapson (which is less stable than DI) + get(dict_in,:guessFreq, 0.0), # for the built in flutter model frequency guessed for the flutter frequency + get(dict_in,:numModes, 20), # ROM model, number of modes used in the analysis type. Less is faster but less accurate + get(dict_in,:adaptiveLoadSteppingFlag, true), # for steady analysis if convergence fails, it will reduce the load and retry then increase the load + get(dict_in,:minLoadStepDelta, 0.0500), # minimum change in load step + get(dict_in,:minLoadStep, 0.0500), # minimum value of reduced load + get(dict_in,:prescribedLoadStep, 0.0), # optional prescribed load fraction + get(dict_in,:maxNumLoadSteps, 20), # used in static (steady state) analysis, max load steps for adaptive load stepping + get(dict_in,:tolerance, 1.0000e-06), # total mesh unsteady analysis convergence tolerance for a timestep within the structural model + get(dict_in,:maxIterations, 50), # total mesh unsteady analysis convergence max iterations for a timestep + get(dict_in,:elementOrder, 1), # Element order, 1st order, 2nd order etc; determines the number of nodes per element (order +1). Orders above 1 have not been tested in a long time + get(dict_in,:alpha, 0.5), # newmark time integration alpha parameter + get(dict_in,:gamma, 0.5), # newmark time integration gamma parameter + get(dict_in,:AddedMass_Coeff_Ca, 0.0), # added mass coefficient, scaling factor (typically 0-1) on the cones of water mass applied to each structural element in the 22 and 33 diagonal terms. 0 turns this off + get(dict_in,:platformTurbineConnectionNodeNumber, 1), # TODO: reconnect this + get(dict_in,:aeroElasticOn, false), # OWENSFEA for the built in flutter model + get(dict_in,:spinUpOn, true), # TODO: remove this since it should always be true since that is how its used. To turn it off, just set RPM and gravity to 0. OWENSFEA modal analysis, calculates steady centrifugal strain stiffening and then passes that model to the modal analysis + get(dict_in,:predef, false), # Predeformation flag for two state analysis where a portion of the blade is deformed and the nonlinear strain stiffening terms are "update"-d, then "use"-d in two different analysis + ) + end +end + +""" + +OWENSOpenFASTWrappers_Options(dict_in::OrderedCollections.OrderedDict{Symbol,Any}) + + # Input + * `windINPfilename`: default nothing, If ifw or AeroDyn is being used, gets overwritten if using the DLC analysis type, the moordyn file location, like in the unit test + * `ifw_libfile`: default nothing, location of the respective OpenFAST library, if nothing it will use the internal OWENS installation + * `hd_lib`: default nothing, location of the respective OpenFAST library, if nothing it will use the internal OWENS installation + * `md_lib`: default nothing, location of the respective OpenFAST library, if nothing it will use the internal OWENS installation + * `adi_lib`: default nothing, location of the respective OpenFAST library, if nothing it will use the internal OWENS installation + * `adi_rootname`: default "/aerodyn", location of the respective OpenFAST library, if nothing it will use the internal OWENS installation + * `hd_input_file`: default "none", If platformActive, the hydrodyn file location, like in the unit test + * `ss_input_file`: default "none", If platformActive, the sea state file location, like in the unit test + * `md_input_file`: default "none", If platformActive, the moordyn file location, like in the unit test + * `potflowfile`: default nothing, If platformActive, the potential flow files location, like in the unit test + * `WindType`: default 3, Derived parameter, inflowwind wind file type when DLC generator is active, matches inflowwind WindType + + # Output + * `OWENSOpenFASTWrappers_Options`: +""" +mutable struct OWENSOpenFASTWrappers_Options + windINPfilename + ifw_libfile + hd_lib + md_lib + adi_lib + adi_rootname + hd_input_file + ss_input_file + md_input_file + potflowfile + WindType + + # Constructor that takes a dictionary + function OWENSOpenFASTWrappers_Options(dict_in::OrderedCollections.OrderedDict{Symbol,Any}) + # Use get to provide default values for missing fields + new( + get(dict_in,:windINPfilename, nothing), # If ifw or AeroDyn is being used, gets overwritten if using the DLC analysis type, the moordyn file location, like in the unit test + get(dict_in,:ifw_libfile, nothing), # location of the respective OpenFAST library, if nothing it will use the internal OWENS installation + get(dict_in,:hd_lib, nothing),# location of the respective OpenFAST library, if nothing it will use the internal OWENS installation + get(dict_in,:md_lib, nothing),# location of the respective OpenFAST library, if nothing it will use the internal OWENS installation + get(dict_in,:adi_lib, nothing),# location of the respective OpenFAST library, if nothing it will use the internal OWENS installation + get(dict_in,:adi_rootname, "/aerodyn"),# location of the respective OpenFAST library, if nothing it will use the internal OWENS installation + get(dict_in,:hd_input_file, "none"), # If platformActive, the hydrodyn file location, like in the unit test + get(dict_in,:ss_input_file, "none"), # If platformActive, the sea state file location, like in the unit test + get(dict_in,:md_input_file, "none"), # If platformActive, the moordyn file location, like in the unit test + get(dict_in,:potflowfile, nothing),# If platformActive, the potential flow files location, like in the unit test + get(dict_in,:WindType, 3),#Derived parameter, inflowwind wind file type when DLC generator is active, matches inflowwind WindType + ) + end +end + + +""" + +Mesh_Options(dict_in::OrderedCollections.OrderedDict{Symbol,Any}) + + # Input + * `ntelem`: default 20, number of tower elements in each blade, plus nodes wherever there is a component overlap + * `nbelem`: default 30, number of blade elements in each blade, plus nodes wherever there is a component overlap + * `ncelem`: default 30, number of cable elements in each cable if ARCUS + * `nselem`: default 10, number of elements in each strut + * `angularOffset`: default 0.0, moves the structure to align with the aero model + * `joint_type`: default 0, optionally can specify the strut to blade joints to be pinned about different axes, or 0 for welded + * `c_mount_ratio`: default 0.05, for ARCUS, where the cable mounts on the lower side of the blade + * `AD15hubR`: default 0.1, parameter, used in aerodyn coupling for the hub radius so that the vortex sheets don't go within the hub + * `cables_connected_to_blade_base`: default true, for ARCUS, for the two part simulation of the blade bending + * `turbineType`: default "Darrieus", mesh Darrieus, H-VAWT, controls if the tips of the blades are joined to the tower in the mesh or not. + + # Output + * `Mesh_Options`: +""" +mutable struct Mesh_Options + ntelem + nbelem + ncelem + nselem + angularOffset + joint_type + c_mount_ratio + AD15hubR + cables_connected_to_blade_base + turbineType + + # Constructor that takes a dictionary + function Mesh_Options(dict_in::OrderedCollections.OrderedDict{Symbol,Any}) + # Use get to provide default values for missing fields + new( + get(dict_in,:ntelem, 20), # number of tower elements in each blade, plus nodes wherever there is a component overlap + get(dict_in,:nbelem, 30), # number of blade elements in each blade, plus nodes wherever there is a component overlap + get(dict_in,:ncelem, 30), # number of cable elements in each cable if ARCUS + get(dict_in,:nselem, 10), # number of elements in each strut + get(dict_in,:angularOffset, 0.0), # moves the structure to align with the aero model + get(dict_in,:joint_type, 0), # optionally can specify the strut to blade joints to be pinned about different axes, or 0 for welded + get(dict_in,:c_mount_ratio, 0.05), # for ARCUS, where the cable mounts on the lower side of the blade + get(dict_in,:AD15hubR, 0.1), # parameter, used in aerodyn coupling for the hub radius so that the vortex sheets don't go within the hub + get(dict_in,:cables_connected_to_blade_base, true), # for ARCUS, for the two part simulation of the blade bending + get(dict_in,:turbineType, "Darrieus"), #mesh Darrieus, H-VAWT, controls if the tips of the blades are joined to the tower in the mesh or not. + ) + end +end + + +""" +Drivetrain_Options(dict_in::OrderedCollections.OrderedDict{Symbol,Any}) + + # Input + * `turbineStartup`: default 0, TODO: clean up since it should be derived from control strategy + * `usingRotorSpeedFunction`: default false, TODO: clean up the speed function since the omegaocp RPM gets splined already + * `driveTrainOn`: default false, flag to turn on the drivetrain model TODO: clean this up to make it always use the drivetrain model, with default 100% efficiency and ratio of 1 so it outputs the values + * `JgearBox`: default 0.0, torsional stiffness of the gearbox TODO: resolve units + * `gearRatio`: default 1.0, ratio between the turbine driveshaft and generator shaft + * `gearBoxEfficiency`: default 1.0, efficiency of the gearbox, just decreases the torque that the generator model sees + * `generatorOn`: default false, TODO: clean up the generator options + * `useGeneratorFunction`: default false, TODO: clean up the generator options + * `generatorProps`: default 0.0, TODO: clean up the generator options + * `ratedTorque`: default 0.0, TODO: clean up the generator options + * `zeroTorqueGenSpeed`: default 0.0, TODO: clean up the generator options + * `pulloutRatio`: default 0.0, TODO: clean up the generator options + * `ratedGenSlipPerc`: default 0.0, TODO: clean up the generator options + * `OmegaGenStart`: default 0.0, TODO: clean up the generator options + * `driveShaftProps_K`: default 0.0, TODO: break this out, driveshaft stiffness and damping + * `driveShaftProps_C`: default 0.0, TODO: break this out, driveshaft stiffness and damping + + # Output + * `Drivetrain_Options`: +""" +mutable struct Drivetrain_Options + turbineStartup + usingRotorSpeedFunction + driveTrainOn + JgearBox + gearRatio + gearBoxEfficiency + generatorOn + useGeneratorFunction + generatorProps + ratedTorque + zeroTorqueGenSpeed + pulloutRatio + ratedGenSlipPerc + OmegaGenStart + driveShaft_K + driveShaft_C + + # Constructor that takes a dictionary + function Drivetrain_Options(dict_in::OrderedCollections.OrderedDict{Symbol,Any}) + # Use get to provide default values for missing fields + new( + get(dict_in,:turbineStartup, 0), # TODO: clean up since it should be derived from control strategy + get(dict_in,:usingRotorSpeedFunction, false), #TODO: clean up the speed function since the omegaocp RPM gets splined already + get(dict_in,:driveTrainOn, false), #flag to turn on the drivetrain model #TODO: clean this up to make it always use the drivetrain model, with default 100% efficiency and ratio of 1 so it outputs the values + get(dict_in,:JgearBox, 0.0), # torsional stiffness of the gearbox TODO: resolve units + get(dict_in,:gearRatio, 1.0), # ratio between the turbine driveshaft and generator shaft + get(dict_in,:gearBoxEfficiency, 1.0), # efficiency of the gearbox, just decreases the torque that the generator model sees + get(dict_in,:generatorOn, false), #TODO: clean up the generator options + get(dict_in,:useGeneratorFunction, false), #TODO: clean up the generator options + get(dict_in,:generatorProps, 0.0), #TODO: clean up the generator options + get(dict_in,:ratedTorque, 0.0), #TODO: clean up the generator options + get(dict_in,:zeroTorqueGenSpeed, 0.0), #TODO: clean up the generator options + get(dict_in,:pulloutRatio, 0.0), #TODO: clean up the generator options + get(dict_in,:ratedGenSlipPerc, 0.0), #TODO: clean up the generator options + get(dict_in,:OmegaGenStart, 0.0), #TODO: clean up the generator options + get(dict_in,:driveShaftProps_K, 0.0), #TODO: break this out, driveshaft stiffness and damping + get(dict_in,:driveShaftProps_C, 0.0), #TODO: break this out, driveshaft stiffness and damping + ) + end +end + +""" + +Unified_Options + + # Input + * `OWENS_Options::OWENS_Options`: + * `DLC_Options::DLC_Options`: + * `OWENSAero_Options::OWENSAero_Options`: + * `OWENSFEA_Options::OWENSFEA_Options`: + * `OWENSOpenFASTWrappers_Options::OWENSOpenFASTWrappers_Options`: + * `Mesh_Options::Mesh_Options`: + * `Drivetrain_Options::Drivetrain_Options`: + + # Output + * `Unified_Options`: +""" +mutable struct Unified_Options + OWENS_Options::OWENS_Options + DLC_Options::DLC_Options + OWENSAero_Options::OWENSAero_Options + OWENSFEA_Options::OWENSFEA_Options + OWENSOpenFASTWrappers_Options::OWENSOpenFASTWrappers_Options + Mesh_Options::Mesh_Options + Drivetrain_Options::Drivetrain_Options +end + +""" + +ModelingOptions(yamlInputfile) + + # Input + * `yamlInputfile::string`: yaml file containing ordered inputs matching the default keys + + + # Output + * `Unified_Options::Unified_Options`: Struct of structs containing all of the OWENS Options +""" function ModelingOptions(yamlInputfile) + yamlInput = YAML.load_file(yamlInputfile;dicttype=OrderedCollections.OrderedDict{Symbol,Any}) + # Unpack YAML - general = yamlInput[:general] - analysisType = general[:analysisType] - turbineType = general[:turbineType] - numTS = general[:numTS] - delta_t = general[:delta_t] - - Inflow = yamlInput[:Inflow] - Vinf = Inflow[:Vinf] - ifw = Inflow[:ifw] - WindType = Inflow[:WindType] - windINPfilename = Inflow[:windINPfilename] - ifw_libfile = Inflow[:ifw_libfile] - - controlParameters = yamlInput[:controlParameters] - controlStrategy = controlParameters[:controlStrategy] - RPM = controlParameters[:RPM] - - AeroParameters = yamlInput[:AeroParameters] - Nslices = AeroParameters[:Nslices] - ntheta = AeroParameters[:ntheta] - AModel = AeroParameters[:AModel] - adi_lib = AeroParameters[:adi_lib] - adi_rootname = AeroParameters[:adi_rootname] - - structuralParameters = yamlInput[:structuralParameters] - structuralModel = structuralParameters[:structuralModel] - ntelem = structuralParameters[:ntelem] - nbelem = structuralParameters[:nbelem] - if haskey(structuralParameters,:ncelem) - ncelem = structuralParameters[:ncelem] - else - ncelem = 10 - end - nselem = structuralParameters[:nselem] + dummy_dict = OrderedCollections.OrderedDict(:nothing=>0.0,:nothing2=>"string") - return MasterInput(analysisType,turbineType,nothing,nothing,nothing,nothing,Vinf, - controlStrategy,RPM,Nslices,ntheta,structuralModel,ntelem,nbelem,ncelem, - nselem,AModel,ifw,WindType,windINPfilename,ifw_libfile,adi_lib,adi_rootname,nothing,nothing,numTS, - delta_t,nothing,nothing, - nothing,nothing,nothing,nothing) + if haskey(yamlInput,:DLC_Options) + dlc_options = DLC_Options(yamlInput[:DLC_Options]) + else + dlc_options = DLC_Options(default_dict) + end + + if haskey(yamlInput,:OWENSAero_Options) + owensaero_options = OWENSAero_Options(yamlInput[:OWENSAero_Options]) + else + owensaero_options = OWENSAero_Options(dummy_dict) + end + + if haskey(yamlInput,:OWENS_Options) + owens_options = OWENS_Options(yamlInput[:OWENS_Options]) + else + owens_options = OWENS_Options(dummy_dict) + end + + if haskey(yamlInput,:OWENSFEA_Options) + owensfea_options = OWENSFEA_Options(yamlInput[:OWENSFEA_Options]) + else + owensfea_options = OWENSFEA_Options(dummy_dict) + end + + if haskey(yamlInput,:OWENSOpenFASTWrappers_Options) + owensopenfastwrappers_options = OWENSOpenFASTWrappers_Options(yamlInput[:OWENSOpenFASTWrappers_Options]) + else + owensopenfastwrappers_options = OWENSOpenFASTWrappers_Options(dummy_dict) + end + + if haskey(yamlInput,:Mesh_Options) + mesh_options = Mesh_Options(yamlInput[:Mesh_Options]) + else + mesh_options = Mesh_Options(dummy_dict) + end + + if haskey(yamlInput,:Drivetrain_Options) + drivetrain_options = Drivetrain_Options(yamlInput[:Drivetrain_Options]) + else + drivetrain_options = Drivetrain_Options(dummy_dict) + end + + return Unified_Options(owens_options,dlc_options,owensaero_options,owensfea_options,owensopenfastwrappers_options,mesh_options,drivetrain_options) end +function Design_Data(file_path::String; design_defaults_yaml="$(module_path)/template_files/design_defaults.yml") + # Load the YAML files + windio = YAML.load_file(file_path; dicttype=OrderedCollections.OrderedDict{Symbol,Any}) + println("Running: $(windio[:name])") + + defaults = YAML.load_file(design_defaults_yaml; dicttype=OrderedCollections.OrderedDict{Symbol,Any}) + + # Create a new dictionary that merges loaded data with defaults + Design_Data = OrderedCollections.OrderedDict{Symbol, Any}() + + # Fill in the Design_Data with defaults and loaded values + for (key, default_value) in defaults + Design_Data[key] = get(windio, key, default_value) + end + + return Design_Data +end + function MasterInput(yamlInputfile) @warn "The old combined yaml file is being depreciated in favor of the windio yaml and the modelingoptions format" @@ -155,7 +661,7 @@ function MasterInput(yamlInputfile) AeroParameters = yamlInput["AeroParameters"] Nslices = AeroParameters["Nslices"] ntheta = AeroParameters["ntheta"] - AModel = AeroParameters["AModel"] + AeroModel = AeroParameters["AeroModel"] adi_lib = AeroParameters["adi_lib"] adi_rootname = AeroParameters["adi_rootname"] @@ -180,12 +686,12 @@ function MasterInput(yamlInputfile) return MasterInput(analysisType,turbineType,eta,Nbld,towerHeight,rho,Vinf, controlStrategy,RPM,Nslices,ntheta,structuralModel,ntelem,nbelem,ncelem, - nselem,AModel,ifw,WindType,windINPfilename,ifw_libfile,adi_lib,adi_rootname,Blade_Height,Blade_Radius,numTS, + nselem,AeroModel,ifw,WindType,windINPfilename,ifw_libfile,adi_lib,adi_rootname,Blade_Height,Blade_Radius,numTS, delta_t,NuMad_geom_xlscsv_file_twr,NuMad_mat_xlscsv_file_twr, NuMad_geom_xlscsv_file_bld,NuMad_mat_xlscsv_file_bld,NuMad_geom_xlscsv_file_strut,NuMad_mat_xlscsv_file_strut) end -function runOWENS(Inp,path;verbosity=2) +function runOWENS(Inp,designparams,path;verbosity=2) analysisType = Inp.analysisType turbineType = Inp.turbineType eta = Inp.eta @@ -204,7 +710,7 @@ function runOWENS(Inp,path;verbosity=2) nselem = Inp.nselem ifw = Inp.ifw WindType = Inp.WindType - AModel = Inp.AModel + AeroModel = Inp.AeroModel windINPfilename = "$(path)$(Inp.windINPfilename)" ifw_libfile = Inp.ifw_libfile if ifw_libfile == "nothing" @@ -276,8 +782,8 @@ mass_breakout_blds,mass_breakout_twr,system,assembly,sections,AD15bldNdIdxRng, A nselem, joint_type = 0, c_mount_ratio = 0.05, - AModel, #AD, DMS, AC - DSModel="BV", + AeroModel, #AD, DMS, AC + DynamicStallModel="BV", RPI=true, cables_connected_to_blade_base = true, meshtype = turbineType) @@ -329,7 +835,7 @@ mass_breakout_blds,mass_breakout_twr,system,assembly,sections,AD15bldNdIdxRng, A # There are inputs for the overall coupled simulation, please see the api reference for specifics on all the options - if AModel=="AD" + if AeroModel=="AD" AD15On = true else AD15On = false @@ -384,7 +890,7 @@ mass_breakout_blds,mass_breakout_twr,system,assembly,sections,AD15bldNdIdxRng, A println("controlStrategy: $controlStrategy") - inputs = OWENS.Inputs(;analysisType = structuralModel, + inputs = OWENS.Inputs(;verbosity,analysisType = structuralModel, tocp, Omegaocp, tocp_Vinf = [0.0,100000.1], @@ -403,7 +909,7 @@ mass_breakout_blds,mass_breakout_twr,system,assembly,sections,AD15bldNdIdxRng, A # Then there are inputs for the finite element models, also, please see the api reference for specifics on the options (TODO: ensure that this is propogated to the docs) feamodel = OWENS.FEAModel(;analysisType = structuralModel, - outFilename = "none", + dataOutputFilename = "none", joint = myjoint, platformTurbineConnectionNodeNumber = 1, pBC, @@ -426,7 +932,7 @@ mass_breakout_blds,mass_breakout_twr,system,assembly,sections,AD15bldNdIdxRng, A topFexternal_hist,rbDataHist = OWENS.Unsteady_Land(inputs;system,assembly, topModel=feamodel,topMesh=mymesh,topEl=myel,aero=aeroForces,deformAero) - if AModel=="AD" + if AeroModel=="AD" OWENSOpenFASTWrappers.endTurb() end @@ -437,8 +943,8 @@ mass_breakout_blds,mass_breakout_twr,system,assembly,sections,AD15bldNdIdxRng, A # for example, strain, or reaction force, etc. This is described in more detail in the api reference for the function and: TODO azi=aziHist#./aziHist*1e-6 - saveName = "$path/vtk/SNL5MW" - OWENS.OWENSVTK(saveName,t,uHist,system,assembly,sections,aziHist,mymesh,myel, + VTKsaveName = "$path/vtk/SNL5MW" + OWENS.OWENSVTK(VTKsaveName,t,uHist,system,assembly,sections,aziHist,mymesh,myel, epsilon_x_hist,epsilon_y_hist,epsilon_z_hist,kappa_x_hist,kappa_y_hist,kappa_z_hist, FReactionHist,topFexternal_hist) @@ -464,167 +970,102 @@ mass_breakout_blds,mass_breakout_twr,system,assembly,sections,AD15bldNdIdxRng, A Twr_LE_U_idx=1,Twr_LE_L_idx=1, AD15bldNdIdxRng,AD15bldElIdxRng,strut_precompoutput=nothing) #TODO: add in ability to have material safety factors and load safety factors - dataDumpFilename = "$path/InitialDataOutputs.h5" - - HDF5.h5open(dataDumpFilename, "w") do file - HDF5.write(file,"t",collect(t)) - HDF5.write(file,"aziHist",aziHist) - HDF5.write(file,"OmegaHist",OmegaHist) - HDF5.write(file,"OmegaDotHist",OmegaDotHist) - HDF5.write(file,"gbHist",gbHist) - HDF5.write(file,"gbDotHist",gbDotHist) - HDF5.write(file,"gbDotDotHist",gbDotDotHist) - HDF5.write(file,"FReactionHist",FReactionHist) - HDF5.write(file,"FTwrBsHist",FTwrBsHist) - HDF5.write(file,"genTorque",genTorque) - HDF5.write(file,"genPower",genPower) - HDF5.write(file,"torqueDriveShaft",torqueDriveShaft) - HDF5.write(file,"uHist",uHist) - HDF5.write(file,"uHist_prp",uHist_prp) - HDF5.write(file,"epsilon_x_hist",epsilon_x_hist) - HDF5.write(file,"epsilon_y_hist",epsilon_y_hist) - HDF5.write(file,"epsilon_z_hist",epsilon_z_hist) - HDF5.write(file,"kappa_x_hist",kappa_x_hist) - HDF5.write(file,"kappa_y_hist",kappa_y_hist) - HDF5.write(file,"kappa_z_hist",kappa_z_hist) - HDF5.write(file,"massOwens",massOwens) - HDF5.write(file,"stress_U",stress_U) - HDF5.write(file,"SF_ult_U",SF_ult_U) - HDF5.write(file,"SF_buck_U",SF_buck_U) - HDF5.write(file,"stress_L",stress_L) - HDF5.write(file,"SF_ult_L",SF_ult_L) - HDF5.write(file,"SF_buck_L",SF_buck_L) - HDF5.write(file,"stress_TU",stress_TU) - HDF5.write(file,"SF_ult_TU",SF_ult_TU) - HDF5.write(file,"SF_buck_TU",SF_buck_TU) - HDF5.write(file,"stress_TL",stress_TL) - HDF5.write(file,"SF_ult_TL",SF_ult_TL) - HDF5.write(file,"SF_buck_TL",SF_buck_TL) - HDF5.write(file,"topstrainout_blade_U",topstrainout_blade_U) - HDF5.write(file,"topstrainout_blade_L",topstrainout_blade_L) - HDF5.write(file,"topstrainout_tower_U",topstrainout_tower_U) - HDF5.write(file,"topstrainout_tower_L",topstrainout_tower_L) - HDF5.write(file,"topDamage_blade_U",topDamage_blade_U) - HDF5.write(file,"topDamage_blade_L",topDamage_blade_L) - HDF5.write(file,"topDamage_tower_U",topDamage_tower_U) - HDF5.write(file,"topDamage_tower_L",topDamage_tower_L) - end + outputData(;mymesh,inputs,t,aziHist,OmegaHist,OmegaDotHist,gbHist,gbDotHist,gbDotDotHist,FReactionHist,genTorque,genPower,torqueDriveShaft,uHist,uHist_prp,epsilon_x_hist,epsilon_y_hist,epsilon_z_hist,kappa_x_hist,kappa_y_hist,kappa_z_hist,FTwrBsHist,massOwens,stress_U,SF_ult_U,SF_buck_U,stress_L,SF_ult_L,SF_buck_L,stress_TU,SF_ult_TU,SF_buck_TU,stress_TL,SF_ult_TL,SF_buck_TL,topstrainout_blade_U,topstrainout_blade_L,topstrainout_tower_U,topstrainout_tower_L,topDamage_blade_U,topDamage_blade_L,topDamage_tower_U,topDamage_tower_L) end -# # Test -# Inp = OWENS.MasterInput(;numTS=3,ifw_libfile="$localpath/../../openfastandy/build/modules/inflowwind/libifw_c_binding") -# OWENS.runDLC(["1_1","1_2"],Inp,localpath;Vinf_range=LinRange(5,20,2),regenWindFiles=true,pathtoturbsim="$localpath/../../openfastandy/build/modules/turbsim/turbsim") -""" -runDLC(DLCs,Inp,path; - Vinf_range=LinRange(5,20,16), - IEC_std="\"2\"", - WindChar="\"A\"", - WindClass=1, - turbsimpath="./turbsimfiles", - templatefile="./templateTurbSim.inp", - pathtoturbsim=nothing, - NumGrid_Z=100, - NumGrid_Y=100, - Vref=10.0, - Vdesign=11.0, - grid_oversize=1.1, - regenWindFiles=false) +""" +runDLC(modelopt,designparams,path;runScript = OWENS.runOWENSWINDIO) + # Input - * `DLCs`: ["1_1","1_2"] - * `Inp::MasterInput`: see ?OWENS.MasterInput + * `modelopt::OWENS.ModelingOptions`: see ?OWENS.ModelingOption + * `designparams::OWENS.Design_Data`: see ?OWENS.Design_Data * `path`: desired path to run everything - * `Vinf_range`: =LinRange(5,20,16), - * `IEC_std`: ="\"2\"", - * `WindChar`: ="\"A\"", - * `WindClass`: =1, - * `turbsimpath`: ="./turbsimfiles", path where it dumps the turbsim files - * `templatefile`: ="./template_files/templateTurbSim.inp", - * `pathtoturbsim`: = nothing, - * `NumGrid_Z`: =100, - * `NumGrid_Y`: =100, - * `Vref`: =10.0, - * `Vdesign`: =11.0, # Design or rated speed - * `grid_oversize`: =1.1, - * `regenWindFiles`: =false + * `runScript`: function handle to run script, defaults to OWENS.runOWENSWINDIO + # Output * `nothing`: - """ -function runDLC(DLCs,Inp,path; - Vinf_range=LinRange(5,20,16), - IEC_std="\"1-ED3\"", - WindChar="\"A\"", - WindClass=1, - turbsimpath="./turbsimfiles", - templatefile="$module_path/template_files/templateTurbSim.inp", - pathtoturbsim=nothing, - NumGrid_Z=nothing, - NumGrid_Y=nothing, - Vref=10.0, - Vdesign=11.0, # Design or rated speed - grid_oversize=1.1, - regenWindFiles=false, - delta_t_turbsim=nothing, - simtime_turbsim=nothing, - runScript = OWENS.runOWENS) +""" +function runDLC(modelopt,designparams,path;runScript = OWENS.runOWENSWINDIO) - if !isdir(turbsimpath) - mkdir(turbsimpath) + if isa(designparams, String) + designparams = Design_Data(designparams) + end + + if isa(modelopt, String) + modelopt = ModelingOptions(modelopt) + end + + DLCs = modelopt.DLC_Options.DLCs + Vinf_range = modelopt.DLC_Options.Vinf_range # = LinRange(5,20,16), + IEC_std = modelopt.DLC_Options.IEC_std # = "\"1-ED3\"", + WindChar = modelopt.DLC_Options.WindChar # = "\"A\"", + WindClass = modelopt.DLC_Options.WindClass # = 1, + turbsimsavepath = modelopt.DLC_Options.turbsimsavepath # = "./turbsimfiles", + pathtoturbsim = modelopt.DLC_Options.pathtoturbsim # = nothing, + NumGrid_Z = modelopt.DLC_Options.NumGrid_Z # = 38, + NumGrid_Y = modelopt.DLC_Options.NumGrid_Y # = 26, + Vref = modelopt.DLC_Options.Vref # = 10.0, + Vdesign = modelopt.DLC_Options.Vdesign # = 11.0, # Design or rated speed + grid_oversize = modelopt.DLC_Options.grid_oversize # = 1.1, + regenWindFiles = modelopt.DLC_Options.regenWindFiles # = false, + delta_t_turbsim = modelopt.DLC_Options.delta_t_turbsim # = 0.05, + simtime_turbsim = modelopt.DLC_Options.simtime_turbsim # = 600.0, + RandSeed1 = modelopt.DLC_Options.RandSeed1 + + if !isdir(turbsimsavepath) + mkdir(turbsimsavepath) end # Fill in DLC parameters based on model inputs - DLCParams = Array{DLCParameters, 1}(undef, length(DLCs)) + DLCParams = Array{DLC_internal, 1}(undef, length(DLCs)) for (iDLC, DLC) in enumerate(DLCs) #TODO parallelize this - DLCParams[iDLC] = getDLCparams(DLC, Inp, Vinf_range, Vdesign, Vref, WindChar,WindClass, IEC_std;grid_oversize,simtime_turbsim,delta_t_turbsim,NumGrid_Z,NumGrid_Y) - + DLCParams[iDLC] = getDLCparams(DLC, modelopt, designparams, Vinf_range, Vdesign, Vref, WindChar,WindClass, IEC_std;grid_oversize,simtime_turbsim,delta_t_turbsim,NumGrid_Z,NumGrid_Y,RandSeed1) # Run Simulation at each Wind Speed for windspeed in DLCParams[iDLC].Vinf_range_used #TODO: parallelize this - - DLCParams[iDLC].URef = windspeed # Check if turbulent inflow file exists, if not create it windspeedStr = round(windspeed;digits=2) windspeedStr = lpad(windspeedStr,4,"0") println("Running DLC $DLC at Vinf $windspeedStr m/s") - windINPfilename = "$turbsimpath/DLC$(DLC)Vinf$(windspeedStr).inp" + windINPfilename = "$turbsimsavepath/DLC$(DLC)Vinf$(windspeedStr).inp" if contains(DLCParams[iDLC].IEC_WindType, "NTM") || contains(DLCParams[iDLC].IEC_WindType, "ETM") || contains(DLCParams[iDLC].IEC_WindType, "EWM") if !isfile(windINPfilename) || regenWindFiles - generateTurbsimBTS(DLCParams[iDLC],windINPfilename,pathtoturbsim;templatefile) + generateTurbsimBTS(DLCParams[iDLC],windINPfilename,pathtoturbsim) end - Inp.WindType = 3 - Inp.windINPfilename = "$(windINPfilename[1:end-4]).bts" + modelopt.OWENSOpenFASTWrappers_Options.WindType = 3 + modelopt.OWENSOpenFASTWrappers_Options.windINPfilename = "$(windINPfilename[1:end-4]).bts" else if !isfile(windINPfilename) || regenWindFiles generateUniformwind(DLCParams[iDLC],windINPfilename) end - Inp.windINPfilename = windINPfilename - Inp.WindType = 2 + modelopt.OWENSOpenFASTWrappers_Options.windINPfilename = windINPfilename + modelopt.OWENSOpenFASTWrappers_Options.WindType = 2 end - Inp.ifw = true - Inp.controlStrategy = DLCParams[iDLC].controlStrategy + modelopt.OWENSAero_Options.ifw = true + modelopt.OWENS_Options.controlStrategy = DLCParams[iDLC].controlStrategy # run owens simulation - runScript(Inp,path) + runScript(modelopt,designparams,path) end end end -mutable struct DLCParameters +mutable struct DLC_internal Vinf_range_used analysis_type # "U", "F", "UF" controlStrategy # "constRPM", function handle RandSeed1 # Turbulent Random Seed Number NumGrid_Z # Vertical grid-point matrix dimension NumGrid_Y # Horizontal grid-point matrix dimension - TimeStepSim # Time step [s] TimeStep # Time step [s] HubHt # Hub height [m] (should be > 0.5*GridHeight) AnalysisTime # Length of analysis time series [s] (program will add time if necessary) @@ -650,28 +1091,41 @@ mutable struct DLCParameters end -function getDLCparams(DLC, Inp, Vinf_range, Vdesign, Vref, WindChar, WindClass, IEC_std;grid_oversize=1.2,simtime_turbsim=nothing,delta_t_turbsim=nothing,NumGrid_Z=nothing,NumGrid_Y=nothing) +function getDLCparams(DLC_case, modelopt, designparams, Vinf_range, Vdesign, Vref, WindChar, WindClass, IEC_std; + RandSeed1 = 40071, + grid_oversize=1.2, + simtime_turbsim=nothing, + delta_t_turbsim=nothing, + NumGrid_Z=nothing, + NumGrid_Y=nothing) + + hub_height = designparams[:assembly][:hub_height] + blade_x = designparams[:components][:blade][:outer_shape_bem][:reference_axis][:x][:values] #Used + blade_y = designparams[:components][:blade][:outer_shape_bem][:reference_axis][:y][:values] #Used + blade_z = designparams[:components][:blade][:outer_shape_bem][:reference_axis][:z][:values] #Used + Blade_Height = maximum(blade_z) #TODO: resolve DLC dependence + Blade_Radius = maximum(sqrt.(blade_x.^2 .+ blade_y.^2)) + + Htwr_base = hub_height-Blade_Height/2 Ve50 = 50.0 #TODO change by class etc Ve1 = 30.0 #TODO - numTS = Inp.numTS - delta_t = Inp.delta_t + numTS = modelopt.OWENS_Options.numTS + delta_t = modelopt.OWENS_Options.delta_t simtime = numTS*delta_t - GridHeight = (Inp.towerHeight-Inp.Blade_Height/2+Inp.Blade_Height)*grid_oversize - GridWidth = Inp.Blade_Radius * 2.0 * grid_oversize + GridHeight = (Htwr_base-Blade_Height/2+Blade_Height)*grid_oversize + GridWidth = Blade_Radius * 2.0 * grid_oversize HubHt = GridHeight*2/3 if !isnothing(NumGrid_Z) - NumGrid_Z = NumGrid_Z #Inp.ntelem+Inp.nbelem - NumGrid_Y = NumGrid_Y #Inp.ntelem+Inp.nbelem + NumGrid_Z = NumGrid_Z + NumGrid_Y = NumGrid_Y else - NumGrid_Z = Inp.ntelem+Inp.nbelem - NumGrid_Y = Inp.nbelem + NumGrid_Z = modelopt.Mesh_Options.ntelem+modelopt.Mesh_Options.nbelem + NumGrid_Y = modelopt.Mesh_Options.nbelem end - - RandSeed1 = 40071 #TODO if !isnothing(simtime_turbsim) AnalysisTime = simtime_turbsim @@ -686,10 +1140,9 @@ function getDLCparams(DLC, Inp, Vinf_range, Vdesign, Vref, WindChar, WindClass, IECturbc = WindChar TurbModel = "\"IECKAI\"" - RefHt = round(Inp.towerHeight) #TODO: what if tower doesn't extend into blade z level + RefHt = round(HubHt) URef = 0.0 #gets filled in later from the Vinf_range when the .bst is generated - TimeStepSim = delta_t if !isnothing(delta_t_turbsim) TimeStep = delta_t_turbsim else @@ -707,19 +1160,19 @@ function getDLCparams(DLC, Inp, Vinf_range, Vdesign, Vref, WindChar, WindClass, UpflowAngle = nothing if contains(IEC_std,"1-") - if DLC == "1_1" || DLC == "1_2" + if DLC_case == "1_1" || DLC_case == "1_2" ControlStrategy = "normal" Vinf_range_used = Vinf_range analysis_type = "UF" IEC_WindType = "\"$(WindClass)NTM\"" - elseif DLC == "1_3" + elseif DLC_case == "1_3" ControlStrategy = "normal" Vinf_range_used = Vinf_range analysis_type = "U" IEC_WindType = "\"$(WindClass)ETM\"" - elseif DLC == "1_4" + elseif DLC_case == "1_4" ControlStrategy = "normal" Vinf_range_used = [Vdesign-2.0,Vdesign+2.0] analysis_type = "U" @@ -734,7 +1187,7 @@ function getDLCparams(DLC, Inp, Vinf_range, Vdesign, Vref, WindChar, WindClass, gustvel = [0,0,7.0,15,7.5,0.0,0.0] UpflowAngle = zeros(length(time)) - elseif DLC == "1_5" + elseif DLC_case == "1_5" ControlStrategy = "normal" Vinf_range_used = Vinf_range analysis_type = "U" @@ -750,14 +1203,14 @@ function getDLCparams(DLC, Inp, Vinf_range, Vdesign, Vref, WindChar, WindClass, UpflowAngle = zeros(length(time)) - elseif DLC == "2_1" || DLC == "2_2" || DLC == "2_4" + elseif DLC_case == "2_1" || DLC_case == "2_2" || DLC_case == "2_4" ControlStrategy = "freewheelatNormalOperatingRPM" Vinf_range_used = Vinf_range analysis_type = "U" IEC_WindType = "\"$(WindClass)NTM\"" - elseif DLC == "2_3" + elseif DLC_case == "2_3" ControlStrategy = "freewheelatNormalOperatingRPM" Vinf_range_used = [collect(LinRange(Vdesign-2.0,Vdesign+2.0,2));Vinf_range[end]] analysis_type = "U" @@ -777,7 +1230,7 @@ function getDLCparams(DLC, Inp, Vinf_range, Vdesign, Vref, WindChar, WindClass, gustT = 10.0 gustvel = simpleGustVel.(time, time_delay, G_amp,gustT) .+ simpleGustVel.(time, time_delay2, G_amp,gustT) - elseif DLC == "3_1" + elseif DLC_case == "3_1" ControlStrategy = "startup" Vinf_range_used = Vinf_range analysis_type = "F" @@ -792,7 +1245,7 @@ function getDLCparams(DLC, Inp, Vinf_range, Vdesign, Vref, WindChar, WindClass, gustvel = zeros(length(time)) UpflowAngle = zeros(length(time)) - elseif DLC == "3_2" + elseif DLC_case == "3_2" ControlStrategy = "startup" Vinf_range_used = [Vinf_range[1];collect(LinRange(Vdesign-2.0,Vdesign+2.0,2));Vinf_range[end]] analysis_type = "U" @@ -812,7 +1265,7 @@ function getDLCparams(DLC, Inp, Vinf_range, Vdesign, Vref, WindChar, WindClass, gustT = 10.0 gustvel = simpleGustVel.(time, time_delay, G_amp,gustT) .+ simpleGustVel.(time, time_delay2, G_amp,gustT) - elseif DLC == "3_3" + elseif DLC_case == "3_3" ControlStrategy = "startup" Vinf_range_used = [Vinf_range[1];collect(LinRange(Vdesign-2.0,Vdesign+2.0,2));Vinf_range[end]] analysis_type = "U" @@ -827,7 +1280,7 @@ function getDLCparams(DLC, Inp, Vinf_range, Vdesign, Vref, WindChar, WindClass, gustvel = [0,0,7.0,15,7.5,0.0,0.0] UpflowAngle = zeros(length(time)) - elseif DLC == "4_1" + elseif DLC_case == "4_1" ControlStrategy = "shutdown" Vinf_range_used = Vinf_range analysis_type = "F" @@ -842,7 +1295,7 @@ function getDLCparams(DLC, Inp, Vinf_range, Vdesign, Vref, WindChar, WindClass, gustvel = zeros(length(time)) UpflowAngle = zeros(length(time)) - elseif DLC == "4_2" + elseif DLC_case == "4_2" ControlStrategy = "shutdown" Vinf_range_used = [collect(LinRange(Vdesign-2.0,Vdesign+2.0,2));Vinf_range[end]] analysis_type = "U" @@ -863,49 +1316,49 @@ function getDLCparams(DLC, Inp, Vinf_range, Vdesign, Vref, WindChar, WindClass, gustvel = simpleGustVel.(time, time_delay, G_amp,gustT) .+ simpleGustVel.(time, time_delay2, G_amp,gustT) - elseif DLC == "5_1" + elseif DLC_case == "5_1" ControlStrategy = "emergencyshutdown" Vinf_range_used = [collect(LinRange(Vdesign-2.0,Vdesign+2.0,2));Vinf_range[end]] analysis_type = "U" IEC_WindType = "\"$(WindClass)NTM\"" - elseif DLC == "6_1" + elseif DLC_case == "6_1" ControlStrategy = "parked" Vinf_range_used = [Ve50] analysis_type = "U" IEC_WindType = "\"$(WindClass)EWM50\"" - elseif DLC == "6_2" + elseif DLC_case == "6_2" ControlStrategy = "parked_idle" Vinf_range_used = [Ve50] analysis_type = "U" IEC_WindType = "\"$(WindClass)EWM50\"" - elseif DLC == "6_3" + elseif DLC_case == "6_3" ControlStrategy = "parked_yaw" Vinf_range_used = [Ve1] analysis_type = "U" IEC_WindType = "\"$(WindClass)EWM1\"" - elseif DLC == "6_4" + elseif DLC_case == "6_4" ControlStrategy = "parked" Vinf_range_used = [0.7*Ve50] analysis_type = "F" IEC_WindType = "\"$(WindClass)NTM\"" - elseif DLC == "7_1" + elseif DLC_case == "7_1" ControlStrategy = "parked" Vinf_range_used = [Ve1] analysis_type = "U" IEC_WindType = "\"$(WindClass)EWM1\"" - elseif DLC == "8_1" #Startup + elseif DLC_case == "8_1" #Startup ControlStrategy = "transport" Vinf_range_used = [Vdesign] analysis_type = "U" IEC_WindType = "\"$(WindClass)EWM1\"" - elseif DLC == "CPCurve" + elseif DLC_case == "CPCurve" ControlStrategy = "normal" Vinf_range_used = Vinf_range analysis_type = "F" @@ -921,129 +1374,128 @@ function getDLCparams(DLC, Inp, Vinf_range, Vdesign, Vref, WindChar, WindClass, UpflowAngle = zeros(length(time)) else - error("IEC61400_1 DLCs such as 1_1, 1_2 defined, you requested $DLC") + error("IEC61400_1 DLC_cases such as 1_1, 1_2 defined, you requested $DLC_case") end elseif contains(IEC_std,"2") - error("IEC61400_2 DLCs are not fully defined") - if DLC == "1_1" + error("IEC61400_2 DLC_cases are not fully defined") + if DLC_case == "1_1" ControlStrategy = "normal" Vinf_range_used = Vinf_range analysis_type = "UF" IEC_WindType = "\"$(WindClass)NTM\"" - elseif DLC == "1_2" + elseif DLC_case == "1_2" ControlStrategy = "normal" Vinf_range_used = [Vdesign] analysis_type = "F" IEC_WindType = "\"$(WindClass)ECD\"" - elseif DLC == "1_3" + elseif DLC_case == "1_3" ControlStrategy = "normal" Vinf_range_used = Vinf_range analysis_type = "U" IEC_WindType = "\"$(WindClass)EOG50\"" - elseif DLC == "1_4" + elseif DLC_case == "1_4" ControlStrategy = "normal" Vinf_range_used = Vinf_range analysis_type = "U" IEC_WindType = "\"$(WindClass)ECD50\"" - elseif DLC == "1_5" + elseif DLC_case == "1_5" ControlStrategy = "normal" Vinf_range_used = [Vdesign] analysis_type = "U" IEC_WindType = "\"$(WindClass)ECG\"" - elseif DLC == "2_1" + elseif DLC_case == "2_1" ControlStrategy = "freewheelatNormalOperatingRPM" Vinf_range_used = [Vdesign] analysis_type = "U" IEC_WindType = "\"$(WindClass)NWP\"" - elseif DLC == "2_2" + elseif DLC_case == "2_2" ControlStrategy = "freewheelatNormalOperatingRPM" Vinf_range_used = Vinf_range analysis_type = "UF" IEC_WindType = "\"$(WindClass)NTM\"" - elseif DLC == "2_3" + elseif DLC_case == "2_3" ControlStrategy = "freewheelatNormalOperatingRPM" Vinf_range_used = Vinf_range analysis_type = "U" IEC_WindType = "\"$(WindClass)EOG1\"" - elseif DLC == "3_1" + elseif DLC_case == "3_1" ControlStrategy = "shutdown" Vinf_range_used = Vinf_range analysis_type = "F" IEC_WindType = "\"$(WindClass)NTM\"" - elseif DLC == "3_2" + elseif DLC_case == "3_2" ControlStrategy = "shutdown" Vinf_range_used = [Vinf_range[end]] analysis_type = "U" IEC_WindType = "\"$(WindClass)EOG1\"" - elseif DLC == "4_1" + elseif DLC_case == "4_1" ControlStrategy = "shutdown" Vinf_range_used = [Vdesign] analysis_type = "U" IEC_WindType = "\"$(WindClass)NTM\"" - elseif DLC == "5_1" + elseif DLC_case == "5_1" ControlStrategy = "freewheelatIdle" Vinf_range_used = [Ve50] analysis_type = "U" IEC_WindType = "\"$(WindClass)EWM\"" - elseif DLC == "5_2" + elseif DLC_case == "5_2" ControlStrategy = "idle" Vinf_range_used = [Vdesign] analysis_type = "F" IEC_WindType = "\"$(WindClass)NTM\"" - elseif DLC == "6_1" + elseif DLC_case == "6_1" ControlStrategy = "parked" Vinf_range_used = [Ve1] analysis_type = "U" IEC_WindType = "\"$(WindClass)EWM\"" - elseif DLC == "8_1" #Startup + elseif DLC_case == "8_1" #Startup ControlStrategy = "startup" Vinf_range_used = Vinf_range analysis_type = "U" IEC_WindType = "\"$(WindClass)EWM\"" else - error("IEC61400_2 DLCs [1.1,1.2,1.3,1.4,1.5,2.1,2.2,2.3,3.1,3.2,4.1,5.1,5.2,6.1] defined, you requested $DLC") + error("IEC61400_2 DLC_cases [1.1,1.2,1.3,1.4,1.5,2.1,2.2,2.3,3.1,3.2,4.1,5.1,5.2,6.1] defined, you requested $DLC") end else error("IEC_std 61400 1-ED3 and 2 defined, you requested $IEC_std") end - return DLCParameters( + return DLC_internal( Vinf_range_used, analysis_type, # array of windspeeds m/s ControlStrategy, # "constRPM", function handle RandSeed1, # Turbulent Random Seed Number NumGrid_Z, # Vertical grid-point matrix dimension NumGrid_Y, # Horizontal grid-point matrix dimension - TimeStepSim, # Time step [s] TimeStep, # Turbsim time step [s] HubHt, # Hub height [m] (should be > 0.5*GridHeight) AnalysisTime, # Length of analysis time series [s] (program will add time if necessary) @@ -1110,7 +1562,7 @@ function generateUniformwind(DLCParams,windINPfilename) end end -function generateTurbsimBTS(DLCParams,windINPfilename,pathtoturbsim;templatefile="$localpath/templateTurbSim.inp") +function generateTurbsimBTS(DLCParams,windINPfilename,pathtoturbsim;templatefile="$module_path/template_files/templateTurbSim.inp") lines = readlines(templatefile) @@ -1140,7 +1592,7 @@ function generateTurbsimBTS(DLCParams,windINPfilename,pathtoturbsim;templatefile end end - if isnothing(pathtoturbsim) + if isnothing(pathtoturbsim) || pathtoturbsim=="nothing" run(`$(OWENSOpenFASTWrappers.turbsim()) $windINPfilename`) else run(`$pathtoturbsim $windINPfilename`) diff --git a/src/utilities.jl b/src/utilities.jl index 8402bf26..334aea50 100644 --- a/src/utilities.jl +++ b/src/utilities.jl @@ -28,8 +28,8 @@ minLoadStep = 0.0500, prescribedLoadStep = 0.0, elementOrder = 1, - numDofPerNode = 6, - hydroOn = false, + numDOFPerNode = 6, + platformActive = false, platformTurbineConnectionNodeNumber = 1, JgearBox =0.0, gearRatio = 1.0, @@ -76,8 +76,8 @@ function owens(owensfile,analysisType; minLoadStep = 0.0500, prescribedLoadStep = 0.0, elementOrder = 1, #linear element order - numDofPerNode = 6, - hydroOn = false, + numDOFPerNode = 6, + platformActive = false, interpOrder = 2, platformTurbineConnectionNodeNumber = 1, JgearBox =0.0, @@ -91,14 +91,14 @@ function owens(owensfile,analysisType; # if(analysisType=="S") #STATIC ANALYSIS # Omega = varargin{3} #initialization of rotor speed (Hz) - # model.nlOn= varargin{4} #flag for nonlinear elastic calculation + # inputs.nlOn= varargin{4} #flag for nonlinear elastic calculation # if(length(varargin)>4) #sets initial guess for nonlinear calculations # displInitGuess = varargin{5} # end # # if(length(varargin)>5) #sets air density if simple thin - # # model.airDensity = varargin{6} # airfoil theory loading desired + # # inputs.airDensity = varargin{6} # airfoil theory loading desired # # else - # model.airDensity = 1.2041 + # inputs.airDensity = 1.2041 # # end if (analysisType=="TNB" || analysisType=="TD") #TRANSIENT ANALYSIS (TNB = newmark beta time integation, TD = dean time integration) @@ -110,70 +110,70 @@ function owens(owensfile,analysisType; end end - # elseif(analysisType=="ROM") #REDUCED ORDER MODEL FOR TRANSIENT ANALYSIS - # model.delta_t = varargin{3} #time step size - # model.numTS = varargin{4} #number of time steps - # model.numModesForROM = varargin{5} #number of lower system modes to include in ROM - # model.nlOn = varargin{6} #flag for nonlinear elastic calculation + # elseif(analysisType=="ROM") #REDUCED ORDER inputs FOR TRANSIENT ANALYSIS + # inputs.delta_t = varargin{3} #time step size + # inputs.numTS = varargin{4} #number of time steps + # inputs.numModesForROM = varargin{5} #number of lower system modes to include in ROM + # inputs.nlOn = varargin{6} #flag for nonlinear elastic calculation # turbineOpFlag = varargin{7} # if(turbineOpFlag == 1) #generator start up operation mode - # model.OmegaInit = varargin{8} #initial rotor speed + # inputs.OmegaInit = varargin{8} #initial rotor speed # elseif(turbineOpFlag == 2) # self starting operation mode - # model.OmegaInit = varargin{8} #initial rotor speed (Hz) - # model.OmegaGenStart = varargin{9} #rotor speed at which generator activates (Hz) + # inputs.OmegaInit = varargin{8} #initial rotor speed (Hz) + # inputs.OmegaGenStart = varargin{9} #rotor speed at which generator activates (Hz) # else #specified rotor speed profile # if(length(varargin) == 7) - # model.usingRotorSpeedFunction = true #set flag to use user specified rotor speed function - # [~,model.OmegaInit,~] = getRotorPosSpeedAccelAtTime(-1.0,0.0,0) + # inputs.usingRotorSpeedFunction = true #set flag to use user specified rotor speed function + # [~,inputs.OmegaInit,~] = getRotorPosSpeedAccelAtTime(-1.0,0.0,0) # else # #this option uses a discretely specified rotor speed profile - # model.usingRotorSpeedFunction = false #set flag to not use user specified rotor speed function - # model.tocp = varargin{8} #time points for rotor speed provfile + # inputs.usingRotorSpeedFunction = false #set flag to not use user specified rotor speed function + # inputs.tocp = varargin{8} #time points for rotor speed provfile # Omegaocp = varargin{9} #rotor speed value at time points (Hz) - # model.Omegaocp = Omegaocp - # model.OmegaInit = Omegaocp(1) + # inputs.Omegaocp = Omegaocp + # inputs.OmegaInit = Omegaocp(1) # end # end # elseif(analysisType=="F") #MANUAL FLUTTER ANALYSIS # Omega = varargin{3} #rotor speed (Hz) - # model.spinUpOn = varargin{4} #flag for pre-stressed modal analysis - # model.guessFreq = varargin{5} #``guess"" modal frequency - # model.aeroElasticOn = true - # model.nlOn = true + # inputs.spinUpOn = varargin{4} #flag for pre-stressed modal analysis + # inputs.guessFreq = varargin{5} #``guess"" modal frequency + # inputs.aeroElasticOn = true + # inputs.nlOn = true # # if(length(varargin)>5) #air density initialization - # model.airDensity = varargin{6} + # inputs.airDensity = varargin{6} # else - # model.airDensity = 1.2041 + # inputs.airDensity = 1.2041 # end # if(length(varargin)>6) #number of lower system modes to extract - # model.numModesToExtract = varargin{7} + # inputs.numModesToExtract = varargin{7} # else - # model.numModesToExtract = 20 + # inputs.numModesToExtract = 20 # end # # elseif(analysisType=="FA") #AUTOMATED FLUTTER ANALYSIS # omegaArray = varargin{3} #array of rotor speed values(Hz) - # model.spinUpOn = varargin{4} #flag for pre-stressed modal analysis - # model.aeroElasticOn = true - # model.nlOn = true + # inputs.spinUpOn = varargin{4} #flag for pre-stressed modal analysis + # inputs.aeroElasticOn = true + # inputs.nlOn = true # # if(length(varargin)>4) #air density initializatio - # model.airDensity = varargin{5} + # inputs.airDensity = varargin{5} # else - # model.airDensity = 1.2041 + # inputs.airDensity = 1.2041 # end # if(length(varargin)>5) #number of lower system modes to extract - # model.numModesToExtract = varargin{6} + # inputs.numModesToExtract = varargin{6} # else - # model.numModesToExtract = 20 + # inputs.numModesToExtract = 20 # end # # else # error("Analysis type not recognized.") # end - fid = open(owensfile,"r") #reads in model file names from .owens file + fid = open(owensfile,"r") #reads in inputs file names from .owens file last_delimiter = findall(r"\W", owensfile) #Find the file directory fdirectory = owensfile[1:last_delimiter[end-1][1]] @@ -208,7 +208,7 @@ function owens(owensfile,analysisType; line = readline(fid) delimiter_idx = findall(" ",line) - hydroOn = Bool(real(parse(Int,line[1]))) #flag for activating hydrodynamic analysis + platformActive = Bool(real(parse(Int,line[1]))) #flag for activating hydrodynamic analysis potflowfile = string(fdirectory, line[delimiter_idx[1][1]+1:delimiter_idx[2][1]-1]) # potential flow file prefix interpOrder = real(parse(Int,line[delimiter_idx[2][1]+1])) # interpolation order for HD/MD libraries line = readline(fid) @@ -224,17 +224,17 @@ function owens(owensfile,analysisType; close(fid) # close .owens file - #model definitions + #inputs definitions #-------------------------------------------- mesh = OWENS.readMesh(meshfilename) #read mesh file bladeData,_,_,_ = OWENS.readBladeData(blddatafilename) #reads overall blade data file - BC = OWENS.readBCdata(bcdatafilename,mesh.numNodes,numDofPerNode) #read boundary condition file + BC = OWENS.readBCdata(bcdatafilename,mesh.numNodes,numDOFPerNode) #read boundary condition file el = OWENS.readElementData(mesh.numEl,eldatafilename,ortdatafilename,bladeData) #read element data file (also reads orientation and blade data file associated with elements) joint = DelimitedFiles.readdlm(jntdatafilename,'\t',skipstart = 0) #readJointData(jntdatafilename) #read joint data file nodalTerms = OWENSFEA.applyConcentratedTerms(mesh.numNodes, 6;filename=ndldatafilename) #read concentrated nodal terms file initCond = [] - # [model] = readDriveShaftProps(model,driveShaftFlag,driveshaftfilename) #reads drive shaft properties + # [inputs] = readDriveShaftProps(inputs,driveShaftFlag,driveshaftfilename) #reads drive shaft properties driveShaftProps = DriveShaftProps(0.0,0.0) #set drive shat properties to 0 @@ -250,17 +250,17 @@ function owens(owensfile,analysisType; end - outFilename = generateOutputFilename(owensfile,analysisType) #generates an output filename for analysis results #TODO: map to the output location instead of input - jointTransform, reducedDOFList = OWENSFEA.createJointTransform(joint,mesh.numNodes,6) #creates a joint transform to constrain model degrees of freedom (DOF) consistent with joint constraints + dataOutputFilename = generateOutputFilename(owensfile,analysisType) #generates an output filename for analysis results #TODO: map to the output location instead of input + jointTransform, reducedDOFList = OWENSFEA.createJointTransform(joint,mesh.numNodes,6) #creates a joint transform to constrain inputs degrees of freedom (DOF) consistent with joint constraints numReducedDof = length(jointTransform[1,:]) nlParams = OWENSFEA.NlParams(iterationType,adaptiveLoadSteppingFlag,tolerance, maxIterations,maxNumLoadSteps,minLoadStepDelta,minLoadStep,prescribedLoadStep) - model = Inputs(;analysisType,turbineStartup,usingRotorSpeedFunction,tocp,numTS,delta_t,Omegaocp, - aeroLoadsOn,driveTrainOn,generatorOn,hydroOn=false,topsideOn=true,interpOrder,hd_input_file=[],md_input_file=[],JgearBox,gearRatio,gearBoxEfficiency, + inputs = Inputs(;analysisType,turbineStartup,usingRotorSpeedFunction,tocp,numTS,delta_t,Omegaocp, + aeroLoadsOn,driveTrainOn,generatorOn,platformActive=false,topsideOn=true,interpOrder,hd_input_file=[],md_input_file=[],JgearBox,gearRatio,gearBoxEfficiency, useGeneratorFunction,generatorProps,OmegaGenStart,omegaControl,OmegaInit, - aeroloadfile,owensfile,potflowfile=[],outFilename,bladeData,driveShaftProps) + aeroloadfile,owensfile,potflowfile=[],dataOutputFilename,bladeData,driveShaftProps) feamodel = OWENSFEA.FEAModel(;analysisType, initCond, @@ -270,7 +270,7 @@ function owens(owensfile,analysisType; gravityOn, nlOn, spinUpOn, - outFilename, + dataOutputFilename, RayleighAlpha, RayleighBeta, elementOrder, @@ -285,12 +285,12 @@ function owens(owensfile,analysisType; nodalTerms) # if(analysisType=="S") #EXECUTE STATIC ANALYSIS - # if(length(varargin)<=4 || ~model.nlOn) #sets initial guess for nonlinear calculations + # if(length(varargin)<=4 || ~inputs.nlOn) #sets initial guess for nonlinear calculations # displInitGuess = zeros(mesh.numNodes*6,1) # end # # OmegaStart = 0.0 - # staticExec(model,mesh,el,displInitGuess,Omega,OmegaStart) + # staticExec(inputs,mesh,el,displInitGuess,Omega,OmegaStart) # end # if (analysisType == "M" || analysisType == "F") #EXECUTE MODAL OR MANUAL FLUTTER ANALYSIS @@ -305,7 +305,7 @@ function owens(owensfile,analysisType; # if(analysisType=="FA") #EXECUTE AUTOMATED FLUTTER ANALYSIS # displ = zeros(mesh.numNodes*6,1) # OmegaStart = 0.0 - # [freq,damp]=ModalAuto(model,mesh,el,displ,omegaArray,OmegaStart) + # [freq,damp]=ModalAuto(inputs,mesh,el,displ,omegaArray,OmegaStart) # end # @@ -316,8 +316,8 @@ function owens(owensfile,analysisType; end if (analysisType=="TNB"||analysisType=="TD"||analysisType=="ROM") #EXECUTE TRANSIENT ANALYSIS - aeroLoadsFile_root = model.aeroloadfile[1:end-16] #cut off the _ElementData.csv - OWENSfile_root = model.owensfile[1:end-6] #cut off the .owens + aeroLoadsFile_root = inputs.aeroloadfile[1:end-16] #cut off the _ElementData.csv + OWENSfile_root = inputs.owensfile[1:end-6] #cut off the .owens geomFn = string(aeroLoadsFile_root, ".geom") loadsFn = string(aeroLoadsFile_root, "_ElementData.csv") @@ -331,9 +331,16 @@ function owens(owensfile,analysisType; aeroForces(t,azi) = externalForcing(t+delta_t,aerotimeArray,aeroForceValHist,aeroForceDof) deformAero(azi;newOmega=-1,newVinf=-1,bld_x=-1,bld_z=-1,bld_twist=-1,accel_flap_in=-1,accel_edge_in=-1,gravity=-1) = 0.0 #placeholder function - Unsteady(model;topModel=feamodel,topMesh=mesh,topEl=el,bin,aero=aeroForces,deformAero) - - return model + + t, aziHist,OmegaHist,OmegaDotHist,gbHist,gbDotHist,gbDotDotHist, + FReactionHist,FTwrBsHist,genTorque,genPower,torqueDriveShaft,uHist, + uHist_prp,epsilon_x_hist,epsilon_y_hist,epsilon_z_hist,kappa_x_hist, + kappa_y_hist,kappa_z_hist,FPtfmHist,FHydroHist,FMooringHist, + topFexternal_hist,rbDataHist = Unsteady(inputs;topModel=feamodel,topMesh=mesh,topEl=el,bin,aero=aeroForces,deformAero) + + outputData(;mymesh=mesh,inputs,t,aziHist,OmegaHist,OmegaDotHist,gbHist,gbDotHist,gbDotDotHist,FReactionHist,genTorque,genPower,torqueDriveShaft,uHist,uHist_prp,epsilon_x_hist,epsilon_y_hist,epsilon_z_hist,kappa_x_hist,kappa_y_hist,kappa_z_hist) + + return inputs end # @@ -517,7 +524,7 @@ function mapCactusLoadsFile(geomFn,loadsFn,bldFn,elFn,ortFn,meshFn) #read element aero_data in mesh = OWENS.readMesh(meshFn) el = OWENS.readElementData(mesh.numEl,elFn,ortFn,bladeData) - numDofPerNode = 6 + numDOFPerNode = 6 # [~,~,timeLen] = size(aeroDistLoadsArrayTime) Fg = zeros(mesh.numNodes*6,numAeroTS) for i=1:numAeroTS @@ -529,7 +536,7 @@ function mapCactusLoadsFile(geomFn,loadsFn,bldFn,elFn,ortFn,meshFn) #get dof map node1 = Int(structuralNodeNumbers[j,k]) node2 = Int(structuralNodeNumbers[j,k+1]) - dofList = [(node1-1)*numDofPerNode.+(1:6) (node2-1)*numDofPerNode.+(1:6)] + dofList = [(node1-1)*numDOFPerNode.+(1:6) (node2-1)*numDOFPerNode.+(1:6)] elementOrder = 1 x = [mesh.x[node1], mesh.x[node2]] @@ -601,19 +608,19 @@ end Caclulates generator torque for simple induction generator #Input -* `generatorProps` object containing generator properties, see ?model +* `generatorProps` object containing generator properties, see ?inputs * `genSpeed::float` generator speed (Hz) #Output * `genTorque::float` generator torque """ -function simpleGenerator(model,genSpeed) +function simpleGenerator(inputs,genSpeed) - #assign generator properties form model object - ratedTorque = model.ratedTorque; - ratedGenSlipPerc = model.ratedGenSlipPerc; - zeroTorqueGenSpeed = model.zeroTorqueGenSpeed; - pulloutRatio = model.pulloutRatio; + #assign generator properties form inputs object + ratedTorque = inputs.ratedTorque; + ratedGenSlipPerc = inputs.ratedGenSlipPerc; + zeroTorqueGenSpeed = inputs.zeroTorqueGenSpeed; + pulloutRatio = inputs.pulloutRatio; #calculate rated generator speed ratedGenSpeed = zeroTorqueGenSpeed*(1.0 + 0.01*ratedGenSlipPerc); diff --git a/src/windio.jl b/src/windio.jl index bafb8ce9..ceaab9c9 100644 --- a/src/windio.jl +++ b/src/windio.jl @@ -1,11 +1,10 @@ -function runOWENSWINDIO(windio,modelopt,path;verbosity=2) - if typeof(windio) == String - windio = YAML.load_file(windio; dicttype=OrderedCollections.OrderedDict{Symbol,Any}) - println("Running: $(windio[:name])") +function runOWENSWINDIO(modelopt,windio,path) + if isa(windio, String) + windio = Design_Data(windio) end - if typeof(modelopt) == String + if isa(modelopt, String) modelopt = ModelingOptions(modelopt) end @@ -16,7 +15,7 @@ function runOWENSWINDIO(windio,modelopt,path;verbosity=2) # rotor_orientation = windio[:assembly][:rotor_orientation] number_of_blades = windio[:assembly][:number_of_blades] #Used # number_of_struts_per_blade = windio[:assembly][:number_of_struts_per_blade] #NEW? - # hub_height = windio[:assembly][:hub_height] + hub_height = windio[:assembly][:hub_height] # rotor_diameter = windio[:assembly][:rotor_diameter] # rated_power = windio[:assembly][:rated_power] # lifetime = windio[:assembly][:lifetime] @@ -33,6 +32,17 @@ function runOWENSWINDIO(windio,modelopt,path;verbosity=2) # blade_z_grid = windio[:components][:blade][:outer_shape_bem][:reference_axis][:z][:grid] blade_z = windio[:components][:blade][:outer_shape_bem][:reference_axis][:z][:values] #Used + + Blade_Height = maximum(blade_z) #TODO: resolve DLC dependence + Blade_Radius = maximum(sqrt.(blade_x.^2 .+ blade_y.^2)) + + Htwr_base = hub_height-Blade_Height/2 + if modelopt.Mesh_Options.turbineType == "Darrieus" + Htwr_blds = Blade_Height + else + Htwr_blds = Blade_Height*0.6 #TODO: finer grained inputs + end + # Struts #TODO: multiple struts tower_strut_connection = windio[:components][:struts][1][:mountfraction_tower] @@ -74,7 +84,7 @@ function runOWENSWINDIO(windio,modelopt,path;verbosity=2) air_dyn_viscosity = windio[:environment][:air_dyn_viscosity] #used # air_speed_sound = windio[:environment][:air_speed_sound] # shear_exp = windio[:environment][:shear_exp] - gravity = windio[:environment][:gravity] #used + gravity = Float64.(windio[:environment][:gravity]) #used # weib_shape_parameter = windio[:environment][:weib_shape_parameter] # water_density = windio[:environment][:water_density] # water_dyn_viscosity = windio[:environment][:water_dyn_viscosity] @@ -137,131 +147,174 @@ function runOWENSWINDIO(windio,modelopt,path;verbosity=2) # capacity_credit = windio[:costs][:capacity_credit] # benchmark_price = windio[:costs][:benchmark_price] + if isa(gravity, Float64) + gravityOn = [0,0,gravity] + else + gravityOn = gravity + end + # Top Level OWENS Options + analysisType = modelopt.OWENS_Options.analysisType + AeroModel = modelopt.OWENS_Options.AeroModel + controlStrategy = modelopt.OWENS_Options.controlStrategy + numTS = modelopt.OWENS_Options.numTS + delta_t = modelopt.OWENS_Options.delta_t + platformActive = modelopt.OWENS_Options.platformActive + topsideOn = modelopt.OWENS_Options.topsideOn + interpOrder = modelopt.OWENS_Options.interpOrder + dataOutputFilename = modelopt.OWENS_Options.dataOutputFilename + rigid = modelopt.OWENS_Options.rigid + TOL = modelopt.OWENS_Options.TOL + MAXITER = modelopt.OWENS_Options.MAXITER + verbosity = modelopt.OWENS_Options.verbosity + VTKsaveName = modelopt.OWENS_Options.VTKsaveName + aeroLoadsOn = modelopt.OWENS_Options.aeroLoadsOn + structuralModel = modelopt.OWENS_Options.structuralModel + Prescribed_RPM_time_controlpoints = modelopt.OWENS_Options.Prescribed_RPM_time_controlpoints + Prescribed_RPM_RPM_controlpoints = modelopt.OWENS_Options.Prescribed_RPM_RPM_controlpoints + Prescribed_Vinf_time_controlpoints = modelopt.OWENS_Options.Prescribed_Vinf_time_controlpoints + Prescribed_Vinf_Vinf_controlpoints = modelopt.OWENS_Options.Prescribed_Vinf_Vinf_controlpoints + + # OWENSAero Options + Nslices = modelopt.OWENSAero_Options.Nslices + ntheta = modelopt.OWENSAero_Options.ntheta + ifw = modelopt.OWENSAero_Options.ifw + DynamicStallModel = modelopt.OWENSAero_Options.DynamicStallModel + RPI = modelopt.OWENSAero_Options.RPI + Aero_Buoyancy_Active = modelopt.OWENSAero_Options.Aero_Buoyancy_Active + Aero_AddedMass_Active = modelopt.OWENSAero_Options.Aero_AddedMass_Active + Aero_RotAccel_Active = modelopt.OWENSAero_Options.Aero_RotAccel_Active + + # DLC Options + DLCs = modelopt.DLC_Options.DLCs + Vinf_range = modelopt.DLC_Options.Vinf_range + IEC_std = modelopt.DLC_Options.IEC_std + WindChar = modelopt.DLC_Options.WindChar + WindClass = modelopt.DLC_Options.WindClass + turbsimsavepath = modelopt.DLC_Options.turbsimsavepath + pathtoturbsim = modelopt.DLC_Options.pathtoturbsim + NumGrid_Z = modelopt.DLC_Options.NumGrid_Z + NumGrid_Y = modelopt.DLC_Options.NumGrid_Y + Vref = modelopt.DLC_Options.Vref + Vdesign = modelopt.DLC_Options.Vdesign + grid_oversize = modelopt.DLC_Options.grid_oversize + regenWindFiles = modelopt.DLC_Options.regenWindFiles + delta_t_turbsim = modelopt.DLC_Options.delta_t_turbsim + simtime_turbsim = modelopt.DLC_Options.simtime_turbsim + + # OWENSFEA Options + nlOn = modelopt.OWENSFEA_Options.nlOn + RayleighAlpha = modelopt.OWENSFEA_Options.RayleighAlpha + RayleighBeta = modelopt.OWENSFEA_Options.RayleighBeta + iterationType = modelopt.OWENSFEA_Options.iterationType + guessFreq = modelopt.OWENSFEA_Options.guessFreq + numModes = modelopt.OWENSFEA_Options.numModes + adaptiveLoadSteppingFlag = modelopt.OWENSFEA_Options.adaptiveLoadSteppingFlag + minLoadStepDelta = modelopt.OWENSFEA_Options.minLoadStepDelta + minLoadStep = modelopt.OWENSFEA_Options.minLoadStep + prescribedLoadStep = modelopt.OWENSFEA_Options.prescribedLoadStep + maxNumLoadSteps = modelopt.OWENSFEA_Options.maxNumLoadSteps + tolerance = modelopt.OWENSFEA_Options.tolerance + maxIterations = modelopt.OWENSFEA_Options.maxIterations + elementOrder = modelopt.OWENSFEA_Options.elementOrder + alpha = modelopt.OWENSFEA_Options.alpha + gamma = modelopt.OWENSFEA_Options.gamma + AddedMass_Coeff_Ca = modelopt.OWENSFEA_Options.AddedMass_Coeff_Ca + platformTurbineConnectionNodeNumber = modelopt.OWENSFEA_Options.platformTurbineConnectionNodeNumber + aeroElasticOn = modelopt.OWENSFEA_Options.aeroElasticOn + spinUpOn = modelopt.OWENSFEA_Options.spinUpOn + predef = modelopt.OWENSFEA_Options.predef + + # OWENSOpenFASTWrappers Options + windINPfilename = modelopt.OWENSOpenFASTWrappers_Options.windINPfilename + ifw_libfile = modelopt.OWENSOpenFASTWrappers_Options.ifw_libfile + hd_lib = modelopt.OWENSOpenFASTWrappers_Options.hd_lib + md_lib = modelopt.OWENSOpenFASTWrappers_Options.md_lib + adi_lib = modelopt.OWENSOpenFASTWrappers_Options.adi_lib + adi_rootname = modelopt.OWENSOpenFASTWrappers_Options.adi_rootname + hd_input_file = modelopt.OWENSOpenFASTWrappers_Options.hd_input_file + ss_input_file = modelopt.OWENSOpenFASTWrappers_Options.ss_input_file + md_input_file = modelopt.OWENSOpenFASTWrappers_Options.md_input_file + potflowfile = modelopt.OWENSOpenFASTWrappers_Options.potflowfile + WindType = modelopt.OWENSOpenFASTWrappers_Options.WindType + + if adi_lib == "nothing" + adi_lib = nothing + end - analysisType = modelopt.analysisType - turbineType = modelopt.turbineType - Vinf = modelopt.Vinf - controlStrategy = modelopt.controlStrategy - RPM = modelopt.RPM - Nslices = modelopt.Nslices - ntheta = modelopt.ntheta - structuralModel = modelopt.structuralModel - ntelem = modelopt.ntelem - nbelem = modelopt.nbelem - ncelem = modelopt.ncelem - nselem = modelopt.nselem - ifw = modelopt.ifw - WindType = modelopt.WindType - AModel = modelopt.AModel - windINPfilename = "$(path)$(modelopt.windINPfilename)" - ifw_libfile = modelopt.ifw_libfile + windINPfilename = "$(path)$windINPfilename" + potflowfile = "$(path)$potflowfile" if ifw_libfile == "nothing" ifw_libfile = nothing end - Blade_Height = modelopt.Blade_Height # WindIO TODO: resolve DLC dependence - Blade_Radius = modelopt.Blade_Radius # WindIO TODO: resolve DLC dependence - numTS = modelopt.numTS - delta_t = modelopt.delta_t - - turbineStartup = 0 - usingRotorSpeedFunction = false - driveTrainOn = false - generatorOn = false - hydroOn = false - topsideOn = true - interpOrder = 2 - hd_input_file = "none" - ss_input_file = "none" - md_input_file = "none" - JgearBox = 0.0 - gearRatio = 1.0 - gearBoxEfficiency = 1.0 - useGeneratorFunction = false - generatorProps = 0.0 - ratedTorque = 0.0 - zeroTorqueGenSpeed = 0.0 - pulloutRatio = 0.0 - ratedGenSlipPerc = 0.0 - OmegaGenStart = 0.0 - omegaControl = false + + # Mesh Options + ntelem = modelopt.Mesh_Options.ntelem + nbelem = modelopt.Mesh_Options.nbelem + ncelem = modelopt.Mesh_Options.ncelem + nselem = modelopt.Mesh_Options.nselem + angularOffset = modelopt.Mesh_Options.angularOffset + joint_type = modelopt.Mesh_Options.joint_type + c_mount_ratio = modelopt.Mesh_Options.c_mount_ratio + AD15hubR = modelopt.Mesh_Options.AD15hubR + cables_connected_to_blade_base = modelopt.Mesh_Options.cables_connected_to_blade_base + turbineType = modelopt.Mesh_Options.turbineType + + # Drivetrain Options + turbineStartup = modelopt.Drivetrain_Options.turbineStartup + usingRotorSpeedFunction = modelopt.Drivetrain_Options.usingRotorSpeedFunction + driveTrainOn = modelopt.Drivetrain_Options.driveTrainOn + JgearBox = modelopt.Drivetrain_Options.JgearBox + gearRatio = modelopt.Drivetrain_Options.gearRatio + gearBoxEfficiency = modelopt.Drivetrain_Options.gearBoxEfficiency + generatorOn = modelopt.Drivetrain_Options.generatorOn + useGeneratorFunction = modelopt.Drivetrain_Options.useGeneratorFunction + generatorProps = modelopt.Drivetrain_Options.generatorProps + ratedTorque = modelopt.Drivetrain_Options.ratedTorque + zeroTorqueGenSpeed = modelopt.Drivetrain_Options.zeroTorqueGenSpeed + pulloutRatio = modelopt.Drivetrain_Options.pulloutRatio + ratedGenSlipPerc = modelopt.Drivetrain_Options.ratedGenSlipPerc + OmegaGenStart = modelopt.Drivetrain_Options.OmegaGenStart + driveShaft_K = modelopt.Drivetrain_Options.driveShaft_K + driveShaft_C = modelopt.Drivetrain_Options.driveShaft_C + + strut_twr_mountpoint = tower_strut_connection + strut_bld_mountpoint = blade_strut_connection + + # Inputs that are part of the overall options, but which are not yet available at the top level yaml input method + nlParams = 0 # derived struct, we aren't going to pass in the nlParams struct, but rather use the detailed inputs above, so hard code here. + bladeData = [] # same as above + numDOFPerNode = 6 #while much of the model can operate with fewer dofs, too much is hard coded on the full 6 dof. + omegaControl = false # this is a derived parameter + meshtype = turbineType #derived, should probably be cleaned up TODO + initCond = [] #OWENSFEA initial conditions array, will be derived at this level, if using the OWENS scripting method, this can be used to initalize the structure + jointTransform = 0.0 #OWENSFEA, derived matrix to transform from total matrix to the reduced matrix and vice-versa + reducedDOFList = zeros(Int,2) #OWENSFEA, derived array that maps the joint-reduced dofs + nodalTerms = 0.0 #OWENSFEA the ability to apply concentrated nodal masses and forces etc., currently only available at the scripting level of analysis + stack_layers_bld = nothing #, enables direct specification of the numbers of stack layers in the numad format + stack_layers_scale = [1.0,1.0] #, simple scaling across the blade span with a linear interpolation between + chord_scale = [1.0,1.0] #, simple scaling across the blade span with a linear interpolation between + thickness_scale = [1.0,1.0] #, simple scaling across the blade span with a linear interpolation between + OmegaInit = 7.2/60 #TODO: simplify this in the code since it is redundant aeroloadfile = "$module_path/../test/data/input_files_test/DVAWT_2B_LCDT_ElementData.csv" owensfile = "$module_path/../test/data/input_files_test/_15mTower_transient_dvawt_c_2_lcdt.owens" - potflowfile = "$module_path/../test/data/potential_flow_data" - outFilename = "none" - numDofPerNode = 6 - bladeData = [] - rigid = false - driveShaftProps = DriveShaftProps(0.0,0.0) - TOl = 1e-4 - MAXITER = 300 - iterwarnings = true - - joint_type = 0 - c_mount_ratio = 0.05 - strut_twr_mountpoint = [tower_strut_connection] #TODO: multiple struts - strut_bld_mountpoint = [blade_strut_connection] - DSModel="BV" - RPI=true - cables_connected_to_blade_base = true - meshtype = turbineType - saveName = "$path/vtk/windio" - aeroLoadsOn = 2 - nlOn = true - RayleighAlpha = 0.05 - RayleighBeta = 0.05 - iterationType = "DI" - gravityOn = [0,0,gravity] - initCond = [] - aeroElasticOn = false #for the automated flutter model - guessFreq = 0.0 - outFilename = "none" - jointTransform = 0.0 - reducedDOFList = zeros(Int,2) - numDOFPerNode = 6 - platformTurbineConnectionNodeNumber = 1 - spinUpOn = false - numModes = 20 - nlParams = 0 # can pass in strut, or leave at 0 to use other inputs - adaptiveLoadSteppingFlag = true - tolerance = 1.0000e-06 - maxIterations = 50 - maxNumLoadSteps = 20 - minLoadStepDelta = 0.0500 - minLoadStep = 0.0500 - prescribedLoadStep = 0.0 - predef = false - elementOrder = 1 - alpha = 0.5 - gamma = 0.5 - nodalTerms = 0.0 - - AD15hubR = 0.1 - Htwr_base = 3.0#maximum(windio[:components][:tower][:outer_shape_bem][:reference_axis][:z][:values]) - stack_layers_bld = nothing - stack_layers_scale = [1.0,1.0] - chord_scale = [1.0,1.0] - thickness_scale = [1.0,1.0] - angularOffset = -pi/2 - Aero_AddedMass_Active = false - Aero_RotAccel_Active = false - Aero_Buoyancy_Active = false + + + driveShaftProps = DriveShaftProps(driveShaft_K,driveShaft_C) + custommesh = nothing tsave_idx=1:3:numTS - NuMad_geom_xlscsv_file_twr = windio #"$(path)$(modelopt.NuMad_geom_xlscsv_file_twr)" - NuMad_mat_xlscsv_file_twr = windio #"$(path)$(modelopt.NuMad_mat_xlscsv_file_twr)" - NuMad_geom_xlscsv_file_bld = windio #"$(path)$(modelopt.NuMad_geom_xlscsv_file_bld)" - NuMad_mat_xlscsv_file_bld = windio #"$(path)$(modelopt.NuMad_mat_xlscsv_file_bld)" - NuMad_geom_xlscsv_file_strut = windio #"$(path)$(modelopt.NuMad_geom_xlscsv_file_strut)" - NuMad_mat_xlscsv_file_strut = windio #"$(path)$(modelopt.NuMad_mat_xlscsv_file_strut)" - adi_lib = modelopt.adi_lib - if adi_lib == "nothing" - adi_lib = nothing - end - adi_rootname = "$(path)$(modelopt.adi_rootname)" + NuMad_geom_xlscsv_file_twr = windio + NuMad_mat_xlscsv_file_twr = windio + NuMad_geom_xlscsv_file_bld = windio + NuMad_mat_xlscsv_file_bld = windio + NuMad_geom_xlscsv_file_strut = windio + NuMad_mat_xlscsv_file_strut = windio + + adi_rootname = "$(path)$(adi_rootname)" shapeZ = blade_z#collect(LinRange(0,H,Nslices+1)) shapeX = blade_x#R.*(1.0.-4.0.*(shapeZ/H.-.5).^2)#shapeX_spline(shapeZ) @@ -269,7 +322,6 @@ function runOWENSWINDIO(windio,modelopt,path;verbosity=2) R = maximum(blade_x) #m H = maximum(blade_z) #m - Htwr_blds = H nothing @@ -285,8 +337,8 @@ function runOWENSWINDIO(windio,modelopt,path;verbosity=2) mu=air_dyn_viscosity, Nslices, ntheta, - RPM, - Vinf, + RPM=Prescribed_RPM_RPM_controlpoints[1], + Vinf=Prescribed_Vinf_Vinf_controlpoints[1], eta=blade_mountpoint, B=number_of_blades, H, @@ -318,8 +370,8 @@ function runOWENSWINDIO(windio,modelopt,path;verbosity=2) c_mount_ratio, strut_twr_mountpoint, strut_bld_mountpoint, - AModel, #AD, DMS, AC - DSModel, + AeroModel, #AD, DMS, AC + DynamicStallModel, RPI, cables_connected_to_blade_base, meshtype, @@ -343,29 +395,6 @@ function runOWENSWINDIO(windio,modelopt,path;verbosity=2) nothing - # If the sectional properties material files includes cost information, that is combined with the density - # to estimate the overall material cost of of materials in the blades - - if verbosity>0 - - println("\nBlades' Mass Breakout") - for (i,name) in enumerate(plyprops_bld.names) - println("$name $(mass_breakout_blds[i]) kg, $(plyprops_bld.costs[i]) \$/kg: \$$(mass_breakout_blds[i]*plyprops_bld.costs[i])") - end - - println("\nTower Mass Breakout") - for (i,name) in enumerate(plyprops_twr.names) - println("$name $(mass_breakout_twr[i]) kg, $(plyprops_twr.costs[i]) \$/kg: \$$(mass_breakout_twr[i]*plyprops_twr.costs[i])") - end - - println("Total Material Cost Blades: \$$(sum(mass_breakout_blds.*plyprops_bld.costs))") - println("Total Material Cost Tower: \$$(sum(mass_breakout_twr.*plyprops_twr.costs))") - println("Total Material Cost: \$$(sum(mass_breakout_blds.*plyprops_bld.costs)+ sum(mass_breakout_twr.*plyprops_twr.costs))") - - end - - nothing - # Here we apply the boundary conditions. For this case, with a regular cantelever tower, the tower base node which is # 1 is constrained in all 6 degrees of freedom to have a displacement of 0. You can change this displacement to allow for things # like pretension, and you can apply boundary conditions to any node. @@ -381,17 +410,79 @@ function runOWENSWINDIO(windio,modelopt,path;verbosity=2) # There are inputs for the overall coupled simulation, please see the api reference for specifics on all the options - if AModel=="AD" + if AeroModel=="AD" AD15On = true else AD15On = false end + # Handle the control strategy #TODO: function and hook up discon controller + if DLCs != "none" + normalRPM = Prescribed_RPM_RPM_controlpoints[1] ./ 60 + slowRPM = 1.0 #RPM + tocp = [0.0,10.0,30.0,1000.0] + turbineStartup = 0 + generatorOn = false + useGeneratorFunction = false + throwawayTimeSteps=1#round(Int,10.0/delta_t) # 10 seconds + if controlStrategy == "normal" + Omegaocp = [normalRPM,normalRPM,normalRPM,normalRPM]./60 #hz + turbineStartup = 0 + generatorOn = false + useGeneratorFunction = false + elseif controlStrategy == "freewheelatNormalOperatingRPM" + Omegaocp = [normalRPM,normalRPM,normalRPM,normalRPM]./60 #hz + turbineStartup = 2 + generatorOn = false + useGeneratorFunction = false + elseif controlStrategy == "startup" + throwawayTimeSteps = 1 + tocp = [0.0,30.0,1000.0] + Omegaocp = [slowRPM,normalRPM,normalRPM]./60 #hz + turbineStartup = 0 + generatorOn = false + useGeneratorFunction = false + elseif controlStrategy == "shutdown" + tocp = [0.0,10.0,15.0,30.0,1000.0] + Omegaocp = [normalRPM,normalRPM,normalRPM/2,slowRPM,0.0]./60 #hz + elseif controlStrategy == "emergencyshutdown" + tocp = [0.0,10.0,15.0,30.0,1000.0] + Omegaocp = [normalRPM,normalRPM,slowRPM,0.0,0.0]./60 #hz + elseif controlStrategy == "parked" + Omegaocp = [slowRPM,slowRPM,slowRPM,slowRPM]./60 #hz + elseif controlStrategy == "parked_idle" + Omegaocp = [slowRPM,slowRPM,slowRPM,slowRPM]./60 #hz + turbineStartup = 2 + generatorOn = false + useGeneratorFunction = false + elseif controlStrategy == "parked_yaw" + Omegaocp = [slowRPM,slowRPM,slowRPM,slowRPM]./60 #hz + elseif controlStrategy == "parked" + Omegaocp = [slowRPM,slowRPM,slowRPM,slowRPM]./60 #hz + elseif controlStrategy == "transport" + Omegaocp = [slowRPM,slowRPM,slowRPM,slowRPM]./60 #hz + elseif controlStrategy == "prescribedRPM" + tocp = Prescribed_RPM_time_controlpoints + Omegaocp = Prescribed_RPM_RPM_controlpoints ./ 60 + else + @warn "ControlStrategy $controlStrategy not recognized, using prescribed RPM spline control points" + tocp = Prescribed_RPM_time_controlpoints + Omegaocp = Prescribed_RPM_RPM_controlpoints ./ 60 + end + else + tocp = Prescribed_RPM_time_controlpoints + Omegaocp = Prescribed_RPM_RPM_controlpoints ./ 60 + + end + + + println("controlStrategy: $controlStrategy") + inputs = OWENS.Inputs(;analysisType = structuralModel, - tocp = [0.0,100000.1], - Omegaocp = [RPM,RPM] ./ 60, - tocp_Vinf = [0.0,100000.1], - Vinfocp = [Vinf,Vinf], + tocp, + Omegaocp, + tocp_Vinf = Prescribed_Vinf_time_controlpoints, + Vinfocp = Prescribed_Vinf_Vinf_controlpoints, numTS, delta_t, AD15On, @@ -400,7 +491,7 @@ function runOWENSWINDIO(windio,modelopt,path;verbosity=2) usingRotorSpeedFunction, driveTrainOn, generatorOn, - hydroOn, + platformActive, topsideOn, interpOrder, hd_input_file, @@ -421,14 +512,13 @@ function runOWENSWINDIO(windio,modelopt,path;verbosity=2) aeroloadfile, owensfile, potflowfile, - outFilename, - numDofPerNode, + dataOutputFilename, + numDOFPerNode, bladeData, rigid, driveShaftProps, - TOl, - MAXITER, - iterwarnings) + TOL, + MAXITER) nothing @@ -447,7 +537,7 @@ function runOWENSWINDIO(windio,modelopt,path;verbosity=2) initCond, aeroElasticOn, #for the automated flutter model guessFreq, - outFilename, + dataOutputFilename, jointTransform, reducedDOFList, numDOFPerNode, @@ -466,6 +556,7 @@ function runOWENSWINDIO(windio,modelopt,path;verbosity=2) elementOrder, alpha, gamma, + AddedMass_Coeff_Ca, nodalTerms) nothing @@ -486,8 +577,7 @@ function runOWENSWINDIO(windio,modelopt,path;verbosity=2) # deformations. Additionaly, there is a method to input custom values and have them show up on the vtk surface mesh # for example, strain, or reaction force, etc. This is described in more detail in the api reference for the function and: TODO - azi=aziHist#./aziHist*1e-6 - OWENS.OWENSVTK(saveName,t,uHist,system,assembly,sections,aziHist,mymesh,myel, + OWENS.OWENSVTK(VTKsaveName,t,uHist,system,assembly,sections,aziHist,mymesh,myel, epsilon_x_hist,epsilon_y_hist,epsilon_z_hist,kappa_x_hist,kappa_y_hist,kappa_z_hist, FReactionHist,topFexternal_hist;tsave_idx) @@ -513,49 +603,5 @@ function runOWENSWINDIO(windio,modelopt,path;verbosity=2) Twr_LE_U_idx=1,Twr_LE_L_idx=1, AD15bldNdIdxRng,AD15bldElIdxRng,strut_precompoutput=nothing) #TODO: add in ability to have material safety factors and load safety factors - dataDumpFilename = "$path/InitialDataOutputs.h5" - - HDF5.h5open(dataDumpFilename, "w") do file - HDF5.write(file,"t",collect(t)) - HDF5.write(file,"aziHist",aziHist) - HDF5.write(file,"OmegaHist",OmegaHist) - HDF5.write(file,"OmegaDotHist",OmegaDotHist) - HDF5.write(file,"gbHist",gbHist) - HDF5.write(file,"gbDotHist",gbDotHist) - HDF5.write(file,"gbDotDotHist",gbDotDotHist) - HDF5.write(file,"FReactionHist",FReactionHist) - HDF5.write(file,"FTwrBsHist",FTwrBsHist) - HDF5.write(file,"genTorque",genTorque) - HDF5.write(file,"genPower",genPower) - HDF5.write(file,"torqueDriveShaft",torqueDriveShaft) - HDF5.write(file,"uHist",uHist) - HDF5.write(file,"uHist_prp",uHist_prp) - HDF5.write(file,"epsilon_x_hist",epsilon_x_hist) - HDF5.write(file,"epsilon_y_hist",epsilon_y_hist) - HDF5.write(file,"epsilon_z_hist",epsilon_z_hist) - HDF5.write(file,"kappa_x_hist",kappa_x_hist) - HDF5.write(file,"kappa_y_hist",kappa_y_hist) - HDF5.write(file,"kappa_z_hist",kappa_z_hist) - HDF5.write(file,"massOwens",massOwens) - HDF5.write(file,"stress_U",stress_U) - HDF5.write(file,"SF_ult_U",SF_ult_U) - HDF5.write(file,"SF_buck_U",SF_buck_U) - HDF5.write(file,"stress_L",stress_L) - HDF5.write(file,"SF_ult_L",SF_ult_L) - HDF5.write(file,"SF_buck_L",SF_buck_L) - HDF5.write(file,"stress_TU",stress_TU) - HDF5.write(file,"SF_ult_TU",SF_ult_TU) - HDF5.write(file,"SF_buck_TU",SF_buck_TU) - HDF5.write(file,"stress_TL",stress_TL) - HDF5.write(file,"SF_ult_TL",SF_ult_TL) - HDF5.write(file,"SF_buck_TL",SF_buck_TL) - HDF5.write(file,"topstrainout_blade_U",topstrainout_blade_U) - HDF5.write(file,"topstrainout_blade_L",topstrainout_blade_L) - HDF5.write(file,"topstrainout_tower_U",topstrainout_tower_U) - HDF5.write(file,"topstrainout_tower_L",topstrainout_tower_L) - HDF5.write(file,"topDamage_blade_U",topDamage_blade_U) - HDF5.write(file,"topDamage_blade_L",topDamage_blade_L) - HDF5.write(file,"topDamage_tower_U",topDamage_tower_U) - HDF5.write(file,"topDamage_tower_L",topDamage_tower_L) - end + outputData(;mymesh,inputs,t,aziHist,OmegaHist,OmegaDotHist,gbHist,gbDotHist,gbDotDotHist,FReactionHist,genTorque,genPower,torqueDriveShaft,uHist,uHist_prp,epsilon_x_hist,epsilon_y_hist,epsilon_z_hist,kappa_x_hist,kappa_y_hist,kappa_z_hist,FTwrBsHist,massOwens,stress_U,SF_ult_U,SF_buck_U,stress_L,SF_ult_L,SF_buck_L,stress_TU,SF_ult_TU,SF_buck_TU,stress_TL,SF_ult_TL,SF_buck_TL,topstrainout_blade_U,topstrainout_blade_L,topstrainout_tower_U,topstrainout_tower_L,topDamage_blade_U,topDamage_blade_L,topDamage_tower_U,topDamage_tower_L) end \ No newline at end of file diff --git a/test/34mROMtest.jl b/test/34mROMtest.jl index 570b0eae..c74f51f6 100644 --- a/test/34mROMtest.jl +++ b/test/34mROMtest.jl @@ -62,7 +62,7 @@ top_idx 5 0 top_idx 6 0] model = OWENS.Inputs(;analysisType = "ROM", - outFilename = "none", + dataOutputFilename = "none", tocp = [0.0,100000.1], numTS = 100, delta_t = 0.1, diff --git a/test/Fig4_5_campbell2.jl b/test/Fig4_5_campbell2.jl index f9ace4b5..78ad588b 100644 --- a/test/Fig4_5_campbell2.jl +++ b/test/Fig4_5_campbell2.jl @@ -40,7 +40,7 @@ nbelem = 60 ncelem = 10 nselem = 5 ifw = false -AModel = "DMS" +AeroModel = "DMS" windINPfilename = nothing ifw_libfile = nothing Blade_Height = 41.9 @@ -132,8 +132,8 @@ mass_breakout_blds,mass_breakout_twr,system, assembly, sections = OWENS.setupOWE joint_type = 0, strut_twr_mountpoint = [0.03,0.97], strut_bld_mountpoint = [0.03,0.97], - AModel, #AD, DMS, AC - DSModel="BV", + AeroModel, #AD, DMS, AC + DynamicStallModel="BV", RPI=true, cables_connected_to_blade_base = true, angularOffset = pi/2, @@ -170,7 +170,7 @@ top_idx 2 0] ############################################# FEAinputs = OWENSFEA.FEAModel(;analysisType = "M", - # outFilename = "$path/data/outplat.out", + # dataOutputFilename = "$path/data/outplat.out", joint = myjoint, platformTurbineConnectionNodeNumber = 1, pBC = pBC, @@ -198,7 +198,7 @@ freq2 = OWENS.AutoCampbellDiagram(FEAinputs,mymesh,myel,system,assembly,sections minRPM = 0.0, maxRPM = 40.0, NRPM = 9, # int - vtksavename="$path/campbellVTK/SNL34m", + VTKsavename="$path/campbellVTK/SNL34m", saveModes = [1,3,5], #must be int mode_scaling = 500.0, ) diff --git a/test/runtests.jl b/test/runtests.jl index d18b15a3..c76d3475 100644 --- a/test/runtests.jl +++ b/test/runtests.jl @@ -32,4 +32,9 @@ end @testset "Buoyancy" begin path = splitdir(@__FILE__)[1] include("$path/../examples/AddedMass_Buoyancy/Buoyancy.jl") -end \ No newline at end of file +end + +# @testset "WindIO" begin +# path = splitdir(@__FILE__)[1] +# include("$path/../examples/Optimization/windio_example.jl") +# end \ No newline at end of file diff --git a/test/testfloating.jl b/test/testfloating.jl index f9383d48..f544277b 100644 --- a/test/testfloating.jl +++ b/test/testfloating.jl @@ -266,11 +266,11 @@ function runSim(; bin = OWENS.Bin(hd_lib, md_lib) inputs = OWENS.Inputs(analysisType = "TNB", - outFilename = "none", + dataOutputFilename = "none", tocp = [0.0,num_ts], Omegaocp = [0.0, 0.0], OmegaInit = 0.0, - hydroOn = true, + platformActive = true, aeroLoadsOn = 2, interpOrder = 2, numTS = num_ts,