docs
0
# CK (C-Kernels/Orientation Data)
1
2
Spacecraft and instrument attitude/pointing data management using C-kernels. CK files store time-ordered orientation information that describes how spacecraft, instruments, and reference frames are oriented in space, enabling precise pointing calculations for observations and navigation.
3
4
## Capabilities
5
6
### CK File Operations
7
8
Create, open, and manage CK files containing orientation data.
9
10
```python { .api }
11
def ckopn(fname: str, ifname: str, ncomch: int) -> int:
12
"""
13
Open new CK file for writing.
14
15
Parameters:
16
- fname: str, CK file name
17
- ifname: str, internal file name
18
- ncomch: int, number of comment characters
19
20
Returns:
21
int: file handle
22
"""
23
24
def ckcls(handle: int) -> None:
25
"""
26
Close CK file.
27
28
Parameters:
29
- handle: int, file handle
30
31
Returns:
32
None
33
"""
34
```
35
36
### Pointing Data Retrieval
37
38
Get spacecraft and instrument pointing information from CK files.
39
40
```python { .api }
41
def ckgp(inst: int, sclkdp: float, tol: float, ref: str) -> Tuple[ndarray, float, bool]:
42
"""
43
Get pointing (attitude matrix) from CK file.
44
45
Parameters:
46
- inst: int, instrument ID code
47
- sclkdp: float, spacecraft clock time
48
- tol: float, time tolerance
49
- ref: str, reference frame
50
51
Returns:
52
Tuple[ndarray, float, bool]: (c_matrix, clkout, found)
53
"""
54
55
def ckgpav(inst: int, sclkdp: float, tol: float, ref: str) -> Tuple[ndarray, ndarray, float, bool]:
56
"""
57
Get pointing and angular velocity from CK file.
58
59
Parameters:
60
- inst: int, instrument ID code
61
- sclkdp: float, spacecraft clock time
62
- tol: float, time tolerance
63
- ref: str, reference frame
64
65
Returns:
66
Tuple[ndarray, ndarray, float, bool]: (c_matrix, av, clkout, found)
67
"""
68
```
69
70
### Frame Transformations
71
72
Compute orientation transformations between reference frames.
73
74
```python { .api }
75
def ckfrot(inst: int, et: float) -> Tuple[ndarray, str, bool]:
76
"""
77
Get frame rotation from CK file using ET.
78
79
Parameters:
80
- inst: int, instrument ID code
81
- et: float, ephemeris time
82
83
Returns:
84
Tuple[ndarray, str, bool]: (rotate, ref, found)
85
"""
86
87
def ckfxfm(inst: int, et: float) -> Tuple[ndarray, str, bool]:
88
"""
89
Get frame transformation (6x6 state matrix) from CK file.
90
91
Parameters:
92
- inst: int, instrument ID code
93
- et: float, ephemeris time
94
95
Returns:
96
Tuple[ndarray, str, bool]: (xform, ref, found)
97
"""
98
```
99
100
### CK Data Writing
101
102
Write various types of CK segments for different attitude parameterizations.
103
104
```python { .api }
105
def ckw01(handle: int, begtim: float, endtim: float, inst: int, ref: str, avflag: bool, segid: str, nrec: int, sclkdp: ndarray, quats: ndarray, avvs: ndarray) -> None:
106
"""
107
Write Type 1 CK segment (discrete pointing).
108
109
Parameters:
110
- handle: int, file handle
111
- begtim: float, segment begin time
112
- endtim: float, segment end time
113
- inst: int, instrument ID
114
- ref: str, reference frame
115
- avflag: bool, angular velocity flag
116
- segid: str, segment identifier
117
- nrec: int, number of records
118
- sclkdp: ndarray, spacecraft clock times
119
- quats: ndarray, quaternions (4 x nrec)
120
- avvs: ndarray, angular velocities (3 x nrec)
121
122
Returns:
123
None
124
"""
125
126
def ckw02(handle: int, begtim: float, endtim: float, inst: int, ref: str, segid: str, nrec: int, start: ndarray, stop: ndarray, quats: ndarray, avvs: ndarray, rates: ndarray) -> None:
127
"""
128
Write Type 2 CK segment (linearly interpolated pointing).
129
130
Parameters:
131
- handle: int, file handle
132
- begtim: float, segment begin time
133
- endtim: float, segment end time
134
- inst: int, instrument ID
135
- ref: str, reference frame
136
- segid: str, segment identifier
137
- nrec: int, number of records
138
- start: ndarray, interval start times
139
- stop: ndarray, interval stop times
140
- quats: ndarray, quaternions
141
- avvs: ndarray, angular velocities
142
- rates: ndarray, angular acceleration
143
144
Returns:
145
None
146
"""
147
148
def ckw03(handle: int, begtim: float, endtim: float, inst: int, ref: str, avflag: bool, segid: str, nrec: int, sclkdp: ndarray, quats: ndarray, avvs: ndarray, nints: int, starts: ndarray) -> None:
149
"""
150
Write Type 3 CK segment (Chebyshev polynomials).
151
152
Parameters:
153
- handle: int, file handle
154
- begtim: float, segment begin time
155
- endtim: float, segment end time
156
- inst: int, instrument ID
157
- ref: str, reference frame
158
- avflag: bool, angular velocity flag
159
- segid: str, segment identifier
160
- nrec: int, number of records
161
- sclkdp: ndarray, spacecraft clock times
162
- quats: ndarray, quaternions
163
- avvs: ndarray, angular velocities
164
- nints: int, number of intervals
165
- starts: ndarray, interval start indices
166
167
Returns:
168
None
169
"""
170
171
def ckw05(handle: int, subtype: int, degree: int, begtim: float, endtim: float, inst: int, ref: str, avflag: bool, segid: str, n: int, sclkdp: ndarray, packts: ndarray, rate: float, nints: int, starts: ndarray) -> None:
172
"""
173
Write Type 5 CK segment (MEX/Rosetta format).
174
175
Parameters:
176
- handle: int, file handle
177
- subtype: int, subtype code
178
- degree: int, polynomial degree
179
- begtim: float, segment begin time
180
- endtim: float, segment end time
181
- inst: int, instrument ID
182
- ref: str, reference frame
183
- avflag: bool, angular velocity flag
184
- segid: str, segment identifier
185
- n: int, number of packets
186
- sclkdp: ndarray, spacecraft clock times
187
- packts: ndarray, data packets
188
- rate: float, nominal tick rate
189
- nints: int, number of intervals
190
- starts: ndarray, interval start indices
191
192
Returns:
193
None
194
"""
195
```
196
197
### CK Coverage Analysis
198
199
Analyze time coverage and data availability in CK files.
200
201
```python { .api }
202
def ckcov(ck: str, idcode: int, needav: bool, level: str, tol: float, timsys: str, cover: SpiceCell) -> None:
203
"""
204
Find time coverage windows for CK object.
205
206
Parameters:
207
- ck: str, CK file name
208
- idcode: int, instrument/spacecraft ID
209
- needav: bool, require angular velocity data
210
- level: str, coverage level ("SEGMENT" or "INTERVAL")
211
- tol: float, time tolerance
212
- timsys: str, time system ("SCLK" or "TDB")
213
- cover: SpiceCell, coverage window (modified)
214
215
Returns:
216
None (coverage window updated in place)
217
"""
218
219
def ckobj(ck: str) -> List[int]:
220
"""
221
Get object ID codes for all objects in CK file.
222
223
Parameters:
224
- ck: str, CK file name
225
226
Returns:
227
List[int]: object ID codes
228
"""
229
```
230
231
### Low-Level Profile Access
232
233
Access raw CK data at the segment level.
234
235
```python { .api }
236
def cklpf(fname: str) -> int:
237
"""
238
Load CK file, return handle.
239
240
Parameters:
241
- fname: str, CK file name
242
243
Returns:
244
int: file handle
245
"""
246
247
def ckupf(handle: int) -> None:
248
"""
249
Unload CK file.
250
251
Parameters:
252
- handle: int, file handle
253
254
Returns:
255
None
256
"""
257
```
258
259
### Segment Information
260
261
Query metadata and structure of CK segments.
262
263
```python { .api }
264
def cknr02(handle: int, descr: SpiceDLADescr) -> int:
265
"""
266
Get number of records in Type 2 CK segment.
267
268
Parameters:
269
- handle: int, CK file handle
270
- descr: SpiceDLADescr, segment descriptor
271
272
Returns:
273
int: number of records
274
"""
275
276
def cknr03(handle: int, descr: SpiceDLADescr) -> int:
277
"""
278
Get number of records in Type 3 CK segment.
279
280
Parameters:
281
- handle: int, CK file handle
282
- descr: SpiceDLADescr, segment descriptor
283
284
Returns:
285
int: number of records
286
"""
287
288
def ckgr02(handle: int, descr: SpiceDLADescr, recno: int) -> Tuple[float, float, ndarray, ndarray, float]:
289
"""
290
Get record from Type 2 CK segment.
291
292
Parameters:
293
- handle: int, CK file handle
294
- descr: SpiceDLADescr, segment descriptor
295
- recno: int, record number
296
297
Returns:
298
Tuple[float, float, ndarray, ndarray, float]: (start, stop, quat, av, rate)
299
"""
300
301
def ckgr03(handle: int, descr: SpiceDLADescr, recno: int) -> Tuple[float, ndarray, ndarray]:
302
"""
303
Get record from Type 3 CK segment.
304
305
Parameters:
306
- handle: int, CK file handle
307
- descr: SpiceDLADescr, segment descriptor
308
- recno: int, record number
309
310
Returns:
311
Tuple[float, ndarray, ndarray]: (sclkdp, quat, av)
312
"""
313
```
314
315
### CK Metadata
316
317
Get information about loaded CK files and instruments.
318
319
```python { .api }
320
def ckmeta(ckid: int, meta: str) -> Union[str, int]:
321
"""
322
Get metadata for CK instrument.
323
324
Parameters:
325
- ckid: int, CK instrument ID
326
- meta: str, metadata item ("SPK_ID", "FRAME_ID", "FRAME_NAME", etc.)
327
328
Returns:
329
Union[str, int]: metadata value
330
"""
331
```
332
333
## Common Usage Patterns
334
335
### Getting Spacecraft Attitude
336
```python
337
import spiceypy as spice
338
import numpy as np
339
340
# Load CK file and other kernels
341
spice.furnsh("spacecraft_attitude.bc")
342
spice.furnsh("spacecraft_sclk.tsc")
343
344
# Convert time to spacecraft clock
345
et = spice.str2et("2023-01-01T12:00:00")
346
spacecraft_id = -123
347
sclk = spice.sce2s(spacecraft_id, et)
348
349
# Get spacecraft pointing matrix
350
inst_id = -123000 # instrument ID
351
tolerance = 1.0 # 1 second tolerance
352
ref_frame = "J2000"
353
354
c_matrix, clkout, found = spice.ckgp(inst_id, sclk, tolerance, ref_frame)
355
356
if found:
357
print(f"Attitude matrix at SCLK {clkout}:")
358
print(c_matrix)
359
360
# Convert to Euler angles if needed
361
angles = spice.m2eul(c_matrix, 3, 1, 3) # Z-X-Z sequence
362
print(f"Euler angles (Z-X-Z): {np.degrees(angles)} degrees")
363
```
364
365
### Getting Attitude with Angular Velocity
366
```python
367
# Get both attitude and angular velocity
368
c_matrix, av, clkout, found = spice.ckgpav(inst_id, sclk, tolerance, ref_frame)
369
370
if found:
371
print(f"Attitude matrix:\n{c_matrix}")
372
print(f"Angular velocity: {av} rad/sec")
373
374
# Angular velocity magnitude
375
av_magnitude = spice.vnorm(av)
376
print(f"Angular velocity magnitude: {av_magnitude} rad/sec")
377
```
378
379
### Creating CK File
380
```python
381
import numpy as np
382
383
# Open new CK file
384
handle = spice.ckopn("spacecraft_attitude.bc", "Spacecraft Attitude Data", 0)
385
386
# Define attitude data
387
inst_id = -123000
388
ref_frame = "J2000"
389
segment_id = "Attitude Segment 1"
390
391
# Time range and data
392
begin_time = spice.str2et("2023-01-01T00:00:00")
393
end_time = spice.str2et("2023-01-02T00:00:00")
394
395
# Convert times to spacecraft clock
396
sclk_times = []
397
for i in range(24): # hourly data points
398
et = begin_time + i * 3600.0 # hours to seconds
399
sclk = spice.sce2s(spacecraft_id, et)
400
sclk_times.append(sclk)
401
402
sclk_array = np.array(sclk_times)
403
404
# Generate quaternions (example: slow rotation about Z-axis)
405
quaternions = []
406
angular_velocities = []
407
408
for i, sclk in enumerate(sclk_times):
409
# Rotation angle increases linearly with time
410
angle = 2 * np.pi * i / len(sclk_times) # one full rotation per day
411
412
# Quaternion for rotation about Z-axis
413
quat = np.array([
414
np.cos(angle/2), 0, 0, np.sin(angle/2) # [w, x, y, z]
415
])
416
quaternions.append(quat)
417
418
# Angular velocity (constant rotation about Z)
419
av = np.array([0, 0, 2*np.pi/(24*3600)]) # rad/sec
420
angular_velocities.append(av)
421
422
quats_array = np.array(quaternions).T # 4 x N
423
avs_array = np.array(angular_velocities).T # 3 x N
424
425
# Write Type 1 CK segment
426
spice.ckw01(
427
handle, begin_time, end_time, inst_id, ref_frame,
428
True, # include angular velocity
429
segment_id, len(sclk_times), sclk_array, quats_array, avs_array
430
)
431
432
# Close CK file
433
spice.ckcls(handle)
434
```
435
436
### Analyzing CK Coverage
437
```python
438
# Create time window for coverage analysis
439
coverage = spice.cell_double(1000)
440
441
# Find coverage for specific instrument
442
ck_file = "spacecraft_attitude.bc"
443
spice.ckcov(
444
ck_file,
445
inst_id,
446
False, # don't require angular velocity
447
"INTERVAL", # interval-level coverage
448
0.0, # no tolerance
449
"SCLK", # spacecraft clock time
450
coverage
451
)
452
453
# Display coverage intervals
454
num_intervals = spice.wncard(coverage)
455
print(f"Found {num_intervals} coverage intervals:")
456
457
for i in range(num_intervals):
458
start_sclk, stop_sclk = spice.wnfetd(coverage, i)
459
460
# Convert back to ET for display
461
start_et = spice.scs2e(spacecraft_id, start_sclk)
462
stop_et = spice.scs2e(spacecraft_id, stop_sclk)
463
464
start_utc = spice.et2utc(start_et, "C", 0)
465
stop_utc = spice.et2utc(stop_et, "C", 0)
466
467
print(f" Interval {i}: {start_utc} to {stop_utc}")
468
```
469
470
### Querying CK File Contents
471
```python
472
# Get all objects in CK file
473
object_ids = spice.ckobj("spacecraft_attitude.bc")
474
print(f"Objects in CK file: {object_ids}")
475
476
# Get metadata for each object
477
for obj_id in object_ids:
478
try:
479
frame_name = spice.ckmeta(obj_id, "FRAME_NAME")
480
frame_id = spice.ckmeta(obj_id, "FRAME_ID")
481
print(f"Object {obj_id}: Frame {frame_name} (ID {frame_id})")
482
except:
483
print(f"Object {obj_id}: Unable to retrieve metadata")
484
```