Difference between revisions of "Extending OpenRocket"
(6 intermediate revisions by the same user not shown) | |||
Line 1: | Line 1: | ||
− | |||
− | |||
OpenRocket is built to be extensible using plugins. You can implement your own functionality or download plugins implemented by others. | OpenRocket is built to be extensible using plugins. You can implement your own functionality or download plugins implemented by others. | ||
Line 7: | Line 5: | ||
− | + | == Plugins == | |
Extensions to OpenRocket are implemented as plugins. All interfaces that may have multiple implementations should be implemented using plugin interfaces internally. That way, external plugins may create new implementations. | Extensions to OpenRocket are implemented as plugins. All interfaces that may have multiple implementations should be implemented using plugin interfaces internally. That way, external plugins may create new implementations. | ||
Line 21: | Line 19: | ||
− | + | == Simulation extensions == | |
Simulation extensions allow modifying simulations before or during a simulation. They allow controlling almost every aspect of a simulation. | Simulation extensions allow modifying simulations before or during a simulation. They allow controlling almost every aspect of a simulation. | ||
− | A simulation extensions typically consists of 2-4 Java classes | + | A simulation extensions typically consists of 2-4 Java classes described below. '''The recommended way of implementing these interfaces is by extending the abstract classes'''. This allows maximum compatibility with future versions of OpenRocket when new methods are added to the interfaces. |
+ | |||
+ | |||
+ | {| class="wikitable" | ||
+ | |- | ||
+ | ! | ||
+ | ! Interface / abstract class | ||
+ | ! Description | ||
+ | |- | ||
+ | ! Simulation extension | ||
+ | | ''<code>SimulationExtension</code>'' <br> <code>AbstractSimulationExtension</code> | ||
+ | | Contains the extension configuration for a single simulation and a method that is called whenever the simulation is started. A new instance is created for each simulation that has the extension defined. | ||
+ | |- | ||
+ | ! Simulation extension ''provider'' | ||
+ | | ''<code>SimulationExtensionProvider</code>'' <br> <code>AbstractSimulationExtensionProvider</code> | ||
+ | | An OpenRocket plugin that functions as a factory class for the simulation extension. It provides the extension ID, location in the UI menu and instances of the extension. | ||
+ | |- | ||
+ | ! Simulation extension ''configurator'' | ||
+ | | <code>SwingSimulationExtensionConfigurator</code> <br> <code>AbstractSwingSimulationExtensionConfigurator</code> | ||
+ | | An (optional) OpenRocket plugin that provides a GUI for configuring the simulation extension. | ||
+ | |- | ||
+ | ! Simulation ''listener'' | ||
+ | | ''<code>SimulationListener</code> <br> <code>SimulationComputationListener</code> <br> <code>SimulationEventListener</code>'' <br> <code>AbstractSimulationListener</code> | ||
+ | | A listener that can be attached to a simulation at runtime. The listener is notified of all actions during the simulation and it can modify and affect the simulation while it is being run. The simulation extension may add a simulation listener to the simulation run when it is started. | ||
+ | |- | ||
+ | |} | ||
+ | |||
+ | |||
+ | === Simulation extension class === | ||
+ | |||
+ | An instance of the simulation extension class is attached to each simulation that has the extension defined. It contains the configuration of the extension and a method that is called when the simulation is run. | ||
+ | |||
+ | You need to extend <code>AbstractSimulationExtension</code> and implement at least the <code>initialize</code> method. This method is called whenever a simulation run is started. It can modify the <code>SimulationConditions</code>, which contains the launch conditions of the simulation. It can also attach simulation listeners to the simulation, which allows interacting with the simulation while it is running. | ||
+ | |||
+ | === Simulation extension provider === | ||
+ | |||
+ | The provider is a factory class that creates instances of the simulation extension. It also provides an ID string identifying the simulation extension and the name and menu location of the extension. | ||
+ | |||
+ | When using <code>AbstractSimulationExtensionProvider</code> you only need to provide the constructor the simulation extension class and the name and menu location. | ||
+ | |||
+ | A single simulation extension provider can be used to provide multiple simulation extensions. For example, the provider could scan a directory for scripts and provide a simulation extension for each script file. The abstract class assumes you are only providing a single simulation extension. | ||
+ | |||
+ | === Simulation extension configurator === | ||
+ | |||
+ | The separate configurator provides a Swing GUI dialog to configure a single instance of a simulation extension. It is implemented as a separate plugin so that the plugin itself can be used also on platforms not supporting Swing (such as Android). | ||
+ | |||
+ | <code>SwingSimulationExtensionConfigurator</code> provides a ready framework where you only need to implement the <code>getConfigurationComponent</code> method, where you add the necessary components to a ready <code>JPanel</code>. | ||
+ | |||
+ | |||
+ | == Simulation listeners == | ||
+ | |||
+ | '''Simulation listeners''' are pieces of custom code that are run during a simulation run. They can either be implemented in Java, or in a scripting language of your choise by adding the Simulation extension in ''User code'' -> ''Scripts''. | ||
+ | |||
+ | In Java, the recommended way of implementing a simulation listener is by extending the <code>AbstractSimulationListener</code> class and overriding the desired methods. | ||
+ | |||
+ | In scripts, you only need to implement the methods you need. | ||
− | + | The methods, their arguments and return values are listed below. For scripting languages, replace with the corresponding object (for example in Ruby return <code>nil</code> instead of <code>null</code>). In many scripting languages, returning nothing or an undefined value will have the same effect as returning <code>null</code>. The methods may also throw exceptions to abort the simulation. | |
− | |||
− | |||
− | |||
− | ''' | + | {| class="wikitable" |
+ | |- | ||
+ | ! Method signature | ||
+ | ! Description | ||
+ | |- | ||
+ | | | ||
+ | void '''startSimulation'''(SimulationStatus status) <br> | ||
+ | void '''endSimulation'''(SimulationStatus status, SimulationException exception) | ||
+ | | Called when starting and ending a simulation. The <code>endSimulation</code> method is provided the exception if the simulation is aborted by one. | ||
+ | |- | ||
+ | | | ||
+ | boolean '''preStep'''(SimulationStatus status) <br> | ||
+ | void '''postStep'''(SimulationStatus status) | ||
+ | | Called before and after taking a simulation step. The <code>preStep</code> method can prevent taking the step by returning <code>false</code>. | ||
+ | |- | ||
+ | | | ||
+ | AccelerationData '''preAccelerationCalculation'''(SimulationStatus status) <br> | ||
+ | AccelerationData postAccelerationCalculation(SimulationStatus status, AccelerationData acceleration) | ||
+ | | Called before and after computing acceleration of the | ||
+ | |} |
Latest revision as of 17:37, 13 January 2015
OpenRocket is built to be extensible using plugins. You can implement your own functionality or download plugins implemented by others.
This document describes how to implement your own extensions to OpenRocket.
Plugins[edit]
Extensions to OpenRocket are implemented as plugins. All interfaces that may have multiple implementations should be implemented using plugin interfaces internally. That way, external plugins may create new implementations.
A plugin is compiled into a JAR file and placed into the OpenRocket plugin directory. These JAR files are included in the OpenRocket classpath at startup and scanned for classes and interfaces annotated with @Plugin
.
- A plugin interface is a Java interface that is annotated with the
@Plugin
annotation. These interfaces are scanned from the classpath at startup and can be queried by the code. - A plugin implementation is a Java class that implements a plugin interface and is annotated with the
@Plugin
annotation.
In practise the plugin interfaces are defined by the internal OpenRocket code, and are extension points which internal and external plugins can implement.
Note: Many of the internal interfaces have not yet been changed to use the plugin interface. They will be migrated one by one. Help is appreciated.
Simulation extensions[edit]
Simulation extensions allow modifying simulations before or during a simulation. They allow controlling almost every aspect of a simulation.
A simulation extensions typically consists of 2-4 Java classes described below. The recommended way of implementing these interfaces is by extending the abstract classes. This allows maximum compatibility with future versions of OpenRocket when new methods are added to the interfaces.
Interface / abstract class | Description | |
---|---|---|
Simulation extension | SimulationExtension AbstractSimulationExtension
|
Contains the extension configuration for a single simulation and a method that is called whenever the simulation is started. A new instance is created for each simulation that has the extension defined. |
Simulation extension provider | SimulationExtensionProvider AbstractSimulationExtensionProvider
|
An OpenRocket plugin that functions as a factory class for the simulation extension. It provides the extension ID, location in the UI menu and instances of the extension. |
Simulation extension configurator | SwingSimulationExtensionConfigurator AbstractSwingSimulationExtensionConfigurator
|
An (optional) OpenRocket plugin that provides a GUI for configuring the simulation extension. |
Simulation listener | SimulationListener SimulationComputationListener SimulationEventListener AbstractSimulationListener
|
A listener that can be attached to a simulation at runtime. The listener is notified of all actions during the simulation and it can modify and affect the simulation while it is being run. The simulation extension may add a simulation listener to the simulation run when it is started. |
Simulation extension class[edit]
An instance of the simulation extension class is attached to each simulation that has the extension defined. It contains the configuration of the extension and a method that is called when the simulation is run.
You need to extend AbstractSimulationExtension
and implement at least the initialize
method. This method is called whenever a simulation run is started. It can modify the SimulationConditions
, which contains the launch conditions of the simulation. It can also attach simulation listeners to the simulation, which allows interacting with the simulation while it is running.
Simulation extension provider[edit]
The provider is a factory class that creates instances of the simulation extension. It also provides an ID string identifying the simulation extension and the name and menu location of the extension.
When using AbstractSimulationExtensionProvider
you only need to provide the constructor the simulation extension class and the name and menu location.
A single simulation extension provider can be used to provide multiple simulation extensions. For example, the provider could scan a directory for scripts and provide a simulation extension for each script file. The abstract class assumes you are only providing a single simulation extension.
Simulation extension configurator[edit]
The separate configurator provides a Swing GUI dialog to configure a single instance of a simulation extension. It is implemented as a separate plugin so that the plugin itself can be used also on platforms not supporting Swing (such as Android).
SwingSimulationExtensionConfigurator
provides a ready framework where you only need to implement the getConfigurationComponent
method, where you add the necessary components to a ready JPanel
.
Simulation listeners[edit]
Simulation listeners are pieces of custom code that are run during a simulation run. They can either be implemented in Java, or in a scripting language of your choise by adding the Simulation extension in User code -> Scripts.
In Java, the recommended way of implementing a simulation listener is by extending the AbstractSimulationListener
class and overriding the desired methods.
In scripts, you only need to implement the methods you need.
The methods, their arguments and return values are listed below. For scripting languages, replace with the corresponding object (for example in Ruby return nil
instead of null
). In many scripting languages, returning nothing or an undefined value will have the same effect as returning null
. The methods may also throw exceptions to abort the simulation.
Method signature | Description |
---|---|
void startSimulation(SimulationStatus status) |
Called when starting and ending a simulation. The endSimulation method is provided the exception if the simulation is aborted by one.
|
boolean preStep(SimulationStatus status) |
Called before and after taking a simulation step. The preStep method can prevent taking the step by returning false .
|
AccelerationData preAccelerationCalculation(SimulationStatus status) |
Called before and after computing acceleration of the |