C API#

The C API provides C level access to the same types and methods as the Python API to extend or embed PyEVSpace in your own Python extensions. PyEVSpace provides a capsule that can be imported which provides binary level access to the types and methods of the package. This makes the capsule more like an application binary interface, similar to Pythons own ABI. You only need to include the evspace_api.h header and import the capsule, and you will have C level access to PyEVSpace.

Note

All methods use the explicit types found in PyEVSpace, however they are all derived from PyObject and can therefore be cast to PyObject* if needed.

Types#

struct EVSpace_Vector#

C struct that defines the Python Vector type. A pointer of this type can be cast to or from a PyObject*.

typedef struct {
    PyObject_HEAD
    double *data;
} EVSpace_Vector;
double *EVSpace_Vector.data#

The internal data array for the vector. The memory is allocated in the EVSpace_Vector constructors to an array of length three. The values of the array of course are mutable, however caution should be used with resect to changing the actual pointer value. Setting the pointer to a new array is much more efficient than copying memory into it, however if the object is currently in use by a buffer object such as a memoryview, you may be unable to free the original data array without rendering any views of the object useless, causing a memory leak. If you must change the pointer value, be sure you have considered all upstream and downstream consequences of doing so.

Note

If you chose to change the value of the data pointer, you are responsible for also freeing the memory. If you do not you must be sure that any other resource with a reference to the memory will free it when it is no longer in use, or else this will result in a memory leak.

struct EVSpace_Matrix#

C struct that defines the Python Matrix type.

typedef struct {
    PyObject_HEAD
    double *data;
} EVSpace_Matrix;
double *EVSpace_Matrix.data#

The internal data array for the matrix. The memory is allocated in the EVSpace_Matrix constructors to a one-demensional array of length nine. The memory starts at index [0, 0] and increases by column first, then by row. The mapping from two-dimensional indices to one-dimension is \(3 * row + col\). The EVSpace_RC_INDEX macro can be used for cleanly mapping between dimensions.

The EVSpace_Matrix_COMP handles the mapping for you, when dealing with an EVSpace_Matrix instance.

The values of the array of course are mutable, however caution should be used with resect to changing the actual pointer value. Setting the pointer to a new array is much more efficient than copying memory into it, however if the object is currently in use by a buffer object such as a memoryview, you may be unable to free the original data array without rendering any views of the object useless, causing a memory leak. If you must change the pointer value, be sure you have considered all upstream and downstream consequences of doing so.

Note

If you chose to change the value of the data pointer, you are responsible for also freeing the memory. If you do not you must be sure that any other resource with a reference to the memory will free it when it is no longer in use, or else this will result in a memory leak.

struct EVSpace_Angles#

C struct that defines the Python Angles type.

typedef struct {
    PyObject_HEAD
    double alpha;
    double beta;
    double gamma;
} EVSpace_Angles;
double EVSpace_Angles.alpha#

The first angle of an Euler rotation, in radians.

double EVSpace_Angles.beta#

The second angle of an Euler rotation, in radians.

double EVSpace_Angles.gamma#

The third angle of an Euler rotation, in radians.

enum EVSpace_Axis#

An enumerated axis type to distinguish between axes, mostly used in describing Euler rotation orders.

typedef enum {
    X_AXIS = 0,
    Y_AXIS = 1,
    Z_AXIS = 2
} EVSpace_Axis;
enumerator EVSpace_Axis.X_AXIS#

Used to indicate the x-axis or an axis aliasing the x-axis in another named reference frame. Has a value of 0.

enumerator EVSpace_Axis.Y_AXIS#

Used to indicate the y-axis or an axis aliasing the y-axis in another named reference frame. Has a value of 1.

enumerator EVSpace_Axis.Z_AXIS#

Used to indicate the z-axis or an axis aliasing the z-axis in another named reference frame. Has a value of 2.

struct EVSpace_Order#

A type used to represent an Euler rotation, consisting of three axes, each indicated by an EVSpace_Axis.

typedef struct {
    PyObject_HEAD
    EVSpace_Axis first;
    EVSpace_Axis second;
    EVSpace_Axis third;
} EVSpace_Order;

There exist twelve unique Euler rotations, all of which are instantiated in the PyEVSpace capsule. As a result, you likely do not need to instantiate an EVSpace_Order object.

struct EVSpace_ReferenceFrame#

This C type is an idealized reference frame, which works by storing an internal matrix that describes a rotation from an intertial (unrotated) reference frame to this reference frame. The type also supports offset frames as well.

