Merge from trunk 16122-16307
This commit is contained in:
@@ -1554,6 +1554,12 @@ static PyObject *Method_Number( PyObject * self, PyObject * args )
|
||||
|
||||
UI_METHOD_ERRORCHECK;
|
||||
|
||||
if ( !PyNumber_Check(inio) || !PyNumber_Check(mino) ||
|
||||
!PyNumber_Check(maxo) ) {
|
||||
return EXPP_ReturnPyObjError( PyExc_TypeError,
|
||||
"expected ints or floats for the initial, min and max values" );
|
||||
}
|
||||
|
||||
but = newbutton( );
|
||||
if (tip) strncpy(but->tooltip, tip, BPY_MAX_TOOLTIP);
|
||||
block = Get_uiBlock( );
|
||||
|
||||
@@ -554,6 +554,7 @@ static int Material_setSssTexScatter( BPy_Material * self, PyObject * value );
|
||||
static int Material_setSssFront( BPy_Material * self, PyObject * value );
|
||||
static int Material_setSssBack( BPy_Material * self, PyObject * value );
|
||||
static int Material_setSssBack( BPy_Material * self, PyObject * value );
|
||||
static int Material_setTexChannel( BPy_Material * self, PyObject * value );
|
||||
|
||||
static PyObject *Material_getColorComponent( BPy_Material * self,
|
||||
void * closure );
|
||||
@@ -633,6 +634,7 @@ static PyObject *Material_getSssBack( BPy_Material * self );
|
||||
static PyObject *Material_getFilter( BPy_Material * self );
|
||||
static PyObject *Material_getTranslucency( BPy_Material * self );
|
||||
static PyObject *Material_getTextures( BPy_Material * self );
|
||||
static PyObject *Material_getTexChannel( BPy_Material * self );
|
||||
static PyObject *Material_clearIpo( BPy_Material * self );
|
||||
|
||||
static PyObject *Material_setTexture( BPy_Material * self, PyObject * args );
|
||||
@@ -1140,7 +1142,11 @@ static PyGetSetDef BPy_Material_getseters[] = {
|
||||
NULL},
|
||||
{"lightGroup",
|
||||
(getter)Material_getLightGroup, (setter)Material_setLightGroup,
|
||||
"Set the light group for this material",
|
||||
"The light group for this material",
|
||||
NULL},
|
||||
{"enabledTextures",
|
||||
(getter)Material_getTexChannel, (setter)Material_setTexChannel,
|
||||
"Enabled texture channels for this material",
|
||||
NULL},
|
||||
{"R",
|
||||
(getter)Material_getColorComponent, (setter)Material_setColorComponent,
|
||||
@@ -1517,6 +1523,36 @@ static PyObject *Material_getLightGroup( BPy_Material * self )
|
||||
return Group_CreatePyObject( self->material->group );
|
||||
}
|
||||
|
||||
static PyObject *Material_getTexChannel( BPy_Material * self )
|
||||
{
|
||||
int i;
|
||||
short mask = 1;
|
||||
PyObject *list = PyList_New(0);
|
||||
if( !list )
|
||||
return EXPP_ReturnPyObjError( PyExc_MemoryError,
|
||||
"PyList_New() failed" );
|
||||
|
||||
for( i = 0, mask = 1; i < MAX_MTEX ; ++i, mask <<= 1 ) {
|
||||
if( self->material->mtex[i] && (mask & self->material->septex) == 0 ) {
|
||||
PyObject * val = PyInt_FromLong(i);
|
||||
if( !val ) {
|
||||
Py_DECREF( list );
|
||||
return EXPP_ReturnPyObjError( PyExc_MemoryError,
|
||||
"PyInt_FromLong() failed" );
|
||||
}
|
||||
if( PyList_Append( list, val ) < 0 ) {
|
||||
Py_DECREF( val );
|
||||
Py_DECREF( list );
|
||||
return EXPP_ReturnPyObjError( PyExc_RuntimeError,
|
||||
"PyList_Append() failed" );
|
||||
}
|
||||
Py_DECREF( val );
|
||||
}
|
||||
}
|
||||
|
||||
return list;
|
||||
}
|
||||
|
||||
static PyObject *Material_getHaloSize( BPy_Material * self )
|
||||
{
|
||||
return PyFloat_FromDouble( ( double ) self->material->hasize );
|
||||
@@ -1982,6 +2018,57 @@ static int Material_setLightGroup( BPy_Material * self, PyObject * value )
|
||||
return GenericLib_assignData(value, (void **) &self->material->group, NULL, 1, ID_GR, 0);
|
||||
}
|
||||
|
||||
static int Material_setTexChannel( BPy_Material * self, PyObject * value )
|
||||
{
|
||||
int i, mask;
|
||||
short septex = 0;
|
||||
int result = 1;
|
||||
|
||||
/* fail if input is not a standard sequence */
|
||||
if( !PyList_Check( value ) && !PyTuple_Check( value ) )
|
||||
return EXPP_ReturnIntError( PyExc_TypeError,
|
||||
"expected tuple or list of integers" );
|
||||
|
||||
/* get a fast sequence; in Python 2.5, this just return the original
|
||||
* list or tuple and INCREFs it, so we must DECREF */
|
||||
value = PySequence_Fast( value, "" );
|
||||
|
||||
/* set the disable bit for each existing texture */
|
||||
for( i= 0, mask= 1; i < MAX_MTEX; ++i, mask <<= 1 )
|
||||
if( self->material->mtex[i] != NULL )
|
||||
septex |= mask;
|
||||
|
||||
/* check the list, and build new septex value */
|
||||
for( i= PySequence_Size(value)-1; i >= 0; --i ) {
|
||||
long ival;
|
||||
PyObject *item = PySequence_Fast_GET_ITEM( value, i );
|
||||
if( !PyInt_Check( item ) ) {
|
||||
PyErr_SetString ( PyExc_TypeError,
|
||||
"expected tuple or list of integers" );
|
||||
goto exit;
|
||||
}
|
||||
ival= PyInt_AsLong( item );
|
||||
if(ival < 0 || ival > MAX_MTEX) {
|
||||
PyErr_SetString( PyExc_ValueError,
|
||||
"channel value out of range" );
|
||||
goto exit;
|
||||
}
|
||||
ival&= (1<<MAX_MTEX)-1;
|
||||
if( self->material->mtex[(int)ival] == NULL ) {
|
||||
PyErr_SetString( PyExc_ValueError,
|
||||
"channels must have a texture assigned" );
|
||||
goto exit;
|
||||
}
|
||||
septex&= ~(1<<ival);
|
||||
}
|
||||
self->material->septex= septex;
|
||||
result = 0;
|
||||
|
||||
exit:
|
||||
Py_DECREF(value);
|
||||
return result;
|
||||
}
|
||||
|
||||
static int Material_setAdd( BPy_Material * self, PyObject * value )
|
||||
{
|
||||
return EXPP_setFloatClamped ( value, &self->material->add,
|
||||
@@ -2313,9 +2400,6 @@ static int Material_setSssBack( BPy_Material * self, PyObject * value )
|
||||
EXPP_MAT_SSS_BACK_MAX);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
static PyObject *Material_setTexture( BPy_Material * self, PyObject * args )
|
||||
{
|
||||
int texnum;
|
||||
|
||||
@@ -5381,11 +5381,11 @@ static PyObject *MFaceSeq_delete( BPy_MFaceSeq * self, PyObject *args )
|
||||
if( PySequence_Size( args ) != 2 ||
|
||||
!PyArg_ParseTuple( args, "iO", &edge_also, &args ) )
|
||||
return EXPP_ReturnPyObjError( PyExc_TypeError,
|
||||
"expected and int and a sequence of ints or MFaces" );
|
||||
"expected an int and a sequence of ints or MFaces" );
|
||||
|
||||
if( !PyList_Check( args ) && !PyTuple_Check( args ) )
|
||||
return EXPP_ReturnPyObjError( PyExc_TypeError,
|
||||
"expected and int and a sequence of ints or MFaces" );
|
||||
"expected an int and a sequence of ints or MFaces" );
|
||||
|
||||
/* see how many args we need to parse */
|
||||
len = PySequence_Size( args );
|
||||
|
||||
@@ -204,6 +204,7 @@ enum obj_consts {
|
||||
EXPP_OBJ_ATTR_SB_INSPRING,
|
||||
EXPP_OBJ_ATTR_SB_INFRICT,
|
||||
|
||||
EXPP_OBJ_ATTR_EMPTY_DRAWTYPE
|
||||
};
|
||||
|
||||
#define EXPP_OBJECT_DRAWSIZEMIN 0.01f
|
||||
@@ -2431,6 +2432,12 @@ static int Object_setDrawType( BPy_Object * self, PyObject * value )
|
||||
OB_BOUNDBOX, OB_TEXTURE, 'b' );
|
||||
}
|
||||
|
||||
static int Object_setEmptyShape( BPy_Object * self, PyObject * value )
|
||||
{
|
||||
return EXPP_setIValueRange( value, &self->object->empty_drawtype,
|
||||
OB_ARROWS, OB_EMPTY_CONE, 'b' );
|
||||
}
|
||||
|
||||
static int Object_setEuler( BPy_Object * self, PyObject * args )
|
||||
{
|
||||
float rot1, rot2, rot3;
|
||||
@@ -3758,6 +3765,9 @@ static PyObject *getIntAttr( BPy_Object *self, void *type )
|
||||
case EXPP_OBJ_ATTR_DRAWTYPE:
|
||||
param = object->dt;
|
||||
break;
|
||||
case EXPP_OBJ_ATTR_EMPTY_DRAWTYPE:
|
||||
param = object->empty_drawtype;
|
||||
break;
|
||||
case EXPP_OBJ_ATTR_PARENT_TYPE:
|
||||
param = object->partype;
|
||||
break;
|
||||
@@ -4938,6 +4948,10 @@ static PyGetSetDef BPy_Object_getseters[] = {
|
||||
(getter)getIntAttr, (setter)Object_setDrawType,
|
||||
"The object's drawing type",
|
||||
(void *)EXPP_OBJ_ATTR_DRAWTYPE},
|
||||
{"emptyShape",
|
||||
(getter)getIntAttr, (setter)Object_setEmptyShape,
|
||||
"The empty's drawing shape",
|
||||
(void *)EXPP_OBJ_ATTR_EMPTY_DRAWTYPE},
|
||||
{"parentType",
|
||||
(getter)getIntAttr, (setter)NULL,
|
||||
"The object's parent type",
|
||||
@@ -5538,6 +5552,24 @@ static PyObject *M_Object_IpoKeyTypesDict( void )
|
||||
return M;
|
||||
}
|
||||
|
||||
static PyObject *M_Object_EmptyShapesDict( void )
|
||||
{
|
||||
PyObject *M = PyConstant_New( );
|
||||
|
||||
if( M ) {
|
||||
BPy_constant *d = ( BPy_constant * ) M;
|
||||
PyConstant_Insert( d, "ARROWS", PyInt_FromLong( OB_ARROWS ) );
|
||||
PyConstant_Insert( d, "AXES", PyInt_FromLong( OB_PLAINAXES ) );
|
||||
PyConstant_Insert( d, "CIRCLE", PyInt_FromLong( OB_CIRCLE ) );
|
||||
PyConstant_Insert( d, "ARROW", PyInt_FromLong( OB_SINGLE_ARROW ) );
|
||||
PyConstant_Insert( d, "CUBE", PyInt_FromLong( OB_CUBE ) );
|
||||
PyConstant_Insert( d, "SPHERE", PyInt_FromLong( OB_EMPTY_SPHERE ) );
|
||||
PyConstant_Insert( d, "CONE", PyInt_FromLong( OB_EMPTY_CONE ) );
|
||||
}
|
||||
return M;
|
||||
}
|
||||
|
||||
|
||||
/*****************************************************************************/
|
||||
/* Function: initObject */
|
||||
/*****************************************************************************/
|
||||
@@ -5552,6 +5584,7 @@ PyObject *Object_Init( void )
|
||||
PyObject *RBFlagsDict = M_Object_RBFlagsDict( );
|
||||
PyObject *RBShapesDict = M_Object_RBShapeBoundDict( );
|
||||
PyObject *IpoKeyTypesDict = M_Object_IpoKeyTypesDict( );
|
||||
PyObject *EmptyShapesDict = M_Object_EmptyShapesDict( );
|
||||
|
||||
PyType_Ready( &Object_Type ) ;
|
||||
|
||||
@@ -5596,7 +5629,9 @@ PyObject *Object_Init( void )
|
||||
if( RBShapesDict )
|
||||
PyModule_AddObject( module, "RBShapes", RBShapesDict );
|
||||
if( IpoKeyTypesDict )
|
||||
PyModule_AddObject( module, "IpoKeyTypes", IpoKeyTypesDict );
|
||||
PyModule_AddObject( module, "IpoKeyTypes", IpoKeyTypesDict );
|
||||
if( EmptyShapesDict )
|
||||
PyModule_AddObject( module, "EmptyShapes", EmptyShapesDict );
|
||||
|
||||
/*Add SUBMODULES to the module*/
|
||||
dict = PyModule_GetDict( module ); /*borrowed*/
|
||||
|
||||
@@ -804,7 +804,7 @@ static PyObject *Part_GetLoc( BPy_PartSys * self, PyObject * args )
|
||||
{
|
||||
ParticleSystem *psys = 0L;
|
||||
Object *ob = 0L;
|
||||
PyObject *partlist,*seglist;
|
||||
PyObject *partlist,*seglist=0L;
|
||||
ParticleCacheKey **cache,*path;
|
||||
PyObject* loc = 0L;
|
||||
ParticleKey state;
|
||||
@@ -1107,7 +1107,7 @@ static PyObject *Part_GetSize( BPy_PartSys * self, PyObject * args )
|
||||
ParticleSystem *psys = 0L;
|
||||
ParticleData *data;
|
||||
Object *ob = 0L;
|
||||
PyObject *partlist,*tuple;
|
||||
PyObject *partlist,*tuple=0L;
|
||||
DerivedMesh* dm;
|
||||
float vm[4][4],wm[4][4];
|
||||
float size;
|
||||
@@ -1217,7 +1217,7 @@ static PyObject *Part_GetAge( BPy_PartSys * self, PyObject * args )
|
||||
ParticleSystem *psys = 0L;
|
||||
ParticleData *data;
|
||||
Object *ob = 0L;
|
||||
PyObject *partlist,*tuple;
|
||||
PyObject *partlist,*tuple=0L;
|
||||
DerivedMesh* dm;
|
||||
float vm[4][4],wm[4][4];
|
||||
float life;
|
||||
|
||||
@@ -132,9 +132,12 @@ static PyObject *Text3d_getAlignment( BPy_Text3d * self );
|
||||
static PyObject *Text3d_setAlignment( BPy_Text3d * self, PyObject * args );
|
||||
static PyObject *Text3d_getFont( BPy_Text3d * self );
|
||||
static PyObject *Text3d_setFont( BPy_Text3d * self, PyObject * args );
|
||||
static PyObject *Text3d_getMaterial( BPy_Text3d * self, PyObject * value );
|
||||
static PyObject *Text3d_setMaterial( BPy_Text3d * self, PyObject * args );
|
||||
static PyObject *Text3d_addFrame( BPy_Text3d * self );
|
||||
static PyObject *Text3d_removeFrame( BPy_Text3d * self, PyObject * args );
|
||||
|
||||
|
||||
/*****************************************************************************/
|
||||
/* Python BPy_Text3d methods table: */
|
||||
/*****************************************************************************/
|
||||
@@ -210,6 +213,10 @@ static PyMethodDef BPy_Text3d_methods[] = {
|
||||
METH_NOARGS, "() - Gets font list for Text3d"},
|
||||
{"setFont", ( PyCFunction ) Text3d_setFont,
|
||||
METH_VARARGS, "() - Sets font for Text3d"},
|
||||
{"getMaterial", ( PyCFunction ) Text3d_getMaterial,
|
||||
METH_O, "() - Gets font list for Text3d"},
|
||||
{"setMaterial", ( PyCFunction ) Text3d_setMaterial,
|
||||
METH_VARARGS, "() - Sets font for Text3d"},
|
||||
{"addFrame", ( PyCFunction ) Text3d_addFrame,
|
||||
METH_NOARGS, "() - adds a new text frame"},
|
||||
{"removeFrame", ( PyCFunction ) Text3d_removeFrame,
|
||||
@@ -1132,6 +1139,45 @@ static PyObject *Text3d_setFont( BPy_Text3d * self, PyObject * args )
|
||||
Py_RETURN_NONE;
|
||||
}
|
||||
|
||||
/* todo, add style access, will be almost exact copy of these 2 */
|
||||
static PyObject *Text3d_getMaterial( BPy_Text3d * self, PyObject * value )
|
||||
{
|
||||
int index = PyInt_AsLong( value );
|
||||
if (index == -1 && PyErr_Occurred())
|
||||
return EXPP_ReturnPyObjError( PyExc_TypeError, "expected a character index" );
|
||||
|
||||
if (index < 0)
|
||||
index = self->curve->len + index;
|
||||
|
||||
if ( index < 0 || index >= self->curve->len )
|
||||
return EXPP_ReturnPyObjError( PyExc_IndexError, "character index out of range" );
|
||||
|
||||
return PyInt_FromLong( self->curve->strinfo[index].mat_nr );
|
||||
}
|
||||
|
||||
static PyObject *Text3d_setMaterial( BPy_Text3d * self, PyObject * args )
|
||||
{
|
||||
int index, mat_nr;
|
||||
if( !PyArg_ParseTuple( args, "ii",&index, &mat_nr) )
|
||||
return NULL; /* Python error is ok */
|
||||
|
||||
if (index < 0)
|
||||
index = self->curve->len + index;
|
||||
|
||||
if ( index < 0 || index >= self->curve->len )
|
||||
return EXPP_ReturnPyObjError( PyExc_IndexError, "character index out of range" );
|
||||
|
||||
if (mat_nr < 0)
|
||||
mat_nr = self->curve->totcol + mat_nr;
|
||||
|
||||
if ( mat_nr < 0 || mat_nr >= self->curve->totcol )
|
||||
return EXPP_ReturnPyObjError( PyExc_IndexError, "material index out of range" );
|
||||
|
||||
self->curve->strinfo[index].mat_nr = mat_nr;
|
||||
|
||||
Py_RETURN_NONE;
|
||||
}
|
||||
|
||||
static PyObject *Text3d_addFrame( BPy_Text3d * self )
|
||||
{
|
||||
Curve *cu = self->curve;
|
||||
|
||||
@@ -323,6 +323,21 @@ class Material:
|
||||
each color a list of 5 floats [0 - 1], [r,g,b,a,pos].
|
||||
The colorband can have between 1 and 31 colors.
|
||||
@type colorbandSpecular: list
|
||||
@type enabledTextures: list of integers
|
||||
@ivar enabledTextures: The texture channels enabled in this material.
|
||||
The attribute returns is list of integers in the range [0, 9], each
|
||||
number representing the respective enabled MTex entry (see
|
||||
L{getTextures()<getTextures>}). Enabling is done by assigning
|
||||
a list of ints or an empty list. Attempting to enable a channel
|
||||
which does not have a texture assigned to it will result in a
|
||||
ValueError exception.
|
||||
Example::
|
||||
mat.enabledTextures = [] # no texture channels are enabled
|
||||
mat.enabledTextures = [0, 6] # texture channels 0 and 6 are enabled
|
||||
ch = mat.enabledTextures
|
||||
ch.append(4)
|
||||
mat.enabledTextures = ch
|
||||
print mat.enabledTextures # will print: [0, 4, 6]
|
||||
|
||||
@ivar enableSSS: If True, subsurface scattering will be rendered on this material.
|
||||
@type enableSSS: bool
|
||||
@@ -1010,7 +1025,7 @@ class Material:
|
||||
|
||||
def setTexture(index, texture, texco, mapto):
|
||||
"""
|
||||
Assign a Blender Texture object to slot number 'number'.
|
||||
Assign a Blender Texture object to channel number 'number'.
|
||||
@type index: int
|
||||
@param index: material's texture index in [0, 9].
|
||||
@type texture: Blender Texture
|
||||
@@ -1033,7 +1048,7 @@ class Material:
|
||||
Get this Material's Texture list.
|
||||
@rtype: list of MTex
|
||||
@return: a list of Blender MTex objects. None is returned for each empty
|
||||
texture slot.
|
||||
texture channel.
|
||||
"""
|
||||
|
||||
def getScriptLinks (event):
|
||||
|
||||
@@ -521,6 +521,15 @@ class Vector:
|
||||
@return: Return a quaternion rotation from the vector and the track and up axis.
|
||||
"""
|
||||
|
||||
def reflect(mirror):
|
||||
"""
|
||||
Return the reflection vector from the mirror vector argument.
|
||||
@type mirror: Vector object
|
||||
@param mirror: This vector could be a normal from the reflecting surface.
|
||||
@rtype: Vector object matching the size of this vector.
|
||||
@return: The reflected vector.
|
||||
"""
|
||||
|
||||
class Euler:
|
||||
"""
|
||||
The Euler object
|
||||
|
||||
@@ -117,6 +117,10 @@ Example::
|
||||
attribute. Only one type can be selected at a time. Values are
|
||||
BOX, SPHERE, CYLINDER, CONE, and POLYHEDERON
|
||||
|
||||
@type EmptyShapes: readonly dictionary
|
||||
@var EmptyShapes: Constant dict used for with L{Object.emptyShape} attribute.
|
||||
Only one type can be selected at a time. Values are
|
||||
ARROW, ARROWS, AXES, CIRCLE, CONE, CUBE AND SPHERE
|
||||
"""
|
||||
|
||||
def New (type, name='type'):
|
||||
@@ -347,7 +351,7 @@ class Object:
|
||||
ob.layers = [] # object won't be visible
|
||||
ob.layers = [1, 4] # object visible only in layers 1 and 4
|
||||
ls = o.layers
|
||||
ls.append([10])
|
||||
ls.append(10)
|
||||
o.layers = ls
|
||||
print ob.layers # will print: [1, 4, 10]
|
||||
B{Note}: changes will only be visible after the screen (at least
|
||||
@@ -525,6 +529,8 @@ class Object:
|
||||
@ivar drawType: The object's drawing type.
|
||||
See L{DrawTypes} constant dict for values.
|
||||
@type drawType: int
|
||||
@ivar emptyShape: The empty drawing shape.
|
||||
See L{EmptyShapes} constant dict for values.
|
||||
@ivar parentType: The object's parent type. Read-only.
|
||||
See L{ParentTypes} constant dict for values.
|
||||
@type parentType: int
|
||||
|
||||
@@ -287,6 +287,26 @@ class Text3d:
|
||||
@param align: The new text3d's Alignment value.
|
||||
"""
|
||||
|
||||
def getMaterial(index):
|
||||
"""
|
||||
get the material index of a character.
|
||||
@rtype: int
|
||||
@return: the material index if the character
|
||||
@type index: int
|
||||
@param index: the index of the character in a string
|
||||
"""
|
||||
|
||||
def setMaterial(index, material_index):
|
||||
"""
|
||||
Set a characters material.
|
||||
@note: after changing this youll need to update the object with object.makeDisplayList() to see the changes.
|
||||
@rtype: None
|
||||
@type index: int
|
||||
@param index: the index of the character in a string
|
||||
@type material_index: int
|
||||
@param material_index: the material index set set the character.
|
||||
"""
|
||||
|
||||
def addFrame():
|
||||
"""
|
||||
Adds a text frame. maximum number of frames is 255.
|
||||
|
||||
@@ -42,6 +42,7 @@ char Vector_Resize3D_doc[] = "() - resize a vector to [x,y,z]";
|
||||
char Vector_Resize4D_doc[] = "() - resize a vector to [x,y,z,w]";
|
||||
char Vector_toPoint_doc[] = "() - create a new Point Object from this vector";
|
||||
char Vector_ToTrackQuat_doc[] = "(track, up) - extract a quaternion from the vector and the track and up axis";
|
||||
char Vector_reflect_doc[] = "(mirror) - return a vector reflected on the mirror normal";
|
||||
char Vector_copy_doc[] = "() - return a copy of the vector";
|
||||
/*-----------------------METHOD DEFINITIONS ----------------------*/
|
||||
struct PyMethodDef Vector_methods[] = {
|
||||
@@ -53,6 +54,7 @@ struct PyMethodDef Vector_methods[] = {
|
||||
{"resize4D", (PyCFunction) Vector_Resize4D, METH_NOARGS, Vector_Resize2D_doc},
|
||||
{"toPoint", (PyCFunction) Vector_toPoint, METH_NOARGS, Vector_toPoint_doc},
|
||||
{"toTrackQuat", ( PyCFunction ) Vector_ToTrackQuat, METH_VARARGS, Vector_ToTrackQuat_doc},
|
||||
{"reflect", ( PyCFunction ) Vector_reflect, METH_O, Vector_reflect_doc},
|
||||
{"copy", (PyCFunction) Vector_copy, METH_NOARGS, Vector_copy_doc},
|
||||
{"__copy__", (PyCFunction) Vector_copy, METH_NOARGS, Vector_copy_doc},
|
||||
{NULL, NULL, 0, NULL}
|
||||
@@ -273,7 +275,55 @@ PyObject *Vector_ToTrackQuat( VectorObject * self, PyObject * args )
|
||||
return newQuaternionObject(quat, Py_NEW);
|
||||
}
|
||||
|
||||
|
||||
/*----------------------------Vector.reflect(mirror) ----------------------
|
||||
return a reflected vector on the mirror normal
|
||||
((2 * DotVecs(vec, mirror)) * mirror) - vec
|
||||
using arithb.c would be nice here */
|
||||
PyObject *Vector_reflect( VectorObject * self, PyObject * value )
|
||||
{
|
||||
VectorObject *mirrvec;
|
||||
float mirror[3];
|
||||
float vec[3];
|
||||
float reflect[4] = {0.0f, 0.0f, 0.0f, 0.0f};
|
||||
float dot2;
|
||||
|
||||
/* for normalizing */
|
||||
int i;
|
||||
float norm = 0.0f;
|
||||
|
||||
if (!VectorObject_Check(value))
|
||||
return EXPP_ReturnPyObjError( PyExc_TypeError, "expected a vector argument" );
|
||||
|
||||
mirrvec = (VectorObject *)value;
|
||||
|
||||
mirror[0] = mirrvec->vec[0];
|
||||
mirror[1] = mirrvec->vec[1];
|
||||
if (mirrvec->size > 2) mirror[2] = mirrvec->vec[2];
|
||||
else mirror[2] = 0.0;
|
||||
|
||||
/* normalize, whos idea was it not to use arithb.c? :-/ */
|
||||
for(i = 0; i < 3; i++) {
|
||||
norm += mirror[i] * mirror[i];
|
||||
}
|
||||
norm = (float) sqrt(norm);
|
||||
for(i = 0; i < 3; i++) {
|
||||
mirror[i] /= norm;
|
||||
}
|
||||
/* done */
|
||||
|
||||
vec[0] = self->vec[0];
|
||||
vec[1] = self->vec[1];
|
||||
if (self->size > 2) vec[2] = self->vec[2];
|
||||
else vec[2] = 0.0;
|
||||
|
||||
dot2 = 2 * vec[0]*mirror[0]+vec[1]*mirror[1]+vec[2]*mirror[2];
|
||||
|
||||
reflect[0] = (dot2 * mirror[0]) - vec[0];
|
||||
reflect[1] = (dot2 * mirror[1]) - vec[1];
|
||||
reflect[2] = (dot2 * mirror[2]) - vec[2];
|
||||
|
||||
return newVectorObject(reflect, self->size, Py_NEW);
|
||||
}
|
||||
|
||||
/*----------------------------Vector.copy() --------------------------------------
|
||||
return a copy of the vector */
|
||||
|
||||
@@ -52,6 +52,7 @@ PyObject *Vector_Resize3D( VectorObject * self );
|
||||
PyObject *Vector_Resize4D( VectorObject * self );
|
||||
PyObject *Vector_toPoint( VectorObject * self );
|
||||
PyObject *Vector_ToTrackQuat( VectorObject * self, PyObject * args );
|
||||
PyObject *Vector_reflect( VectorObject * self, PyObject * value );
|
||||
PyObject *Vector_copy( VectorObject * self );
|
||||
PyObject *newVectorObject(float *vec, int size, int type);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user