Dynamic Derivatives

Contents

Dynamic Derivatives#

This example demonstrates the computation of dynamic stability derivatives for an airfoil undergoing pitching oscillations. It employs a sliding mesh approach, where the airfoil is enclosed within a rotating cylindrical interface. The simulation strategy involves two stages: first, a steady-state simulation is performed to establish a baseline flow field, followed by an unsteady simulation where the sliding interface oscillates according to a specified sinusoidal motion to capture the dynamic effects. The script showcases the setup for both the steady initialization and the subsequent unsteady, oscillating simulation using the Flow360 Python API.

  1"""
  2Example script for calculating dynamic derivatives using sliding interfaces in Flow360
  3See documentation for more information:
  4 https://docs.flexcompute.com/projects/flow360/en/latest/tutorials/DynamicDerivatives/DynamicDerivatives.html
  5"""
  6
  7import math
  8
  9import flow360 as fl
 10from flow360.examples import TutorialDynamicDerivatives
 11
 12TutorialDynamicDerivatives.get_files()
 13project = fl.Project.from_geometry(
 14    TutorialDynamicDerivatives.geometry,
 15    name="Tutorial Calculating Dynamic Derivatives using Sliding Interfaces from Python",
 16)
 17geometry = project.geometry
 18
 19
 20# show face groupings
 21geometry.show_available_groupings(verbose_mode=True)
 22geometry.group_faces_by_tag("faceName")
 23geometry.group_edges_by_tag("edgeName")
 24
 25with fl.SI_unit_system:
 26    cylinder = fl.Cylinder(
 27        name="cylinder",
 28        axis=[0, 1, 0],
 29        center=[0, 0, 0],
 30        inner_radius=0,
 31        outer_radius=1.0,
 32        height=2.5,
 33    )
 34    sliding_interface = fl.RotationCylinder(
 35        spacing_axial=0.04,
 36        spacing_radial=0.04,
 37        spacing_circumferential=0.04,
 38        entities=cylinder,
 39        enclosed_entities=geometry["wing"],
 40    )
 41    farfield = fl.AutomatedFarfield()
 42    params = fl.SimulationParams(
 43        meshing=fl.MeshingParams(
 44            defaults=fl.MeshingDefaults(
 45                surface_max_edge_length=0.03 * fl.u.m,
 46                curvature_resolution_angle=8 * fl.u.deg,
 47                surface_edge_growth_rate=1.15,
 48                boundary_layer_first_layer_thickness=1e-6,
 49                boundary_layer_growth_rate=1.15,
 50            ),
 51            refinement_factor=1.0,
 52            volume_zones=[sliding_interface, farfield],
 53            refinements=[
 54                fl.SurfaceEdgeRefinement(
 55                    name="leadingEdge",
 56                    method=fl.AngleBasedRefinement(value=1 * fl.u.degree),
 57                    edges=geometry["leadingEdge"],
 58                ),
 59                fl.SurfaceEdgeRefinement(
 60                    name="trailingEdge",
 61                    method=fl.HeightBasedRefinement(value=0.001),
 62                    edges=geometry["trailingEdge"],
 63                ),
 64            ],
 65        ),
 66        reference_geometry=fl.ReferenceGeometry(
 67            moment_center=[0, 0, 0],
 68            moment_length=[1, 1, 1],
 69            area=2,
 70        ),
 71        operating_condition=fl.AerospaceCondition(
 72            velocity_magnitude=50,
 73        ),
 74        time_stepping=fl.Unsteady(
 75            max_pseudo_steps=80,
 76            steps=400,
 77            step_size=0.01 * 2.0 * math.pi / 20.0 * fl.u.s,
 78            CFL=fl.AdaptiveCFL(),
 79        ),
 80        outputs=[
 81            fl.VolumeOutput(
 82                output_fields=[
 83                    "Mach",
 84                ],
 85            ),
 86            fl.SurfaceOutput(
 87                surfaces=geometry["*"],
 88                output_fields=[
 89                    "Cp",
 90                    "CfVec",
 91                ],
 92            ),
 93        ],
 94        models=[
 95            fl.Rotation(
 96                volumes=cylinder,
 97                spec=fl.AngleExpression("0.0349066 * sin(0.05877271 * t)"),
 98            ),
 99            fl.Freestream(surfaces=farfield.farfield),
100            fl.Wall(surfaces=geometry["wing"]),
101            fl.Fluid(
102                navier_stokes_solver=fl.NavierStokesSolver(
103                    absolute_tolerance=1e-9,
104                    linear_solver=fl.LinearSolver(max_iterations=35),
105                ),
106                turbulence_model_solver=fl.SpalartAllmaras(
107                    absolute_tolerance=1e-8,
108                    linear_solver=fl.LinearSolver(max_iterations=25),
109                ),
110            ),
111        ],
112    )
113# Run unsteady case with an oscillating sliding interface to collecting the data.
114project.run_case(
115    params=params,
116    name="Tutorial Calculating Dynamic Derivatives using Sliding Interfaces",
117)

Notes#

  • Two-Stage Simulation: A steady-state case initializes the flow field before the unsteady simulation begins, utilizing fork_from to inherit the flow field solution.

  • Sliding Interface Oscillation: The pitching motion is modeled using a RotationCylinder sliding interface. Its angular position over time is defined via AngleExpression, incorporating nondimensional time (t) and frequency.