typedef struct {
    PyObject_HEAD
    EVSpace_Order* order;
    EVSpace_Angles* angles;
    EVSpace_Matrix* matrix;
    EVSpace_Vector* offset;
} EVSpace_ReferenceFrame;

Capsule#

struct EVSpace_CAPI

The full capsule documentation can be found here. A list of its contents follow:

Types#

PyTypeObject *EVSpace_CAPI.VectorType
PyTypeObject *EVSpace_CAPI.MatrixType
PyTypeObject *EVSpace_CAPI.AnglesType
PyTypeObject *EVSpace_CAPI.OrderType
PyTypeObject *EVSpace_CAPI.RefFrameType

Constructors#

EVSpace_Vector *EVSpace_CAPI.Vector_FromArray(double *array, PyTypeObject *type)
EVSpace_Vector *EVSpace_CAPI.Vector_StealArray(double *array, PyTypeObject *type)
EVSpace_Matrix *EVSpace_CAPI.Matrix_FromArray(double *array, PyTypeObject *type)
EVSpace_Matrix *EVSpace_CAPI.Matrix_StealArray(double *array, PyTypeObject *type)
EVSpace_Angles *EVSpace_CAPI.Angles_New(double alpha, double beta, double gamma, PyTypeObject *type)
EVSpace_Order *EVSpace_CAPI.Order_New(EVSpace_Axis first, EVSpace_Axis second, EVSpace_Axis third, PyTypeObject *type)
EVSpace_ReferenceFrame *EVSpace_CAPI.RefFrame_New(EVSpace_Order *order, EVSpace_Angles *angles, EVSpace_Vector *offset, PyTypeObject *type)

Vector numeric methods#

EVSpace_Vector *EVSpace_CAPI.Vector_add(const EVSpace_Vector *lhs, const EVSpace_Vector *rhs)
EVSpace_Vector *EVSpace_CAPI.Vector_subtract(const EVSpace_Vector *lhs, const EVSpace_Vector *rhs)
EVSpace_Vector *EVSpace_CAPI.Vector_multiply(const EVSpace_Vector *lhs, double scalar)
EVSpace_Vector *EVSpace_CAPI.Vector_multiply_m(const EVSpace_Vector *vector, const EVSpace_Matrix *matrix)
PyObject *EVSpace_CAPI.Vector_divide(const EVSpace_Vector *lhs, double scalar)
void EVSpace_CAPI.Vector_iadd(EVSpace_Vector *self, const EVSpace_Vector *other)
void EVSpace_CAPI.Vector_isubtract(EVSpace_Vector *self, const EVSpace_Vector *other)
void EVSpace_CAPI.Vector_imultiply(EVSpace_Vector *self, double scalar)
void EVSpace_CAPI.Vector_idivide(EVSpace_Vector *self, double scalar)
PyObject *EVSpace_CAPI.Vector_negative(const EVSpace_Vector *self)

Matrix numeric methods#

PyObject *EVSpace_CAPI.Matrix_add(const EVSpace_Matrix *lhs, const EVSpace_Matrix *rhs)
PyObject *EVSpace_CAPI.Matrix_subtract(const EVSpace_Matrix *lhs, const EVSpace_Matrix *rhs)
PyObject *EVSpace_CAPI.Matrix_multiply_v(const EVSpace_Matrix *matrix, const EVSpace_Vector *vector)
PyObject *EVSpace_CAPI.Matrix_multiply_m(const EVSpace_Matrix *lhs, const EVSpace_Matrix *rhs)
PyObject *EVSpace_CAPI.Matrix_multiply_s(const EVSpace_Matrix *self, double scalar)
PyObject *EVSpace_CAPI.Matrix_divide(const EVSpace_Matrix *lhs, double scalar)
void EVSpace_CAPI.Matrix_iadd(EVSpace_Matrix *self, const EVSpace_Matrix *other)
void EVSpace_CAPI.Matrix_isubtract(EVSpace_Matrix *self, const EVSpace_Matrix *other)
void EVSpace_CAPI.Matrix_imultiply(EVSpace_Matrix *self, double scalar)
PyObject *EVSpace_CAPI.Matrix_negative(const EVSpace_Matrix *matrix)

Vector instance methods#

double EVSpace_CAPI.Vector_mag(const EVSpace_Vector *vector)
double EVSpace_CAPI.Vector_mag2(const EVSpace_Vector *vector)
void EVSpace_CAPI.Vector_normalize(EVSpace_Vector *self)

Vector module methods#

