Jump to content

Community Helm Control Management API Discussion


Recommended Posts

We\'re beginning to run into problems where guidance computers are interfering with each other and throwing the ship into wild spirals (see: dodADA + MechJeb, Ascent Computer + MechJeb, etc).

So, I propose we come together to find a common way to communicate that a Part has the helm, so to speak. This would need to operate on a Vessel-by-Vessel basis. Anything I mention here is just an idea I\'m throwing out for feedback, none of this is set in stone. This would also probably be a third-party library that all participating parts would reference and use.

My idea would be to have a class named HelmManager or something with the following public members:

METHODS


  • [li]static boolean RequestHelm(Part yourPart) - Returns true and sets the part as the active helm handler if no other Parts are using the helm in the specified parent vessel (e.g. in Manual); also triggers HelmControlRequested event.[/li]
    [li]static void ReleaseHelm(Part yourPart) - Releases helm control, triggers HelmReleased event.[/li]
    [li]static void DemandHelm(Part yourPart) - Sets helm control to that part (should only be used if it\'s absolutely mission-critical, or on user input, such as pressing an on button). Triggers HelmControlDemanded event.[/li]

EVENTS (Listed as delegate method signatures)


  • [li]boolean HelmControlRequested(Part requestingPart, Part currentPart) - return false to deny access to helm (e.g. when an a descent computer is in the middle of landing)[/li]
    [li]void HelmControlReleased(Part releasingPart) - Might be used to re-request helm control for some parts.[/li]
    [li]void HelmControlDemanded(Part demandingPart) - A courtesy note sent when an AI mutiny occurs and results in a helm control change.[/li]

The sequence would be to RequestHelm when your part is 'turned on'. Then, when it\'s done, just ReleaseHelm. If another part wants access, you can either yield control (and turn off) or tell it to bugger off if you\'re in the middle of something important.

What are your ideas?

Link to comment
Share on other sites

I fully support this product and/or service.

EDIT:

A thought...

Such an API would be good to have with any plugin requesting the use of a key, as its perfectly possible that multiple plugins request the use of the same key.

Would be bad if pressing one key activates the self destruct, while you just wanted to extend the solar panels.

Link to comment
Share on other sites

I\'m happy to implement something like this in my ascent autopilot if it would be useful. I think in addition we need a method that will tell you which part has the helm, so that we can put an if(HelmManager.atHelm() == this) {} around our code that manipulates flight controls. Or is the idea that we just tell the HelmManager what our fly-by-wire function is and the HelmManager calls it each frame if we have the helm?

I confess I haven\'t really tried out any of the other guidance computers so I\'m not sure when these problems are occurring. Under what circumstances are people trying to use multiple guidance computers at once?

Link to comment
Share on other sites

Maybe step back a level and associate a set of key/value pairs with each Vessel that Parts could use to coordinate state (this is probably a good feature request for the KSP developers for future versions, but could be mocked up now).

Link to comment
Share on other sites

This is just a particular example of a much larger problem that KSP is ill-suited to handle (in its current state): event priorities.

It\'s difficult to predict all the different types of input that parts might handle. Autopilots? Stabilizers? Some in-between? What happens when more than one part demands the helm? What if a stabilizer and an auto-lander both consider themselves to be more important than the other, and thus nobody gets helm control? Your proposed setup essentially defers the problem to a later place in the code, but the fundamental problem is still there.

Perhaps a better way to solve this might be to stack modules when determining inputs. By default, there is always one entry: the player. Most plugins will probably want to give the player the last word, but some might act as stabilizers and 'soften' the player\'s input. This should be an option. An auto-lander will certainly want control, but some stabilizers might want to 'filter' its controls to soften the descent.

There\'s nothing we can do to prevent poorly-designed plugins from completely interfering with others, but you can at least establish a 'best practice' where each plugin is allowed to see the inputs of each plugin which came before it and adjust as necessary. Establish some categories where plugins can register themselves. Such a framework might even warn the user when multiple high-level autopilots are mounted on the ship.

Link to comment
Share on other sites

This is just a particular example of a much larger problem that KSP is ill-suited to handle (in its current state): event priorities.

It\'s difficult to predict all the different types of input that parts might handle. Autopilots? Stabilizers? Some in-between? What happens when more than one part demands the helm? What if a stabilizer and an auto-lander both consider themselves to be more important than the other, and thus nobody gets helm control? Your proposed setup essentially defers the problem to a later place in the code, but the fundamental problem is still there.

Perhaps a better way to solve this might be to stack modules when determining inputs. By default, there is always one entry: the player. Most plugins will probably want to give the player the last word, but some might act as stabilizers and 'soften' the player\'s input. This should be an option. An auto-lander will certainly want control, but some stabilizers might want to 'filter' its controls to soften the descent.

There\'s nothing we can do to prevent poorly-designed plugins from completely interfering with others, but you can at least establish a 'best practice' where each plugin is allowed to see the inputs of each plugin which came before it and adjust as necessary. Establish some categories where plugins can register themselves. Such a framework might even warn the user when multiple high-level autopilots are mounted on the ship.

http://en.wikipedia.org/wiki/Subsumption_architecture

Most of the autopilots currently in existance are reactive systems -- they follow very basic behaviors (in AI terms) based on various stimuli (user input and/or variables in the environment such as altitude, etc).

I might recommend a plugin which allows the user to define which behaviors subsume, or take priority, over the others. It would identify all plugin-enabled parts on the rocket, and the user would check-mark which ones are actually autopilots. Then they\'d assign each autopilot a priority number and -- through some form of witchcraft (or by dropping in an overload which redirects the ship control interface to the autopilot subsumption manager [???]) -- only permits calls from lower-priority autopilots if a higher-priority autopilot hasn\'t issued a command to the rocket for some user-defined period of time.

Link to comment
Share on other sites

You know, just a thought, but perhaps you could implement a menu system for your parts that all has enable/disable features to not interfere until we get something to assist with part collaboration?

My part currently works only on user input (pressing a button, but I hope to add a GUI which makes it easier to turn off/on in the next version), and the user always have the option of overriding the helm control (by turning it off). When off, dodADA shouldn\'t interfere with other autopilots at all (if it does then there\'s a bug in my code somewhere, or I\'ve misunderstood how the whole system works).

If other developers felt we needed to add a helm-control system, I would implement it in my plugins, but I don\'t see it as necessary for what my part is designed to do (control the helm, but only when the user asks it to).

Maybe this would become necessary for parts that are designed to fully-automate an entire mission, but at the moment that\'s not happening.

A discussion I think maybe we should have though, is about namespaces, as I\'m pretty sure I\'m not the only one who will write a class called \'FlightComputer\' :) (I\'ll be calling it \'dodFlightComputer\' in the next release).

Link to comment
Share on other sites

A discussion I think maybe we should have though, is about namespaces, as I\'m pretty sure I\'m not the only one who will write a class called \'FlightComputer\' :) (I\'ll be calling it \'dodFlightComputer\' in the next release).

You can do something like this:


// reference this class in your part.cfg
public class DodrianFlightComputerPartClass : Dodrian.FlightComputer { }

namespace Dodrian {
public class FlightComputer : global::Part {
// put your class code here
}

// put other namespace classes here
}

Link to comment
Share on other sites

In keeping with the finest Kerbal Engineering Practices, allowing three or five entirely different autopilots to vote (or perhaps argue) over the correct control inputs seems reasonable...

Only if the one determined to have priority overheats and explodes.

Link to comment
Share on other sites

There\'s nothing we can do to prevent poorly-designed plugins from completely interfering with others, but you can at least establish a 'best practice' where each plugin is allowed to see the inputs of each plugin which came before it and adjust as necessary. Establish some categories where plugins can register themselves. Such a framework might even warn the user when multiple high-level autopilots are mounted on the ship.

Something like the old TSR programs in DOS, and interrupt hooking? Seems like a good idea.

It would basically require a way to define the order of startup of the various plugins, and an interface to flight commands that is 'passed' (more or less literally) between them. Those who have delved into KSP internals have ideas about how to implement this?

In keeping with the finest Kerbal Engineering Practices, allowing three or five entirely different autopilots to vote (or perhaps argue) over the correct control inputs seems reasonable...

senzanomenl.png

Link to comment
Share on other sites

Something like the old TSR programs in DOS, and interrupt hooking? Seems like a good idea.

Or a more modern example of this pattern is Java\'s Servlet FilterChain:

tfessh-pic-1.gif

Or JavaScript\'s DOM event chain:

events_a.png

Each Flight Controller would implement an interface:


interface FlightController {
protected void handleEvent(Event e, FlightContollerChain chain);
}

Flight Controllers can then do whatever they need to do in handleEvent() and can optionally invoke FlightContollerChain.proceed(Event) to let downstream Flight Controllers have a chance to handle the event. E.g.:


public class SharingFlightController : FlightController {
protected void handleEvent(Event e, FlightContollerChain chain) {
Console.WriteLine('Before downstream FlightContollers are invoked: event=' + event);
chain.proceed(e);
Console.WriteLine('After downstream FlightControllers are invoked because I like to share');
}
}

public class SelfishFlightController : FlightController {
protected void handleEvent(Event e, EventChain chain) {
Console.WriteLine('Before downstream FlightContollers: event=' + event);
//chain.proceed(e);
Console.WriteLine('Downstream FlightControllers never invoked because I got this...');
}
}

The only trick is setting up the order of the Flight Controllers; do we let the user define/adjust the order?

Link to comment
Share on other sites

The only trick is setting up the order of the Flight Controllers; do we let the user define/adjust the order?

Well, I see two. Correct me if I\'m wrong.

Trick 1: what builds the chain of handlers? Seems like a meta-plugin would be required (that reads a list of names off its cfg?)

Trick 2: The chain nees to pass not just the event, but the command vectors calculated by the previous elements of the chain, and each handler should implement some sort of blending of its decisions with the previous ones. This isn\'t trivial, and it\'s a bit more complex than the way current autopilots work.

(I suppose the state vectors are available to everything directly)

Link to comment
Share on other sites

Great topic. Can I suggest, as best practice, that helm components start or initialise in the OFF position. This will prevent half a dozen components all turning themselves on at the same time (upon vessel load) and then who actually has the helm becomes blurred. Avoid the deadlock, start off, and let the pilot determine priorities.

Link to comment
Share on other sites

This thread is quite old. Please consider starting a new thread rather than reviving this one.

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...