-
Notifications
You must be signed in to change notification settings - Fork 226
/
Copy pathOrbiterAPI.h
7527 lines (6825 loc) · 310 KB
/
OrbiterAPI.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
// Copyright (c) Martin Schweiger
// Licensed under the MIT License
// ======================================================================
// ORBITER SOFTWARE DEVELOPMENT KIT
// OrbiterAPI.h
// ORBITER Application Programming Interface (OAPI)
// ======================================================================
/**
* \file OrbiterAPI.h
* \brief General API interface functions
* \todo Check functions in VESSELSTATUS2::arot and oapiGetPlanetObliquityMatrix(),
* minus sign has changed a place in a matrix. Is this correct??
* \todo class CameraMode documentation
*/
#ifndef __ORBITERAPI_H
#define __ORBITERAPI_H
#if defined(_MSC_VER) && (_MSC_VER >= 1300 ) // Microsoft Visual Studio Version 2003 and higher
#if !defined(_CRT_SECURE_NO_DEPRECATE)
#define _CRT_SECURE_NO_DEPRECATE
#endif
#endif
#include <fstream>
#include <windows.h>
#include <float.h>
#include <math.h>
#include <vector>
extern "C" {
#include "Lua/lua.h"
}
// Assumes MS VC++ compiler. Modify these statements for other compilers
#define DLLEXPORT __declspec(dllexport)
#define DLLIMPORT __declspec(dllimport)
#define DLLCLBK extern "C" __declspec(dllexport)
#ifdef OAPI_IMPLEMENTATION
#define OAPIFUNC DLLEXPORT
#else
#define OAPIFUNC DLLIMPORT
#endif
#pragma warning(disable: 4201)
// Message loop return type - maintain backward compatibility for 32-bit
#ifdef _WIN64
#define OAPI_MSGTYPE LRESULT
#else
#define OAPI_MSGTYPE int
#endif
// ======================================================================
/// \defgroup constants Some useful general constants
// ======================================================================
//@{
const double PI = 3.14159265358979323846; ///< pi
const double PI05 = 1.57079632679489661923; ///< pi/2
const double PI2 = 6.28318530717958647693; ///< pi*2
const double RAD = PI/180.0; ///< factor to map degrees to radians
const double DEG = 180.0/PI; ///< factor to map radians to degrees
const double C0 = 299792458.0; ///< speed of light in vacuum [m/s]
const double TAUA = 499.004783806; ///< light time for 1 AU [s]
const double AU = C0*TAUA; ///< astronomical unit (mean geocentric distance of the sun) [m]
const double GGRAV = 6.67259e-11; ///< gravitational constant [m^3 kg^-1 s^-2]
const double G = 9.81; ///< gravitational acceleration [m/s^2] at Earth mean radius
const double ATMP = 101.4e3; ///< atmospheric pressure [Pa] at Earth sea level
const double ATMD = 1.293; ///< atmospheric density [kg/m^3] at Earth sea level
//@}
// ======================================================================
// Some general utility functions
// ======================================================================
/**
* \brief Returns the input argument normalised to range -pi ... pi
* \param angle input angle [rad]
* \return normalised angle [rad]
*/
inline double normangle (double angle)
{
double a = fmod (angle, PI2);
return (a >= PI ? a-PI2 : a < -PI ? a+PI2 : a);
}
/**
* \brief Returns the input argument normalised to range 0 ... 2 pi
* \param angle input angle [rad]
* \return normalised angle [rad]
*/
inline double posangle (double angle)
{
double a = fmod (angle, PI2);
return (a >= 0.0 ? a : a+PI2);
}
/**
* \brief Write a floating point value to a string
* \param cbuf character buffer
* \param n size of cbuf array
* \param f floating point value
* \param precision output precision
* \note Formats the string in the standard Orbiter convention,
* with 'k', 'M', 'G' postfixes as required
* \note cbuf must be allocated to sufficient size to hold the string
*/
OAPIFUNC void FormatValue (char *cbuf, int n, double f, int precision=4);
// ======================================================================
// API data types
// ======================================================================
class VESSEL;
class CELBODY;
class ExternMFD;
class Interpreter;
namespace oapi {
class Module;
class Sketchpad;
class Font;
class Pen;
class Brush;
union FVECTOR4;
}
// ======================================================================
/// \defgroup defines Defines and Enumerations
/// \defgroup structures Structure definitions
// ======================================================================
// ======================================================================
/// \ingroup defines
/// \defgroup handle Handles
// ======================================================================
//@{
/// \brief Handle for objects (vessels, stations, planets)
typedef void *OBJHANDLE;
/// \brief Handle for vessel superstructures
typedef void *SUPERVESSELHANDLE;
/// \brief Handle for visuals
typedef void *VISHANDLE;
/// \brief Handle for meshes
typedef void *MESHHANDLE;
/// \brief Handle for graphics-client-specific meshes
typedef int *DEVMESHHANDLE;
//struct DEVMESHHANDLE {
// DEVMESHHANDLE() { hMesh = NULL; }
// DEVMESHHANDLE(MESHHANDLE h) { hMesh = h; }
// DWORD id;
// MESHHANDLE hMesh;
// operator int() { return (int)hMesh; }
//};
/// \brief Handle for bitmap surfaces and textures (panels and panel items)
typedef void *SURFHANDLE;
/// \brief Handle for 2D instrument panels
typedef void *PANELHANDLE;
/// \brief Handle for file streams
typedef void *FILEHANDLE;
/// \brief Handle for script interpreters
typedef void *INTERPRETERHANDLE;
/// \brief Handle for thrusters
typedef void *THRUSTER_HANDLE;
/// \brief Handle for logical thruster groups
typedef void *THGROUP_HANDLE;
/// \brief Propellant resource handle
typedef void *PROPELLANT_HANDLE;
/// \brief Handle for particle streams
typedef void *PSTREAM_HANDLE;
/// \brief Handle for vessel docking ports
typedef void *DOCKHANDLE;
/// \brief Handle vor vessel passive attachment points
typedef void *ATTACHMENTHANDLE;
/// \brief Handle for vessel airfoils
typedef void *AIRFOILHANDLE;
/// \brief Handle for vessel aerodynamic control surfaces
typedef void *CTRLSURFHANDLE;
/// \brief Handle for a navigation radio transmitter (VOR, ILS, IDS, XPDR)
typedef void *NAVHANDLE;
/// \brief Handle for animation components
typedef void *ANIMATIONCOMPONENT_HANDLE;
/// \brief Handle for custom items added to Launchpad "Extra" list
typedef void *LAUNCHPADITEM_HANDLE;
/// \brief Handle for onscreen annotation objects
typedef void *NOTEHANDLE;
/// \brief Handle for elevation query managers
typedef void *ELEVHANDLE;
//@}
typedef enum { FILE_IN, FILE_OUT, FILE_APP, FILE_IN_ZEROONFAIL } FileAccessMode;
typedef enum { ROOT, CONFIG, SCENARIOS, TEXTURES, TEXTURES2, MESHES, MODULES } PathRoot;
/// \defgroup surfid Identifiers for special render surfaces
/// @{
#define RENDERTGT_NONE ((SURFHANDLE)-1) ///< no surface
#define RENDERTGT_MAINWINDOW 0 ///< main render target
/// @}
// ===========================================================================
/**
* \defgroup vec Vectors and matrices
* Vectors and matrices are used to represent positions, velocities, translations,
* rotations, etc. in the 3-dimensional object space. Orbiter provides the
* %VECTOR3 and %MATRIX3 structures for 3-D vectors and matrices. A number
* of utility functions allow common operations such as matrix-vector
* products, dot and vector products, etc.
*/
// ===========================================================================
//@{
/**
* \brief 3-element vector
*/
typedef union {
double data[3]; ///< array data interface
struct { double x, y, z; }; ///< named data interface
} VECTOR3;
/**
* \brief 4-element vector
*/
typedef union {
double data[4]; ///< array data interface
struct { double x, y, z, w; }; ///< named data interface
} VECTOR4;
/**
* \brief 3x3-element matrix
*/
typedef union {
double data[9]; ///< array data interface (row-sorted)
struct { double m11, m12, m13, m21, m22, m23, m31, m32, m33; }; ///< named data interface
} MATRIX3;
typedef union { // 4x4 matrix
double data[16];
struct { double m11, m12, m13, m14, m21, m22, m23, m24, m31, m32, m33, m34, m41, m42, m43, m44; };
} MATRIX4;
//@}
/**
* \ingroup structures
* \brief colour definition
*/
typedef struct {
float r; ///< read colour component [0..1]
float g; ///< green colour component [0..1]
float b; ///< blue colour component [0..1]
float a; ///< alpha (opacity) component (0..1)
} COLOUR4;
/**
* \ingroup structures
* \brief vertex definition including normals and texture coordinates
*/
typedef struct {
float x; ///< vertex x position
float y; ///< vertex y position
float z; ///< vertex z position
float nx; ///< vertex x normal
float ny; ///< vertex y normal
float nz; ///< vertex z normal
float tu; ///< vertex u texture coordinate
float tv; ///< vertex v texture coordinate
} NTVERTEX;
/**
* \ingroup structures
* \brief Defines a mesh group (subset of a mesh).
*
* A mesh group contains a vertex list, an index list,
* a material and texture index, and a set of flags.
*/
typedef struct {
NTVERTEX *Vtx; ///< vertex list
WORD *Idx; ///< index list
DWORD nVtx; ///< vertex count
DWORD nIdx; ///< index count
DWORD MtrlIdx; ///< material index (>= 1, 0=none)
DWORD TexIdx; ///< texture index (>= 1, 0=none)
DWORD UsrFlag; ///< user-defined flag
WORD zBias; ///< z bias
WORD Flags; ///< internal flags
} MESHGROUP;
const DWORD MAXTEX = 1; // max. extra textures per mesh group
/**
* \ingroup structures
* \brief extended mesh group definition
*/
typedef struct {
NTVERTEX *Vtx; ///< vertex list
WORD *Idx; ///< index list
DWORD nVtx; ///< vertex count
DWORD nIdx; ///< index count
DWORD MtrlIdx; ///< material index (>= 1, 0=none)
DWORD TexIdx; ///< texture index (>= 1, 0=none)
DWORD UsrFlag; ///< user-defined flag
WORD zBias; ///< z bias
WORD Flags; ///< internal flags
DWORD TexIdxEx[MAXTEX]; ///< additional texture indices
float TexMixEx[MAXTEX]; ///< texture mix values
} MESHGROUPEX;
/**
* \ingroup defines
* \defgroup surfacecaps Surface and texture attributes
* These bitflags are used during texture creation or loading to
* specify what they will be used for. This information is required
* by the graphics clients to initialise and optimise the surfaces
* accordingly.
* \sa oapiCreateSurfaceEx, oapiLoadSurfaceEx
*/
//@{
#define OAPISURFACE_TEXTURE 0x0001 ///< Surface can be used as a texture (e.g. by associating it with a mesh)
#define OAPISURFACE_RENDERTARGET 0x0002 ///< Surface can be rendered to by the graphics device
#define OAPISURFACE_GDI 0x0004 ///< A HDC context can be requested from the surface for GDI drawing
#define OAPISURFACE_SKETCHPAD 0x0008 ///< A Sketchpad context can be requested from the surface for Sketchpad drawing
#define OAPISURFACE_MIPMAPS 0x0010 ///< Create a full chain of mipmaps for the surface. If loaded from file, add any missing mipmap levels
#define OAPISURFACE_NOMIPMAPS 0x0020 ///< Don't create mipmaps. If loaded from file, ignore any mipmap levels present
#define OAPISURFACE_ALPHA 0x0040 ///< Create an alpha channel for the surface. If loaded from file, add an alpha channel if required
#define OAPISURFACE_NOALPHA 0x0080 ///< Don't create an alpha channel. If loaded from file, strip any existing alpha channel
#define OAPISURFACE_UNCOMPRESS 0x0100 ///< Create an uncompressed surface. If loaded from file, uncompress if required.
#define OAPISURFACE_SYSMEM 0x0200 ///< Create the surface in system (host) memory
#define OAPISURFACE_RENDER3D 0x0400 ///< Create a surface that can act as a target for rendering a 3D scene
#define OAPISURFACE_ANTIALIAS 0x0800 ///< Create a surface with anti-aliasing the level will depend on launchpad settings.
#define OAPISURFACE_SHARED 0x1000 ///< Create a shared resource
//@}
/**
* \ingroup defines
* \defgroup grpedit Mesh group editing flags
* These constants can be applied to the \e flags field of the
* \ref GROUPEDITSPEC structure to define which parts of a
* mesh group are to be modified.
* \note The GRPEDIT_SETUSERFLAG, GRPEDIT_ADDUSERFLAG and
* GRPEDIT_DELUSERFLAG flags are mutually exclusive. Only one
* can be used at a time.
* \sa GROUPEDITSPEC, oapiEditMeshGroup
*/
//@{
#define GRPEDIT_SETUSERFLAG 0x00001 ///< replace the group's UsrFlag entry with the value in the GROUPEDITSPEC structure.
#define GRPEDIT_ADDUSERFLAG 0x00002 ///< Add the UsrFlag value to the group's UsrFlag entry
#define GRPEDIT_DELUSERFLAG 0x00004 ///< Remove the UsrFlag value from the group's UsrFlag entry
#define GRPEDIT_VTXCRDX 0x00008 ///< Replace vertex x-coordinates
#define GRPEDIT_VTXCRDY 0x00010 ///< Replace vertex y-coordinates
#define GRPEDIT_VTXCRDZ 0x00020 ///< Replace vertex z-coordinates
#define GRPEDIT_VTXCRD (GRPEDIT_VTXCRDX | GRPEDIT_VTXCRDY | GRPEDIT_VTXCRDZ) ///< Replace vertex coordinates
#define GRPEDIT_VTXNMLX 0x00040 ///< Replace vertex x-normals
#define GRPEDIT_VTXNMLY 0x00080 ///< Replace vertex y-normals
#define GRPEDIT_VTXNMLZ 0x00100 ///< Replace vertex z-normals
#define GRPEDIT_VTXNML (GRPEDIT_VTXNMLX | GRPEDIT_VTXNMLY | GRPEDIT_VTXNMLZ) ///< Replace vertex normals
#define GRPEDIT_VTXTEXU 0x00200 ///< Replace vertex texture u-coordinates
#define GRPEDIT_VTXTEXV 0x00400 ///< Replace vertex texture v-coordinates
#define GRPEDIT_VTXTEX (GRPEDIT_VTXTEXU | GRPEDIT_VTXTEXV) ///< Replace vertex texture coordinates
#define GRPEDIT_VTX (GRPEDIT_VTXCRD | GRPEDIT_VTXNML | GRPEDIT_VTXTEX) ///< Replace vertices
#define GRPEDIT_VTXCRDADDX 0x00800 ///< Add to vertex x-coordinates
#define GRPEDIT_VTXCRDADDY 0x01000 ///< Add to vertex y-coordinates
#define GRPEDIT_VTXCRDADDZ 0x02000 ///< Add to vertex z-coordinates
#define GRPEDIT_VTXCRDADD (GRPEDIT_VTXCRDADDX | GRPEDIT_VTXCRDADDY | GRPEDIT_VTXCRDADDZ) ///< Add to vertex coordinates
#define GRPEDIT_VTXNMLADDX 0x04000 ///< Add to vertex x-normals
#define GRPEDIT_VTXNMLADDY 0x08000 ///< Add to vertex y-normals
#define GRPEDIT_VTXNMLADDZ 0x10000 ///< Add to vertex z-normals
#define GRPEDIT_VTXNMLADD (GRPEDIT_VTXNMLADDX | GRPEDIT_VTXNMLADDY | GRPEDIT_VTXNMLADDZ) ///< Add to vertex normals
#define GRPEDIT_VTXTEXADDU 0x20000 ///< Add to vertex texture u-coordinates
#define GRPEDIT_VTXTEXADDV 0x40000 ///< Add to vertex texture v-coordinates
#define GRPEDIT_VTXTEXADD (GRPEDIT_VTXTEXADDU | GRPEDIT_VTXTEXADDV) ///< Add to vertex texture coordinates
#define GRPEDIT_VTXADD (GRPEDIT_VTXCRDADD | GRPEDIT_VTXNMLADD | GRPEDIT_VTXTEXADD)
#define GRPEDIT_VTXMOD (GRPEDIT_VTX | GRPEDIT_VTXADD)
//@}
/**
* \ingroup structures
* \brief Structure used by \ref oapiEditMeshGroup to define the
* group elements to be replaced or modified.
* \note Only the group elements specified in the \e flags entry will
* be replaced or modified. The elements that are to remain unchanged
* can be left undefined in the GROUPEDITSPEC structure. For example,
* if only GRPEDIT_VTXCRDX is specified, only the 'x' fields in the
* Vtx array need to be assigned.
* \note to replace individual vertices in the group, the nVtx entry
* should contain the number of vertices to be replaced, the vIdx
* array should contain the indices (>= 0) of the vertices to be
* replaced, and Vtx should contain the new vertex values of those
* vertices. If vIdx==NULL, vertices are replaced in sequence from
* the beginning of the group's vertex list.
* nVtx must be less or equal the number of vertices in the group.
* \sa oapiEditMeshGroup, grpedit
*/
typedef struct {
DWORD flags; ///< flags (see \ref grpedit)
DWORD UsrFlag; ///< Replacement for group UsrFlag entry
NTVERTEX *Vtx; ///< Replacement for group vertices
DWORD nVtx; ///< Number of vertices to be replaced
WORD *vIdx; ///< Index list for vertices to be replaced
} GROUPEDITSPEC;
/**
* \ingroup structures
* \brief Structure used by \ref oapiGetMeshGroup containing data
* buffers to be filled with vertex and index data.
*/
typedef struct {
NTVERTEX *Vtx; ///< Vertex buffer
DWORD nVtx; ///< Number of vertices to return
WORD *VtxPerm; ///< Vertex permutation index list
WORD *Idx; ///< Triangle index buffer
DWORD nIdx; ///< Number of indices to return
WORD *IdxPerm; ///< Triangle permutation index list
DWORD MtrlIdx; ///< Material index
DWORD TexIdx; ///< Texture index
} GROUPREQUESTSPEC;
/**
* \ingroup structures
* \brief material definition
*/
typedef struct {
COLOUR4 diffuse; ///< diffuse component
COLOUR4 ambient; ///< ambient component
COLOUR4 specular; ///< specular component
COLOUR4 emissive; ///< emissive component
float power; ///< specular power
} MATERIAL;
enum MatProp {
Diffuse, ///< Material Diffuse color or Albedo depending on shader used. [.rgba]
Ambient, ///< Ambient color or Ambien occlusion [.rgb]
Specular, ///< Specular color [.rgb] power in [.a]
Light, ///< DX7 Style emission (color is added in light that lits the diffuse texture) (i.e. light map) [.rgb]
Emission, ///< Still in a development currently: output = max(diffuse*light, emission) [.rgb]
Reflect, ///< Reflectivity [.rgb]
Smooth, ///< Smoothness in [.r] (1 = smooth, 0 = rough)
Metal, ///< Meralness in [.r] (1 = metal, 0 = non-metal)
Fresnel, ///< Fresnel terms for fresnel effect. Used in older 2nd generation shader.
SpecialFX ///< Heat map effect control variable in [.r] (i.e. average part temperature)
};
/**
* \brief Kepler orbital elements
*
* A set of 6 scalar parameters defining the state of an object in a 2-body
* (Keplerian) orbit. The orbital trajectory is a conic section, either
* closed (circular, elliptic), or open (parabolic, hyperbolic).
* \note semi-major axis a is positive for closed orbits, and negative for
* open orbits (in that case, a is referred to as real semi-axis).
* \note eccentricity e:
* - circular orbit: e = 0
* - elliptic orbit: 0 < e < 1
* - parabolic orbit: e = 1
* - hyperbolic orbit: e > 1
* \note The a and e parameters define the shape of the orbit, the i, theta
* and omegab parameters define the orientation of the orbital plane in
* space, and the L parameter defines the object position along the
* trajectory at a given time.
* \note This is a generic data format. Additional data are required to
* fully define an object's state in space (position and velocity
* vectors). These include the position of the orbited body, the
* orientation of the reference coordinate system, and the date to which
* the mean longitude parameter refers.
* \sa ORBITPARAM, \subpage orbit
*/
typedef struct {
double a; ///< semi-major axis [m]
double e; ///< eccentricity
double i; ///< inclination [rad]
double theta; ///< longitude of ascending node [rad]
double omegab; ///< longitude of periapsis [rad]
double L; ///< mean longitude at epoch
} ELEMENTS;
/**
* \brief Secondary orbital parameters derived from the primary \ref ELEMENTS.
*
* This members of this structure provide additional parameters to the
* primary elements of contained in the ELEMENTS structure.
* \note SMi: for open orbits, this represents the imaginary semi-axis
* \note PeD: distance to lowest point of the orbit from focal point
* \note ApD: distance of highest point of the orbit from focal point. Only
* defined for closed orbits.
* \note T: orbit period only defined for closed orbits.
* \note PeT: For open orbits, this is negative after periapis passage
* \note ApT: Only defined for closed orbits.
* \sa ELEMENTS, \subpage orbit
*/
typedef struct {
double SMi; ///< semi-minor axis [m]
double PeD; ///< periapsis distance [m]
double ApD; ///< apoapsis distance [m]
double MnA; ///< mean anomaly [rad]
double TrA; ///< true anomaly [rad]
double MnL; ///< mean longitude [rad]
double TrL; ///< true longitude [rad]
double EcA; ///< eccentric anomaly [rad]
double Lec; ///< linear eccentricity [m]
double T; ///< orbit period [s]
double PeT; ///< time to next periapsis passage [s]
double ApT; ///< time to next apoapsis passage [s]
} ORBITPARAM;
/**
* \ingroup structures
* \brief Planetary atmospheric constants structure
*/
typedef struct {
double p0; ///< pressure at mean radius ('sea level') [Pa]
double rho0; ///< density at mean radius
double R; ///< specific gas constant [J/(K kg)]
double gamma; ///< ratio of specific heats, c_p/c_v
double C; ///< exponent for pressure equation (temporary)
double O2pp; ///< partial pressure of oxygen
double altlimit; ///< atmosphere altitude limit [m]
double radlimit; ///< radius limit (altlimit + mean radius)
double horizonalt; ///< horizon rendering altitude
VECTOR3 color0; ///< sky colour at sea level during daytime
} ATMCONST;
/** \brief Atmospheric parameters structure */
typedef struct {
double T; ///< temperature [K]
double p; ///< pressure [Pa]
double rho; ///< density [kg/m^3]
} ATMPARAM;
/** \brief Engine status */
typedef struct {
double main; ///< -1 (full retro) .. +1 (full main)
double hover; ///< 0 .. +1 (full hover)
int attmode; ///< 0=rotation, 1=translation
} ENGINESTATUS;
/**
* \ingroup defines
* \defgroup exhaustflag Bitflags for EXHAUSTSPEC flags field.
* \sa EXHAUSTSPEC
*/
//@{
#define EXHAUST_CONSTANTLEVEL 0x0001 ///< exhaust level is constant
#define EXHAUST_CONSTANTPOS 0x0002 ///< exhaust position is constant
#define EXHAUST_CONSTANTDIR 0x0004 ///< exhaust direction is constant
//@}
/**
* \brief Engine exhaust render parameters
* \sa VESSEL::AddExhaust(EXHAUSTSPEC*)
*/
typedef struct {
THRUSTER_HANDLE th;///< handle of associated thruster (or NULL if none)
double *level; ///< pointer to variable containing exhaust level (0..1)
VECTOR3 *lpos; ///< pointer to exhaust position vector [m]
VECTOR3 *ldir; ///< pointer to engine thrust direction (=negative exhaust direction)
double lsize; ///< exhaust length [m]
double wsize; ///< exhaust width [m]
double lofs; ///< longitudinal offset from engine [m]
double modulate; ///< magnitude of random intensity variations (0..1)
SURFHANDLE tex; ///< custom texture handle
DWORD flags; ///< Bit flags (see \ref exhaustflag)
UINT id; ///< reserved
} EXHAUSTSPEC;
/**
* \brief Particle stream parameters
* \note The following mapping methods (LEVELMAP) between stream
* level L and opacity a are supported:
* - LVL_FLAT: \f$ \alpha = \mathrm{const} \f$
* - LVL_LIN: \f$ \alpha = L \f$
* - LVL_SQRT: \f$ \alpha = \sqrt(L) \f$
* - LVL_PLIN: \f$ \alpha = \left\lbrace \begin{array}{ll}
0 & \mathrm{if} L < L_\mathrm{min} \\
\frac{L-L_\mathrm{min}}{L_\mathrm{max}-L_\mathrm{min}} & \mathrm{if} L_\mathrm{min} \leq L \leq L_\mathrm{max} \\
1 & \mathrm{if} L > L_\mathrm{max}
\end{array} \right. \f$
* - LVL_PSQRT: \f$ \alpha = \left\lbrace \begin{array}{ll}
0 & \mathrm{if} L < L_\mathrm{min} \\
\sqrt{\frac{L-L_\mathrm{min}}{L_\mathrm{max}-L_\mathrm{min}}} & \mathrm{if} L_\mathrm{min} \leq L \leq L_\mathrm{max} \\
1 & \mathrm{if} L > L_\mathrm{max}
\end{array} \right. \f$
*/
typedef struct {
DWORD flags; ///< streamspec bitflags
double srcsize; ///< particle size at creation [m]
double srcrate; ///< average particle creation rate [Hz]
double v0; ///< emission velocity [m/s]
double srcspread; ///< velocity spread during creation
double lifetime; ///< average particle lifetime [s]
double growthrate; ///< particle growth rate [m/s]
double atmslowdown;///< slowdown rate in atmosphere
/** \brief Particle lighting method */
enum LTYPE {
EMISSIVE, ///< emissive lighting (example: plasma stream)
DIFFUSE ///< diffuse lighting (example: vapour stream)
} ltype; ///< render lighting method
/** \brief Mapping from level to alpha value (particle opacity) */
enum LEVELMAP {
LVL_FLAT, ///< constant (alpha independent of level)
LVL_LIN, ///< linear mapping (alpha = level)
LVL_SQRT, ///< square root mapping (alpha = sqrt(level)
LVL_PLIN, ///< linear mapping in sub-range
LVL_PSQRT ///< square-root mapping in sub-range
} levelmap; ///< mapping from level to alpha
double lmin, lmax; ///< min and max levels for level PLIN and PSQRT mapping types
enum ATMSMAP { ATM_FLAT, ATM_PLIN, ATM_PLOG } atmsmap; ///< mapping from atmospheric params to alpha
double amin, amax; ///< min and max densities for atms PLIN mapping
SURFHANDLE tex; ///< particle texture handle (NULL for default)
} PARTICLESTREAMSPEC;
/**
* \defgroup locallight Local lighting interface
*
* The classes in this group define local light sources.
* \sa VESSEL3::AddPointLight, VESSEL3::AddSpotLight
*/
//@{
/**
* \brief Base class for defining a light source that can illuminate other objects.
*/
class OAPIFUNC LightEmitter {
public:
enum TYPE {
LT_NONE, LT_POINT, LT_SPOT, LT_DIRECTIONAL
};
enum VISIBILITY {
VIS_EXTERNAL=1, VIS_COCKPIT=2, VIS_ALWAYS=3
};
/**
* \brief Create a light source with default parameters.
* \note Creates a light source with white spectrum for diffuse, specular
* and emissive colour components.
* \note Intensity is set to 1, position (for point source objects) is set to (0,0,0)
* and direction (for spot and directional lights) is set to (0,0,1). To change
* these, use \ref SetPosition, \ref SetPositionRef, \ref SetDirection,
* \ref SetDirectionRef, \ref SetIntensity, \ref SetIntensityRef
*/
LightEmitter ();
/**
* \brief Create a light source with specific colour parameters.
* \param diffuse light source's contribution to lit objects' diffuse colour component
* \param specular light source's contribution to lit objects' specular colour component
* \param ambient light source's contribution to lit objects' ambient colour component
* \note Intensity is set to 1, position (for point source objects) is set to (0,0,0)
* and direction (for spot and directional lights) is set to (0,0,1). To change
* these, use \ref SetPosition, \ref SetPositionRef, \ref SetIntensity, \ref SetIntensityRef
*/
LightEmitter (COLOUR4 diffuse, COLOUR4 specular, COLOUR4 ambient);
/**
* \brief Returns the light source type.
*/
TYPE GetType() const { return ltype; }
/**
* \brief Returns the light visibility mode
* \return visibility mode
*/
VISIBILITY GetVisibility() const { return visibility; }
/**
* \brief Set the light visibility mode
* \param vis visibility mode
*/
void SetVisibility (VISIBILITY vis) { visibility = vis; }
const COLOUR4 &GetDiffuseColour() const { return col_diff; }
const COLOUR4 &GetSpecularColour() const { return col_spec; }
const COLOUR4 &GetAmbientColour() const { return col_ambi; }
/**
* \brief Activate or deactivate the light source
* \param act if \e true, activates the light source. Otherwise, deactivates
* the light source
* \sa IsActive
*/
void Activate (bool act);
/**
* \brief Returns activation status of light source
* \return \e true if source is active, \e false otherwise.
* \sa Activate
*/
bool IsActive () const;
/**
* \brief Set light source position.
* \param p new position [<b>m</b>] (in object or global coordinates)
* \note The source position is only relevant for point and spot lights. It is
* ignored for directional lights
* \note If the source is attached to an object (see \ref Attach) the position is
* interpreted in the local object coordinates. Otherwise, the position is
* taken to be in global coordinates.
* \note After a displacement of the vessel's centre of mass (see \ref VESSEL::ShiftCG),
* all light sources that define their position explicitly (via SetPosition) are
* updated automatically. Light sources with implicit position definition (via
* \ref SetPositionRef) must update their positions themselves.
* \sa GetPosition, SetPositionRef, GetPositionRef
*/
void SetPosition (const VECTOR3 &p);
/**
* \brief Returns the current source position.
* \return Current source position [<b>m</b>]
* \note The source position is only relevant for point and spot lights. It is
* ignored for directional lights
* \note If the source is attached to an object (see \ref Attach) the returned
* vector is the source position in local object coordinates. Otherwise, the
* returned vector is the global source position.
* \sa SetPosition, SetPositionRef, GetPositionRef
*/
inline VECTOR3 GetPosition () const { return *pos; }
/**
* \brief Set the reference pointer to the light source position.
* \param p pointer to vector defining the source position
* \note This method links the position of the light source to an externally
* defined vector. By modifying the vector elements, the light source can
* be re-positioned instantly.
* \note The vector variable pointed to by \a p must remain valid for the
* lifetime of the light source.
* \note The source position is only relevant for point and spot lights. It is
* ignored for directional lights
* \sa SetPosition, GetPosition, GetPositionRef
*/
void SetPositionRef (const VECTOR3 *p);
/**
* \brief Returns a pointer to the position reference variable.
* \return Pointer to the variable defining the light source position
* \note If the position is defined explicitly (see \ref SetPosition),
* this method simply returns a pointer to the lpos member variable.
* Otherwise, is returns the pointer specified in \ref SetPositionRef.
* \sa SetPosition, SetPositionRef, GetPosition
*/
const VECTOR3 *GetPositionRef () const;
/**
* \brief Adds an offset to the explicit position definition of the source.
* \param ofs offset vector in local vessel coordinates
* \note This method has only an effect for light sources whose positions are
* defined explicitly (via \ref SetPosition). If the source position is defined
* implicitly (via \ref SetPositionRef), this method has no effect. Modules that
* define their light source positions via implicit references must keep the
* positions up to date themselves (e.g. reacting to shifts in the centre of gravity).
* \sa SetPosition, SetPositionRef, VESSEL::ShiftCG
*/
void ShiftExplicitPosition (const VECTOR3 &ofs);
/**
* \brief Set light source direction.
* \param p new direction (in object or global coordinates)
* \note The vector argument should be normalised to length 1.
* \note The source direction is only relevant for spot and directional lights.
* It is ignored for point lights.
* \note If the source is attached to an object (see \ref Attach) the direction is
* interpreted in the local object coordinates. Otherwise, the direction is
* taken to be in global coordinates.
* \sa GetDirection, SetDirectionRef, GetDirectionRef
*/
void SetDirection (const VECTOR3 &d);
/**
* \brief Returns the current source direction.
* \return Current source direction.
* \note The source direction is only relevant for spot and directional lights.
* It is ignored for point lights.
* \note If the source is attached to an object (see \ref Attach) the returned
* vector is the source direction in local object coordinates. Otherwise, the
* returned vector is the global source direction.
* \sa SetDirection, SetDirectionRef, GetDirectionRef
*/
VECTOR3 GetDirection () const;
/**
* \brief Set the reference pointer to the light source direction.
* \param d pointer to vector defining the source direction
* \note This method links the direction of the light source to an externally
* defined vector. By modifying the vector elements, the light source can
* be re-directed instantly.
* \note The vector variable pointed to by \a d must remain valid for the
* lifetime of the light source.
* \note The source direction is only relevant for spot and directional lights.
* It is ignored for point lights
* \sa SetDirection, GetDirection, GetDirectionRef
*/
void SetDirectionRef (const VECTOR3 *d);
/**
* \brief Returns a pointer to the direction reference variable.
* \return Pointer to the variable defining the light source direction
* \note If the direction is defined explicitly (see \ref SetDirection),
* this method simply returns a pointer to the ldir member variable.
* Otherwise, is returns the pointer specified in \ref SetDirectionRef.
* \sa SetDirection, SetDirectionRef, GetDirection
*/
const VECTOR3 *GetDirectionRef () const;
/**
* \brief Returns the handle of the object the light source is attached to.
* \return Object handle, or NULL if not attached
*/
const OBJHANDLE GetObjectHandle () const { return hRef; }
void SetIntensity (double in);
double GetIntensity () const;
void SetIntensityRef (double *pin);
const double *GetIntensityRef () const;
protected:
OBJHANDLE Attach (OBJHANDLE hObj);
OBJHANDLE Detach ();
TYPE ltype;
VISIBILITY visibility;
OBJHANDLE hRef;
bool active;
COLOUR4 col_diff;
COLOUR4 col_spec;
COLOUR4 col_ambi;
const double *intens;
double lintens;
const VECTOR3 *pos;
const VECTOR3 *dir;
VECTOR3 lpos;
VECTOR3 ldir;
};
/**
* \brief Class for isotropic point light source
*/
class OAPIFUNC PointLight: public LightEmitter {
public:
/**
* \brief Creates a white isotropic point light.
* \param hObj handle of object the point light is attached to
* \param _pos light position in local object coordinates [<b>m</b>]
* \param _range point light range [m]
* \param att0 light attenuation parameters
* \param att1 light attenuation parameters
* \param att2 light attenuation parameters
*/
PointLight (OBJHANDLE hObj, const VECTOR3 &_pos, double _range, double att0, double att1, double att2);
/**
* \brief Creates a coloured isotropic point light.
* \param hObj handle of object the point light is attached to
* \param _pos point light position in local object coordinates [<b>m</b>]
* \param _range spotlight range [m]
* \param att0 light attenuation parameters
* \param att1 light attenuation parameters
* \param att2 light attenuation parameters
* \param diffuse light source's contribution to lit objects' diffuse colour component
* \param specular light source's contribution to lit objects' specular colour component
* \param ambient light source's contribution to lit objects' ambient colour component
*/
PointLight (OBJHANDLE hObj, const VECTOR3 &_pos, double _range, double att0, double att1, double att2, COLOUR4 diffuse, COLOUR4 specular, COLOUR4 ambient);
/**
* \brief Returns the light source range.
* \return Light source range [m]
*/
double GetRange() const { return range; }
/**
* \brief Set the light source range.
* \param _range new light source range [m]
* \note When changing the range, the attenuation factors usually should be adjusted
* accordingly, to avoid sharp cutoff edges or large areas of negligible intensity.
*/
void SetRange (double _range);
/**
* \brief Returns a pointer to attenuation coefficients.
* \return Pointer to array of 3 attenuation coefficients.
* \note The attenuation coefficients define the fractional light intensity I/I0 as
* a function of distance d:
* \f[ \frac{I}{I_0} = \frac{1}{\mathrm{att}_0 + d \mathrm{att}_1 + d^2 \mathrm{att}_2} \f]
*/
const double *GetAttenuation() const { return att; }
/**
* \brief Set the attenuation coefficients.
* \param att0 attenuation coefficient
* \param att1 attenuation coefficient
* \param att2 attenuation coefficient
* \note The attenuation coefficients define the fractional light intensity I/I0 as
* a function of distance d:
* \f[ \frac{I}{I_0} = \frac{1}{\mathrm{att}_0 + d \mathrm{att}_1 + d^2 \mathrm{att}_2} \f]
*/
void SetAttenuation (double att0, double att1, double att2);
protected:
double range;
double att[3];
};
/**
* \brief Class for directed spot light sources
*/
class OAPIFUNC SpotLight: public PointLight {
public:
/**
* \brief Creates a white spotlight.
* \param hObj handle of object the spotlight is attached to
* \param _pos spotlight position in local object coordinates [<b>m</b>]
* \param _dir spotlight direction in local object coordinates
* \param _range spotlight range [m]
* \param att0 light attenuation parameters
* \param att1 light attenuation parameters
* \param att2 light attenuation parameters
* \param _umbra angular aperture of inner (maximum intensity) cone [rad]
* \param _penumbra angular aperture of outer (zero intensity) cone [rad]
* \note Direction vector \a _dir must be normalised to length 1.
* \note 0 < _umbra <= penumbra <= pi is reqired.
* \note The intensity falloff between _umbra and _penumbra is linear from
* maximum intensity to zero.
*/
SpotLight (OBJHANDLE hObj, const VECTOR3 &_pos, const VECTOR3 &_dir, double _range, double att0, double att1, double att2, double _umbra, double _penumbra);
/**
* \brief Creates a coloured spotlight.
* \param hObj handle of object the spotlight is attached to
* \param _pos spotlight position in local object coordinates [<b>m</b>]
* \param _dir spotlight direction in local object coordinates
* \param _range spotlight range [m]
* \param att0 light attenuation parameters
* \param att1 light attenuation parameters
* \param att2 light attenuation parameters
* \param _umbra angular aperture of inner (maximum intensity) cone [rad]
* \param _penumbra angular aperture of outer (zero intensity) cone [rad]
* \param diffuse light source's contribution to lit objects' diffuse colour component
* \param specular light source's contribution to lit objects' specular colour component
* \param ambient light source's contribution to lit objects' ambient colour component
* \note Direction vector \a _dir must be normalised to length 1.
* \note 0 < _umbra <= penumbra <= pi is reqired.
* \note The intensity falloff between _umbra and _penumbra is linear from
* maximum intensity to zero.
*/
SpotLight (OBJHANDLE hObj, const VECTOR3 &_pos, const VECTOR3 &_dir, double _range, double att0, double att1, double att2, double _umbra, double _penumbra, COLOUR4 diffuse, COLOUR4 specular, COLOUR4 ambient);
/**
* \brief Returns the angular aperture of inner (maximum intensity) cone.
* \return Aperture of inner spotlight cone [rad]
* \sa GetPenumbra
*/
double GetUmbra() const { return umbra; }
/**
* \brief Returns the angular aperture of outer (zero intensity) cone.
* \return Aperture of outer spotlight cone [rad]
* \sa GetUmbra
*/
double GetPenumbra() const { return penumbra; }
/**
* \brief Set the spotlight cone geometry.
* \param _umbra angular aperture of inner (maximum intensity) cone [rad]
* \param _penumbra angular aperture of outer (zero intensity) cone [rad]
*/
void SetAperture (double _umbra, double _penumbra);
protected:
double umbra;
double penumbra;
};
//@}
/** \brief Navigation transmitter data
*
* This structure contains both general data (transmitter type, channel,
* output power and description string) and type-specific data.
* To query type-specific data, first check the transmitter type, for example