double EVSpace_CAPI.Vector_dot(const EVSpace_Vector *lhs, const EVSpace_Vector *rhs)
EVSpace_Vector *EVSpace_CAPI.Vector_cross(const EVSpace_Vector *lhs, const EVSpace_Vector *rhs)
EVSpace_Vector *EVSpace_CAPI.Vector_norm(const EVSpace_Vector *vector)
double EVSpace_CAPI.Vector_vang(const EVSpace_Vector *from, const EVSpace_Vector *to)
EVSpace_Vector *EVSpace_CAPI.Vector_vxcl(const EVSpace_Vector *vector, const EVSpace_Vector *exclude)
EVSpace_Vector *EVSpace_CAPI.Vector_proj(const EVSpace_Vector *proj, const EVSpace_Vector *onto)

Matrix module methods#

double EVSpace_CAPI.Matrix_det(const EVSpace_Matrix *matrix)
EVSpace_Matrix *EVSpace_CAPI.Matrix_transpose(const EVSpace_Matrix *matrix)

Rotation order instances

const EVSpace_Order *Order_XYZ
const EVSpace_Order *Order_XZY
const EVSpace_Order *Order_YXZ
const EVSpace_Order *Order_YZX
const EVSpace_Order *Order_ZXY
const EVSpace_Order *Order_ZYX
const EVSpace_Order *Order_XYX
const EVSpace_Order *Order_XZX
const EVSpace_Order *Order_YXY
const EVSpace_Order *Order_YZY
const EVSpace_Order *Order_ZXZ
const EVSpace_Order *Order_ZYZ

Rotation matrix methods#

EVSpace_Matrix *EVSpace_CAPI.Get_matrix(EVSpace_Axis axis, double angle)
EVSpace_Matrix *EVSpace_CAPI.Get_euler(const EVSpace_Order *order, const EVSpace_Angles *angles)
EVSpace_Matrix *EVSpace_CAPI.Get_from_to(const EVSpace_Order *orderFrom, const EVSpace_Angles *anglesFrom, const EVSpace_Order *orderTo, const EVSpace_Angles *anglesTo)

Vector rotate methods#

EVSpace_Vector *EVSpace_CAPI.Rotate_axis_to(EVSpace_Axis axis, double angle, const EVSpace_Vector *vector)
EVSpace_Vector *EVSpace_CAPI.Rotate_axis_from(EVSpace_Axis axis, double angle, const EVSpace_Vector *vector)
EVSpace_Vector *EVSpace_CAPI.Rotate_euler_to(const EVSpace_Order *order, const EVSpace_Angles *angles, const EVSpace_Vector *vector)
EVSpace_Vector *EVSpace_CAPI.Rotate_euler_from(const EVSpace_Order *order, const EVSpace_Angles *angles, const EVSpace_Vector *vector)
EVSpace_Vector *EVSpace_CAPI.Rotate_matrix_to(const EVSpace_Matrix *matrix, const EVSpace_Vector *vector)
EVSpace_Vector *EVSpace_CAPI.Rotate_matrix_from(const EVSpace_Matrix *matrix, const EVSpace_Vector *vector)
EVSpace_Vector *EVSpace_CAPI.Rotate_offset_to(const EVSpace_Matrix *matrix, const EVSpace_Vector *offset, const EVSpace_Vector *vector)
EVSpace_Vector *EVSpace_CAPI.Rotate_offset_from(const EVSpace_Matrix *matrix, const EVSpace_Vector *offset, const EVSpace_Vector *vector)

Reference frame functions#

EVSpace_Vector *EVSpace_CAPI.Rotate_ref_to(const EVSpace_ReferenceFrame *frame, const EVSpace_Vector *vector)
EVSpace_Vector *EVSpace_CAPI.Rotate_ref_from(const EVSpace_ReferenceFrame *frame, const EVSpace_Vector *vector)
EVSpace_Vector *EVSpace_CAPI.Rotate_ref_to_ref(const EVSpace_ReferenceFrame *frame, const EVSpace_ReferenceFrame *to, const EVSpace_Vector *vector)
EVSpace_Vector *EVSpace_CAPI.Rotate_ref_from_ref(const EVSpace_ReferenceFrame *frame, const EVSpace_ReferenceFrame *from, const EVSpace_Vector *vector)

Macros#

EVSpace_VECTOR_X(obj)#

Simplifies accessing the X component of a vector by casting obj to an EVSpace_Vector* and calling the underlying array.

Parameters:
  • obj – a PyObject* or EVSpace_Vector* to get the X component of

EVSpace_VECTOR_Y(obj)#

