diff options
Diffstat (limited to 'extern/mantaflow/helper/pwrapper/pvec3.cpp')
-rw-r--r-- | extern/mantaflow/helper/pwrapper/pvec3.cpp | 414 |
1 files changed, 414 insertions, 0 deletions
diff --git a/extern/mantaflow/helper/pwrapper/pvec3.cpp b/extern/mantaflow/helper/pwrapper/pvec3.cpp new file mode 100644 index 00000000000..69bde2a2ad0 --- /dev/null +++ b/extern/mantaflow/helper/pwrapper/pvec3.cpp @@ -0,0 +1,414 @@ +/****************************************************************************** + * + * MantaFlow fluid solver framework + * Copyright 2011 Tobias Pfaff, Nils Thuerey + * + * This program is free software, distributed under the terms of the + * Apache License, Version 2.0 + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Vec3 class extension for python + * + ******************************************************************************/ + +#include "pythonInclude.h" +#include <string> +#include <sstream> +#include "vectorbase.h" +#include "structmember.h" +#include "manta.h" + +using namespace std; + +namespace Manta { + +extern PyTypeObject PbVec3Type; + +struct PbVec3 { + PyObject_HEAD float data[3]; +}; + +static void PbVec3Dealloc(PbVec3 *self) +{ + Py_TYPE(self)->tp_free((PyObject *)self); +} + +static PyObject *PbVec3New(PyTypeObject *type, PyObject *args, PyObject *kwds) +{ + return type->tp_alloc(type, 0); +} + +static int PbVec3Init(PbVec3 *self, PyObject *args, PyObject *kwds) +{ + + float x1 = numeric_limits<float>::quiet_NaN(), x2 = x1, x3 = x1; + if (!PyArg_ParseTuple(args, "|fff", &x1, &x2, &x3)) + return -1; + + if (!c_isnan(x1)) { + self->data[0] = x1; + if (!c_isnan(x2) && !c_isnan(x3)) { + self->data[1] = x2; + self->data[2] = x3; + } + else { + if (!c_isnan(x2) || !c_isnan(x3)) { + errMsg("Invalid partial init of vec3"); + } + self->data[1] = x1; + self->data[2] = x1; + } + } + else { + self->data[0] = 0; + self->data[1] = 0; + self->data[2] = 0; + } + return 0; +} + +static PyObject *PbVec3Repr(PbVec3 *self) +{ + Manta::Vec3 v(self->data[0], self->data[1], self->data[2]); + return PyUnicode_FromFormat(v.toString().c_str()); +} + +static PyMemberDef PbVec3Members[] = { + {(char *)"x", T_FLOAT, offsetof(PbVec3, data), 0, (char *)"X"}, + {(char *)"y", T_FLOAT, offsetof(PbVec3, data) + sizeof(float), 0, (char *)"Y"}, + {(char *)"z", T_FLOAT, offsetof(PbVec3, data) + sizeof(float) * 2, 0, (char *)"Z"}, + {NULL} // Sentinel +}; + +static PyMethodDef PbVec3Methods[] = { + //{"name", (PyCFunction)Noddy_name, METH_NOARGS, "Return the name, combining the first and last + //name" }, + {NULL} // Sentinel +}; + +// operator overloads + +inline PyObject *PbNew(const Vec3 &a) +{ + PbVec3 *obj = (PbVec3 *)PbVec3New(&PbVec3Type, 0, 0); + obj->data[0] = a.x; + obj->data[1] = a.y; + obj->data[2] = a.z; + return (PyObject *)obj; +} + +#define CONVERTVEC(obj) \ + Vec3 v##obj; \ + if (PyObject_TypeCheck(obj, &PbVec3Type)) \ + v##obj = Vec3(&(((PbVec3 *)obj)->data[0])); \ + else if (PyFloat_Check(obj)) \ + v##obj = Vec3(PyFloat_AsDouble(obj)); \ + else if (PyLong_Check(obj)) \ + v##obj = Vec3(PyLong_AsDouble(obj)); \ + else { \ + Py_INCREF(Py_NotImplemented); \ + return Py_NotImplemented; \ + } + +#define OPHEADER \ + if (!PyObject_TypeCheck(a, &PbVec3Type) && !PyObject_TypeCheck(b, &PbVec3Type)) { \ + Py_INCREF(Py_NotImplemented); \ + return Py_NotImplemented; \ + } \ + CONVERTVEC(a) \ + CONVERTVEC(b) + +#define OPHEADER1 \ + if (!PyObject_TypeCheck(a, &PbVec3Type)) { \ + Py_INCREF(Py_NotImplemented); \ + return Py_NotImplemented; \ + } \ + CONVERTVEC(a) + +PyObject *PbVec3Add(PyObject *a, PyObject *b) +{ + OPHEADER + return PbNew(va + vb); +} + +PyObject *PbVec3Sub(PyObject *a, PyObject *b) +{ + OPHEADER + return PbNew(va - vb); +} + +PyObject *PbVec3Mult(PyObject *a, PyObject *b) +{ + OPHEADER + return PbNew(va * vb); +} + +PyObject *PbVec3Div(PyObject *a, PyObject *b) +{ + OPHEADER + return PbNew(va / vb); +} + +PyObject *PbVec3Negative(PyObject *a) +{ + OPHEADER1 + return PbNew(-va); +} + +// numbers are defined subtely different in Py3 (WTF?) +#if PY_MAJOR_VERSION >= 3 +static PyNumberMethods PbVec3NumberMethods = { + (binaryfunc)PbVec3Add, // binaryfunc nb_add; + (binaryfunc)PbVec3Sub, // binaryfunc nb_sub; + (binaryfunc)PbVec3Mult, // binaryfunc nb_mult; + 0, // binaryfunc nb_remainder; + 0, // binaryfunc nb_divmod; + 0, // ternaryfunc nb_power; + (unaryfunc)PbVec3Negative, // unaryfunc nb_negative; + 0, // unaryfunc nb_positive; + 0, // unaryfunc nb_absolute; + 0, // inquiry nb_bool; + 0, // unaryfunc nb_invert; + 0, // binaryfunc nb_lshift; + 0, // binaryfunc nb_rshift; + 0, // binaryfunc nb_and; + 0, // binaryfunc nb_xor; + 0, // binaryfunc nb_or; + 0, // unaryfunc nb_int; + 0, // void *nb_reserved; + 0, // unaryfunc nb_float; + 0, // binaryfunc nb_inplace_add; + 0, // binaryfunc nb_inplace_subtract; + 0, // binaryfunc nb_inplace_multiply; + 0, // binaryfunc nb_inplace_remainder; + 0, // ternaryfunc nb_inplace_power; + 0, // binaryfunc nb_inplace_lshift; + 0, // binaryfunc nb_inplace_rshift; + 0, // binaryfunc nb_inplace_and; + 0, // binaryfunc nb_inplace_xor; + 0, // binaryfunc nb_inplace_or; + + 0, // binaryfunc nb_floor_divide; + (binaryfunc)PbVec3Div, // binaryfunc nb_true_divide; + 0, // binaryfunc nb_inplace_floor_divide; + 0, // binaryfunc nb_inplace_true_divide; + + 0 // unaryfunc nb_index; +}; +#else +static PyNumberMethods PbVec3NumberMethods = { + (binaryfunc)PbVec3Add, // binaryfunc nb_add; + (binaryfunc)PbVec3Sub, // binaryfunc nb_sub; + (binaryfunc)PbVec3Mult, // binaryfunc nb_mult; + 0, // binaryfunc nb_divide; + 0, // binaryfunc nb_remainder; + 0, // binaryfunc nb_divmod; + 0, // ternaryfunc nb_power; + (unaryfunc)PbVec3Negative, // unaryfunc nb_negative; + 0, // unaryfunc nb_positive; + 0, // unaryfunc nb_absolute; + 0, // inquiry nb_nonzero; + 0, // unaryfunc nb_invert; + 0, // binaryfunc nb_lshift; + 0, // binaryfunc nb_rshift; + 0, // binaryfunc nb_and; + 0, // binaryfunc nb_xor; + 0, // binaryfunc nb_or; + 0, // coercion nb_coerce; + 0, // unaryfunc nb_int; + 0, // unaryfunc nb_long; + 0, // unaryfunc nb_float; + 0, // unaryfunc nb_oct; + 0, // unaryfunc nb_hex; + 0, // binaryfunc nb_inplace_add; + 0, // binaryfunc nb_inplace_subtract; + 0, // binaryfunc nb_inplace_multiply; + 0, // binaryfunc nb_inplace_divide; + 0, // binaryfunc nb_inplace_remainder; + 0, // ternaryfunc nb_inplace_power; + 0, // binaryfunc nb_inplace_lshift; + 0, // binaryfunc nb_inplace_rshift; + 0, // binaryfunc nb_inplace_and; + 0, // binaryfunc nb_inplace_xor; + 0, // binaryfunc nb_inplace_or; + 0, // binaryfunc nb_floor_divide; + (binaryfunc)PbVec3Div, // binaryfunc nb_true_divide; + 0, // binaryfunc nb_inplace_floor_divide; + 0, // binaryfunc nb_inplace_true_divide; + 0, // unaryfunc nb_index; +}; +#endif + +PyTypeObject PbVec3Type = { + PyVarObject_HEAD_INIT(NULL, 0) "manta.vec3", /* tp_name */ + sizeof(PbVec3), /* tp_basicsize */ + 0, /* tp_itemsize */ + (destructor)PbVec3Dealloc, /* tp_dealloc */ + 0, /* tp_print */ + 0, /* tp_getattr */ + 0, /* tp_setattr */ + 0, /* tp_reserved */ + (reprfunc)PbVec3Repr, /* tp_repr */ + &PbVec3NumberMethods, /* tp_as_number */ + 0, /* tp_as_sequence */ + 0, /* tp_as_mapping */ + 0, /* tp_hash */ + 0, /* tp_call */ + 0, /* tp_str */ + 0, /* tp_getattro */ + 0, /* tp_setattro */ + 0, /* tp_as_buffer */ +#if PY_MAJOR_VERSION >= 3 + Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */ +#else + Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE | Py_TPFLAGS_CHECKTYPES, /* tp_flags */ +#endif + "float vector type", /* tp_doc */ + 0, /* tp_traverse */ + 0, /* tp_clear */ + 0, /* tp_richcompare */ + 0, /* tp_weaklistoffset */ + 0, /* tp_iter */ + 0, /* tp_iternext */ + PbVec3Methods, /* tp_methods */ + PbVec3Members, /* tp_members */ + 0, /* tp_getset */ + 0, /* tp_base */ + 0, /* tp_dict */ + 0, /* tp_descr_get */ + 0, /* tp_descr_set */ + 0, /* tp_dictoffset */ + (initproc)PbVec3Init, /* tp_init */ + 0, /* tp_alloc */ + PbVec3New, /* tp_new */ +}; + +inline PyObject *castPy(PyTypeObject *p) +{ + return reinterpret_cast<PyObject *>(static_cast<void *>(p)); +} + +// 4d vector + +extern PyTypeObject PbVec4Type; + +struct PbVec4 { + PyObject_HEAD float data[4]; +}; + +static PyMethodDef PbVec4Methods[] = { + {NULL} // Sentinel +}; + +static PyMemberDef PbVec4Members[] = { + {(char *)"x", T_FLOAT, offsetof(PbVec4, data), 0, (char *)"X"}, + {(char *)"y", T_FLOAT, offsetof(PbVec4, data) + sizeof(float) * 1, 0, (char *)"Y"}, + {(char *)"z", T_FLOAT, offsetof(PbVec4, data) + sizeof(float) * 2, 0, (char *)"Z"}, + {(char *)"t", T_FLOAT, offsetof(PbVec4, data) + sizeof(float) * 3, 0, (char *)"T"}, + {NULL} // Sentinel +}; + +static void PbVec4Dealloc(PbVec4 *self) +{ + Py_TYPE(self)->tp_free((PyObject *)self); +} + +static PyObject *PbVec4New(PyTypeObject *type, PyObject *args, PyObject *kwds) +{ + return type->tp_alloc(type, 0); +} + +static int PbVec4Init(PbVec4 *self, PyObject *args, PyObject *kwds) +{ + + float x1 = numeric_limits<float>::quiet_NaN(), x2 = x1, x3 = x1, x4 = x1; + if (!PyArg_ParseTuple(args, "|ffff", &x1, &x2, &x3, &x4)) + return -1; + + if (!c_isnan(x1)) { + self->data[0] = x1; + if (!c_isnan(x2) && !c_isnan(x3) && !c_isnan(x4)) { + self->data[1] = x2; + self->data[2] = x3; + self->data[3] = x4; + } + else { + if (!c_isnan(x2) || !c_isnan(x3) || !c_isnan(x4)) { + errMsg("Invalid partial init of vec4"); + } + self->data[1] = self->data[2] = self->data[3] = x1; + } + } + else { + self->data[0] = self->data[1] = self->data[2] = self->data[3] = 0; + } + return 0; +} + +static PyObject *PbVec4Repr(PbVec4 *self) +{ + Manta::Vec4 v(self->data[0], self->data[1], self->data[2], self->data[3]); + return PyUnicode_FromFormat(v.toString().c_str()); +} + +PyTypeObject PbVec4Type = { + PyVarObject_HEAD_INIT(NULL, 0) "manta.vec4", /* tp_name */ + sizeof(PbVec4), /* tp_basicsize */ + 0, /* tp_itemsize */ + (destructor)PbVec4Dealloc, /* tp_dealloc */ + 0, /* tp_print */ + 0, /* tp_getattr */ + 0, /* tp_setattr */ + 0, /* tp_reserved */ + (reprfunc)PbVec4Repr, /* tp_repr */ + NULL, // &PbVec4NumberMethods, /* tp_as_number */ + 0, /* tp_as_sequence */ + 0, /* tp_as_mapping */ + 0, /* tp_hash */ + 0, /* tp_call */ + 0, /* tp_str */ + 0, /* tp_getattro */ + 0, /* tp_setattro */ + 0, /* tp_as_buffer */ +#if PY_MAJOR_VERSION >= 3 + Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */ +#else + Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE | Py_TPFLAGS_CHECKTYPES, /* tp_flags */ +#endif + "float vector type", /* tp_doc */ + 0, /* tp_traverse */ + 0, /* tp_clear */ + 0, /* tp_richcompare */ + 0, /* tp_weaklistoffset */ + 0, /* tp_iter */ + 0, /* tp_iternext */ + PbVec4Methods, /* tp_methods */ + PbVec4Members, /* tp_members */ + 0, /* tp_getset */ + 0, /* tp_base */ + 0, /* tp_dict */ + 0, /* tp_descr_get */ + 0, /* tp_descr_set */ + 0, /* tp_dictoffset */ + (initproc)PbVec4Init, /* tp_init */ + 0, /* tp_alloc */ + PbVec4New, /* tp_new */ +}; + +// register + +void PbVecInitialize(PyObject *module) +{ + if (PyType_Ready(&PbVec3Type) < 0) + errMsg("can't initialize Vec3 type"); + Py_INCREF(castPy(&PbVec3Type)); + PyModule_AddObject(module, "vec3", (PyObject *)&PbVec3Type); + + if (PyType_Ready(&PbVec4Type) < 0) + errMsg("can't initialize Vec4 type"); + Py_INCREF(castPy(&PbVec4Type)); + PyModule_AddObject(module, "vec4", (PyObject *)&PbVec4Type); +} +const static Pb::Register _REG(PbVecInitialize); + +} // namespace Manta |