Potential plugin structure
This commit is contained in:
parent
723539619c
commit
660a53ec28
16
core/src/net/sf/openrocket/gui/plugin/DoSomethingPlugin.java
Normal file
16
core/src/net/sf/openrocket/gui/plugin/DoSomethingPlugin.java
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
package net.sf.openrocket.gui.plugin;
|
||||||
|
|
||||||
|
import javax.swing.Action;
|
||||||
|
|
||||||
|
import net.sf.openrocket.document.OpenRocketDocument;
|
||||||
|
import net.sf.openrocket.gui.main.BasicFrame;
|
||||||
|
|
||||||
|
public class DoSomethingPlugin extends OpenRocketSwingMenuPlugin {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Action getAction(BasicFrame frame, OpenRocketDocument document) {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,22 @@
|
|||||||
|
package net.sf.openrocket.gui.plugin;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
import net.sf.openrocket.plugin.framework.Service;
|
||||||
|
|
||||||
|
public abstract class OpenRocketSwingMenuPlugin implements Service, SwingMenuPlugin {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String[] getMenuPosition() {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public <E> List<E> getPlugins(Class<E> type, Object... args) {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
40
core/src/net/sf/openrocket/gui/plugin/SwingMenuPlugin.java
Normal file
40
core/src/net/sf/openrocket/gui/plugin/SwingMenuPlugin.java
Normal file
@ -0,0 +1,40 @@
|
|||||||
|
package net.sf.openrocket.gui.plugin;
|
||||||
|
|
||||||
|
import javax.swing.Action;
|
||||||
|
|
||||||
|
import net.sf.openrocket.document.OpenRocketDocument;
|
||||||
|
import net.sf.openrocket.gui.main.BasicFrame;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A plugin that provides a menu item to the Swing GUI menus.
|
||||||
|
* This may open a dialog window or perform some other action on
|
||||||
|
* the current document.
|
||||||
|
* <p>
|
||||||
|
* During plugin discovery, the BasicFrame and OpenRocketDocument
|
||||||
|
* objects are passed to the plugin.
|
||||||
|
*
|
||||||
|
* @author Sampo Niskanen <sampo.niskanen@iki.fi>
|
||||||
|
*/
|
||||||
|
public interface SwingMenuPlugin {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Return the menu position where the action is placed.
|
||||||
|
* The first string in the array indicates the menu to place
|
||||||
|
* the item in, the second is the sub-menu, the third is the
|
||||||
|
* sub-sub-menu etc.
|
||||||
|
* <p>
|
||||||
|
* The strings are translated menu names.
|
||||||
|
*
|
||||||
|
* @return the menu position for the action
|
||||||
|
*/
|
||||||
|
public String[] getMenuPosition();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Return the Action that the menu item performs. This contains
|
||||||
|
* the menu item text and may contain an icon.
|
||||||
|
*
|
||||||
|
* @return the action to perform on the menu item.
|
||||||
|
*/
|
||||||
|
public Action getAction(BasicFrame frame, OpenRocketDocument document);
|
||||||
|
|
||||||
|
}
|
29
core/src/net/sf/openrocket/plugin/Configurable.java
Normal file
29
core/src/net/sf/openrocket/plugin/Configurable.java
Normal file
@ -0,0 +1,29 @@
|
|||||||
|
package net.sf.openrocket.plugin;
|
||||||
|
|
||||||
|
public interface Configurable {
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Return the plugin ID. This is a text string uniquely identifying this plugin.
|
||||||
|
* The recommended format is similar to the fully-qualified class name of the
|
||||||
|
* plugin, though a shorter format starting with the developer's domain name
|
||||||
|
* is also possible for future compatibility.
|
||||||
|
*
|
||||||
|
* @return the plugin ID
|
||||||
|
*/
|
||||||
|
public String getPluginID();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Test whether this plugin provides functionality corresponding to the specified
|
||||||
|
* plugin ID. This provides backwards compatibility if the plugin ID should change.
|
||||||
|
*
|
||||||
|
* @param pluginID the plugin ID to test
|
||||||
|
* @return whether this plugin provides the requested functionality
|
||||||
|
*/
|
||||||
|
public boolean isCompatible(String pluginID);
|
||||||
|
|
||||||
|
public void loadFromXML(Object... objects);
|
||||||
|
|
||||||
|
public void saveToXML(Object... objects);
|
||||||
|
|
||||||
|
}
|
@ -1,13 +0,0 @@
|
|||||||
package net.sf.openrocket.plugin;
|
|
||||||
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import net.xeoh.plugins.base.Plugin;
|
|
||||||
|
|
||||||
public interface Service extends Plugin {
|
|
||||||
|
|
||||||
|
|
||||||
public <E> List<E> getPlugins(Class<E> e, Object... args);
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
37
core/src/net/sf/openrocket/plugin/SwingConfigurator.java
Normal file
37
core/src/net/sf/openrocket/plugin/SwingConfigurator.java
Normal file
@ -0,0 +1,37 @@
|
|||||||
|
package net.sf.openrocket.plugin;
|
||||||
|
|
||||||
|
import java.awt.Component;
|
||||||
|
|
||||||
|
import net.xeoh.plugins.base.Plugin;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Interface that defined a Swing configurator for a plugin.
|
||||||
|
* The implemeting class should be a plugin that provides the
|
||||||
|
* capability "<pluginID>:config" where <pluginID> is the
|
||||||
|
* plugin ID of the plugin to configure.
|
||||||
|
* <p>
|
||||||
|
*
|
||||||
|
* @param <P> The plugin class that is being configured
|
||||||
|
* @author Sampo Niskanen <sampo.niskanen@iki.fi>
|
||||||
|
*/
|
||||||
|
public interface SwingConfigurator<P> extends Plugin {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Return whether this plugin is configurable or not.
|
||||||
|
*
|
||||||
|
* @param plugin the plugin to test.
|
||||||
|
* @return whether the plugin has a configuration component.
|
||||||
|
*/
|
||||||
|
public boolean isConfigurable(P plugin);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Return the configuration component for configuring the
|
||||||
|
* provided plugin.
|
||||||
|
*
|
||||||
|
* @param plugin the plugin to configure.
|
||||||
|
* @return a Swing component for configuring the plugin.
|
||||||
|
*/
|
||||||
|
public Component getConfigurationComponent(P plugin);
|
||||||
|
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,42 @@
|
|||||||
|
package net.sf.openrocket.plugin.example;
|
||||||
|
|
||||||
|
import java.awt.Component;
|
||||||
|
|
||||||
|
public class AirStartSimulationExtension extends OpenRocketSimulationListener {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getName() {
|
||||||
|
return "Air-start";
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String[] getMenuPosition() {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void loadFromXML(Object... objects) {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void saveToXML(Object... objects) {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isConfigurable() {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Component getConfigurationComponent() {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
}
|
@ -1,7 +1,7 @@
|
|||||||
package net.sf.openrocket.plugin.example;
|
package net.sf.openrocket.plugin.example;
|
||||||
|
|
||||||
import net.sf.openrocket.plugin.JSPFPluginFactory;
|
import net.sf.openrocket.plugin.framework.JSPFPluginFactory;
|
||||||
import net.sf.openrocket.plugin.PluginFactory;
|
import net.sf.openrocket.plugin.framework.PluginFactory;
|
||||||
|
|
||||||
public class ExampleMain {
|
public class ExampleMain {
|
||||||
|
|
||||||
|
@ -3,7 +3,7 @@ package net.sf.openrocket.plugin.example;
|
|||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import net.sf.openrocket.plugin.AbstractService;
|
import net.sf.openrocket.plugin.framework.AbstractService;
|
||||||
import net.xeoh.plugins.base.annotations.PluginImplementation;
|
import net.xeoh.plugins.base.annotations.PluginImplementation;
|
||||||
|
|
||||||
@PluginImplementation
|
@PluginImplementation
|
||||||
|
@ -0,0 +1,88 @@
|
|||||||
|
package net.sf.openrocket.plugin.example;
|
||||||
|
|
||||||
|
import java.awt.Component;
|
||||||
|
import java.util.Arrays;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
import net.sf.openrocket.plugin.Configurable;
|
||||||
|
import net.sf.openrocket.plugin.SwingConfigurator;
|
||||||
|
import net.sf.openrocket.plugin.framework.Service;
|
||||||
|
import net.sf.openrocket.simulation.listeners.AbstractSimulationListener;
|
||||||
|
import net.sf.openrocket.util.BugException;
|
||||||
|
import net.xeoh.plugins.base.Plugin;
|
||||||
|
import net.xeoh.plugins.base.annotations.Capabilities;
|
||||||
|
|
||||||
|
public abstract class OpenRocketSimulationListener extends AbstractSimulationListener
|
||||||
|
implements Plugin, Service, SwingConfigurator<OpenRocketSimulationListener>, Configurable {
|
||||||
|
|
||||||
|
private final String[] ids;
|
||||||
|
private final String[] capabilities;
|
||||||
|
|
||||||
|
public OpenRocketSimulationListener(String... ids) {
|
||||||
|
if (ids.length == 0) {
|
||||||
|
ids = new String[] { this.getClass().getCanonicalName() };
|
||||||
|
}
|
||||||
|
|
||||||
|
this.ids = ids.clone();
|
||||||
|
this.capabilities = new String[ids.length * 2];
|
||||||
|
for (int i = 0; i < ids.length; i++) {
|
||||||
|
capabilities[i * 2] = ids[i] + ":service";
|
||||||
|
capabilities[i * 2 + 1] = ids[i] + ":config";
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Capabilities
|
||||||
|
public String[] capabilities() {
|
||||||
|
return capabilities.clone();
|
||||||
|
}
|
||||||
|
|
||||||
|
@SuppressWarnings("unchecked")
|
||||||
|
@Override
|
||||||
|
public <E> List<E> getPlugins(Class<E> e, Object... args) {
|
||||||
|
if (e != this.getClass()) {
|
||||||
|
throw new BugException("Attempting to get plugin of type " + e + " but I am of type " + this.getClass());
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
return (List<E>) Arrays.asList(this.getClass().newInstance());
|
||||||
|
} catch (IllegalAccessException e1) {
|
||||||
|
throw new BugException("Could not instantiate new object of type " + this.getClass(), e1);
|
||||||
|
} catch (InstantiationException e2) {
|
||||||
|
throw new BugException("Could not instantiate new object of type " + this.getClass(), e2);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isConfigurable(OpenRocketSimulationListener plugin) {
|
||||||
|
return plugin.isConfigurable();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Component getConfigurationComponent(OpenRocketSimulationListener plugin) {
|
||||||
|
return plugin.getConfigurationComponent();
|
||||||
|
}
|
||||||
|
|
||||||
|
public abstract boolean isConfigurable();
|
||||||
|
|
||||||
|
public abstract Component getConfigurationComponent();
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getPluginID() {
|
||||||
|
return ids[0];
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isCompatible(String pluginID) {
|
||||||
|
for (String id : ids) {
|
||||||
|
if (pluginID.equals(id)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
}
|
135
core/src/net/sf/openrocket/plugin/example/stuff.txt
Normal file
135
core/src/net/sf/openrocket/plugin/example/stuff.txt
Normal file
@ -0,0 +1,135 @@
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
Plugin:
|
||||||
|
|
||||||
|
foo()
|
||||||
|
bar()
|
||||||
|
getValue()
|
||||||
|
setValue()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
Service:
|
||||||
|
|
||||||
|
getPlugins(args...)
|
||||||
|
capabilities() -> "pluginid:service"
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
SwingConfigurator:
|
||||||
|
|
||||||
|
getConfigurationComponent(plugin)
|
||||||
|
capabilities() -> "pluginid:config"
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
OpenRocketSimulationListener extends SimulationListener implements Service, SwingConfigurator:
|
||||||
|
|
||||||
|
|
||||||
|
constructor:
|
||||||
|
pluginid = class name
|
||||||
|
|
||||||
|
|
||||||
|
getPlugins():
|
||||||
|
return new this
|
||||||
|
|
||||||
|
capabilities: pluginid:service, pluginid:config
|
||||||
|
|
||||||
|
getConfigurationComponent(plugin)
|
||||||
|
plugin.getConfigurationComponent()
|
||||||
|
|
||||||
|
abstract getConfigurationComponent()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
Types of plugins:
|
||||||
|
|
||||||
|
|
||||||
|
AtmosphericModel
|
||||||
|
- Name -> dropdown
|
||||||
|
- Config component -> dialog window (or button)
|
||||||
|
- stateful, non-dynamic
|
||||||
|
- stored
|
||||||
|
|
||||||
|
|
||||||
|
SimulationListener
|
||||||
|
- Name + menu position -> Add extension menu
|
||||||
|
- Config component -> dialog after edit button
|
||||||
|
- stateful, (dynamic?)
|
||||||
|
- stored
|
||||||
|
|
||||||
|
|
||||||
|
OptimizationModifier
|
||||||
|
- contains its own name, description, related object
|
||||||
|
- config N/A
|
||||||
|
- stateful, dynamic
|
||||||
|
- not stored
|
||||||
|
|
||||||
|
|
||||||
|
OptimizationParameter
|
||||||
|
- name
|
||||||
|
- config N/A
|
||||||
|
- stateful, (dynamic?)
|
||||||
|
- not stored
|
||||||
|
|
||||||
|
|
||||||
|
PluginDialogWindow
|
||||||
|
- name + menu position -> Menu
|
||||||
|
- stateful, non-dynamic
|
||||||
|
- not stored
|
||||||
|
|
||||||
|
|
||||||
|
Motor
|
||||||
|
- Name -> Config tab
|
||||||
|
- Config component -> tab contents ????
|
||||||
|
- or a separate configuration interface?
|
||||||
|
- stored
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
Name is common - out, instead have name separately in plugin interfaces?
|
||||||
|
Menu position used twice - out
|
||||||
|
|
||||||
|
Leave common configuration out
|
||||||
|
-> :config supported by those that make sense
|
||||||
|
-> may have separate interface from SwingConfigurator (e.g. SwingMotorConfigurator)
|
||||||
|
|
||||||
|
Motor
|
||||||
|
-> :loader separately? for injecting placeholders
|
||||||
|
or store data and call loaders later
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
<extension pluginid="com.example.MyFancyExtension">
|
||||||
|
<param type="double" key="altitude">100.0</param>
|
||||||
|
<param type="material" key="mat">
|
||||||
|
<name>Gold</name>
|
||||||
|
<type>bulk</type>
|
||||||
|
<density>16000</density>
|
||||||
|
</param>
|
||||||
|
</extension>
|
||||||
|
|
||||||
|
|
||||||
|
<extension pluginid="com.example.MyFancyExtension">
|
||||||
|
<param type="double" key="altitude">100.0</param>
|
||||||
|
<param type="material" key="mat">
|
||||||
|
<name>Gold</name>
|
||||||
|
<type>bulk</type>
|
||||||
|
<density>16000</density>
|
||||||
|
</param>
|
||||||
|
</extension>
|
||||||
|
|
||||||
|
|
||||||
|
<extension pluginid="com.example.MyFancyExtension">
|
||||||
|
</extension>
|
||||||
|
|
||||||
|
|
||||||
|
<extension pluginid="com.example.MyFancyExtension">
|
||||||
|
</extension>
|
||||||
|
|
||||||
|
|
@ -1,4 +1,4 @@
|
|||||||
package net.sf.openrocket.plugin;
|
package net.sf.openrocket.plugin.framework;
|
||||||
|
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import java.util.List;
|
import java.util.List;
|
@ -1,4 +1,4 @@
|
|||||||
package net.sf.openrocket.plugin;
|
package net.sf.openrocket.plugin.framework;
|
||||||
|
|
||||||
import java.net.URI;
|
import java.net.URI;
|
||||||
import java.net.URISyntaxException;
|
import java.net.URISyntaxException;
|
@ -1,4 +1,4 @@
|
|||||||
package net.sf.openrocket.plugin;
|
package net.sf.openrocket.plugin.framework;
|
||||||
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
30
core/src/net/sf/openrocket/plugin/framework/Service.java
Normal file
30
core/src/net/sf/openrocket/plugin/framework/Service.java
Normal file
@ -0,0 +1,30 @@
|
|||||||
|
package net.sf.openrocket.plugin.framework;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
import net.xeoh.plugins.base.Plugin;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A discovery service that returns plugins of a specified type with
|
||||||
|
* provided arguments.
|
||||||
|
*
|
||||||
|
* @author Sampo Niskanen <sampo.niskanen@iki.fi>
|
||||||
|
*/
|
||||||
|
public interface Service extends Plugin {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Return the plugins that match the provided type and are applicable
|
||||||
|
* for the arguments. The arguments depend on the class type.
|
||||||
|
* <p>
|
||||||
|
* This method may return different plugins for different arguments.
|
||||||
|
* For example, if the arguments contain the OpenRocketDocument, the
|
||||||
|
* service may return only plugins applicable for the specified document.
|
||||||
|
*
|
||||||
|
* @param type the plugin interface type
|
||||||
|
* @param args arguments for the interface.
|
||||||
|
* @return the plugin instances applicable.
|
||||||
|
*/
|
||||||
|
public <E> List<E> getPlugins(Class<E> type, Object... args);
|
||||||
|
|
||||||
|
|
||||||
|
}
|
Loading…
x
Reference in New Issue
Block a user