Orange reported fix: Stride bone offset was blending with any strip, even
[blender.git] / source / blender / python / api2_2x / Armature.c
1 /*
2  * $Id$
3  *
4  * ***** BEGIN GPL/BL DUAL LICENSE BLOCK *****
5  *
6  * This program is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU General Public License
8  * as published by the Free Software Foundation; either version 2
9  * of the License, or (at your option) any later version. The Blender
10  * Foundation also sells licenses for use in proprietary software under
11  * the Blender License.  See http://www.blender.org/BL/ for information
12  * about this.
13  *
14  * This program is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17  * GNU General Public License for more details.
18  *
19  * You should have received a copy of the GNU General Public License
20  * along with this program; if not, write to the Free Software Foundation,
21  * Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
22  *
23  * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
24  * All rights reserved.
25  *
26  * ***** END GPL/BL DUAL LICENSE BLOCK *****
27 */
28
29 #include "Armature.h" //This must come first
30
31 #include "BKE_main.h"
32 #include "BKE_global.h"
33 #include "BKE_armature.h"
34 #include "BKE_library.h"
35 #include "BKE_depsgraph.h"
36 #include "BKE_utildefines.h"
37 #include "BLI_blenlib.h"
38 #include "BLI_arithb.h"
39 #include "MEM_guardedalloc.h"
40 #include "Bone.h"
41 #include "NLA.h"
42 #include "gen_utils.h"
43
44 #include "DNA_object_types.h" //This must come before BIF_editarmature.h...
45 #include "BIF_editarmature.h"
46
47 //------------------UNDECLARED EXTERNAL PROTOTYPES--------------------
48 //These are evil 'extern' declarations for functions with no anywhere
49 extern void free_editArmature(void);
50 extern void make_boneList(ListBase* list, ListBase *bones, EditBone *parent);
51 extern void editbones_to_armature (ListBase *list, Object *ob);
52
53 //------------------------ERROR CODES---------------------------------
54 //This is here just to make me happy and to have more consistant error strings :)
55 static const char sBoneDictError[] = "ArmatureType.bones - Error: ";
56 static const char sBoneDictBadArgs[] = "ArmatureType.bones - Bad Arguments: ";
57 static const char sArmatureError[] = "ArmatureType - Error: ";
58 static const char sArmatureBadArgs[] = "ArmatureType - Bad Arguments: ";
59 static const char sModuleError[] = "Blender.Armature - Error: ";
60 static const char sModuleBadArgs[] = "Blender.Armature - Bad Arguments: ";
61
62 //################## BonesDict_Type (internal) ########################
63 /*This is an internal psuedo-dictionary type that allows for manipulation
64 * of bones inside of an armature. It is a subobject of armature.
65 * i.e. Armature.bones['key']*/
66 //#####################################################################
67
68 //------------------METHOD IMPLEMENTATIONS-----------------------------
69 //------------------------Armature.bones.items()
70 //Returns a list of key:value pairs like dict.items()
71 PyObject* BonesDict_items(BPy_BonesDict *self)
72 {
73         if (self->editmode_flag){
74                 return PyDict_Items(self->editbonesMap); 
75         }else{
76                 return PyDict_Items(self->bonesMap); 
77         }
78 }
79 //------------------------Armature.bones.keys()
80 //Returns a list of keys like dict.keys()
81 PyObject* BonesDict_keys(BPy_BonesDict *self)
82 {
83         if (self->editmode_flag){
84                 return PyDict_Keys(self->editbonesMap);
85         }else{
86                 return PyDict_Keys(self->bonesMap);
87         }
88 }
89 //------------------------Armature.bones.values()
90 //Returns a list of values like dict.values()
91 PyObject* BonesDict_values(BPy_BonesDict *self)
92 {
93         if (self->editmode_flag){
94                 return PyDict_Values(self->editbonesMap);
95         }else{
96                 return PyDict_Values(self->bonesMap);
97         }
98 }
99 //------------------ATTRIBUTE IMPLEMENTATION---------------------------
100 //------------------TYPE_OBECT IMPLEMENTATION-----------------------
101 //------------------------tp_doc
102 //The __doc__ string for this object
103 static char BPy_BonesDict_doc[] = "This is an internal subobject of armature\
104 designed to act as a Py_Bone dictionary.";
105
106 //------------------------tp_methods
107 //This contains a list of all methods the object contains
108 static PyMethodDef BPy_BonesDict_methods[] = {
109         {"items", (PyCFunction) BonesDict_items, METH_NOARGS, 
110                 "() - Returns the key:value pairs from the dictionary"},
111         {"keys", (PyCFunction) BonesDict_keys, METH_NOARGS, 
112                 "() - Returns the keys the dictionary"},
113         {"values", (PyCFunction) BonesDict_values, METH_NOARGS, 
114                 "() - Returns the values from the dictionary"},
115         {NULL}
116 };
117 //-----------------(internal)
118 static int BoneMapping_Init(PyObject *dictionary, ListBase *bones){
119         Bone *bone = NULL;
120         PyObject *py_bone = NULL;
121
122         for (bone = bones->first; bone; bone = bone->next){
123                 py_bone = PyBone_FromBone(bone);
124                 if (!py_bone)
125                         return -1;
126
127                 if(PyDict_SetItem(dictionary, 
128                         PyString_FromString(bone->name), py_bone) == -1){
129                         return -1;
130                 }
131                 Py_DECREF(py_bone);
132                 if (bone->childbase.first) 
133                         BoneMapping_Init(dictionary, &bone->childbase);
134         }
135         return 0;
136 }
137 //-----------------(internal)
138 static int EditBoneMapping_Init(PyObject *dictionary, ListBase *editbones){
139         EditBone *editbone = NULL;
140         PyObject *py_editbone = NULL;
141
142         for (editbone = editbones->first; editbone; editbone = editbone->next){
143                 py_editbone = PyEditBone_FromEditBone(editbone);
144                 if (!py_editbone)
145                         return -1;
146
147                 if(PyDict_SetItem(dictionary, 
148                         PyString_FromString(editbone->name), py_editbone) == -1){
149                         return -1;
150                 }
151                 Py_DECREF(py_editbone);
152         }
153         return 0;
154 }
155 //----------------- BonesDict_InitBones
156 static int BonesDict_InitBones(BPy_BonesDict *self)
157 {
158         PyDict_Clear(self->bonesMap);
159         if (BoneMapping_Init(self->bonesMap, self->bones) == -1)
160                 return 0;
161         return 1;
162
163 //----------------- BonesDict_InitEditBones
164 static int BonesDict_InitEditBones(BPy_BonesDict *self)
165 {
166         PyDict_Clear(self->editbonesMap);
167         if (EditBoneMapping_Init(self->editbonesMap, &self->editbones) == -1)
168                 return 0;
169         return 1;
170 }
171 //------------------------tp_repr
172 //This is the string representation of the object
173 static PyObject *BonesDict_repr(BPy_BonesDict *self)
174 {
175         char buffer[128], str[4096];
176         PyObject *key, *value;
177         int pos = 0;
178
179         BLI_strncpy(str,"",4096);
180         sprintf(buffer, "[Bone Dict: {");
181         strcat(str,buffer);
182         if (self->editmode_flag){
183                 while (PyDict_Next(self->editbonesMap, &pos, &key, &value)) {
184                         sprintf(buffer, "%s : %s, ", PyString_AsString(key), 
185                                 PyString_AsString(value->ob_type->tp_repr(value)));
186                         strcat(str,buffer);
187                 }
188         }else{
189                 while (PyDict_Next(self->bonesMap, &pos, &key, &value)) {
190                         sprintf(buffer, "%s : %s, ", PyString_AsString(key), 
191                                 PyString_AsString(value->ob_type->tp_repr(value)));
192                         strcat(str,buffer);
193                 }
194         }
195         sprintf(buffer, "}]\n");
196         strcat(str,buffer);
197         return PyString_FromString(str);
198 }
199
200 //------------------------tp_dealloc
201 //This tells how to 'tear-down' our object when ref count hits 0
202 static void BonesDict_dealloc(BPy_BonesDict * self)
203 {
204         Py_DECREF(self->bonesMap);
205         Py_DECREF(self->editbonesMap);
206         BLI_freelistN(&self->editbones); 
207         BonesDict_Type.tp_free(self);
208         return;
209 }
210 //------------------------mp_length
211 //This gets the size of the dictionary
212 int BonesDict_len(BPy_BonesDict *self)
213 {
214         if (self->editmode_flag){
215                 return BLI_countlist(&self->editbones);
216         }else{
217                 return BLI_countlist(self->bones);
218         }
219 }
220 //-----------------------mp_subscript
221 //This defines getting a bone from the dictionary - x = Bones['key']
222 PyObject *BonesDict_GetItem(BPy_BonesDict *self, PyObject* key)
223
224         PyObject *value = NULL;
225
226         if (self->editmode_flag){
227                 value = PyDict_GetItem(self->editbonesMap, key);
228         }else{
229                 value = PyDict_GetItem(self->bonesMap, key);
230         }
231         if(value == NULL){
232         return EXPP_incr_ret(Py_None);
233         }
234         return EXPP_incr_ret(value);
235 }
236 //-----------------------mp_ass_subscript
237 //This does dict assignment - Bones['key'] = value
238 int BonesDict_SetItem(BPy_BonesDict *self, PyObject *key, PyObject *value)
239 {
240         BPy_EditBone *editbone_for_deletion;
241         struct EditBone *editbone = NULL;
242         char *key_str = "";
243
244         if (self->editmode_flag){
245                 //Get the key name
246                 if(key && PyString_Check(key)){
247                         key_str = PyString_AsString(key);
248                 }else{
249                         goto AttributeError;
250                 }
251                 //parse value for assignment
252                 if (value && EditBoneObject_Check(value)){
253                         //create a new editbone
254                         editbone = MEM_callocN(sizeof(EditBone), "eBone");
255                         BLI_strncpy(editbone->name, key_str, 32);
256                         unique_editbone_name(editbone->name);
257                         editbone->dist = ((BPy_EditBone*)value)->dist;
258                         editbone->ease1 = ((BPy_EditBone*)value)->ease1;
259                         editbone->ease2 = ((BPy_EditBone*)value)->ease2;
260                         editbone->flag = ((BPy_EditBone*)value)->flag;
261                         editbone->parent = ((BPy_EditBone*)value)->parent;
262                         editbone->rad_head = ((BPy_EditBone*)value)->rad_head;
263                         editbone->rad_tail = ((BPy_EditBone*)value)->rad_tail;
264                         editbone->roll = ((BPy_EditBone*)value)->roll;
265                         editbone->segments = ((BPy_EditBone*)value)->segments;
266                         editbone->weight = ((BPy_EditBone*)value)->weight;
267                         editbone->xwidth = ((BPy_EditBone*)value)->xwidth;
268                         editbone->zwidth = ((BPy_EditBone*)value)->zwidth;
269                         VECCOPY(editbone->head, ((BPy_EditBone*)value)->head);
270                         VECCOPY(editbone->tail, ((BPy_EditBone*)value)->tail);
271
272                         //set object pointer
273                         ((BPy_EditBone*)value)->editbone = editbone;
274
275                         //fix the bone's head position if flags indicate that it is 'connected'
276                         if (editbone->flag & BONE_CONNECTED){
277                                 if(!editbone->parent){
278                                         ((BPy_EditBone*)value)->editbone = NULL;
279                                         MEM_freeN(editbone);
280                                         goto AttributeError3;
281                                 }else{
282                                         VECCOPY(editbone->head, editbone->parent->tail);
283                                 }
284                         }
285
286                         //set in editbonelist
287                         BLI_addtail(&self->editbones, editbone);
288
289                         //set the new editbone in the mapping
290                         if(PyDict_SetItemString(self->editbonesMap, key_str, value) == -1){
291                                 ((BPy_EditBone*)value)->editbone = NULL;
292                                 BLI_freelinkN(&self->editbones, editbone);
293                                 goto RuntimeError;
294                         }
295                 }else if(!value){
296                         //they are trying to delete the bone using 'del'
297                         if(PyDict_GetItem(self->editbonesMap, key) != NULL){
298                                 /*first kill the datastruct then remove the item from the dict
299                                 and wait for GC to pick it up.
300                                 We have to delete the datastruct here because the tp_dealloc
301                                 doesn't handle it*/
302                                 editbone_for_deletion = (BPy_EditBone*)PyDict_GetItem(self->editbonesMap, key);
303                                 /*this is ugly but you have to set the parent to NULL for else 
304                                 editbones_to_armature will crash looking for this bone*/
305                                 for (editbone = self->editbones.first; editbone; editbone = editbone->next){
306                                         if (editbone->parent == editbone_for_deletion->editbone)
307                                                 editbone->parent = NULL;
308                                             /*any parent's were connected to this we must remove the flag
309                                             or else the 'root' ball doesn't get draw*/
310                                             if (editbone->flag & BONE_CONNECTED)
311                                                         editbone->flag &= ~BONE_CONNECTED;
312                                 }
313                                 BLI_freelinkN(&self->editbones, editbone_for_deletion->editbone);
314                                 if(PyDict_DelItem(self->editbonesMap, key) == -1)
315                                         goto RuntimeError;
316                         }else{
317                                 goto KeyError;
318                         }
319                 }
320                 return 0;
321         }else{
322                 goto AttributeError2;
323         }
324
325 KeyError:
326 return EXPP_intError(PyExc_KeyError, "%s%s%s%s", 
327             sBoneDictError,  "The key: ", key_str, " is not present in this dictionary!");
328 RuntimeError:
329         return EXPP_intError(PyExc_RuntimeError, "%s%s", 
330                 sBoneDictError,  "Unable to access dictionary!");
331 AttributeError:
332         return EXPP_intError(PyExc_AttributeError, "%s%s", 
333                 sBoneDictBadArgs,  "Expects EditboneType Object");
334 AttributeError2:
335         return EXPP_intError(PyExc_AttributeError, "%s%s", 
336                 sBoneDictBadArgs,  "You must call makeEditable() first");
337 AttributeError3:
338         return EXPP_intError(PyExc_AttributeError, "%s%s", 
339                 sBoneDictBadArgs,  "The 'connected' flag is set but the bone has no parent!");
340 }
341 //------------------TYPE_OBECT DEFINITION--------------------------
342 //Mapping Protocol
343 static PyMappingMethods BonesDict_MapMethods = {
344         (inquiry) BonesDict_len,                                        //mp_length
345         (binaryfunc)BonesDict_GetItem,          //mp_subscript
346         (objobjargproc)BonesDict_SetItem,       //mp_ass_subscript
347 };
348 //BonesDict TypeObject
349 PyTypeObject BonesDict_Type = {
350         PyObject_HEAD_INIT(NULL)                        //tp_head
351         0,                                                                                              //tp_internal
352         "BonesDict",                                                            //tp_name
353         sizeof(BPy_BonesDict),                                  //tp_basicsize
354         0,                                                                                              //tp_itemsize
355         (destructor)BonesDict_dealloc,          //tp_dealloc
356         0,                                                                                              //tp_print
357         0,                                                                                              //tp_getattr
358         0,                                                                                              //tp_setattr
359         0,                                                                                              //tp_compare
360         (reprfunc) BonesDict_repr,                              //tp_repr
361         0,                                                                                              //tp_as_number
362         0,                                                                                              //tp_as_sequence
363         &BonesDict_MapMethods,                          //tp_as_mapping
364         0,                                                                                              //tp_hash
365         0,                                                                                              //tp_call
366         0,                                                                                              //tp_str
367         0,                                                                                              //tp_getattro
368         0,                                                                                              //tp_setattro
369         0,                                                                                              //tp_as_buffer
370         Py_TPFLAGS_DEFAULT,                                     //tp_flags
371         BPy_BonesDict_doc,                                              //tp_doc
372         0,                                                                                              //tp_traverse
373         0,                                                                                              //tp_clear
374         0,                                                                                              //tp_richcompare
375         0,                                                                                              //tp_weaklistoffset
376         0,                                                                                              //tp_iter
377         0,                                                                                              //tp_iternext
378         BPy_BonesDict_methods,                          //tp_methods
379         0,                                                                                              //tp_members
380         0,                                                                                              //tp_getset
381         0,                                                                                              //tp_base
382         0,                                                                                              //tp_dict
383         0,                                                                                              //tp_descr_get
384         0,                                                                                              //tp_descr_set
385         0,                                                                                              //tp_dictoffset
386         0,                                                              //tp_init
387         0,                                                                                              //tp_alloc
388         0,                                                                                              //tp_new
389         0,                                                                                              //tp_free
390         0,                                                                                              //tp_is_gc
391         0,                                                                                              //tp_bases
392         0,                                                                                              //tp_mro
393         0,                                                                                              //tp_cache
394         0,                                                                                              //tp_subclasses
395         0,                                                                                              //tp_weaklist
396         0                                                                                               //tp_del
397 };
398 //-----------------------PyBonesDict_FromPyArmature
399 static PyObject *PyBonesDict_FromPyArmature(BPy_Armature *py_armature)
400 {
401         BPy_BonesDict *py_BonesDict = NULL;
402
403         //create py object
404         py_BonesDict = (BPy_BonesDict *)BonesDict_Type.tp_alloc(&BonesDict_Type, 0); 
405         if (!py_BonesDict)
406                 goto RuntimeError;
407
408         //create internal dictionaries
409         py_BonesDict->bonesMap = PyDict_New();
410         py_BonesDict->editbonesMap = PyDict_New();
411         if (!py_BonesDict->bonesMap || !py_BonesDict->editbonesMap)
412                 goto RuntimeError;
413
414         //set listbase pointer
415         py_BonesDict->bones = &py_armature->armature->bonebase;
416
417         //now that everything is setup - init the mappings
418         if (!BonesDict_InitBones(py_BonesDict))
419                 goto RuntimeError;
420         if (!BonesDict_InitEditBones(py_BonesDict))
421                 goto RuntimeError;
422
423         //set editmode flag
424         py_BonesDict->editmode_flag = 0; 
425
426         return (PyObject*)py_BonesDict;
427
428 RuntimeError:
429         return EXPP_objError(PyExc_RuntimeError, "%s%s", 
430                 sBoneDictError, "Failed to create class");
431 }
432
433 //######################### Armature_Type #############################
434 /*This type represents a thin wrapper around bArmature data types
435 * internal to blender. It contains the psuedo-dictionary BonesDict
436 * as an assistant in manipulating it's own bone collection*/
437 //#################################################################
438
439 //------------------METHOD IMPLEMENTATION------------------------------
440 //------------------------Armature.makeEditable()
441 static PyObject *Armature_makeEditable(BPy_Armature *self)
442 {
443         if (self->armature->flag & ARM_EDITMODE)
444                 goto AttributeError;
445
446         make_boneList(&self->Bones->editbones, self->Bones->bones, NULL);
447         if (!BonesDict_InitEditBones(self->Bones))
448                 return NULL;
449         self->Bones->editmode_flag = 1;
450         return EXPP_incr_ret(Py_None);
451
452 AttributeError:
453         return EXPP_objError(PyExc_AttributeError, "%s%s", 
454                 sArmatureBadArgs, "The armature cannot be placed manually in editmode before you call makeEditable()!");
455 }
456 //------------------------Armature.update()
457 //This is a bit ugly because you need an object link to do this
458 static PyObject *Armature_update(BPy_Armature *self)
459 {
460         Object *obj = NULL;
461
462         for (obj = G.main->object.first; obj; obj = obj->id.next){
463                 if (obj->data == self->armature)
464                         break;
465         }
466         if (obj){
467                 editbones_to_armature (&self->Bones->editbones, obj);
468                 if (!BonesDict_InitBones(self->Bones))
469                         return NULL;
470                 self->Bones->editmode_flag = 0;
471         }else{
472                 goto AttributeError;
473         }
474         return EXPP_incr_ret(Py_None);
475
476 AttributeError:
477         return EXPP_objError(PyExc_AttributeError, "%s%s", 
478                 sArmatureBadArgs, "The armature must be linked to an object before you can save changes!");
479 }
480 //------------------ATTRIBUTE IMPLEMENTATION---------------------------
481 //------------------------Armature.autoIK (getter)
482 static PyObject *Armature_getAutoIK(BPy_Armature *self, void *closure)
483 {
484         if (self->armature->flag & ARM_AUTO_IK)
485                 return EXPP_incr_ret(Py_True);
486         else
487                 return EXPP_incr_ret(Py_False);
488 }
489 //------------------------Armature.autoIK (setter)
490 static int Armature_setAutoIK(BPy_Armature *self, PyObject *value, void *closure)
491 {
492         if(value){
493                 if(PyBool_Check(value)){
494                         if (value == Py_True){
495                                 self->armature->flag |= ARM_AUTO_IK;
496                                 return 0;
497                         }else if (value == Py_False){
498                                 self->armature->flag &= ~ARM_AUTO_IK;
499                                 return 0;
500                         }
501                 }
502         }
503         goto AttributeError;
504
505 AttributeError:
506         return EXPP_intError(PyExc_AttributeError, "%s%s", 
507                 sArmatureBadArgs, "Expects True or False");
508 }
509 //------------------------Armature.mirrorEdit (getter)
510 static PyObject *Armature_getMirrorEdit(BPy_Armature *self, void *closure)
511 {
512         if (self->armature->flag & ARM_MIRROR_EDIT)
513                 return EXPP_incr_ret(Py_True);
514         else
515                 return EXPP_incr_ret(Py_False);
516 }
517 //------------------------Armature.mirrorEdit (setter)
518 static int Armature_setMirrorEdit(BPy_Armature *self, PyObject *value, void *closure)
519 {
520         if(value){
521                 if(PyBool_Check(value)){
522                         if (value == Py_True){
523                                 self->armature->flag |= ARM_MIRROR_EDIT;
524                                 return 0;
525                         }else if (value == Py_False){
526                                 self->armature->flag &= ~ARM_MIRROR_EDIT;
527                                 return 0;
528                         }
529                 }
530         }
531         goto AttributeError;
532
533 AttributeError:
534         return EXPP_intError(PyExc_AttributeError, "%s%s", 
535                 sArmatureBadArgs, "Expects True or False");
536 }
537 //------------------------Armature.drawType (getter)
538 static PyObject *Armature_getDrawType(BPy_Armature *self, void *closure)
539 {
540         if (self->armature->drawtype == ARM_OCTA){
541                 return EXPP_GetModuleConstant("Blender.Armature", "OCTAHEDRON") ;
542         }else if (self->armature->drawtype == ARM_LINE){
543                 return EXPP_GetModuleConstant("Blender.Armature", "STICK") ;
544         }else if (self->armature->drawtype == ARM_B_BONE){
545                 return EXPP_GetModuleConstant("Blender.Armature", "BBONE") ;
546         }else if (self->armature->drawtype == ARM_ENVELOPE){
547                 return EXPP_GetModuleConstant("Blender.Armature", "ENVELOPE") ;
548         }else{
549                 goto RuntimeError;
550         }
551
552 RuntimeError:
553         return EXPP_objError(PyExc_RuntimeError, "%s%s%s", 
554                 sArmatureError, "drawType: ", "Internal failure!");
555 }
556 //------------------------Armature.drawType (setter)
557 static int Armature_setDrawType(BPy_Armature *self, PyObject *value, void *closure)
558 {
559         PyObject *val = NULL, *name = NULL;
560         long numeric_value;
561
562         if(value){
563                 if(BPy_Constant_Check(value)){
564                         name = PyDict_GetItemString(((BPy_constant*)value)->dict, "name");
565                         if (!STREQ2(PyString_AsString(name), "OCTAHEDRON", "STICK") &&
566                                 !STREQ2(PyString_AsString(name), "BBONE", "ENVELOPE"))
567                                 goto ValueError;
568                         val = PyDict_GetItemString(((BPy_constant*)value)->dict, "value");
569                         if (PyInt_Check(val)){
570                                 numeric_value = PyInt_AS_LONG(val);
571                                 self->armature->drawtype = (int)numeric_value;
572                                 return 0;
573                         }
574                 }
575         }
576         goto AttributeError;
577
578 AttributeError:
579         return EXPP_intError(PyExc_AttributeError, "%s%s", 
580                 sArmatureBadArgs, "Expects module constant");
581
582 ValueError:
583         return EXPP_intError(PyExc_AttributeError, "%s%s", 
584                 sArmatureBadArgs, "Argument must be the constant OCTAHEDRON, STICK, BBONE, or ENVELOPE");
585 }
586 //------------------------Armature.ghostStep (getter)
587 static PyObject *Armature_getStep(BPy_Armature *self, void *closure)
588 {
589         return PyInt_FromLong((long)self->armature->ghostsize);
590 }
591 //------------------------Armature.ghostStep (setter)
592 static int Armature_setStep(BPy_Armature *self, PyObject *value, void *closure)
593 {
594         long numerical_value;
595
596         if(value){
597                 if(PyInt_Check(value)){
598                         numerical_value = PyInt_AS_LONG(value);
599                         if (numerical_value > 20.0f || numerical_value < 1.0f)
600                                 goto ValueError;
601                         self->armature->ghostsize = (short)numerical_value;
602                         return 0;
603                 }
604         }
605         goto AttributeError;
606
607 AttributeError:
608         return EXPP_intError(PyExc_AttributeError, "%s%s", 
609                 sArmatureBadArgs, "Expects Integer");
610
611 ValueError:
612         return EXPP_intError(PyExc_AttributeError, "%s%s", 
613                 sArmatureBadArgs, "Argument must fall within 1-20");
614 }
615 //------------------------Armature.ghost (getter)
616 static PyObject *Armature_getGhost(BPy_Armature *self, void *closure)
617 {
618         return PyInt_FromLong((long)self->armature->ghostep);
619 }
620 //------------------------Armature.ghost (setter)
621 static int Armature_setGhost(BPy_Armature *self, PyObject *value, void *closure)
622 {
623         long numerical_value;
624
625         if(value){
626                 if(PyInt_Check(value)){
627                         numerical_value = PyInt_AS_LONG(value);
628                         if (numerical_value > 30.0f || numerical_value < 0.0f)
629                                 goto ValueError;
630                         self->armature->ghostep = (short)numerical_value;
631                         return 0;
632                 }
633         }
634         goto AttributeError;
635
636 AttributeError:
637         return EXPP_intError(PyExc_AttributeError, "%s%s", 
638                 sArmatureBadArgs, "Expects Integer");
639
640 ValueError:
641         return EXPP_intError(PyExc_AttributeError, "%s%s", 
642                 sArmatureBadArgs, "Argument must fall within 0-30");
643 }
644 //------------------------Armature.drawNames (getter)
645 static PyObject *Armature_getDrawNames(BPy_Armature *self, void *closure)
646 {
647         if (self->armature->flag & ARM_DRAWNAMES)
648                 return EXPP_incr_ret(Py_True);
649         else
650                 return EXPP_incr_ret(Py_False);
651 }
652 //------------------------Armature.drawNames (setter)
653 static int Armature_setDrawNames(BPy_Armature *self, PyObject *value, void *closure)
654 {
655         if(value){
656                 if(PyBool_Check(value)){
657                         if (value == Py_True){
658                                 self->armature->flag |= ARM_DRAWNAMES;
659                                 return 0;
660                         }else if (value == Py_False){
661                                 self->armature->flag &= ~ARM_DRAWNAMES;
662                                 return 0;
663                         }
664                 }
665         }
666         goto AttributeError;
667
668 AttributeError:
669         return EXPP_intError(PyExc_AttributeError, "%s%s", 
670                 sArmatureBadArgs, "Expects True or False");
671 }
672 //------------------------Armature.drawAxes (getter)
673 static PyObject *Armature_getDrawAxes(BPy_Armature *self, void *closure)
674 {
675         if (self->armature->flag & ARM_DRAWAXES)
676                 return EXPP_incr_ret(Py_True);
677         else
678                 return EXPP_incr_ret(Py_False);
679 }
680 //------------------------Armature.drawAxes (setter)
681 static int Armature_setDrawAxes(BPy_Armature *self, PyObject *value, void *closure)
682 {
683         if(value){
684                 if(PyBool_Check(value)){
685                         if (value == Py_True){
686                                 self->armature->flag |= ARM_DRAWAXES;
687                                 return 0;
688                         }else if (value == Py_False){
689                                 self->armature->flag &= ~ARM_DRAWAXES;
690                                 return 0;
691                         }
692                 }
693         }
694         goto AttributeError;
695
696 AttributeError:
697         return EXPP_intError(PyExc_AttributeError, "%s%s", 
698                 sArmatureBadArgs, "Expects True or False");
699 }
700 //------------------------Armature.delayDeform (getter)
701 static PyObject *Armature_getDelayDeform(BPy_Armature *self, void *closure)
702 {
703         if (self->armature->flag & ARM_DELAYDEFORM)
704                 return EXPP_incr_ret(Py_True);
705         else
706                 return EXPP_incr_ret(Py_False);
707 }
708 //------------------------Armature.delayDeform (setter)
709 static int Armature_setDelayDeform(BPy_Armature *self, PyObject *value, void *closure)
710 {
711         if(value){
712                 if(PyBool_Check(value)){
713                         if (value == Py_True){
714                                 self->armature->flag |= ARM_DELAYDEFORM;
715                                 return 0;
716                         }else if (value == Py_False){
717                                 self->armature->flag &= ~ARM_DELAYDEFORM;
718                                 return 0;
719                         }
720                 }
721         }
722         goto AttributeError;
723
724 AttributeError:
725         return EXPP_intError(PyExc_AttributeError, "%s%s", 
726                 sArmatureBadArgs, "Expects True or False");
727 }
728 //------------------------Armature.restPosition (getter)
729 static PyObject *Armature_getRestPosition(BPy_Armature *self, void *closure)
730 {
731         if (self->armature->flag & ARM_RESTPOS)
732                 return EXPP_incr_ret(Py_True);
733         else
734                 return EXPP_incr_ret(Py_False);
735 }
736 //------------------------Armature.restPosition (setter)
737 static int Armature_setRestPosition(BPy_Armature *self, PyObject *value, void *closure)
738 {
739         if(value){
740                 if(PyBool_Check(value)){
741                         if (value == Py_True){
742                                 self->armature->flag |= ARM_RESTPOS;
743                                 return 0;
744                         }else if (value == Py_False){
745                                 self->armature->flag &= ~ARM_RESTPOS;
746                                 return 0;
747                         }
748                 }
749         }
750         goto AttributeError;
751
752 AttributeError:
753         return EXPP_intError(PyExc_AttributeError, "%s%s", 
754                 sArmatureBadArgs, "Expects True or False");
755 }
756 //------------------------Armature.envelopes (getter)
757 static PyObject *Armature_getEnvelopes(BPy_Armature *self, void *closure)
758 {
759         if (self->armature->deformflag & ARM_DEF_ENVELOPE)
760                 return EXPP_incr_ret(Py_True);
761         else
762                 return EXPP_incr_ret(Py_False);
763 }
764 //------------------------Armature.envelopes (setter)
765 static int Armature_setEnvelopes(BPy_Armature *self, PyObject *value, void *closure)
766 {
767         if(value){
768                 if(PyBool_Check(value)){
769                         if (value == Py_True){
770                                 self->armature->deformflag |= ARM_DEF_ENVELOPE;
771                                 return 0;
772                         }else if (value == Py_False){
773                                 self->armature->deformflag &= ~ARM_DEF_ENVELOPE;
774                                 return 0;
775                         }
776                 }
777         }
778         goto AttributeError;
779
780 AttributeError:
781         return EXPP_intError(PyExc_AttributeError, "%s%s", 
782                 sArmatureBadArgs, "Expects True or False");
783 }
784 //------------------------Armature.vertexGroups (getter)
785 static PyObject *Armature_getVertexGroups(BPy_Armature *self, void *closure)
786 {
787         if (self->armature->deformflag & ARM_DEF_VGROUP)
788                 return EXPP_incr_ret(Py_True);
789         else
790                 return EXPP_incr_ret(Py_False);
791 }
792 //------------------------Armature.vertexGroups (setter)
793 static int Armature_setVertexGroups(BPy_Armature *self, PyObject *value, void *closure)
794 {
795         if(value){
796                 if(PyBool_Check(value)){
797                         if (value == Py_True){
798                                 self->armature->deformflag |= ARM_DEF_VGROUP;
799                                 return 0;
800                         }else if (value == Py_False){
801                                 self->armature->deformflag &= ~ARM_DEF_VGROUP;
802                                 return 0;
803                         }
804                 }
805         }
806         goto AttributeError;
807
808 AttributeError:
809         return EXPP_intError(PyExc_AttributeError, "%s%s", 
810                 sArmatureBadArgs, "Expects True or False");
811 }
812 //------------------------Armature.name (getter)
813 //Gets the name of the armature
814 static PyObject *Armature_getName(BPy_Armature *self, void *closure)
815 {
816     return PyString_FromString(self->armature->id.name +2); //*new*
817 }
818 //------------------------Armature.name (setter)
819 //Sets the name of the armature
820 static int Armature_setName(BPy_Armature *self, PyObject *value, void *closure)
821 {
822         char buffer[24];
823         char *name = "";
824
825         if(value){
826                 if(PyString_Check(value)){
827                         name = PyString_AsString(value);
828                         PyOS_snprintf(buffer, sizeof(buffer), "%s", name);
829                         rename_id(&self->armature->id, buffer);
830                         return 0; 
831                 }
832         }
833         goto AttributeError;
834
835 AttributeError:
836         return EXPP_intError(PyExc_AttributeError, "%s%s", 
837                 sArmatureBadArgs, "Expects string");
838 }
839 //------------------------Armature.bones (getter)
840 //Gets the name of the armature
841 static PyObject *Armature_getBoneDict(BPy_Armature *self, void *closure)
842 {
843     return EXPP_incr_ret((PyObject*)self->Bones);
844 }
845 //------------------------Armature.bones (setter)
846 //Sets the name of the armature
847 /*TODO*/
848 /*Copy Bones through x = y*/
849 static int Armature_setBoneDict(BPy_Armature *self, PyObject *value, void *closure)
850 {
851         goto AttributeError;
852
853 AttributeError:
854         return EXPP_intError(PyExc_AttributeError, "%s%s", 
855                 sArmatureError, "You are not allowed to change the .Bones attribute");
856 }
857 //------------------TYPE_OBECT IMPLEMENTATION--------------------------
858 //------------------------tp_doc
859 //The __doc__ string for this object
860 static char BPy_Armature_doc[] = "This object wraps a Blender Armature object.";
861 //------------------------tp_methods
862 //This contains a list of all methods the object contains
863 static PyMethodDef BPy_Armature_methods[] = {
864         {"makeEditable", (PyCFunction) Armature_makeEditable, METH_NOARGS, 
865                 "() - Unlocks the ability to modify armature bones"},
866         {"update", (PyCFunction) Armature_update, METH_NOARGS, 
867                 "() - Rebuilds the armature based on changes to bones since the last call to makeEditable"},
868         {NULL}
869 };
870 //------------------------tp_getset
871 //This contains methods for attributes that require checking
872 static PyGetSetDef BPy_Armature_getset[] = {
873         {"name", (getter)Armature_getName, (setter)Armature_setName, 
874                 "The armature's name", NULL},
875         {"bones", (getter)Armature_getBoneDict, (setter)Armature_setBoneDict, 
876                 "The armature's Bone dictionary", NULL},
877         {"vertexGroups", (getter)Armature_getVertexGroups, (setter)Armature_setVertexGroups, 
878                 "Enable/Disable vertex group defined deformation", NULL},
879         {"envelopes", (getter)Armature_getEnvelopes, (setter)Armature_setEnvelopes, 
880                 "Enable/Disable bone envelope defined deformation", NULL},
881         {"restPosition", (getter)Armature_getRestPosition, (setter)Armature_setRestPosition, 
882                 "Show armature rest position - disables posing", NULL},
883         {"delayDeform", (getter)Armature_getDelayDeform, (setter)Armature_setDelayDeform, 
884                 "Don't deform children when manipulating bones in pose mode", NULL},
885         {"drawAxes", (getter)Armature_getDrawAxes, (setter)Armature_setDrawAxes, 
886                 "Enable/Disable  drawing  the bone axes", NULL},
887         {"drawNames", (getter)Armature_getDrawNames, (setter)Armature_setDrawNames, 
888                 "Enable/Disable  drawing the bone names", NULL},
889         {"ghost", (getter)Armature_getGhost, (setter)Armature_setGhost, 
890                 "Draw a number of ghosts around the current frame for current Action", NULL},
891         {"ghostStep", (getter)Armature_getStep, (setter)Armature_setStep, 
892                 "The number of frames between ghost instances", NULL},
893         {"drawType", (getter)Armature_getDrawType, (setter)Armature_setDrawType, 
894                 "The type of drawing currently applied to the armature", NULL},
895         {"mirrorEdit", (getter)Armature_getMirrorEdit, (setter)Armature_setMirrorEdit, 
896                 "Enable/Disable X-axis mirrored editing", NULL},
897         {"autoIK", (getter)Armature_getAutoIK, (setter)Armature_setAutoIK, 
898                 "Adds temporal IK chains while grabbing bones", NULL},
899         {NULL}
900 };
901 //------------------------tp_new
902 //This methods creates a new object (note it does not initialize it - only the building)
903 //This can be called through python by myObject.__new__() however, tp_init is not called
904 static PyObject *Armature_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
905 {
906         BPy_Armature *py_armature = NULL;
907         bArmature *bl_armature;
908
909         bl_armature = add_armature();
910         if(bl_armature) {
911                 bl_armature->id.us = 0; // return count to 0 - add_armature() inc'd it 
912
913                 py_armature = (BPy_Armature*)type->tp_alloc(type, 0); //*new*
914                 if (py_armature == NULL)
915                         goto RuntimeError;
916
917                 py_armature->armature = bl_armature;
918
919                 //create armature.bones
920                 py_armature->Bones = (BPy_BonesDict*)PyBonesDict_FromPyArmature(py_armature);
921                 if (!py_armature->Bones)
922                         goto RuntimeError;
923
924         } else {
925                 goto RuntimeError;
926         }
927         return (PyObject*)py_armature; 
928
929 RuntimeError:
930         return EXPP_objError(PyExc_RuntimeError, "%s%s%s", 
931                 sArmatureError, " __new__: ", "couldn't create Armature Data in Blender");
932 }
933 //------------------------tp_init
934 //This methods does initialization of the new object
935 //This method will get called in python by 'myObject(argument, keyword=value)'
936 //tp_new will be automatically called before this
937 static int Armature_init(BPy_Armature *self, PyObject *args, PyObject *kwds)
938 {
939         char buf[21];
940         char *name = "myArmature";
941         static char *kwlist[] = {"name", NULL};
942
943         if(!PyArg_ParseTupleAndKeywords(args, kwds, "|s", kwlist, &name)){
944                 goto AttributeError;
945         }
946
947         //rename the armature if a name is supplied
948         if(!BLI_streq(name, "myArmature")){
949                 PyOS_snprintf(buf, sizeof(buf), "%s", name);
950                 rename_id(&self->armature->id, buf);
951         }
952         return 0;
953
954 AttributeError:
955         return EXPP_intError(PyExc_AttributeError, "%s%s%s", 
956                 sArmatureBadArgs, " __init__: ", "Expects string(name)");
957 }
958 //------------------------tp_richcompare
959 //This method allows the object to use comparison operators
960 //TODO: We need some armature comparisons
961 static PyObject *Armature_richcmpr(BPy_Armature *self, PyObject *v, int op)
962 {
963         return EXPP_incr_ret(Py_None);
964 }
965 //------------------------tp_repr
966 //This is the string representation of the object
967 static PyObject *Armature_repr(BPy_Armature *self)
968 {
969         return PyString_FromFormat( "[Armature: \"%s\"]", self->armature->id.name + 2 ); //*new*
970 }
971 //------------------------tp_dealloc
972 //This tells how to 'tear-down' our object when ref count hits 0
973 ///tp_dealloc
974 static void Armature_dealloc(BPy_Armature * self)
975 {
976         Py_DECREF(self->Bones);
977         Armature_Type.tp_free(self);
978         return;
979 }
980 //------------------TYPE_OBECT DEFINITION--------------------------
981 PyTypeObject Armature_Type = {
982         PyObject_HEAD_INIT(NULL)                //tp_head
983         0,                                                              //tp_internal
984         "Armature",                                             //tp_name
985         sizeof(BPy_Armature),                   //tp_basicsize
986         0,                                                              //tp_itemsize
987         (destructor)Armature_dealloc,   //tp_dealloc
988         0,                                                              //tp_print
989         0,                                                              //tp_getattr
990         0,                                                              //tp_setattr
991         0,                                                              //tp_compare
992         (reprfunc) Armature_repr,               //tp_repr
993         0,                                                              //tp_as_number
994         0,                                                              //tp_as_sequence
995         0,                                                              //tp_as_mapping
996         0,                                                              //tp_hash
997         0,                                                              //tp_call
998         0,                                                              //tp_str
999         0,                                                              //tp_getattro
1000         0,                                                              //tp_setattro
1001         0,                                                              //tp_as_buffer
1002         Py_TPFLAGS_DEFAULT,                             //tp_flags
1003         BPy_Armature_doc,                               //tp_doc
1004         0,                                                              //tp_traverse
1005         0,                                                              //tp_clear
1006         (richcmpfunc)Armature_richcmpr, //tp_richcompare
1007         0,                                                              //tp_weaklistoffset
1008         0,                                                              //tp_iter
1009         0,                                                              //tp_iternext
1010         BPy_Armature_methods,                   //tp_methods
1011         0,                                                              //tp_members
1012         BPy_Armature_getset,                    //tp_getset
1013         0,                                                              //tp_base
1014         0,                                                              //tp_dict
1015         0,                                                              //tp_descr_get
1016         0,                                                              //tp_descr_set
1017         0,                                                              //tp_dictoffset
1018         (initproc)Armature_init,                //tp_init
1019         0,                                                              //tp_alloc
1020         (newfunc)Armature_new,                  //tp_new
1021         0,                                                              //tp_free
1022         0,                                                              //tp_is_gc
1023         0,                                                              //tp_bases
1024         0,                                                              //tp_mro
1025         0,                                                              //tp_cache
1026         0,                                                              //tp_subclasses
1027         0,                                                              //tp_weaklist
1028         0                                                               //tp_del
1029 };
1030
1031 //-------------------MODULE METHODS IMPLEMENTATION------------------------
1032 //----------------Blender.Armature.Get()
1033 /* This function will return a Py_Armature when a single string is passed
1034 * or else it will return a {key:value} dictionary when mutliple strings are passed
1035 * or it will return a {key:value} dictionary of all armatures when nothing is passed*/
1036 static PyObject *M_Armature_Get(PyObject * self, PyObject * args)
1037 {
1038         PyObject *seq = NULL, *item = NULL, *dict = NULL, *py_armature = NULL;
1039         char *name = "", buffer[24];
1040         int size = 0, i;
1041         void *data;
1042
1043         //GET ARGUMENTS - () ('s') ('s',..) (['s',..]) are exceptable
1044         size = PySequence_Length(args);
1045         if (size == 1) {
1046                 seq = PySequence_GetItem(args, 0); //*new*
1047                 if (!seq)
1048                         goto RuntimeError;
1049                 if(!PyString_Check(seq)){
1050                         if (PySequence_Check(seq)) {
1051                                 size = PySequence_Length(seq);
1052                         } else {
1053                                 Py_DECREF(seq);
1054                                 goto AttributeError;
1055                         }
1056                 }
1057         } else {
1058                 seq = EXPP_incr_ret(args); //*take ownership*
1059         }
1060         //'seq' should be a list, empty tuple or string - check list for strings
1061         if(!PyString_Check(seq)){
1062                 for(i = 0; i < size; i++){
1063                         item = PySequence_GetItem(seq, i); //*new*
1064                         if (!item) {
1065                                 Py_DECREF(seq);
1066                                 goto RuntimeError;
1067                         }
1068                         if(!PyString_Check(item)){
1069                                 EXPP_decr2(item, seq);
1070                                 goto AttributeError;
1071                         }
1072                         Py_DECREF(item);
1073                 }
1074         }
1075
1076         //GET ARMATURES
1077         if(size != 1){
1078                 dict = PyDict_New(); //*new*
1079                 if(!dict){
1080                         Py_DECREF(seq);
1081                         goto RuntimeError;
1082                 }
1083                 if(size == 0){  //GET ALL ARMATURES
1084                         data = G.main->armature.first; //get the first data ID from the armature library
1085                         while (data){
1086                                 py_armature = PyArmature_FromArmature(data); //*new*
1087                                 sprintf(buffer, "%s", ((bArmature*)data)->id.name +2);
1088                                 if(PyDict_SetItemString(dict, buffer, py_armature) == -1){ //add to dictionary
1089                                         EXPP_decr3(seq, dict, py_armature);
1090                                         goto RuntimeError;
1091                                 }
1092                                 Py_DECREF(py_armature);
1093                                 data = ((ID*)data)->next;
1094                         }
1095                         Py_DECREF(seq);
1096                 }else{  //GET ARMATURE LIST
1097                         for (i = 0; i < size; i++) {
1098                                 item = PySequence_GetItem(seq, i); //*new*
1099                                 name = PyString_AsString(item);
1100                                 Py_DECREF(item);
1101                                 data = find_id("AR", name); //get data from library
1102                                 if (data != NULL){
1103                                         py_armature = PyArmature_FromArmature(data); //*new*
1104                                         if(PyDict_SetItemString(dict, name, py_armature) == -1){ //add to dictionary
1105                                                 EXPP_decr3(seq, dict, py_armature);
1106                                                 goto RuntimeError;
1107                                         }
1108                                         Py_DECREF(py_armature);
1109                                 }else{
1110                                         if(PyDict_SetItemString(dict, name, Py_None) == -1){ //add to dictionary
1111                                                 EXPP_decr2(seq, dict);
1112                                                 goto RuntimeError;
1113                                         }
1114                                         Py_DECREF(Py_None);
1115                                 }
1116                         }
1117                         Py_DECREF(seq);
1118                 }
1119                 return dict;
1120         }else{  //GET SINGLE ARMATURE
1121                 if(!PyString_Check(seq)){ //This handles the bizarre case where (['s']) is passed
1122                         item = PySequence_GetItem(seq, 0); //*new*
1123                         name = PyString_AsString(item);
1124                         Py_DECREF(item);
1125                 }else{
1126                         name = PyString_AsString(seq);
1127                 }
1128                 Py_DECREF(seq);
1129                 data = find_id("AR", name); //get data from library
1130                 if (data != NULL){
1131                         return PyArmature_FromArmature(data); //*new*
1132                 }else{
1133                         return EXPP_incr_ret(Py_None);
1134                 }
1135         }
1136
1137 RuntimeError:
1138         return EXPP_objError(PyExc_RuntimeError, "%s%s%s", 
1139                 sModuleError, "Get(): ", "Internal Error Ocurred");
1140
1141 AttributeError:
1142         return EXPP_objError(PyExc_AttributeError, "%s%s%s", 
1143                 sModuleBadArgs, "Get(): ", "- Expects (optional) string sequence");
1144 }
1145
1146 //-------------------MODULE METHODS DEFINITION-----------------------------
1147 static PyObject *M_Armature_Get( PyObject * self, PyObject * args );
1148
1149 static char M_Armature_Get_doc[] = "(name) - return the armature with the name 'name', \
1150   returns None if not found.\n If 'name' is not specified, it returns a list of all \
1151   armatures in the\ncurrent scene.";
1152
1153 struct PyMethodDef M_Armature_methods[] = {
1154         {"Get", M_Armature_Get, METH_VARARGS, M_Armature_Get_doc},
1155         {NULL}
1156 };
1157 //------------------VISIBLE PROTOTYPE IMPLEMENTATION-----------------------
1158 //-----------------(internal)
1159 //Converts a bArmature to a PyArmature
1160 PyObject *PyArmature_FromArmature(struct bArmature *armature)
1161 {
1162         BPy_Armature *py_armature = NULL;
1163
1164         //create armature type
1165         py_armature = (BPy_Armature*)Armature_Type.tp_alloc(&Armature_Type, 0); //*new*
1166         if (!py_armature)
1167                 goto RuntimeError;
1168         py_armature->armature = armature;
1169
1170         //create armature.bones
1171         py_armature->Bones = (BPy_BonesDict*)PyBonesDict_FromPyArmature(py_armature);
1172         if (!py_armature->Bones)
1173                 goto RuntimeError;
1174
1175         return (PyObject *) py_armature; 
1176
1177 RuntimeError:
1178         return EXPP_objError(PyExc_RuntimeError, "%s%s%s", 
1179                 sModuleError, "PyArmature_FromArmature: ", "Internal Error Ocurred");
1180 }
1181 //-----------------(internal)
1182 //Converts a PyArmature to a bArmature
1183 struct bArmature *PyArmature_AsArmature(BPy_Armature *py_armature)
1184 {
1185         return (py_armature->armature);
1186 }
1187 //-------------------MODULE INITIALIZATION--------------------------------
1188 PyObject *Armature_Init(void)
1189 {
1190         PyObject *module, *dict;
1191
1192         //Initializes TypeObject.ob_type
1193         if (PyType_Ready(&Armature_Type) < 0 || PyType_Ready(&BonesDict_Type) < 0 || 
1194                 PyType_Ready(&EditBone_Type) < 0 ||     PyType_Ready(&Bone_Type) < 0) {
1195                 return EXPP_incr_ret(Py_None);
1196         }
1197
1198         //Register the module
1199         module = Py_InitModule3("Blender.Armature", M_Armature_methods, 
1200                 "The Blender Armature module"); 
1201
1202         //Add TYPEOBJECTS to the module
1203         PyModule_AddObject(module, "Armature", 
1204                 EXPP_incr_ret((PyObject *)&Armature_Type)); //*steals*
1205         PyModule_AddObject(module, "Bone", 
1206                 EXPP_incr_ret((PyObject *)&Bone_Type)); //*steals*
1207         PyModule_AddObject(module, "Editbone", 
1208                 EXPP_incr_ret((PyObject *)&EditBone_Type)); //*steals*
1209
1210         //Add CONSTANTS to the module
1211         PyModule_AddObject(module, "CONNECTED", 
1212                 EXPP_incr_ret(PyConstant_NewInt("CONNECTED", BONE_CONNECTED)));
1213         PyModule_AddObject(module, "HINGE", 
1214                 EXPP_incr_ret(PyConstant_NewInt("HINGE", BONE_HINGE)));
1215         PyModule_AddObject(module, "NO_DEFORM", 
1216                 EXPP_incr_ret(PyConstant_NewInt("NO_DEFORM", BONE_NO_DEFORM)));
1217         PyModule_AddObject(module, "MULTIPLY", 
1218                 EXPP_incr_ret(PyConstant_NewInt("MULTIPLY", BONE_MULT_VG_ENV)));
1219         PyModule_AddObject(module, "HIDDEN_EDIT", 
1220                 EXPP_incr_ret(PyConstant_NewInt("HIDDEN_EDIT", BONE_HIDDEN_A)));
1221         PyModule_AddObject(module, "ROOT_SELECTED", 
1222                 EXPP_incr_ret(PyConstant_NewInt("ROOT_SELECTED", BONE_ROOTSEL)));
1223         PyModule_AddObject(module, "BONE_SELECTED", 
1224                 EXPP_incr_ret(PyConstant_NewInt("BONE_SELECTED", BONE_SELECTED)));
1225         PyModule_AddObject(module, "TIP_SELECTED", 
1226                 EXPP_incr_ret(PyConstant_NewInt("TIP_SELECTED", BONE_TIPSEL)));
1227
1228         PyModule_AddObject(module, "OCTAHEDRON", 
1229                 EXPP_incr_ret(PyConstant_NewInt("OCTAHEDRON", ARM_OCTA)));
1230         PyModule_AddObject(module, "STICK", 
1231                 EXPP_incr_ret(PyConstant_NewInt("STICK", ARM_LINE)));
1232         PyModule_AddObject(module, "BBONE", 
1233                 EXPP_incr_ret(PyConstant_NewInt("BBONE", ARM_B_BONE)));
1234         PyModule_AddObject(module, "ENVELOPE", 
1235                 EXPP_incr_ret(PyConstant_NewInt("ENVELOPE", ARM_ENVELOPE)));
1236
1237         //Add SUBMODULES to the module
1238         dict = PyModule_GetDict( module ); //borrowed
1239         PyDict_SetItemString(dict, "NLA", NLA_Init()); //creates a *new* module
1240
1241         return module;
1242 }