Simplifies accessing the Y component of a vector by casting obj to an EVSpace_Vector* and calling the underlying array.

Parameters:
  • obj – a PyObject* or EVSpace_Vector* to get the Y component of

EVSpace_VECTOR_Z(obj)#

Simplifies accessing the Z component of a vector by casting obj to an EVSpace_Vector* and calling the underlying array.

Parameters:
  • obj – a PyObject* or EVSpace_Vector* to get the Z component of

EVSpace_RC_INDEX(row, col)#

Maps a row and column index to a single 1-dimensional contiguous array index. This is simply 3 * row + col, but looks much cleaner in code.

Parameters:
  • row – row index

  • col – col index

EVSpace_MATRIX_COMP(obj, row, col)#

Simplifies accessing a component of obj by casting to a EVSpace_Matrix* and calling the underlying array.

Parameters:
  • obj – a PyObject* or EVSpace_Vector* to get the component of

  • row – the row of the component to get

  • col – the column of the component to get

Vector_Check(obj)#

Checks if obj is an EVSpace_VectorType.

Parameters:
  • obj – a PyObject* to check the type of

Matrix_Check(obj)#

Checks if obj is an EVSpace_MatrixType.

Parameters:
  • obj – a PyObject* to check the type of

Angles_Check(obj)#

Checks if obj is an EVSpace_AnglesType.

Parameters:
  • obj – a PyObject* to check the type of

Order_Check(obj)#

Checks if obj is an EVSpace_OrderType.

Parameters:
  • obj – a PyObject* to check the type of

ReferenceFrame_Check(obj)#

Checks if obj is an EVSpace_ReferenceFrameType.

Parameters:
  • obj – a PyObject* to check the type of

The following macros are all for calls to capsule functions. They are of the form Evs_XXX, where XXX is the name of the capsule function. The Order instances do not follow this rule, for example the macro for Order_XYZ is just Evs_XYZ.

Constructors#

The constructor macros handle the type argument in the constructor call.

Evs_Vector_FromArray(array)#

Maps to EVSpace_CAPI.Vector_FromArray().

Evs_Vector_StealArray(array)#

Maps to EVSpace_CAPI.Vector_StealArray().

Evs_Matrix_FromArray(array)#

Maps to EVSpace_CAPI.Matrix_FromArray().

Evs_Matrix_StealArray(array)#

Maps to EVSpace_CAPI.Matrix_StealArray().

Evs_Angles_New(alpha, beta, gamma)#

Maps to EVSpace_CAPI.Angles_New().

Evs_Order_New(order, angles)#

Maps to EVSpace_CAPI.Order_New().

Evs_RefFrame_New(order, angles, offset)#

Maps to EVSpace_CAPI.RefFrame_New().

Vector number methods#

Evs_Vector_add(lhs, rhs)#

Maps to EVSpace_CAPI.Vector_add().

Evs_Vector_subtract(lhs, rhs)#

Maps to EVSpace_CAPI.Vector_subtract().

Evs_Vector_multiply(self, scalar)#

Maps to EVSpace_CAPI.Vector_multiply().

Evs_Vector_multiply_m(lhs, rhs)#

Maps to EVSpace_CAPI.Vector_multiply_m().

Evs_Vector_divide(self, scalar)#

Maps to EVSpace_CAPI.Vector_divide().

Evs_Vector_iadd(self, other)#

Maps to EVSpace_CAPI.Vector_iadd().

Evs_Vector_isubtract(self, other)#

Maps to EVSpace_CAPI.Vector_isubtract().

Evs_Vector_imultiply(self, scalar)#

Maps to EVSpace_CAPI.Vector_imultiply().

Evs_Vector_idivide(self, scalar)#

Maps to EVSpace_CAPI.Vector_idivide().

Evs_Vector_negative(self)#

Maps to EVSpace_CAPI.Vector_negative().

Matrix number methods#

Evs_Matrix_add(lhs, rhs)#

Maps to EVSpace_CAPI.Matrix_add().

Evs_Matrix_subtract(lhs, rhs)#

Maps to EVSpace_CAPI.Matrix_subtract().

Evs_Matrix_multiply_v(lhs, rhs)#

Maps to EVSpace_CAPI.Matrix_multiply_v().

Evs_Matrix_multiply_m(lhs, rhs)#

Maps to EVSpace_CAPI.Matrix_multiply_m().

Evs_Matrix_multiply_s(self, scalar)#

Maps to EVSpace_CAPI.Matrix_multiply_s().

Evs_Matrix_divide(lhs, rhs)#

