Hello,
My team and I are trying to simulate two satellites pointing at each other through their orbits using the python wrapper, any ideas on how to get stared?
Thanks.
Hello,
My team and I are trying to simulate two satellites pointing at each other through their orbits using the python wrapper, any ideas on how to get stared?
Thanks.
Hi @jemeza
First, welcome to the Orekit forum !
To answer your question, I don’t think Orekit has an attitude model able to simulate two satellites pointing at each other.
Orekit has many attitude laws (i.e. Celestial body pointing, ground pointing, predefined attitude table, etc.) but not for what you want. Indeed, to common point between that attitude laws in Orekit is that the target is considered as fixed during the propagation time.
Therefore, you will have to implement your own attitude law. I am very far to be an expert of Python. However, if you want to add a new attitude model, you have to implement AttitudeProvider
interface.
Another problem is that the getAttitude()
methods only uses the dynamic coordinates of the propagated spacecraft. In other words, this methods cannot access the coordinates of the pointed spacecraft. Therefore, to access the coordinates of the pointed satellite, I think you have to initialize them at the construction of the attitude model. For instance, by using a List<TimeStampedPVCoordinates>
. The pointed satellite ephemeris can be easily computed using an analytical orbit propagator (TLEPropagator
or KeplerianPropagator
for instance).
Finally, for attitude computation, you can look at the already attitude models developed in Orekit to help you.
Kind regards,
Bryan
There is a workaround: you can use CelestialBodyPointed
, but there is a subtle trick in the setup. At construction, CelestialBodyPointed
needs a PVCoordinatesProvider
to point to the body (which in your case would not be a CelestialBody
but a regular spacecraft. Any Propagator
is also a PVCoordinatesProvider
so you may be tempted to do that (don’t do that, read further on):
Propagator p1 = new SomePropagatorYouWant(...config for spacecraft 1...);
Propagator p2 = new SomePropagatorYouWant(...config for spacecraft 2...);
AttitudeProvider doesntWork1 = new CelestialBodyPointed(eme2000,
p2,
Vector3D.PLUS_K,
Vector3D.PLUS_K,
Vector3D.MINUS_J));
p1.setAttitudeProvider(doesntWork1);
AttitudeProvider doesntWork2 = new CelestialBodyPointed(eme2000,
p1,
Vector3D.PLUS_K,
Vector3D.PLUS_K,
Vector3D.MINUS_J));
p2.setAttitudeProvider(doesntWork2);
p1.propagate(someDate); // <-- this will blow up with stack overflow due to infinite recursion
As explained in the comment in the snippet above, this setting would cause infinite recursion because propagator 1 calls its attitude provider, which calls propagator 2, which calls its own attitude provider, which calls propagator 1, which…
As in fact we only need a PVCoordinatesProvider
for building the CelestialBodyPointed
instances, we don’t really use the full state created by the Propagator
we embed into it. So the idea to break the infinite recursion is to use different propagators embedded in the CelestialBodyPointed
, and to have these propagators not manage the attitude (or rather just let them use their default basic attitude law) since the attitude part will in fact be ignored: the CelestialBodyPointed
just need to know where to look, it see its target as a point and don’t need to know how the body centered at this point is oriented.
In order to avoid lengthy computations, I would highly recommend to use analytical propagators to be embedded within the CelestialBodyPointed
instances, using numerical propagators would introduce big performance bottleneck. If you need your pointing to be accurate with many perturbations taken into account, then I would recommend doing this in several steps:
Propagator
and therefore also a PVCoordinatesProvider
CelestialBodyPointed
with ephemeris2 being used for propagator1If you really want highly accurate computation and your force model includes surface forces like solar radiation pressure or drag with a BoxAndSolarArraySpacecraft
, then you may need to run the previous steps twice, but I doubt this will change much the results. It would change things if surface force were so large that wrong orientation of spacecraft 1 would imply wrong forces and wrong trajectory, and therefore would imply wrong orientation of spacecraft 2. Such a loop would converge rather quickly. Suppose for example that wrong orientation in spacecraft 1 introduce a 10 meters position error during one iteration and the other spacecraft is very close, say 1 kilometer away only. Then the attitude error of the other spacecraft would be about 0.6°. Changing an attitude by 0.6° changes the surface forces very slightly so the next propagation for the second spacecraft would probably be much more accurate than 10 meters. You could do some experiments, but I am pretty sure you won’t really need to loop.
Hey @bcazabonne and @luc ,
Thank you so much for the help–I’m on the team with jemeza, and we’ve been trying to impliment the CelestialBodyPointed solution. Before this, we were trying to use TargetPointing by simply putting in the coordinate point of the second satellite and the same of the earth and then updating the law with every point, but the CelestialBodyPointed solution seems much better.
Question about your CelestialBodyPointed method: we definitely won’t be needing the numerical propagators for this project at the initial phase, but I’m getting an error when I simply define the law any both of these ways:
law = CelestialBodyPointed(p1) or law = CelestialBodyPointed(pv)
where pv is a PVCoordinate.
Might you be able to show how/what would be put into the constructor of the law to avoid the recursion? If it’s possible to adapt the script with the overflow error it would be incredibly helpful–we’re working on a Jupyter notebook tutorial for this, so we’d love to share it once we figure this out.
Thank you so much for the help!
Thank you for your feedback, we were able get it working!