The solution
interface describes the trajectory of a point or a rigid body. If the motion of only a point is being described, then the position and velocity of the point are provided at evenly-spaced time instants. If a rigid body is being described, then the orientation and angular velocity of the body are also included.
The following nodes consume or generate solution
streams:
You can run ...
sdgps generate-simple-trajectory --angular-velocity-enu '[0,0,1]' ! pretty-print
... to see an example of a rigid-body solution
stream. Note that the output of the pretty-print
node is not itself a valid solution stream (e.g. because newlines are inserted in the middle of packets to make them more readable). Use ...
sdgps generate-simple-trajectory --angular-velocity-enu '[0,0,1]' ! write-solution-file test.sol
... to generate a valid solution
stream file.
Help
JSON schema representations: Config | Packet
Format
The solution
interface representation consists of one or more newline-delimited JSON Objects. Unix-style line endings (\n
) are used.
The first line contains a header with the following keys:
Key | Type | Unit | Required | Description |
type | String | | Yes | Stream type and format version. Must be solution_v6 . |
sample_rate | Real | Hz | Yes | The rate of trajectory samples in the following stream |
metadata | Object | | No | Information about the program and command that were used to generate the file |
All subsequent lines contain packets, which are the trajectory sampled at a given time t = index / sample_rate
. The sample packets have the following keys:
Key | Type | Unit | Required | Description |
index | Integer | | Yes | Zero-based index of sample packet; must start at 0 and increment by 1 with every packet |
running | Boolean | | Yes | true if a solution is available |
running_reason | String | | Iff running is false | Reason that running is false
Example: "not enough SVs being tracked" |
time | String | seconds | Iff running is true | GPS Time
Example: "1813335305.770000000000000" |
position_ecef | 3-vector | meters | Iff running is true | Position of body origin in ECEF frame
Example: [ 740883.0, -5497747.0, 3136908.0 ] |
velocity_ecef | 3-vector | meters | Iff running is true | Velocity of body origin in ECEF frame |
orientation_ecef | quaternion | | Iff running is true and
this is a rigid-body stream | Quaternion that rotates body-frame vectors into ECEF frame
Example: {"w": -0.850, "x": -0.477, "y": -0.157, "z": 0.159} |
angular_velocity_body | 3-vector | radians/second | Iff running is true and
this is a rigid-body stream | Angular velocity of body frame with respect to ECEF frame, given in body frame
Example: [ 0.0, 0.0, 1.0 ] |
iff stands for if and only if.
Sample
The following was produced as the output of sdgps generate-simple-trajectory --duration 1 --rate inf --sample-rate 10 ! write-solution-file --no-metadata test.sol
:
{"sample_offset":0,"sample_rate":10,"type":"solution_v6"}
{"index":0,"running":true,"time":"1298764809.869604401089357952","position_ecef":[740883,-5497747,3136908],"velocity_ecef":[0,0,0],"orientation_ecef":{"w":0.8625646414485761,"x":0.5015007591183263,"y":0.033639382315581993,"z":0.057858619788739664},"angular_velocity_body":[0,0,0]}
{"index":1,"running":true,"time":"1298764809.969604401089357952","position_ecef":[740883,-5497747,3136908],"velocity_ecef":[0,0,0],"orientation_ecef":{"w":0.8625646414485761,"x":0.5015007591183263,"y":0.033639382315581993,"z":0.057858619788739664},"angular_velocity_body":[0,0,0]}
{"index":2,"running":true,"time":"1298764810.069604401089357952","position_ecef":[740883,-5497747,3136908],"velocity_ecef":[0,0,0],"orientation_ecef":{"w":0.8625646414485761,"x":0.5015007591183263,"y":0.033639382315581993,"z":0.057858619788739664},"angular_velocity_body":[0,0,0]}
{"index":3,"running":true,"time":"1298764810.169604401089357952","position_ecef":[740883,-5497747,3136908],"velocity_ecef":[0,0,0],"orientation_ecef":{"w":0.8625646414485761,"x":0.5015007591183263,"y":0.033639382315581993,"z":0.057858619788739664},"angular_velocity_body":[0,0,0]}
{"index":4,"running":true,"time":"1298764810.269604401089357952","position_ecef":[740883,-5497747,3136908],"velocity_ecef":[0,0,0],"orientation_ecef":{"w":0.8625646414485761,"x":0.5015007591183263,"y":0.033639382315581993,"z":0.057858619788739664},"angular_velocity_body":[0,0,0]}
{"index":5,"running":true,"time":"1298764810.369604401089357952","position_ecef":[740883,-5497747,3136908],"velocity_ecef":[0,0,0],"orientation_ecef":{"w":0.8625646414485761,"x":0.5015007591183263,"y":0.033639382315581993,"z":0.057858619788739664},"angular_velocity_body":[0,0,0]}
{"index":6,"running":true,"time":"1298764810.469604401089357952","position_ecef":[740883,-5497747,3136908],"velocity_ecef":[0,0,0],"orientation_ecef":{"w":0.8625646414485761,"x":0.5015007591183263,"y":0.033639382315581993,"z":0.057858619788739664},"angular_velocity_body":[0,0,0]}
{"index":7,"running":true,"time":"1298764810.569604401089357952","position_ecef":[740883,-5497747,3136908],"velocity_ecef":[0,0,0],"orientation_ecef":{"w":0.8625646414485761,"x":0.5015007591183263,"y":0.033639382315581993,"z":0.057858619788739664},"angular_velocity_body":[0,0,0]}
{"index":8,"running":true,"time":"1298764810.669604401089357952","position_ecef":[740883,-5497747,3136908],"velocity_ecef":[0,0,0],"orientation_ecef":{"w":0.8625646414485761,"x":0.5015007591183263,"y":0.033639382315581993,"z":0.057858619788739664},"angular_velocity_body":[0,0,0]}
{"index":9,"running":true,"time":"1298764810.769604401089357952","position_ecef":[740883,-5497747,3136908],"velocity_ecef":[0,0,0],"orientation_ecef":{"w":0.8625646414485761,"x":0.5015007591183263,"y":0.033639382315581993,"z":0.057858619788739664},"angular_velocity_body":[0,0,0]}
Sample (pretty-printed with an external tool)
This is the same data, but pretty-printed for ease of reading. Note that it SDGPS will not accept it due to the newlines present within the header and packets.
{
"sample_offset": 0,
"sample_rate": 10,
"type": "solution_v6"
}
{
"angular_velocity_body": [0, 0, 0],
"index": 0,
"orientation_ecef": {
"w": 0.8625646414485761,
"x": 0.5015007591183263,
"y": 0.033639382315581993,
"z": 0.057858619788739664
},
"position_ecef": [740883, -5497747, 3136908],
"running": true,
"time": "1298764809.869604401089357952",
"velocity_ecef": [0, 0, 0]
}
{
"angular_velocity_body": [0, 0, 0],
"index": 1,
"orientation_ecef": {
"w": 0.8625646414485761,
"x": 0.5015007591183263,
"y": 0.033639382315581993,
"z": 0.057858619788739664
},
"position_ecef": [740883, -5497747, 3136908],
"running": true,
"time": "1298764809.969604401089357952",
"velocity_ecef": [0, 0, 0]
}
{
"angular_velocity_body": [0, 0, 0],
"index": 2,
"orientation_ecef": {
"w": 0.8625646414485761,
"x": 0.5015007591183263,
"y": 0.033639382315581993,
"z": 0.057858619788739664
},
"position_ecef": [740883, -5497747, 3136908],
"running": true,
"time": "1298764810.069604401089357952",
"velocity_ecef": [0, 0, 0]
}
{
"angular_velocity_body": [0, 0, 0],
"index": 3,
"orientation_ecef": {
"w": 0.8625646414485761,
"x": 0.5015007591183263,
"y": 0.033639382315581993,
"z": 0.057858619788739664
},
"position_ecef": [740883, -5497747, 3136908],
"running": true,
"time": "1298764810.169604401089357952",
"velocity_ecef": [0, 0, 0]
}