Maps to EVSpace_CAPI.Matrix_divide().

Evs_Matrix_iadd(self, other)#

Maps to EVSpace_CAPI.Matrix_iadd().

Evs_Matrix_isubtract(self, other)#

Maps to EVSpace_CAPI.Matrix_isubtract().

Evs_Matrix_imultiply(self, scalar)#

Maps to EVSpace_CAPI.Matrix_imultiply().

Evs_Matrix_idivide(self, scalar)#

Maps to EVSpace_CAPI.Matrix_idivide().

Evs_Matrix_negative(self)#

Maps to EVSpace_CAPI.Matrix_negative().

Vector instance methods#

Evs_mag(self)#

Maps to EVSpace_CAPI.Vector_mag().

Evs_mag2(self)#

Maps to EVSpace_CAPI.Vector_mag2().

Evs_normalize(self)#

Maps to EVSpace_CAPI.Vector_normalize().

Vector functions#

Evs_dot(lhs, rhs)#

Maps to EVSpace_CAPI.Vector_dot().

Evs_cross(lhs, rhs)#

Maps to EVSpace_CAPI.Vector_cross().

Evs_norm(self)#

Maps to EVSpace_CAPI.Vector_norm().

Evs_vang(from, to)#

Maps to EVSpace_CAPI.Vector_vang().

Evs_vxcl(vec, xcl)#

Maps to EVSpace_CAPI.Vector_vxcl().

Evs_proj(proj, onto)#

Maps to EVSpace_CAPI.Vector_proj().

Matrix functions#

Evs_det(self)#

Maps to EVSpace_CAPI.Matrix_det().

Evs_transpose(self)#

Maps to EVSpace_CAPI.Matrix_transpose().

Rotation order instances#

Evs_XYZ#

Maps to EVSpace_CAPI.Order_XYZ.

Evs_XZY#

Maps to EVSpace_CAPI.Order_XZY.

Evs_YXZ#

Maps to EVSpace_CAPI.Order_YXZ.

Evs_YZX#

Maps to EVSpace_CAPI.Order_YZX.

Evs_ZXY#

Maps to EVSpace_CAPI.Order_ZXY.

Evs_ZYX#

Maps to EVSpace_CAPI.Order_ZYX.

Evs_XYX#

Maps to EVSpace_CAPI.Order_XYX.

Evs_XZX#

Maps to EVSpace_CAPI.Order_XZX.

Evs_YXY#

Maps to EVSpace_CAPI.Order_YXY.

Evs_YZY#

Maps to EVSpace_CAPI.Order_YZY.

Evs_ZXZ#

Maps to EVSpace_CAPI.Order_ZXZ.

Evs_ZYZ#

Maps to EVSpace_CAPI.Order_ZYZ.

Rotation matrix functions#

Evs_get_matrix(axis, angle)#

Maps to EVSpace_CAPI.Get_matrix().

Evs_get_euler(order, angles)#

Maps to EVSpace_CAPI.Get_euler().

Evs_from_to(orderFrom, anglesFrom, orderTo, anglesTo)#

Maps to EVSpace_CAPI.Get_from_to().

Rotate vector functions#

Evs_axis_to(axis, angle, vector)#

Maps to EVSpace_CAPI.Rotate_axis_to().

Evs_axis_from(axis, angle, vector)#

Maps to EVSpace_CAPI.Rotate_axis_from().

Evs_euler_to(order, angles, vector)#

Maps to EVSpace_CAPI.Rotate_euler_to().

Evs_euler_from(order, angles, vector)#

Maps to EVSpace_CAPI.Rotate_euler_from().

Evs_matrix_to(matrix, vector)#

Maps to EVSpace_CAPI.Rotate_matrix_to().

Evs_matrix_from(matrix, vector)#

Maps to EVSpace_CAPI.Rotate_matrix_from().

Evs_offset_to(matrix, offset, vector)#

Maps to EVSpace_CAPI.Rotate_offset_to().

Evs_offset_from(matrix, offset, vector)#

Maps to EVSpace_CAPI.Rotate_offset_from().

Reference frame functions#

Evs_ref_to(frame, vector)#

Maps to EVSpace_CAPI.Rotate_ref_to().

Evs_ref_from(frame, vector)#

Maps to EVSpace_CAPI.Rotate_ref_from().

Evs_ref_to_ref(self, frameTo, vector)#

Maps to EVSpace_CAPI.Rotate_ref_to_ref().

Evs_ref_from_ref(self, frameFrom, vector)#

Maps to EVSpace_CAPI.Rotate_ref_from_ref().