diff options
author | Campbell Barton <ideasman42@gmail.com> | 2011-12-18 11:27:11 +0400 |
---|---|---|
committer | Campbell Barton <ideasman42@gmail.com> | 2011-12-18 11:27:11 +0400 |
commit | 414370b8d42324878485e569fc332b814131887f (patch) | |
tree | 84b9b3077cccc3a5237bb8c033b6b39859cf9538 /source/blender/python/mathutils/mathutils_Vector.c | |
parent | bfdaa3b187b947a0efcf3a02cb70bbe8aff5e301 (diff) |
Support for arbitrary sized vectors - (was limited by 2-4 previously)
patch http://codereview.appspot.com/5482043
from Andrew Hale
* Text from the submission *
This patch adds the ability to use arbitrary sized vectors from mathutils.
Currently vectors are only of size 2, 3 or 4 since they are generally restricted
to geometric applications. However, we can use arbitrary sized vectors for
efficient calculations and data manipulation.
Diffstat (limited to 'source/blender/python/mathutils/mathutils_Vector.c')
-rw-r--r-- | source/blender/python/mathutils/mathutils_Vector.c | 516 |
1 files changed, 465 insertions, 51 deletions
diff --git a/source/blender/python/mathutils/mathutils_Vector.c b/source/blender/python/mathutils/mathutils_Vector.c index 9d1a22adb12..a812311dad4 100644 --- a/source/blender/python/mathutils/mathutils_Vector.c +++ b/source/blender/python/mathutils/mathutils_Vector.c @@ -54,15 +54,29 @@ static int row_vector_multiplication(float rvec[MAX_DIMENSIONS], VectorObject *v */ static PyObject *Vector_new(PyTypeObject *type, PyObject *args, PyObject *UNUSED(kwds)) { - float vec[4]= {0.0f, 0.0f, 0.0f, 0.0f}; + float *vec= NULL; int size= 3; /* default to a 3D vector */ switch(PyTuple_GET_SIZE(args)) { case 0: + vec= PyMem_Malloc(size * sizeof(float)); + + if (vec == NULL) { + PyErr_SetString(PyExc_MemoryError, + "Vector(): " + "problem allocating pointer space"); + return NULL; + } + + fill_vn_fl(vec, size, 0.0f); break; case 1: - if ((size=mathutils_array_parse(vec, 2, 4, PyTuple_GET_ITEM(args, 0), "mathutils.Vector()")) == -1) + if ((size=mathutils_array_parse_alloc(&vec, 2, PyTuple_GET_ITEM(args, 0), "mathutils.Vector()")) == -1) { + if (vec) { + PyMem_Free(vec); + } return NULL; + } break; default: PyErr_SetString(PyExc_TypeError, @@ -87,6 +101,215 @@ static PyObject *vec__apply_to_copy(PyNoArgsFunction vec_func, VectorObject *sel } } +/*-----------------------CLASS-METHODS----------------------------*/ +PyDoc_STRVAR(C_Vector_Fill_doc, +".. classmethod:: Fill(size, fill=0.0)\n" +"\n" +" Create a vector of length size with all values set to fill.\n" +"\n" +" :arg size: The length of the vector to be created.\n" +" :type size: int\n" +" :arg fill: The value used to fill the vector.\n" +" :type fill: float\n" +); +static PyObject *C_Vector_Fill(PyObject *cls, PyObject *args) +{ + float *vec; + int size; + float fill= 0.0f; + + if (!PyArg_ParseTuple(args, "i|f:Vector.Fill", &size, &fill)) { + return NULL; + } + + if (size < 2) { + PyErr_SetString(PyExc_RuntimeError, + "Vector(): invalid size"); + return NULL; + } + + vec= PyMem_Malloc(size * sizeof(float)); + + if (vec == NULL) { + PyErr_SetString(PyExc_MemoryError, + "Vector.Fill(): " + "problem allocating pointer space"); + return NULL; + } + + fill_vn_fl(vec, size, fill); + + return Vector_CreatePyObject_alloc(vec, size, (PyTypeObject *)cls); +} + +PyDoc_STRVAR(C_Vector_Range_doc, +".. classmethod:: Range(start=0, stop, step=1)\n" +"\n" +" Create a filled with a range of values.\n" +"\n" +" :arg start: The start of the range used to fill the vector.\n" +" :type start: int\n" +" :arg stop: The end of the range used to fill the vector.\n" +" :type stop: int\n" +" :arg step: The step between successive values in the vector.\n" +" :type step: int\n" +); +static PyObject *C_Vector_Range(PyObject *cls, PyObject *args) +{ + float *vec; + int stop, size; + int start= 0; + int step= 1; + + if (!PyArg_ParseTuple(args, "i|ii:Vector.Range", &start, &stop, &step)) { + return NULL; + } + + switch(PyTuple_GET_SIZE(args)){ + case 1: + size = start; + start= 0; + break; + case 2: + if (start >= stop) { + PyErr_SetString(PyExc_RuntimeError, + "Start value is larger" + "than the stop value"); + return NULL; + } + + size= stop - start; + break; + default: + if (start >= stop) { + PyErr_SetString(PyExc_RuntimeError, + "Start value is larger" + "than the stop value"); + return NULL; + } + size= (stop - start)/step; + if (size%step) + size++; + break; + } + + vec= PyMem_Malloc(size * sizeof(float)); + + if (vec == NULL) { + PyErr_SetString(PyExc_MemoryError, + "Vector.Range(): " + "problem allocating pointer space"); + return NULL; + } + + range_vn_fl(vec, size, (float)start, (float)step); + + return Vector_CreatePyObject_alloc(vec, size, (PyTypeObject *)cls); +} + +PyDoc_STRVAR(C_Vector_Linspace_doc, +".. classmethod:: Linspace(start, stop, size)\n" +"\n" +" Create a vector of the specified size which is filled with linearly spaced values between start and stop values.\n" +"\n" +" :arg start: The start of the range used to fill the vector.\n" +" :type start: int\n" +" :arg stop: The end of the range used to fill the vector.\n" +" :type stop: int\n" +" :arg size: The size of the vector to be created.\n" +" :type size: int\n" +); +static PyObject *C_Vector_Linspace(PyObject *cls, PyObject *args) +{ + float *vec; + int size; + float start, end, step; + + if (!PyArg_ParseTuple(args, "ffi:Vector.Linspace", &start, &end, &size)) { + return NULL; + } + + if (size < 2) { + PyErr_SetString(PyExc_RuntimeError, + "Vector.Linspace(): invalid size"); + return NULL; + } + + step= (end - start)/(float)(size-1); + + vec= PyMem_Malloc(size * sizeof(float)); + + if (vec == NULL) { + PyErr_SetString(PyExc_MemoryError, + "Vector.Linspace(): " + "problem allocating pointer space"); + return NULL; + } + + range_vn_fl(vec, size, start, step); + + return Vector_CreatePyObject_alloc(vec, size, (PyTypeObject *)cls); +} + +PyDoc_STRVAR(C_Vector_Repeat_doc, +".. classmethod:: Repeat(vector, size)\n" +"\n" +" Create a vector by repeating the values in vector until the required size is reached.\n" +"\n" +" :arg tuple: The vector to draw values from.\n" +" :type tuple: :class:`mathutils.Vector`\n" +" :arg size: The size of the vector to be created.\n" +" :type size: int\n" +); +static PyObject *C_Vector_Repeat(PyObject *cls, PyObject *args) +{ + float *vec; + float *iter_vec= NULL; + int i, size, value_size; + PyObject *value; + + if (!PyArg_ParseTuple(args, "Oi:Vector.Repeat", &value, &size)) { + return NULL; + } + + if (size < 2) { + PyErr_SetString(PyExc_RuntimeError, + "Vector.Repeat(): invalid size"); + return NULL; + } + + if ((value_size=mathutils_array_parse_alloc(&iter_vec, 2, value, "Vector.Repeat(vector, size), invalid 'vector' arg")) == -1) { + PyMem_Free(iter_vec); + return NULL; + } + + if (iter_vec == NULL) { + PyErr_SetString(PyExc_MemoryError, + "Vector.Repeat(): " + "problem allocating pointer space"); + return NULL; + } + + vec= PyMem_Malloc(size * sizeof(float)); + + if (vec == NULL) { + PyErr_SetString(PyExc_MemoryError, + "Vector.Repeat(): " + "problem allocating pointer space"); + return NULL; + } + + i= 0; + while (i < size) { + vec[i]= iter_vec[i % value_size]; + i++; + } + + PyMem_Free(iter_vec); + + return Vector_CreatePyObject_alloc(vec, size, (PyTypeObject *)cls); +} + /*-----------------------------METHODS---------------------------- */ PyDoc_STRVAR(Vector_zero_doc, ".. method:: zero()\n" @@ -137,6 +360,101 @@ static PyObject *Vector_normalized(VectorObject *self) return vec__apply_to_copy((PyNoArgsFunction)Vector_normalize, self); } +PyDoc_STRVAR(Vector_resize_doc, +".. method:: resize(size=3)\n" +"\n" +" Resize the vector to have size number of elements.\n" +"\n" +" :return: an instance of itself\n" +" :rtype: :class:`Vector`\n" +); +static PyObject *Vector_resize(VectorObject *self, PyObject *value) +{ + int size; + + if (self->wrapped==Py_WRAP) { + PyErr_SetString(PyExc_TypeError, + "Vector.resize(): " + "cannot resize wrapped data - only python vectors"); + return NULL; + } + if (self->cb_user) { + PyErr_SetString(PyExc_TypeError, + "Vector.resize(): " + "cannot resize a vector that has an owner"); + return NULL; + } + + if ((size = PyLong_AsLong(value)) == -1) { + PyErr_SetString(PyExc_TypeError, + "Vector.resize(size): " + "expected size argument to be an integer"); + return NULL; + } + + if (size < 2) { + PyErr_SetString(PyExc_RuntimeError, + "Vector.resize(): invalid size"); + return NULL; + } + + self->vec = PyMem_Realloc(self->vec, (size * sizeof(float))); + if (self->vec == NULL) { + PyErr_SetString(PyExc_MemoryError, + "Vector.resize(): " + "problem allocating pointer space"); + return NULL; + } + + /* If the vector has increased in length, set all new elements to 0.0f */ + if (size > self->size) { + fill_vn_fl(self->vec + self->size, size - self->size, 0.0f); + } + + self->size = size; + Py_RETURN_NONE; +} + +PyDoc_STRVAR(Vector_resized_doc, +".. method:: resized(size=3)\n" +"\n" +" Return a resized copy of the vector with size number of elements.\n" +"\n" +" :return: a new vector\n" +" :rtype: :class:`Vector`\n" +); +static PyObject *Vector_resized(VectorObject *self, PyObject *value) +{ + int size; + float *vec; + + /*if (!PyArg_ParseTuple(args, "i:resize", &size)) + return NULL;*/ + if ((size = PyLong_AsLong(value)) == -1){ + return NULL; + } + + if (size < 2) { + PyErr_SetString(PyExc_RuntimeError, + "Vector.resized(): invalid size"); + return NULL; + } + + vec= PyMem_Malloc(size * sizeof(float)); + + if (vec == NULL) { + PyErr_SetString(PyExc_MemoryError, + "Vector.resized(): " + "problem allocating pointer space"); + return NULL; + } + + fill_vn_fl(vec, size, 0.0f); + memcpy(vec, self->vec, self->size * sizeof(float)); + + return Vector_CreatePyObject_alloc(vec, size, NULL); +} + PyDoc_STRVAR(Vector_resize_2d_doc, ".. method:: resize_2d()\n" "\n" @@ -505,6 +823,12 @@ static PyObject *Vector_reflect(VectorObject *self, PyObject *value) if ((value_size= mathutils_array_parse(tvec, 2, 4, value, "Vector.reflect(other), invalid 'other' arg")) == -1) return NULL; + if (self->size < 2 || self->size > 4) { + PyErr_SetString(PyExc_ValueError, + "Vector must be 2D, 3D or 4D"); + return NULL; + } + mirror[0] = tvec[0]; mirror[1] = tvec[1]; if (value_size > 2) mirror[2] = tvec[2]; @@ -544,6 +868,12 @@ static PyObject *Vector_cross(VectorObject *self, PyObject *value) if (mathutils_array_parse(tvec, self->size, self->size, value, "Vector.cross(other), invalid 'other' arg") == -1) return NULL; + if (self->size != 3) { + PyErr_SetString(PyExc_ValueError, + "Vector must be 3D"); + return NULL; + } + ret= (VectorObject *)Vector_CreatePyObject(NULL, 3, Py_NEW, Py_TYPE(self)); cross_v3_v3v3(ret->vec, self->vec, tvec); return (PyObject *)ret; @@ -561,15 +891,20 @@ PyDoc_STRVAR(Vector_dot_doc, ); static PyObject *Vector_dot(VectorObject *self, PyObject *value) { - float tvec[MAX_DIMENSIONS]; + float *tvec; if (BaseMath_ReadCallback(self) == -1) return NULL; - if (mathutils_array_parse(tvec, self->size, self->size, value, "Vector.dot(other), invalid 'other' arg") == -1) - return NULL; + if (mathutils_array_parse_alloc(&tvec, self->size, value, "Vector.dot(other), invalid 'other' arg") == -1) { + goto cleanup; + } return PyFloat_FromDouble(dot_vn_vn(self->vec, tvec, self->size)); + +cleanup: + PyMem_Free(tvec); + return NULL; } PyDoc_STRVAR(Vector_angle_doc, @@ -607,6 +942,12 @@ static PyObject *Vector_angle(VectorObject *self, PyObject *args) if (mathutils_array_parse(tvec, self->size, self->size, value, "Vector.angle(other), invalid 'other' arg") == -1) return NULL; + if (self->size > 4) { + PyErr_SetString(PyExc_ValueError, + "Vector must be 2D, 3D or 4D"); + return NULL; + } + for (x = 0; x < size; x++) { dot_self += (double)self->vec[x] * (double)self->vec[x]; dot_other += (double)tvec[x] * (double)tvec[x]; @@ -647,7 +988,7 @@ static PyObject *Vector_rotation_difference(VectorObject *self, PyObject *value) { float quat[4], vec_a[3], vec_b[3]; - if (self->size < 3) { + if (self->size < 3 || self->size > 4) { PyErr_SetString(PyExc_ValueError, "vec.difference(value): " "expects both vectors to be size 3 or 4"); @@ -692,6 +1033,12 @@ static PyObject *Vector_project(VectorObject *self, PyObject *value) if (mathutils_array_parse(tvec, size, size, value, "Vector.project(other), invalid 'other' arg") == -1) return NULL; + if (self->size > 4) { + PyErr_SetString(PyExc_ValueError, + "Vector must be 2D, 3D or 4D"); + return NULL; + } + if (BaseMath_ReadCallback(self) == -1) return NULL; @@ -725,24 +1072,41 @@ static PyObject *Vector_lerp(VectorObject *self, PyObject *args) const int size= self->size; PyObject *value= NULL; float fac, ifac; - float tvec[MAX_DIMENSIONS], vec[MAX_DIMENSIONS]; + float *tvec, *vec; int x; if (!PyArg_ParseTuple(args, "Of:lerp", &value, &fac)) return NULL; - if (mathutils_array_parse(tvec, size, size, value, "Vector.lerp(other), invalid 'other' arg") == -1) - return NULL; + if (mathutils_array_parse_alloc(&tvec, size, value, "Vector.lerp(other), invalid 'other' arg") == -1) { + goto cleanup; + } - if (BaseMath_ReadCallback(self) == -1) + if (BaseMath_ReadCallback(self) == -1) { + goto cleanup; + } + + vec= PyMem_Malloc(size * sizeof(float)); + if (vec == NULL) { + PyErr_SetString(PyExc_MemoryError, + "Vector.lerp(): " + "problem allocating pointer space"); return NULL; + } ifac= 1.0f - fac; for (x = 0; x < size; x++) { vec[x] = (ifac * self->vec[x]) + (fac * tvec[x]); } - return Vector_CreatePyObject(vec, size, Py_NEW, Py_TYPE(self)); + + PyMem_Free(tvec); + + return Vector_CreatePyObject_alloc(vec, size, Py_TYPE(self)); + +cleanup: + PyMem_Free(tvec); + return NULL; } PyDoc_STRVAR(Vector_rotate_doc, @@ -763,7 +1127,7 @@ static PyObject *Vector_rotate(VectorObject *self, PyObject *value) if (mathutils_any_to_rotmat(other_rmat, value, "Vector.rotate(value)") == -1) return NULL; - if (self->size < 3) { + if (self->size < 3 || self->size > 4) { PyErr_SetString(PyExc_ValueError, "Vector must be 3D or 4D"); return NULL; @@ -903,8 +1267,8 @@ static PyObject *Vector_slice(VectorObject *self, int begin, int end) /* sequence slice (set): vector[a:b] = value */ static int Vector_ass_slice(VectorObject *self, int begin, int end, PyObject *seq) { - int y, size = 0; - float vec[MAX_DIMENSIONS]; + int size = 0; + float *vec= NULL; if (BaseMath_ReadCallback(self) == -1) return -1; @@ -914,18 +1278,30 @@ static int Vector_ass_slice(VectorObject *self, int begin, int end, PyObject *se begin = MIN2(begin, end); size = (end - begin); - if (mathutils_array_parse(vec, size, size, seq, "vector[begin:end] = [...]") == -1) + if (mathutils_array_parse_alloc(&vec, size, seq, "vector[begin:end] = [...]") == -1) { + goto cleanup; + } + + if (vec == NULL) { + PyErr_SetString(PyExc_MemoryError, + "vec[:] = seq: " + "problem allocating pointer space"); return -1; + } /*parsed well - now set in vector*/ - for (y = 0; y < size; y++) { - self->vec[begin + y] = vec[y]; - } + memcpy(self->vec + begin, vec, size * sizeof(float)); if (BaseMath_WriteCallback(self) == -1) return -1; + PyMem_Free(vec); + return 0; + +cleanup: + PyMem_Free(vec); + return -1; } /* Numeric Protocols */ @@ -933,7 +1309,7 @@ static int Vector_ass_slice(VectorObject *self, int begin, int end, PyObject *se static PyObject *Vector_add(PyObject *v1, PyObject *v2) { VectorObject *vec1 = NULL, *vec2 = NULL; - float vec[MAX_DIMENSIONS]; + float *vec= NULL; if (!VectorObject_Check(v1) || !VectorObject_Check(v2)) { PyErr_Format(PyExc_AttributeError, @@ -956,9 +1332,18 @@ static PyObject *Vector_add(PyObject *v1, PyObject *v2) return NULL; } + vec= PyMem_Malloc(vec1->size * sizeof(float)); + + if (vec == NULL) { /*allocation failure*/ + PyErr_SetString(PyExc_MemoryError, + "Vector(): " + "problem allocating pointer space"); + return NULL; + } + add_vn_vnvn(vec, vec1->vec, vec2->vec, vec1->size); - return Vector_CreatePyObject(vec, vec1->size, Py_NEW, Py_TYPE(v1)); + return Vector_CreatePyObject_alloc(vec, vec1->size, Py_TYPE(v1)); } /* addition in-place: obj += obj */ @@ -997,7 +1382,7 @@ static PyObject *Vector_iadd(PyObject *v1, PyObject *v2) static PyObject *Vector_sub(PyObject *v1, PyObject *v2) { VectorObject *vec1 = NULL, *vec2 = NULL; - float vec[MAX_DIMENSIONS]; + float *vec; if (!VectorObject_Check(v1) || !VectorObject_Check(v2)) { PyErr_Format(PyExc_AttributeError, @@ -1019,9 +1404,18 @@ static PyObject *Vector_sub(PyObject *v1, PyObject *v2) return NULL; } + vec= PyMem_Malloc(vec1->size * sizeof(float)); + + if (vec == NULL) { /*allocation failure*/ + PyErr_SetString(PyExc_MemoryError, + "Vector(): " + "problem allocating pointer space"); + return NULL; + } + sub_vn_vnvn(vec, vec1->vec, vec2->vec, vec1->size); - return Vector_CreatePyObject(vec, vec1->size, Py_NEW, Py_TYPE(v1)); + return Vector_CreatePyObject_alloc(vec, vec1->size, Py_TYPE(v1)); } /* subtraction in-place: obj -= obj */ @@ -1104,9 +1498,18 @@ int column_vector_multiplication(float rvec[MAX_DIMENSIONS], VectorObject* vec, static PyObject *vector_mul_float(VectorObject *vec, const float scalar) { - float tvec[MAX_DIMENSIONS]; + float *tvec= NULL; + tvec= PyMem_Malloc(vec->size * sizeof(float)); + + if (tvec == NULL) { /*allocation failure*/ + PyErr_SetString(PyExc_MemoryError, + "vec * float: " + "problem allocating pointer space"); + return NULL; + } + mul_vn_vn_fl(tvec, vec->vec, vec->size, scalar); - return Vector_CreatePyObject(tvec, vec->size, Py_NEW, Py_TYPE(vec)); + return Vector_CreatePyObject_alloc(tvec, vec->size, Py_TYPE(vec)); } static PyObject *Vector_mul(PyObject *v1, PyObject *v2) @@ -1277,8 +1680,7 @@ static PyObject *Vector_imul(PyObject *v1, PyObject *v2) /* divid: obj / obj */ static PyObject *Vector_div(PyObject *v1, PyObject *v2) { - int i; - float vec[4], scalar; + float *vec= NULL, scalar; VectorObject *vec1 = NULL; if (!VectorObject_Check(v1)) { /* not a vector */ @@ -1287,7 +1689,7 @@ static PyObject *Vector_div(PyObject *v1, PyObject *v2) "Vector must be divided by a float"); return NULL; } - vec1 = (VectorObject*)v1; /* vector */ + vec1 = (VectorObject *)v1; /* vector */ if (BaseMath_ReadCallback(vec1) == -1) return NULL; @@ -1306,16 +1708,23 @@ static PyObject *Vector_div(PyObject *v1, PyObject *v2) return NULL; } - for (i = 0; i < vec1->size; i++) { - vec[i] = vec1->vec[i] / scalar; + vec= PyMem_Malloc(vec1->size * sizeof(float)); + + if (vec == NULL) { /*allocation failure*/ + PyErr_SetString(PyExc_MemoryError, + "vec / value: " + "problem allocating pointer space"); + return NULL; } - return Vector_CreatePyObject(vec, vec1->size, Py_NEW, Py_TYPE(v1)); + + mul_vn_vn_fl(vec, vec1->vec, vec1->size, 1.0f/scalar); + + return Vector_CreatePyObject_alloc(vec, vec1->size, Py_TYPE(v1)); } /* divide in-place: obj /= obj */ static PyObject *Vector_idiv(PyObject *v1, PyObject *v2) { - int i; float scalar; VectorObject *vec1 = (VectorObject*)v1; @@ -1335,9 +1744,8 @@ static PyObject *Vector_idiv(PyObject *v1, PyObject *v2) "divide by zero error"); return NULL; } - for (i = 0; i < vec1->size; i++) { - vec1->vec[i] /= scalar; - } + + mul_vn_fl(vec1->vec, vec1->size, 1.0f/scalar); (void)BaseMath_WriteCallback(vec1); @@ -1349,29 +1757,24 @@ static PyObject *Vector_idiv(PyObject *v1, PyObject *v2) returns the negative of this object*/ static PyObject *Vector_neg(VectorObject *self) { - float tvec[MAX_DIMENSIONS]; + float *tvec; if (BaseMath_ReadCallback(self) == -1) return NULL; + tvec= PyMem_Malloc(self->size * sizeof(float)); negate_vn_vn(tvec, self->vec, self->size); - return Vector_CreatePyObject(tvec, self->size, Py_NEW, Py_TYPE(self)); + return Vector_CreatePyObject_alloc(tvec, self->size, Py_TYPE(self)); } /*------------------------vec_magnitude_nosqrt (internal) - for comparing only */ static double vec_magnitude_nosqrt(float *data, int size) { - double dot = 0.0f; - int i; - - for (i=0; i<size; i++) { - dot += (double)data[i]; - } /*return (double)sqrt(dot);*/ /* warning, line above removed because we are not using the length, rather the comparing the sizes and for this we do not need the sqrt for the actual length, the dot must be sqrt'd */ - return dot; + return dot_vn_vn(data, data, size); } @@ -1606,16 +2009,10 @@ static int Vector_setAxis(VectorObject *self, PyObject *value, void *type) /* vector.length */ static PyObject *Vector_getLength(VectorObject *self, void *UNUSED(closure)) { - double dot = 0.0f; - int i; - if (BaseMath_ReadCallback(self) == -1) return NULL; - for (i = 0; i < self->size; i++) { - dot += (double)(self->vec[i] * self->vec[i]); - } - return PyFloat_FromDouble(sqrt(dot)); + return PyFloat_FromDouble(sqrt(dot_vn_vn(self->vec, self->vec, self->size))); } static int Vector_setLength(VectorObject *self, PyObject *value) @@ -2242,6 +2639,12 @@ static PyObject *Vector_negate(VectorObject *self) } static struct PyMethodDef Vector_methods[] = { + /* Class Methods */ + {"Fill", (PyCFunction) C_Vector_Fill, METH_VARARGS | METH_CLASS, C_Vector_Fill_doc}, + {"Range", (PyCFunction) C_Vector_Range, METH_VARARGS | METH_CLASS, C_Vector_Range_doc}, + {"Linspace", (PyCFunction) C_Vector_Linspace, METH_VARARGS | METH_CLASS, C_Vector_Linspace_doc}, + {"Repeat", (PyCFunction) C_Vector_Repeat, METH_VARARGS | METH_CLASS, C_Vector_Repeat_doc}, + /* in place only */ {"zero", (PyCFunction) Vector_zero, METH_NOARGS, Vector_zero_doc}, {"negate", (PyCFunction) Vector_negate, METH_NOARGS, Vector_negate_doc}, @@ -2250,6 +2653,8 @@ static struct PyMethodDef Vector_methods[] = { {"normalize", (PyCFunction) Vector_normalize, METH_NOARGS, Vector_normalize_doc}, {"normalized", (PyCFunction) Vector_normalized, METH_NOARGS, Vector_normalized_doc}, + {"resize", (PyCFunction) Vector_resize, METH_O, Vector_resize_doc}, + {"resized", (PyCFunction) Vector_resized, METH_O, Vector_resized_doc}, {"to_2d", (PyCFunction) Vector_to_2d, METH_NOARGS, Vector_to_2d_doc}, {"resize_2d", (PyCFunction) Vector_resize_2d, METH_NOARGS, Vector_resize_2d_doc}, {"to_3d", (PyCFunction) Vector_to_3d, METH_NOARGS, Vector_to_3d_doc}, @@ -2375,7 +2780,7 @@ PyObject *Vector_CreatePyObject(float *vec, const int size, const int type, PyTy { VectorObject *self; - if (size > 4 || size < 2) { + if (size < 2) { PyErr_SetString(PyExc_RuntimeError, "Vector(): invalid size"); return NULL; @@ -2429,3 +2834,12 @@ PyObject *Vector_CreatePyObject_cb(PyObject *cb_user, int size, int cb_type, int return (PyObject *)self; } + +PyObject *Vector_CreatePyObject_alloc(float *vec, const int size, PyTypeObject *base_type) +{ + VectorObject *vect_ob; + vect_ob= (VectorObject *)Vector_CreatePyObject(vec, size, Py_WRAP, base_type); + vect_ob->wrapped= Py_NEW; + + return (PyObject *)vect_ob; +} |