pytrebuchet.simulation module

Module for simulating trebuchet projectile launches.

pytrebuchet.simulation.requires_solved(func: Callable) Callable

Ensure that the simulation has been solved before accessing the decorated method.

Raises:

ValueError – If the simulation has not been run yet (self.solved is False).

class pytrebuchet.simulation.SimulationPhases(*values)

Bases: StrEnum

Enumeration of the different phases of the simulation.

ALL = 'ALL'
SLING = 'SLING'
BALLISTIC = 'BALLISTIC'
static _generate_next_value_(name, start, count, last_values)

Return the lower-cased version of the member name.

class pytrebuchet.simulation.SlingODETerminationEvent

Bases: object

Event class to terminate the integration of the sling ode.

terminal = True
direction = 0
class pytrebuchet.simulation.BallisticODETerminationEvent

Bases: object

Event class to terminate the integration of the ballistic ode.

terminal = True
direction = 0
class pytrebuchet.simulation.Simulation(trebuchet: Trebuchet, environment: EnvironmentConfig | None = None, *, verify_sling_tension: bool = True, atol: float = 1e-06, rtol: float = 1e-05)

Bases: object

Class for simulating trebuchet projectile launches.

Parameters:
  • trebuchet – Trebuchet object containing trebuchet parameters

  • wind_speed – Wind speed in m/s (default is 0.0)

  • air_density – Density of the air in kg/m^3 (default is standard air density at sea level)

  • air_kinematic_viscosity – Kinematic viscosity of the air in m^2/s (default is approximate value at 15 degrees Celsius at sea level)

  • gravitational_acceleration – Gravitational acceleration in m/s^2 (default is Earth’s gravity)

  • verify_sling_tension – Whether to verify sling tension after solving the simulation (default is True)

  • atol – Absolute tolerance for the ODE solver (default is 1e-6)

  • rtol – Relative tolerance for the ODE solver (default is 1e-5), spikes in the distance calculations occur for rtol >= 1e-4

__init__(trebuchet: Trebuchet, environment: EnvironmentConfig | None = None, *, verify_sling_tension: bool = True, atol: float = 1e-06, rtol: float = 1e-05) None

Initialize the simulation with the given trebuchet and projectile.

Parameters:
  • trebuchet – Trebuchet object containing trebuchet parameters

  • environment – EnvironmentConfig object containing environment parameters

  • verify_sling_tension – Whether to verify sling tension after solving the simulation (default is True)

  • atol – Absolute tolerance for the ODE solver (default is 1e-6)

  • rtol – Relative tolerance for the ODE solver (default is 1e-5), spikes in the distance calculations seem to occur for rtol >= 1e-4

_sling_phases: tuple[SlingPhases, ...]
_sling_phase_solutions: dict[SlingPhases, Bunch | None]
_ballistic_solution: Bunch | None
_get_sling_phase_solution(phase: SlingPhases) Bunch

Get sling phase solution with validation.

Parameters:

phase – The sling phase to get the solution for

Returns:

The solve_ivp solution for the specified phase

Raises:

RuntimeError – If the solution is not available

_get_ballistic_solution() Bunch

Get ballistic phase solution with validation.

Returns:

The solve_ivp solution for the ballistic phase

Raises:

RuntimeError – If the solution is not available

solve() None

Run the simulation of the trebuchet launching the projectile.

_solve_sling_phase(phase_index: int) None

Solve the differential equations for a specific sling phase.

Parameters:

phase_index – The index of the sling phase to be solved

_solve_ballistic_phase() None

Solve the differential equations for the ballistic phase.

The differential equations have the following arguments: environment: EnvironmentConfig object containing environment parameters projectile: Projectile object containing properties of the projectile

get_phase_end_time(sim_phase: SimulationPhases, sling_phase: SlingPhases | None = None) float

Return the end time of the specified phase.

Parameters:
  • sim_phase – The simulation phase to get the end time for.

  • sling_phase – The sling phase to get the end time for, required if sim_phase is SLING.

Returns:

The end time of the specified phase.

property solved: bool

Return whether the simulation has been run.

Returns:

True if the simulation has been run, False otherwise.

property distance_traveled: float

Return the horizontal distance traveled by the projectile.

Distance as measured from the pivot’s x-coordinate.

Returns:

Horizontal distance traveled by the projectile.

property release_velocity: float

Return the velocity of the projectile at sling release.

Returns:

Velocity of the projectile at sling release.

get_tsteps(sim_phase: SimulationPhases = SimulationPhases.ALL, sling_phase: SlingPhases | None = None) ndarray[tuple[Any, ...], dtype[floating]]

Return the time steps for the specified phase(s) of the simulation.

Parameters:
  • sim_phase – Phase of the simulation to get time steps for. Options are: ALL - all phases (default) BALLISTIC - ballistic phase SLING - sling phases

  • sling_phase – Specific sling phase to get time steps for, required if sim_phase is SLING.

Returns:

Numpy array of time steps for the specified phase(s).

_get_phase_state_variables(sim_phase: SimulationPhases, sling_phase: SlingPhases | None = None) ndarray[tuple[Any, ...], dtype[floating]]

Return the state variables of the specified sling phase.

Combines the regular solution and the event solution.

Parameters:
  • sim_phase – The simulation phase to get the state variables for.

  • sling_phase – The sling phase to get the state variables for, required if sim_phase is SLING.

Returns:

Numpy array of shape (n, 6) where n is the number of time steps, containing the state variables

get_trebuchet_state_variables(*, calculate_accelerations: bool = False) ndarray[tuple[Any, ...], dtype[floating]]

Return the state variables (angles and angular velocities) of the trebuchet.

Parameters:

calculate_accelerations – Whether to include angular accelerations in the returned array (default is False)

Returns:

Numpy array of shape (n, 6) or (n, 9) where n is the number of time steps, containing the state variables [ angle_arm, angle_weight, angle_projectile, angular_velocity_arm, angular_velocity_weight, angular_velocity_projectile, angular_acceleration_arm (if calculate_accelerations is True), angular_acceleration_weight (if calculate_accelerations is True), angular_acceleration_projectile (if calculate_accelerations is True), ]

get_projectile_state_variables(phase: SimulationPhases = SimulationPhases.ALL, *, calculate_accelerations: bool = False) ndarray[tuple[Any, ...], dtype[floating]]

Return the state variables of the projectile throughout its flight.

This includes the (positions, velocities, optional accelerations)

Parameters:
  • phase – Phase of the simulation to get projectile state variables for. Options are: ALL - all phases (default) BALLISTIC - ballistic phase SLING - sling phases

  • calculate_accelerations – Whether to include accelerations in the returned array (default is False)

Returns:

Numpy array of shape (n, 4) or (n, 6) where n is the number of time steps, containing the state variables [ position_x, position_y, velocity_x, velocity_y, acceleration_x (if calculate_accelerations is True), acceleration_y (if calculate_accelerations is True), ]

where_sling_in_tension(*, return_projection_array: bool = False) ndarray[tuple[Any, ...], dtype[floating]] | ndarray[tuple[Any, ...], dtype[bool]]

Determine where the sling is in tension throughout the sling phases.

Parameters:

return_projection_array – If True, returns the projection values instead of booleans (default is False)

Returns:

if return_projection_array: Numpy array of projection values

at each time step.

else: Numpy boolean array indicating whether the sling is in tension

at each time step.