Structs

A struct is an assembled object that contains variables, pointers, or further structs. Members of a struct are individually accessed using the struct name, followed by a '.' and the member name. Example:

typedef struct { 
  int x; 
  int y; 
  char* name;
} SPOT;  // defines a struct type named "SPOT"
...
SPOT myspot; // creates an uninitalized SPOT struct named "myspot"
SPOT* pspot; // creates an uninitalized pointer to a SPOT struct ... myspot.x = 10; myspot.name = "test!";

A struct can contain pointers to previously defined structs, and even pointers on itself, but no pointers to later defined structs:

typedef struct SPOT { 
  int x; 
  int y; 
  char* name;
  struct SPOT* next; // pointer to a SPOT struct
} SPOT;  // defines a struct type named "SPOT"

Unlike variables, structs can not be initialized when they are created. However global struct pointers can (to preserve backwards compatibility with C-Script). Example:

SPOT* myspot = { x = 1; y = 2; name = "my struct"; }  
// creates a new SPOT struct with initial values that is then referenced through the myspot pointer

 !!  Note that this initialization only works for global struct pointers, but not for local struct pointers that are defined within a function, and not for arrays. While you can define struct pointer arrays (like SPOT* pspots[100];), you can not initialize them in the definition. Within the struct initialization, any numbers, variables, character strings, or pointers to other structs can be used, but internal engine variables (such as "camera"), and #defines (such as a previously defined "NUMBER_OF_ARRAY_ELEMENTS") can not be used.

In standard C / C++, members of structs are accessed by a dot '.' and members of struct pointers are accessed by an arrow '->'. In lite-C or C-Script, the dot '.' can normally be used for both because the compiler automatically detects whether a simple object is a pointer or not. You only need to give the '->' in ambiguous cases, for instance when the struct pointer is a member of another struct pointer.

SPOT* myspot = { x = 1; y = 2; name = "my struct"; }
...
myspot->x = 1; // standard C/C++; works also in lite-c
myspot.y = 2;  // C-Script / lite-C 

Working with structs is explained in any C/C++ book, so we won't cover it here in detail. For creating structs or arrays of structs at run time, the standard C library functions malloc() and free() can be used. For initializing or copying structs, use the C library functions memset() and memcpy():

function foo()
{
  SPOT* myspot = malloc(sizeof(SPOT)); // creates a new SPOT struct at runtime
  memset(myspot,0,sizeof(SPOT)); // set the struct content to zero (it's undefined after malloc)
  myspot->x = 1;  
  SPOT* spot_array = malloc(100*sizeof(SPOT)); // creates an array of 100 SPOT structs
  memcpy(&spot_array[0],myspot,sizeof(SPOT));  // copy the myspot struct to the first member of the array
  ...
  free(myspot); // removes the created structs
  free(myspot_array);
}

 !!  There is plenty information about C, C++, or Windows library functions on the Internet or in online C courses. It is highly recommended for adcanced lite-C programming to work through such a course or book and learn about malloc, memcpy and all the other library functions that you can use.

Vectors

Besides the engine objects, there are also standard structs that can be used as parameter to functions: a VECTOR struct with x, y, z vars, an Euler ANGLE struct with pan, tilt, roll vars (see "coordinates"), and a COLOR struct with blue, green, red vars. They are also defined in include\atypes.h and used in many engine functions.

Structs themselves are not passed as arguments to or returned by functions, but struct pointers are. Lite-C automatically detects whether the argument is a pointer, and converts it to a pointer if not. Example:

function spot_init(SPOT* spot) 
{ 
  if (!spot) return; // prevent crash when an empty pointer is passed
  spot.x = 1; 
  spot.y = 1; 
}
...
SPOT myspot; // creates an uninitalized SPOT struct named "myspot"
...
spot_init(myspot); // passes a pointer to myspot

sizeof(struct)

The sizeof() macro that is used in the example above gives the size of a variable or a struct in bytes. This can be used to initialize structs through the zero macro that is defined in include\acknex.h:
#define zero(struct) memset((void*)&struct,0,sizeof(struct))
...
VECTOR speed;
zero(speed);	// initializes the VECTOR struct "speed" to zero

 !!  Arrays are internally treated as a pointer to a memory area. So, sizeof(any_array) always equals to 4 because that is the size of a pointer.

 !!  sizeof() is a macro and not a function. It can be used for setting a variable or passing a parameter to a function, but can not be used in expressions. Thus, long_size = sizeof(long); is ok, but long_size_times_ten = sizeof(long)*10; is not. This restriction does not apply to A7.7 or above.

See also:

Variables, pointers, functions,

► latest version online