Java Propagator Parallelizer

I am also working on formation and RPO studies and would appreciate some assistance in using the PropagatorsParallelizer and MultiSatStepHandler but in Java. I followed the PropagatorConversion example using two single propagators and two step handlers. I saw the example given by Petrus Hyvonen on the MultiSatStepHandler but could use some help in setting this up in Java. Thanks.

First of all, beware that parallel propagation has some caveats: all propagators will run in separate threads, so we must configure them as independently as possible (not reusing objects from one propagator in another one) to avoid data corruption problems. There is a terse explanation in the class javadoc.

So the idea is that we first build all propagators as usual, but don’t set up any step handler for them (it would be overriden by the parallelizer) and don’t call their propagate method directly. We can use event detectors in each lindividual propagator, though. We put he propagators in a list, prepare a MutliStepHandler and build the parallelizer using the list and the global handler. Note that despite we were able to set up events at individual propagators level, we can’t set up global events that would depend on several propagators. It would be a nice feature to have, but up to now we have not found a proper way to implement it. We then call the propagate(start, target) method of the parallelizer. Calling this method will set up the synchronization logic, create the threads (one for each propagator) and launch the propagators in their dedicated thread. The parallelizer, which still runs in the original thread will monitor all propagators progression and call the MutliStepHandler according to this progression, until either target date is reached or one of the propagator stops (maybe due to an event). If one propagator stops, all the remaining propagators will be forcibly stopped too.

Here is a skeleton code that use a parallelizer to display the distance between two spacecrafts every minute, assuming we have a buildPropagator custom method to set up some propagator given an initial orbit:

  List<Propagator> propagators = new ArrayList<>();
  PropagatorParallelizer parallelizer = new PropagatorParallelizer(propagators, new DistancelHandler(60));
  parallelizer.propagate(start, end);

with a custom global handler

public class DistanceHandler implements MultiSatStepHandler {

    private final double displayStep;
    private AbsoluteDate next;

    public DistanceHandler(final double displayStep) {
      this.displayStep = displayStep;

    public void init(List<SpacecraftState> states0, final AbsoluteDate t) {
      // ensure that the first time handleStep is called, it will display something
      next = null;

    public void handleStep(List<OrekitStepInterpolator> interpolators, boolean isLast) {

       final OrekitStepInterpolator i0 = interpolators.get(0);
       final OrekitStepInterpolator i1 = interpolators.get(1);

       // we arbitrarily use the frame from first propagator to compute geometry
       final Frame frame = i0.getPreviousState().getFrame();

       if (next = null) {
         // this is the first time we are called
        next = i0.getPreviousState().getDate();

      // we check date only on interpolator 0 because we know all interpolators are already synchronized
      while (next.isBetweenOrEqualTo(i0.getPreviousState().getDate(),
                                     i0.getCurrentState().getDate())) {

        // we now know next is a date that is in the current common part of all interpolators,
       // so we can use this date to retrieve positions of all spacecrafts
        final Vector3D p0 = i0.getInterpolatedState(next).getPVCoordinates(frame).getPosition();
        final Vector3D p1 = i1.getInterpolatedState(next).getPVCoordinates(frame).getPosition();
        System.out.format(Locale.US, "%s %12.3f%n", next, Vector3D.distance(p0, p1));

       // prepare date of next display
        next = next.shiftedBy(i0.isForward() ? +displayStep : -displayStep);


Beware, I have just written this code snippet in the forum editor, I probably made some syntax errors, but you get the idea.

Thanks for the assistance with this. I have attached my code where I am running into an exception with the AbsoluteDate variable next. It is probably something simple that I am not seeing due to my rudimentary Java knowledge. Than you (9.3 KB)

You should replace

if (next.equals(null)) {...}


if (next == null) {...}

The equals method is used to check equality of the content of an existing instance with the content of another instance. It therefore works only if the instance you invoke it on (i.e. next here) does exist. Basically, next is a reference and you dereference it (or follow the pointer). Here, we don’ t want to compare contents, we want to check if there is an instance to start with (because we explicitly put null in the init method).

With your current code, as next is null on first call, you invoke the equals method of an inexistant instance, so you probably get a NullPointerException at that line.

Thank you. That did the trick. I missed that when I copied your previous code. I didn’t catch that the “next = null” should have been “next == null.” I have got some good answers now and will go onto to expand the code for my RPO analysis.

Hi luc,

First of all, I just started using Orekit and not sure asking in proper place. Sorry for these.

I have some questions about a basic logic of ‘MultiSatStepHandler’. I found it require interpolators in ‘handleStep’ method. I’m curious about the usage of interpolation. Is it used only for generating specific date or also for getting states? (or other usage…) I’m in problem with understanding ‘Stephandler’ I think. Thank you in advance.

The OrekitStepInterpolator objects will be provided by the various propagators managed by the parallelizer. These objects will each refer to one propagator and will contain the data associated with the step this specific propagator is currently handling. Prior to calling the handleStep method, the parallelizer already has synchronized all the propagators to cover compatible time ranges, and already has restricted the steps to the common range; this means when entering the handleStep method, all steps are guaranteed to be the same: calling getPreviousState().getDate() on any interpolator will return the same date and calling getCurrentState().getDate() on any interpolator will return the same date. The other data contained in the states (orbit, attitude, mass, additional states) will of course be different for each interpolator, so you could for example compute the distance between any two spacecrafts considered.

The interpolators can be used to navigate to any time between the previous and current states, they are valid throughout the step. The getInterpolatedState(date) method provided by the interpolator is vailable for this. This method returns a full-fledged state that contains orbit, attitude, mass, and additional states if you configured the propagator to manage them. So you can use it to retrieve data within the step, which may be desirable if the common time range selected by the parallelizer is too long for you and you want more fine grained data extraction. Beware that if you call getInterpolatedState(date) with a date that is outside of the covered range between previous and current, the interpolator will happily return data, but it may be inaccurate: the interpolators are good only within their range, or very slightly outside. So you need to check if you are within boundaries (the AbsoluteDate.isBetween method is your friend). Also take care that previous and current states correspond to propagation direction, so if you are performing a backward propagation, previous is later and current is earlier. There is a convenience method in the interpolator called isForward that you could use to set up your internal loops in the proper direction.