- replaced G.{edve,eded,edvl} with G.editMesh, atm just a structure to
[blender.git] / source / blender / src / editarmature.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  * The Original Code is: all of this file.
27  *
28  * Contributor(s): none yet.
29  *
30  * ***** END GPL/BL DUAL LICENSE BLOCK *****
31  * editarmature.c: Interface for creating and posing armature objects
32  */
33
34 #include <stdlib.h>
35 #include <string.h>
36 #include <math.h>
37
38 #ifdef HAVE_CONFIG_H
39 #include <config.h>
40 #endif
41
42 #ifdef WIN32
43 #include "BLI_winstuff.h"
44 #endif
45
46 #include "MEM_guardedalloc.h"
47
48 #include "BMF_Api.h"
49
50 #include "DNA_action_types.h"
51 #include "DNA_armature_types.h"
52 #include "DNA_constraint_types.h"
53 #include "DNA_mesh_types.h"
54 #include "DNA_meshdata_types.h"
55 #include "DNA_object_types.h"
56 #include "DNA_scene_types.h"
57 #include "DNA_screen_types.h"
58 #include "DNA_space_types.h"
59 #include "DNA_view3d_types.h"
60
61 #include "BLI_blenlib.h"
62 #include "BLI_arithb.h"
63 #include "BLI_editVert.h"
64
65 #include "BKE_utildefines.h"
66 #include "BKE_action.h"
67 #include "BKE_armature.h"
68 #include "BKE_constraint.h"
69 #include "BKE_global.h"
70 #include "BKE_object.h"
71 #include "BKE_subsurf.h"
72
73 #include "BIF_gl.h"
74 #include "BIF_graphics.h"
75 #include "BIF_interface.h"
76 #include "BIF_resources.h"
77 #include "BIF_screen.h"
78 #include "BIF_space.h"
79 #include "BIF_toolbox.h"
80 #include "BIF_editarmature.h"
81 #include "BIF_editconstraint.h"
82 #include "BIF_poseobject.h"
83 #include "BIF_mywindow.h"
84 #include "BIF_editdeform.h"
85
86 #include "BDR_editobject.h"
87 #include "BDR_drawobject.h"
88
89 #include "BSE_edit.h"
90 #include "BSE_view.h"
91 #include "BSE_trans_types.h"
92 #include "BSE_editaction.h"
93
94 #include "mydevice.h"
95 #include "blendef.h"
96 #include "nla.h"
97
98 /*  >>>>> FIXME: ARG!  Colours should be defined in a header somewhere! */
99 /*      Note, these came from drawobject.c  They really should be in a nice header file somewhere */
100 #define B_YELLOW        0x77FFFF
101 #define B_PURPLE        0xFF70FF
102
103 #define B_CYAN          0xFFFF00
104 #define B_AQUA          0xFFBB55 /* 0xFF8833*/
105
106 extern  int tottrans;                                   /* Originally defined in editobject.c */
107 extern  struct TransOb *transmain;                              /* Originally defined in editobject.c */
108 extern  float centre[3], centroid[3];   /* Originally defined in editobject.c */
109
110 /*      Macros  */
111 #define TEST_EDITARMATURE {if(G.obedit==0) return; if( (G.vd->lay & G.obedit->lay)==0 ) return;}
112
113 /* Local Function Prototypes */
114 static void editbones_to_armature (ListBase *bones, Object *ob);
115
116 static void fix_bonelist_roll (ListBase *bonelist, ListBase *editbonelist);
117 static int      select_bonechildren_by_name (struct Bone *bone, char *name, int select);
118
119 static void draw_boneverti (float x, float y, float z, float size, int flag);
120 static void draw_bone (int armflag, int boneflag, unsigned int id, char *name, float length);
121 static void draw_bonechildren (struct Bone *bone, int flag, unsigned int *index);
122 static void add_bone_input (struct Object *ob);
123 static void make_boneList(struct ListBase* list, struct ListBase *bones, struct EditBone *parent);
124 static void make_bone_menu_children (struct Bone *bone, char *str, int *index);
125 static void delete_bone(struct EditBone* exBone);
126 static void clear_armature_children (struct Bone *bone, struct bPose *pose, char mode);
127
128 static int      count_bones (struct bArmature *arm, int flagmask, int allbones);
129
130 static int      count_bonechildren (struct Bone *bone, int incount, int flagmask, int allbones);
131 static int      add_trans_bonechildren (struct Object* ob, struct Bone* bone, struct TransOb* buffer, int index, char mode);
132 static void deselect_bonechildren (struct Bone *bone, int mode);
133 static void selectconnected_posebonechildren (struct Bone *bone);
134
135 static int      editbone_name_exists (char* name);
136
137 static void *get_nearest_bone (int findunsel);
138 static EditBone * get_nearest_editbonepoint (int findunsel, int *selmask);
139
140 static Bone *get_first_selected_bonechildren (Bone *bone);
141
142
143 /* Functions */
144
145
146
147 void apply_rot_armature (Object *ob, float mat[3][3]){
148         ListBase        list;
149         EditBone *ebone;
150         bArmature *arm;
151
152         arm = get_armature(ob);
153
154         if (!arm)
155                 return;
156
157         /* Put the armature into editmode */
158         list.first= list.last = NULL;
159         make_boneList(&list, &arm->bonebase, NULL);
160
161         /* Do the rotations */
162         for (ebone = list.first; ebone; ebone=ebone->next){
163         
164                 {
165
166                         /* Fixme: This is essentially duplicated from join_armature */
167
168                         float premat[4][4];
169                         float postmat[4][4];
170                         float difmat[4][4];
171                         float imat[4][4];
172                         float temp[4][4];
173                         float delta[3];
174                         float rmat[4][4];
175                         
176                         Mat4CpyMat3 (rmat, mat);
177                         /* Get the premat */
178                         VecSubf (delta, ebone->tail, ebone->head);
179                         make_boneMatrixvr(temp, delta, ebone->roll);
180                         Mat4MulMat4 (premat, temp, rmat);
181                         
182                         Mat4MulVecfl(rmat, ebone->head);
183                         Mat4MulVecfl(rmat, ebone->tail);
184                         
185                         /* Get the postmat */
186                         VecSubf (delta, ebone->tail, ebone->head);
187                         make_boneMatrixvr(postmat, delta, ebone->roll);
188                         
189                         /* Find the roll */
190                         Mat4Invert (imat, premat);
191                         Mat4MulMat4 (difmat, postmat, imat);
192                         
193 #if 0
194                         printmatrix4 ("Difmat", difmat);
195 #endif
196                         ebone->roll -=atan(difmat[2][0]/difmat[2][2]);
197                         
198                         if (difmat[0][0]<0)
199                                 ebone->roll +=M_PI;
200                         
201                 }
202
203                 
204         }
205         
206         /* Turn the list into an armature */
207         editbones_to_armature(&list, ob);
208         
209         /* Free the editbones */
210         if (list.first){
211                 BLI_freelistN (&list);
212         }
213
214 }
215
216
217
218 static Bone *get_first_selected_bonechildren (Bone *bone)
219 {
220         Bone *curbone, *result;
221
222         if (bone->flag & BONE_SELECTED)
223                 return bone;
224
225         for (curbone = bone->childbase.first; curbone; curbone=curbone->next){
226                 result = get_first_selected_bonechildren(curbone);
227                 if (result)
228                         return result;
229         };
230
231         return NULL;
232 }
233
234 Bone *get_first_selected_bone (void)
235 {
236         Bone *curbone, *result;
237         bArmature *arm;
238
239         arm = get_armature(OBACT);
240         if (!arm)
241                 return NULL;
242
243         for (curbone = arm->bonebase.first; curbone; curbone=curbone->next){
244                 result = get_first_selected_bonechildren(curbone);
245                 if (result)
246                         return result;
247         }
248
249         return NULL;
250 }
251
252 void clever_numbuts_posearmature (void)
253 {
254         /* heh -- 'clever numbuts'! */
255         bArmature *arm;
256         Bone *bone;
257         bPoseChannel *chan;
258
259         arm = get_armature(OBACT);
260         if (!arm)
261                 return;
262
263         bone = get_first_selected_bone();
264
265         if (!bone)
266                 return;
267
268         add_numbut(0, NUM|FLO, "Loc X:", -G.vd->far, G.vd->far, bone->loc, 0);
269         add_numbut(1, NUM|FLO, "Loc Y:", -G.vd->far, G.vd->far, bone->loc+1, 0);
270         add_numbut(2, NUM|FLO, "Loc Z:", -G.vd->far, G.vd->far, bone->loc+2, 0);
271
272         add_numbut(3, NUM|FLO, "Quat X:", -G.vd->far, G.vd->far, bone->quat, 0);
273         add_numbut(4, NUM|FLO, "Quat Y:", -G.vd->far, G.vd->far, bone->quat+1, 0);
274         add_numbut(5, NUM|FLO, "Quat Z:", -G.vd->far, G.vd->far, bone->quat+2, 0);
275         add_numbut(6, NUM|FLO, "Quat W:", -G.vd->far, G.vd->far, bone->quat+3, 0);
276
277         add_numbut(7, NUM|FLO, "Size X:", -G.vd->far, G.vd->far, bone->size, 0);
278         add_numbut(8, NUM|FLO, "Size Y:", -G.vd->far, G.vd->far, bone->size+1, 0);
279         add_numbut(9, NUM|FLO, "Size Z:", -G.vd->far, G.vd->far, bone->size+2, 0);
280
281         do_clever_numbuts("Active Bone", 10, REDRAW);
282
283         /* This is similar to code in special_trans_update */
284         
285         if (!G.obpose->pose) G.obpose->pose= MEM_callocN(sizeof(bPose), "pose");
286         chan = MEM_callocN (sizeof (bPoseChannel), "transPoseChannel");
287
288         chan->flag |= POSE_LOC|POSE_ROT|POSE_SIZE;
289         memcpy (chan->loc, bone->loc, sizeof (chan->loc));
290         memcpy (chan->quat, bone->quat, sizeof (chan->quat));
291         memcpy (chan->size, bone->size, sizeof (chan->size));
292         strcpy (chan->name, bone->name);
293         
294         set_pose_channel (G.obpose->pose, chan);
295         
296 }
297
298 void clever_numbuts_armature (void)
299 {
300         EditBone *ebone, *child;
301         
302         ebone= G.edbo.first;
303
304         for (ebone = G.edbo.first; ebone; ebone=ebone->next){
305                 if (ebone->flag & BONE_SELECTED)
306                         break;
307         }
308
309         if (!ebone)
310                 return;
311
312         add_numbut(0, NUM|FLO, "Root X:", -G.vd->far, G.vd->far, ebone->head, 0);
313         add_numbut(1, NUM|FLO, "Root Y:", -G.vd->far, G.vd->far, ebone->head+1, 0);
314         add_numbut(2, NUM|FLO, "Root Z:", -G.vd->far, G.vd->far, ebone->head+2, 0);
315
316         add_numbut(3, NUM|FLO, "Tip X:", -G.vd->far, G.vd->far, ebone->tail, 0);
317         add_numbut(4, NUM|FLO, "Tip Y:", -G.vd->far, G.vd->far, ebone->tail+1, 0);
318         add_numbut(5, NUM|FLO, "Tip Z:", -G.vd->far, G.vd->far, ebone->tail+2, 0);
319
320         /* Convert roll to degrees */
321         ebone->roll *= (180.0F/M_PI);
322         add_numbut(6, NUM|FLO, "Roll:", -G.vd->far, G.vd->far, &ebone->roll, 0);
323
324         do_clever_numbuts("Active Bone", 7, REDRAW);
325
326         /* Convert roll to radians */
327         ebone->roll /= (180.0F/M_PI);
328
329         //      Update our parent
330         if (ebone->parent && ebone->flag & BONE_IK_TOPARENT){
331                 VECCOPY (ebone->parent->tail, ebone->head);
332         }
333
334         //      Update our children if necessary
335         for (child = G.edbo.first; child; child=child->next){
336                 if (child->parent == ebone && child->flag & BONE_IK_TOPARENT){
337                         VECCOPY (child->head, ebone->tail);
338                 }
339         }
340 }
341
342 void select_bone_by_name (bArmature *arm, char *name, int select)
343 {
344         Bone *bone;
345
346         if (!arm)
347                 return;
348
349         for (bone=arm->bonebase.first; bone; bone=bone->next)
350                 if (select_bonechildren_by_name (bone, name, select))
351                         break;
352 }
353
354 static int select_bonechildren_by_name (Bone *bone, char *name, int select)
355 {
356         Bone *curBone;
357
358         if (!strcmp (bone->name, name)){
359                 if (select)
360                         bone->flag |= BONE_SELECTED;
361                 else
362                         bone->flag &= ~BONE_SELECTED;
363                 return 1;
364         }
365
366         for (curBone=bone->childbase.first; curBone; curBone=curBone->next){
367                 if (select_bonechildren_by_name (curBone, name, select))
368                         return 1;
369         }
370
371         return 0;
372 }
373 void selectconnected_armature(void)
374 {
375         EditBone *bone, *curBone, *next;
376
377         if (G.qual & LR_SHIFTKEY)
378                 bone= get_nearest_bone(0);
379         else
380                 bone= get_nearest_bone(1);
381
382         if (!bone)
383                 return;
384
385         /* Select parents */
386         for (curBone=bone; curBone; curBone=next){
387                 if (G.qual & LR_SHIFTKEY){
388                         curBone->flag &= ~(BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
389                 }
390                 else{
391                         curBone->flag |= (BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
392                 }
393
394                 if (curBone->flag & BONE_IK_TOPARENT)
395                         next=curBone->parent;
396                 else
397                         next=NULL;
398         }
399
400         /* Select children */
401         while (bone){
402                 for (curBone=G.edbo.first; curBone; curBone=next){
403                         next = curBone->next;
404                         if (curBone->parent == bone){
405                                 if (curBone->flag & BONE_IK_TOPARENT){
406                                         if (G.qual & LR_SHIFTKEY)
407                                                 curBone->flag &= ~(BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
408                                         else
409                                                 curBone->flag |= (BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
410                                         bone=curBone;
411                                         break;
412                                 }
413                                 else{ 
414                                         bone=NULL;
415                                         break;
416                                 }
417                         }
418                 }
419                 if (!curBone)
420                         bone=NULL;
421
422         }
423
424         countall();
425         allqueue (REDRAWVIEW3D, 0);
426
427 }
428
429 void selectconnected_posearmature(void)
430 {
431         Bone *bone, *curBone, *next;
432
433         if (G.qual & LR_SHIFTKEY)
434                 bone= get_nearest_bone(0);
435         else
436                 bone = get_nearest_bone(1);
437
438         if (!bone)
439                 return;
440
441         /* Select parents */
442         for (curBone=bone; curBone; curBone=next){
443                 select_actionchannel_by_name (G.obpose->action, curBone->name, !(G.qual & LR_SHIFTKEY));
444                 if (G.qual & LR_SHIFTKEY)
445                         curBone->flag &= ~BONE_SELECTED;
446                 else
447                         curBone->flag |= BONE_SELECTED;
448
449                 if (curBone->flag & BONE_IK_TOPARENT)
450                         next=curBone->parent;
451                 else
452                         next=NULL;
453         }
454
455         /* Select children */
456         for (curBone=bone->childbase.first; curBone; curBone=next){
457                 selectconnected_posebonechildren (curBone);
458         }
459         
460         countall();
461         allqueue (REDRAWVIEW3D, 0);
462         allqueue (REDRAWACTION, 0);
463 }
464
465 static void selectconnected_posebonechildren (Bone *bone)
466 {
467         Bone *curBone;
468
469         if (!(bone->flag & BONE_IK_TOPARENT))
470                 return;
471
472         select_actionchannel_by_name (G.obpose->action, bone->name, !(G.qual & LR_SHIFTKEY));
473
474         if (G.qual & LR_SHIFTKEY)
475                 bone->flag &= ~BONE_SELECTED;
476         else
477                 bone->flag |= BONE_SELECTED;
478
479         for (curBone=bone->childbase.first; curBone; curBone=curBone->next){
480                 selectconnected_posebonechildren (curBone);
481         }
482 }
483
484
485 char *make_bone_menu (bArmature *arm)
486 {
487         char *menustr=NULL;
488         Bone *curBone;
489         int             size;
490         int             index=0;
491         
492
493         //      Count the bones
494         size = (count_bones (arm, 0xFFFFFFFF, 1)*48) + 256;
495         menustr = MEM_callocN(size, "bonemenu");
496
497         sprintf (menustr, "Select Bone%%t");
498
499         for (curBone=arm->bonebase.first; curBone; curBone=curBone->next){
500                 make_bone_menu_children (curBone, menustr, &index);
501         }
502
503         return menustr;
504 }
505
506 static void make_bone_menu_children (Bone *bone, char *str, int *index)
507 {
508         Bone *curBone;
509
510         sprintf (str, "%s|%s%%x%d", str, bone->name, *index);
511         (*index) ++;
512
513         for (curBone=bone->childbase.first; curBone; curBone=curBone->next)
514                 make_bone_menu_children (curBone, str, index);
515 }
516
517 void free_editArmature(void)
518 {
519
520         /*      Clear the editbones list */
521         if (G.edbo.first){
522                 BLI_freelistN (&G.edbo);
523         }
524 }
525
526 static EditBone * get_nearest_editbonepoint (int findunsel, int *selmask){
527         EditBone        *ebone;
528         unsigned int buffer[MAXPICKBUF];
529         short           hits;
530         int              i, takeNext=0;
531         int             sel;
532         unsigned int    hitresult, hitbone, firstunSel=-1;
533
534         persp(PERSP_VIEW);
535
536         glInitNames();
537         hits= selectprojektie(buffer, 0, 0, 0, 0);
538
539         /* See if there are any selected bones in this group */
540         if (hits){
541                 for (i=0; i< hits; i++){
542                         hitresult = buffer[3+(i*4)];
543                         if (!(hitresult&BONESEL_NOSEL)){
544
545                                 /* Determine which points are selected */
546                                 hitbone = hitresult & ~(BONESEL_ROOT|BONESEL_TIP);
547
548                                 /* Determine what the current bone is */
549                                 ebone = BLI_findlink(&G.edbo, hitbone);
550
551                                 /* See if it is selected */
552                                 sel = 0;
553                                 if ((hitresult & (BONESEL_TIP|BONESEL_ROOT)) == (BONESEL_TIP|BONESEL_ROOT))
554                                         sel = (ebone->flag & (BONE_TIPSEL| BONE_ROOTSEL)) == (BONE_TIPSEL|BONE_ROOTSEL) ? 1 : 0;
555                                 else if (hitresult & BONESEL_TIP)
556                                         sel |= ebone->flag & BONE_TIPSEL;
557                                 else if (hitresult & BONESEL_ROOT)
558                                         sel |= ebone->flag & BONE_ROOTSEL;
559                                 if (!findunsel)
560                                         sel = !sel;
561                         
562                                 if (sel)
563                                         takeNext=1;
564                                 else{
565                                         if (firstunSel == -1)
566                                                 firstunSel = hitresult;
567                                         if (takeNext){
568                                                 *selmask =0;
569                                                 if (hitresult & BONESEL_ROOT)
570                                                         *selmask |= BONE_ROOTSEL;
571                                                 if (hitresult & BONESEL_TIP)
572                                                         *selmask |= BONE_TIPSEL;
573                                                 return ebone;
574                                         }
575                                 }
576                         }
577                 }
578
579                 if (firstunSel != -1){
580                         *selmask = 0;
581                         if (firstunSel & BONESEL_ROOT)
582                                 *selmask |= BONE_ROOTSEL;
583                         if (firstunSel & BONESEL_TIP)
584                                 *selmask |= BONE_TIPSEL;
585                         return BLI_findlink(&G.edbo, firstunSel & ~(BONESEL_ROOT|BONESEL_TIP));
586                 }
587 #if 1
588                 else{
589                         *selmask = 0;
590                         if (buffer[3] & BONESEL_ROOT)
591                                 *selmask |= BONE_ROOTSEL;
592                         if (buffer[3] & BONESEL_TIP)
593                                 *selmask |= BONE_TIPSEL;
594 #if 1
595                         return BLI_findlink(&G.edbo, buffer[3] & ~(BONESEL_ROOT|BONESEL_TIP));
596 #else
597                         return NULL;
598 #endif
599                 }
600 #endif
601         }
602
603         *selmask = 0;
604         return NULL;
605 }
606
607 static void * get_nearest_bone (int findunsel){
608         void            *firstunSel=NULL, *data;
609         unsigned int buffer[MAXPICKBUF];
610         short           hits;
611         int              i, takeNext=0;
612         int             sel;
613         unsigned int    hitresult;
614         Bone *bone;
615         EditBone *ebone;
616
617         persp(PERSP_VIEW);
618
619         glInitNames();
620         hits= selectprojektie(buffer, 0, 0, 0, 0);
621
622
623         /* See if there are any selected bones in this group */
624         if (hits){
625                 for (i=0; i< hits; i++){
626                         hitresult = buffer[3+(i*4)];
627                         if (!(hitresult&BONESEL_NOSEL)){
628
629                                 /* Determine which points are selected */
630                                 hitresult &= ~(BONESEL_ROOT|BONESEL_TIP);
631
632                                 /* Determine what the current bone is */
633                                 if (!G.obedit){
634                                         bone = get_indexed_bone(OBACT->data, hitresult);
635                                         if (findunsel)
636                                                 sel = (bone->flag & BONE_SELECTED);
637                                         else
638                                                 sel = !(bone->flag & BONE_SELECTED);                                    
639                                         data = bone;
640                                 }
641                                 else{
642                                         ebone = BLI_findlink(&G.edbo, hitresult);
643                                         if (findunsel)
644                                                 sel = (ebone->flag & BONE_SELECTED);
645                                         else
646                                                 sel = !(ebone->flag & BONE_SELECTED);
647                                         
648                                         data = ebone;
649                                 }
650                                 
651                                 if (sel)
652                                         takeNext=1;
653                                 else{
654                                         if (!firstunSel)
655                                                 firstunSel=data;
656                                         if (takeNext)
657                                                 return data;
658                                 }
659                         }
660                 }
661
662                 if (firstunSel)
663                         return firstunSel;
664 #if 1
665                 else{
666 #if 1
667                         if (G.obedit)
668                                 return BLI_findlink(&G.edbo, buffer[3] & ~(BONESEL_ROOT|BONESEL_TIP));
669                         else
670                                 return get_indexed_bone(OBACT->data, buffer[3] & ~(BONESEL_ROOT|BONESEL_TIP));
671 #else
672                         return NULL;
673 #endif
674                 }
675 #endif
676         }
677
678         return NULL;
679 }
680
681 void delete_armature(void)
682 {
683         EditBone        *curBone, *next;
684         
685         TEST_EDITARMATURE;
686         if(okee("Erase selected")==0) return;
687         
688         for (curBone=G.edbo.first;curBone;curBone=next){
689                 next=curBone->next;
690                 if (curBone->flag&BONE_SELECTED)
691                         delete_bone(curBone);
692         }
693         
694         
695         allqueue(REDRAWVIEW3D, 0);
696         allqueue(REDRAWBUTSEDIT, 0);
697         allqueue(REDRAWBUTSOBJECT, 0);
698         countall();
699 }
700
701
702 static void delete_bone(EditBone* exBone)
703 {
704         EditBone        *curBone;
705         bPoseChannel *chan;
706         
707         /*      Find any bones that refer to this bone  */
708         for (curBone=G.edbo.first;curBone;curBone=curBone->next){
709                 if (curBone->parent==exBone){
710                         curBone->parent=exBone->parent;
711                         curBone->flag &= ~BONE_IK_TOPARENT;
712                 }
713         }
714         
715         /*  Erase any associated pose channel */
716         if (G.obedit->pose){
717                 for (chan=G.obedit->pose->chanbase.first; chan; chan=chan->next){
718                         if (!strcmp (chan->name, exBone->name)){
719                                 free_constraints(&chan->constraints);
720                                 BLI_freelinkN (&G.obedit->pose->chanbase, chan);
721                                 break;
722                         }
723                 }
724         }
725
726
727         allqueue(REDRAWBUTSOBJECT, 0);
728         allqueue(REDRAWBUTSEDIT, 0);
729
730         BLI_freelinkN (&G.edbo,exBone);
731 }
732
733 void remake_editArmature(void)
734 {
735         if(okee("Reload Original data")==0) return;
736         
737         make_editArmature();
738         allqueue(REDRAWVIEW3D, 0);
739         allqueue(REDRAWBUTSHEAD, 0);
740         allqueue(REDRAWBUTSOBJECT, 0);
741         allqueue(REDRAWBUTSEDIT, 0);
742 }
743
744 void mouse_armature(void)
745 {
746         EditBone*       nearBone = NULL;
747         int     selmask;
748
749         nearBone=get_nearest_editbonepoint(1, &selmask);
750
751         if (nearBone){
752                 if ((G.qual & LR_SHIFTKEY) && (nearBone->flag & selmask))
753                         nearBone->flag &= ~selmask;
754                 else
755                         nearBone->flag |= selmask;
756
757                 if (!(G.qual & LR_SHIFTKEY)){
758                         deselectall_armature();
759                         nearBone->flag |= selmask;
760                 }
761                 allqueue(REDRAWVIEW3D, 0);
762                 allqueue(REDRAWBUTSEDIT, 0);
763                 allqueue(REDRAWBUTSOBJECT, 0);
764         };
765         countall();
766         rightmouse_transform();
767 }
768
769 void make_editArmature(void)
770 {
771         bArmature       *arm;
772         
773         if (G.obedit==0)
774                 return;
775         
776         free_editArmature();
777         
778         arm= get_armature(G.obedit);
779         if (!arm)
780                 return;
781         
782         make_boneList (&G.edbo, &arm->bonebase,NULL);
783 }
784
785 static void editbones_to_armature (ListBase *list, Object *ob)
786 {
787         bArmature *arm;
788         EditBone *eBone;
789         Bone    *newBone;
790
791         arm = get_armature(ob);
792         if (!list)
793                 return;
794         if (!arm)
795                 return;
796
797         free_bones(arm);
798         
799
800         /*      Copy the bones from the editData into the armature*/
801         for (eBone=list->first;eBone;eBone=eBone->next){
802                 newBone=MEM_callocN (sizeof(Bone), "bone");
803                 eBone->temp= newBone;   /* Associate the real Bones with the EditBones */
804                 
805                 strcpy (newBone->name, eBone->name);
806                 memcpy (newBone->head, eBone->head, sizeof(float)*3);
807                 memcpy (newBone->tail, eBone->tail, sizeof(float)*3);
808                 newBone->flag=eBone->flag &~(BONE_SELECTED|BONE_HILIGHTED);
809 //              newBone->roll=eBone->roll;
810                 newBone->roll = 0.0F;
811
812                 /*      >>>>> FIXME: This isn't a very good system: a lot of
813                                         pointless copying involved.  To be investigated
814                                         once things are working better.
815                 */
816
817                 newBone->weight = eBone->weight;
818                 newBone->dist = eBone->dist;
819                 newBone->boneclass = eBone->boneclass;
820
821                 memcpy (newBone->loc, eBone->loc, sizeof(eBone->loc));
822                 memcpy (newBone->dloc, eBone->dloc, sizeof(eBone->dloc));
823 /*              memcpy (newBone->orig, eBone->orig, sizeof(eBone->orig));*/
824                 memcpy (newBone->size, eBone->size, sizeof(eBone->size));
825                 memcpy (newBone->dsize, eBone->dsize, sizeof(eBone->dsize));
826                 memcpy (newBone->quat, eBone->quat, sizeof(eBone->quat));
827                 memcpy (newBone->dquat, eBone->dquat, sizeof(eBone->dquat));
828                 memcpy (newBone->obmat, eBone->obmat, sizeof(eBone->obmat));
829         }
830
831         /*      Fix parenting in a separate pass to ensure ebone->bone connections
832                 are valid at this point */
833         for (eBone=list->first;eBone;eBone=eBone->next){
834                 newBone= (Bone*) eBone->temp;
835                 if (eBone->parent){
836                         newBone->parent=(Bone*) eBone->parent->temp;
837                         BLI_addtail (&newBone->parent->childbase,newBone);
838
839                         {
840                                 float M_boneRest[4][4];
841                                 float M_parentRest[4][4];
842                                 float iM_parentRest[4][4];
843                                 float   delta[3];
844                         
845                                 /* Get the parent's global matrix (rotation only)*/
846                                 VecSubf (delta, eBone->parent->tail, eBone->parent->head);
847                                 make_boneMatrixvr(M_parentRest, delta, eBone->parent->roll);
848
849                                 /* Get this bone's global matrix (rotation only)*/
850                                 VecSubf (delta, eBone->tail, eBone->head);
851                                 make_boneMatrixvr(M_boneRest, delta, eBone->roll);
852
853                                 /* Invert the parent matrix */
854                                 Mat4Invert (iM_parentRest, M_parentRest);
855
856                                 /* Get the new head and tail */
857                                 VecSubf (newBone->head, eBone->head, eBone->parent->tail);
858                                 VecSubf (newBone->tail, eBone->tail, eBone->parent->tail);
859
860                                 Mat4MulVecfl(iM_parentRest, newBone->head);
861                                 Mat4MulVecfl(iM_parentRest, newBone->tail);
862         
863
864                         }
865
866                 }
867                 /*      ...otherwise add this bone to the armature's bonebase */
868                 else
869                         BLI_addtail (&arm->bonebase,newBone);
870         }
871
872         /* Make a pass through the new armature to fix rolling */
873         fix_bonelist_roll (&arm->bonebase, list);
874         /* Get rid of pose channels that may have belonged to deleted bones */
875         collect_pose_garbage(ob);
876         /* Ensure all bones have channels */
877         apply_pose_armature(arm, ob->pose, 0);
878
879         /* Calculate and cache the inverse restposition matrices (needed for deformation)*/
880         precalc_bonelist_irestmats(&arm->bonebase);
881 }
882
883
884 void load_editArmature(void)
885 {
886         bArmature               *arm;
887
888         arm=get_armature(G.obedit);
889         if (!arm)
890                 return;
891         
892 #if 1
893         editbones_to_armature(&G.edbo, G.obedit);
894 #else
895         free_bones(arm);
896         
897
898         /*      Copy the bones from the editData into the armature*/
899         for (eBone=G.edbo.first;eBone;eBone=eBone->next){
900                 newBone=MEM_callocN (sizeof(Bone), "bone");
901                 eBone->temp= newBone;   /* Associate the real Bones with the EditBones */
902                 
903                 strcpy (newBone->name, eBone->name);
904                 memcpy (newBone->head, eBone->head, sizeof(float)*3);
905                 memcpy (newBone->tail, eBone->tail, sizeof(float)*3);
906                 newBone->flag=eBone->flag &~(BONE_SELECTED|BONE_HILIGHTED);
907         //      newBone->roll=eBone->roll;
908                 newBone->roll = 0.0F;
909
910                 /*      >>>>> FIXME: This isn't a very good system: a lot of
911                                         pointless copying involved.  To be investigated
912                                         once things are working better.
913                 */
914
915                 newBone->weight = eBone->weight;
916                 newBone->dist = eBone->dist;
917                 newBone->boneclass = eBone->boneclass;
918
919                 memcpy (newBone->loc, eBone->loc, sizeof(eBone->loc));
920                 memcpy (newBone->dloc, eBone->dloc, sizeof(eBone->dloc));
921 /*              memcpy (newBone->orig, eBone->orig, sizeof(eBone->orig));*/
922                 memcpy (newBone->size, eBone->size, sizeof(eBone->size));
923                 memcpy (newBone->dsize, eBone->dsize, sizeof(eBone->dsize));
924                 memcpy (newBone->quat, eBone->quat, sizeof(eBone->quat));
925                 memcpy (newBone->dquat, eBone->dquat, sizeof(eBone->dquat));
926                 memcpy (newBone->obmat, eBone->obmat, sizeof(eBone->obmat));
927         }
928
929         /*      Fix parenting in a separate pass to ensure ebone->bone connections
930                 are valid at this point */
931         for (eBone=G.edbo.first;eBone;eBone=eBone->next){
932                 newBone= (Bone*) eBone->temp;
933                 if (eBone->parent){
934                         newBone->parent=(Bone*) eBone->parent->temp;
935                         BLI_addtail (&newBone->parent->childbase,newBone);
936
937                         {
938                                 float M_boneRest[4][4];
939                                 float M_parentRest[4][4];
940                                 float M_relativeBone[4][4];
941                                 float iM_parentRest[4][4];
942                                 float   delta[3];
943                         
944                                 /* Get the parent's global matrix (rotation only)*/
945                                 VecSubf (delta, eBone->parent->tail, eBone->parent->head);
946                                 make_boneMatrixvr(M_parentRest, delta, eBone->parent->roll);
947
948                                 /* Get this bone's global matrix (rotation only)*/
949                                 VecSubf (delta, eBone->tail, eBone->head);
950                                 make_boneMatrixvr(M_boneRest, delta, eBone->roll);
951
952                                 /* Invert the parent matrix */
953                                 Mat4Invert (iM_parentRest, M_parentRest);
954
955                                 /* Get the new head and tail */
956                                 VecSubf (newBone->head, eBone->head, eBone->parent->tail);
957                                 VecSubf (newBone->tail, eBone->tail, eBone->parent->tail);
958
959                                 Mat4MulVecfl(iM_parentRest, newBone->head);
960                                 Mat4MulVecfl(iM_parentRest, newBone->tail);
961         
962
963                         }
964
965                 }
966                 /*      ...otherwise add this bone to the armature's bonebase */
967                 else
968                         BLI_addtail (&arm->bonebase,newBone);
969         }
970
971         /* Make a pass through the new armature to fix rolling */
972         fix_bonelist_roll (&arm->bonebase, &G.edbo);
973
974         /* Get rid of pose channels that may have belonged to deleted bones */
975         collect_pose_garbage(G.obedit);
976 #endif
977 }
978
979 static void fix_bonelist_roll (ListBase *bonelist, ListBase *editbonelist)
980 {
981         Bone *curBone;
982         EditBone *ebone;
983
984         for (curBone=bonelist->first; curBone; curBone=curBone->next){
985                 
986                 /* Fix this bone's roll */
987 #if 1
988                 {
989                         float premat[4][4];
990                         float postmat[4][4];
991                         float difmat[4][4];
992                         float imat[4][4];
993                         float delta[3];
994
995                         /* Find the associated editbone */
996                         for (ebone = editbonelist->first; ebone; ebone=ebone->next)
997                                 if ((Bone*)ebone->temp == curBone)
998                                         break;
999                         
1000                                 if (ebone){
1001                                         /* Get the premat */
1002                                         VecSubf (delta, ebone->tail, ebone->head);
1003                                         make_boneMatrixvr(premat, delta, ebone->roll);
1004                                         
1005                                         /* Get the postmat */
1006                                         get_objectspace_bone_matrix(curBone, postmat, 1, 0);
1007                                         postmat[3][0]=postmat[3][1]=postmat[3][2]=0.0F;
1008 #if 1
1009                                         Mat4Invert (imat, premat);
1010                                         Mat4MulMat4 (difmat, postmat, imat);
1011 #else
1012                                         Mat4Invert (imat, postmat);
1013                                         Mat4MulMat4 (difmat, premat, imat);
1014 #endif
1015 #if 0
1016                                         printf ("Bone %s\n", curBone->name);
1017                                         printmatrix4 ("premat", premat);
1018                                         printmatrix4 ("postmat", postmat);
1019                                         printmatrix4 ("difmat", difmat);
1020                                         printf ("Roll = %f\n",  (-atan(difmat[2][0]/difmat[2][2]) * (180.0/M_PI)));
1021 #endif
1022                                         curBone->roll = -atan(difmat[2][0]/difmat[2][2]);
1023                                         
1024                                         if (difmat[0][0]<0)
1025                                                 curBone->roll +=M_PI;
1026                                         
1027                                 }
1028                 }
1029 #endif
1030                 
1031                 fix_bonelist_roll (&curBone->childbase, editbonelist);
1032         }
1033 }
1034
1035 void make_bone_parent(void)
1036 {
1037 /*      error ("Bone Parenting not yet implemented");   */
1038         return;
1039 }
1040
1041 static void make_boneList(ListBase* list, ListBase *bones, EditBone *parent)
1042 {
1043         EditBone        *eBone;
1044         Bone            *curBone;
1045         
1046         for (curBone=bones->first; curBone; curBone=curBone->next){
1047                 eBone=MEM_callocN(sizeof(EditBone),"make_editbone");
1048                 
1049                 /*      Copy relevant data from bone to eBone */
1050                 eBone->parent=parent;
1051                 strcpy (eBone->name, curBone->name);
1052                 eBone->flag = curBone->flag & ~(BONE_SELECTED|BONE_TIPSEL|BONE_ROOTSEL);
1053
1054                 /* Print bone matrix before and after */
1055
1056                 get_bone_root_pos(curBone, eBone->head, 0);
1057                 get_bone_tip_pos(curBone, eBone->tail, 0);
1058 //              eBone->roll=curBone->roll;
1059                 eBone->roll=0;
1060
1061 #if 1
1062                 {
1063                         float delta[3];
1064                         float premat[4][4];
1065                         float postmat[4][4];
1066                         float imat[4][4];
1067                         float difmat[4][4];
1068
1069                         VecSubf (delta, eBone->tail, eBone->head);
1070                         make_boneMatrixvr(postmat, delta, eBone->roll);
1071
1072                         get_objectspace_bone_matrix(curBone, premat, 1, 0);
1073
1074 #if 0
1075                         Mat4Invert (imat, premat);
1076                         Mat4MulMat4 (difmat, postmat, imat);
1077 #else
1078                         Mat4Invert (imat, postmat);
1079                         Mat4MulMat4 (difmat, premat, imat);
1080 #endif
1081 #if 0
1082                         printf ("Bone %s\n", curBone->name);
1083                         printmatrix4 ("diffmat", difmat);
1084                         printf ("Roll : atan of %f / %f = %f\n", difmat[2][0], difmat[2][2], (float)atan(difmat[2][0]/difmat[2][2])*(180.0F/M_PI));
1085 #endif
1086                         eBone->roll = atan(difmat[2][0]/difmat[2][2]);
1087
1088                          if (difmat[0][0]<0)
1089                                 eBone->roll +=M_PI;
1090                 }
1091 #endif          
1092                 eBone->dist= curBone->dist;
1093                 eBone->weight= curBone->weight;
1094                 eBone->boneclass = curBone->boneclass;
1095                 memcpy (eBone->loc, curBone->loc, sizeof(curBone->loc));
1096                 memcpy (eBone->dloc, curBone->dloc, sizeof(curBone->dloc));
1097                 /*              memcpy (eBone->orig, curBone->orig, sizeof(curBone->orig));*/
1098                 memcpy (eBone->size, curBone->size, sizeof(curBone->size));
1099                 memcpy (eBone->dsize, curBone->dsize, sizeof(curBone->dsize));
1100                 memcpy (eBone->quat, curBone->quat, sizeof(curBone->quat));
1101                 memcpy (eBone->dquat, curBone->dquat, sizeof(curBone->dquat));
1102                 memcpy (eBone->obmat, curBone->obmat, sizeof(curBone->obmat));
1103                 
1104
1105                 BLI_addtail (list, eBone);
1106                 
1107                 /*      Add children if necessary */
1108                 if (curBone->childbase.first) 
1109                         make_boneList (list, &curBone->childbase, eBone);
1110         }
1111         
1112
1113 }
1114
1115 #if 0
1116 static EditVert*         add_armatureVert (float *loc)
1117 {
1118         EditMesh *em = G.editMesh;
1119         EditVert*       vert=NULL;
1120
1121         vert = MEM_callocN (sizeof (EditVert), "armaturevert");
1122         if (vert){
1123                 VECCOPY (vert->co, loc);
1124                 BLI_addtail (&em->verts,vert);
1125         }
1126
1127         return vert;
1128
1129 }
1130
1131 static EditVert* get_armatureVert (float *loc)
1132 {
1133         EditMesh *em = G.editMesh;
1134         EditVert*       vert;
1135
1136         for (vert=em->verts.first;vert;vert=vert->next){
1137                 if ((vert->co[0]==loc[0])&&(vert->co[1]==loc[1])&&(vert->co[2]==loc[2])){
1138                         return (vert);
1139                 }
1140         }
1141
1142         return add_armatureVert (loc);
1143 }
1144 #endif
1145
1146 void draw_armature(Object *ob)
1147 {
1148         bArmature       *arm;
1149         Bone            *bone;
1150         EditBone        *eBone;
1151         unsigned int    index;
1152         float           delta[3],offset[3];
1153         float           bmat[4][4];
1154         float   length;
1155         
1156         if (ob==NULL) return;
1157         
1158         arm= ob->data; 
1159         if (arm==NULL) return;
1160
1161         if (!(ob->lay & G.vd->lay))
1162                 return;
1163
1164         if (arm->flag & ARM_DRAWXRAY) {
1165                 if(G.zbuf) glDisable(GL_DEPTH_TEST);
1166         }
1167
1168         /* If we're in editmode, draw the Global edit data */
1169         if(ob==G.obedit || (G.obedit && ob->data==G.obedit->data)) {
1170                 cpack (0x000000);
1171                 
1172                 arm->flag |= ARM_EDITMODE;
1173                 for (eBone=G.edbo.first, index=0; eBone; eBone=eBone->next, index++){
1174                         if (ob==G.obedit){
1175         //                      if ((eBone->flag&(BONE_TIPSEL | BONE_ROOTSEL))==(BONE_TIPSEL|BONE_ROOTSEL))
1176         //                              cpack (B_YELLOW);
1177         //                      else
1178                                         cpack (B_PURPLE);
1179                         }
1180                         else cpack (0x000000);
1181                         
1182                         glPushMatrix();
1183                         
1184                         /*      Compose the parent transforms (i.e. their translations) */
1185                         VECCOPY (offset,eBone->head);
1186
1187                         glTranslatef (offset[0],offset[1],offset[2]);
1188                         
1189                         delta[0]=eBone->tail[0]-eBone->head[0]; 
1190                         delta[1]=eBone->tail[1]-eBone->head[1]; 
1191                         delta[2]=eBone->tail[2]-eBone->head[2];
1192                         
1193                         length = sqrt (delta[0]*delta[0] + delta[1]*delta[1] +delta[2]*delta[2]);
1194
1195                         make_boneMatrixvr(bmat, delta, eBone->roll);
1196                         glMultMatrixf (bmat);
1197                         draw_bone (arm->flag, eBone->flag, index, eBone->name, length);
1198
1199                         glPopMatrix();
1200                         if (eBone->parent){
1201                                 glLoadName (-1);
1202                                 setlinestyle(3);
1203                                 
1204                                 glBegin(GL_LINES);
1205                                 glVertex3fv(eBone->parent->tail);
1206                                 glVertex3fv(eBone->head);
1207                                 glEnd();
1208
1209                                 setlinestyle(0);
1210                         }
1211                 };
1212                 arm->flag &= ~ARM_EDITMODE;
1213                 cpack (B_YELLOW);
1214                 
1215         }
1216         else{
1217                 /*      Draw hierarchical bone list (non-edit data) */
1218
1219                 /* Ensure we're using the mose recent pose */
1220                 if (!ob->pose)
1221                         ob->pose=MEM_callocN (sizeof(bPose), "pose");
1222
1223 #if 1   /* Activate if there are problems with action lag */
1224                 apply_pose_armature(arm, ob->pose, 0);
1225                 where_is_armature (ob);
1226 #endif
1227
1228                 if (G.obpose == ob){
1229                         arm->flag |= ARM_POSEMODE;
1230 #if 0   /* Depreciated interactive ik goal drawing */
1231                         if (arm->chainbase.first){
1232                                 glPushMatrix();
1233                                 glTranslatef(((PoseChain*)arm->chainbase.first)->goal[0],
1234                                         ((PoseChain*)arm->chainbase.first)->goal[1],
1235                                         ((PoseChain*)arm->chainbase.first)->goal[2]);
1236                                 drawaxes(1.0);
1237                                 glPopMatrix();
1238                         }
1239 #endif
1240                 }
1241                 index = 0;
1242                 for (bone=arm->bonebase.first; bone; bone=bone->next) {
1243                         glPushMatrix();
1244                         draw_bonechildren(bone, arm->flag, &index);
1245                         glPopMatrix();
1246                         if (arm->flag & ARM_POSEMODE)
1247                                 cpack (B_CYAN);
1248                 }
1249
1250                 arm->flag &= ~ARM_POSEMODE; 
1251         }
1252
1253         if (arm->flag & ARM_DRAWXRAY) {
1254                 if(G.zbuf) glEnable(GL_DEPTH_TEST);
1255         }
1256 }
1257
1258 static void draw_boneverti (float x, float y, float z, float size, int flag)
1259 {
1260         GLUquadricObj   *qobj;
1261
1262         size*=0.05;
1263
1264 /*
1265                 Ultimately dots should be drawn in screenspace
1266                 For now we'll just draw them any old way.
1267 */
1268         glPushMatrix();
1269
1270         glTranslatef(x, y, z);
1271
1272         qobj    = gluNewQuadric(); 
1273         gluQuadricDrawStyle(qobj, GLU_SILHOUETTE); 
1274         gluPartialDisk( qobj, 0,  1.0F*size, 32, 1, 360.0, 360.0);
1275
1276         glRotatef (90, 0, 1, 0);
1277         gluPartialDisk( qobj, 0,  1.0F*size, 32, 1, 360.0, 360.0);
1278
1279         glRotatef (90, 1, 0, 0);
1280         gluPartialDisk( qobj, 0,  1.0F*size, 32, 1, 360.0, 360.0);
1281
1282         gluDeleteQuadric(qobj);  
1283
1284         glPopMatrix();
1285 }
1286
1287 static void draw_bonechildren (Bone *bone, int flag, unsigned int *index)
1288 {
1289         Bone *cbone;
1290         float   delta[3];
1291         float   length;
1292         float M_objectspacemat[4][4];
1293
1294         if (bone==NULL) return;
1295         
1296         if (flag & ARM_POSEMODE){
1297                 if (bone->flag & BONE_SELECTED)
1298                         cpack (B_CYAN);
1299                 else
1300                         cpack (B_AQUA);
1301         }
1302         
1303         //      Draw a line from our root to the parent's tip
1304         if (bone->parent && !(bone->flag & (BONE_IK_TOPARENT|BONE_HIDDEN)) ){
1305                 float childMat[4][4];
1306                 float boneMat[4][4];
1307                 float tip[3], root[3];
1308                 get_objectspace_bone_matrix(bone->parent, boneMat, 0, 1);
1309                 get_objectspace_bone_matrix(bone, childMat, 1, 1);
1310                 
1311                 VECCOPY (tip, boneMat[3]);
1312                 VECCOPY (root, childMat[3]);
1313                 
1314                 if (flag & ARM_POSEMODE)
1315                         glLoadName (-1);
1316                 setlinestyle(3);
1317                 glBegin(GL_LINES);
1318                 glVertex3fv(tip);
1319                 glVertex3fv(root);
1320                 glEnd();
1321                 setlinestyle(0);
1322         }
1323         
1324         
1325         /* Draw this bone in objectspace */
1326         delta[0]=bone->tail[0]-bone->head[0];
1327         delta[1]=bone->tail[1]-bone->head[1];
1328         delta[2]=bone->tail[2]-bone->head[2];
1329         length = sqrt (delta[0]*delta[0] + delta[1]*delta[1] + delta[2]*delta[2] );
1330         
1331         /* Incorporates offset, rest rotation, user rotation and parent coordinates*/
1332         get_objectspace_bone_matrix(bone, M_objectspacemat, 1, 1);
1333         
1334         if (!(bone->flag & BONE_HIDDEN)){
1335                 glPushMatrix();
1336                 glMultMatrixf(M_objectspacemat);
1337                 
1338                 
1339                 if (flag & ARM_POSEMODE)
1340                         draw_bone(flag, (bone->parent && bone->parent->flag & BONE_HIDDEN) ? (bone->flag & ~BONE_IK_TOPARENT) : (bone->flag), *index, bone->name, length);
1341                 else
1342                         draw_bone(flag, (bone->parent && bone->parent->flag & BONE_HIDDEN) ? (bone->flag & ~BONE_IK_TOPARENT) : (bone->flag), -1, bone->name, length);
1343                 glPopMatrix();
1344         }
1345         (*index)++;
1346
1347         /* Draw the children */
1348         for (cbone= bone->childbase.first; cbone; cbone=cbone->next){
1349                 draw_bonechildren (cbone, flag, index);
1350         }
1351 }
1352
1353 static void draw_bone (int armflag, int boneflag, unsigned int id, char *name, float length)
1354 {
1355         float vec[2];
1356         float   bulge;
1357         float   pointsize;
1358         /* 
1359         FIXME: This routine should probably draw the bones in screenspace using
1360         the projected start & end points of the transformed bone 
1361         */
1362         
1363         pointsize = length;
1364         if (pointsize<0.1)
1365                 pointsize=0.1;
1366
1367         /*      Draw a 3d octahedral bone       */
1368         
1369         bulge=length*0.1;
1370
1371         if (id!=-1)
1372                 glLoadName((GLuint) id );
1373
1374         glPushMatrix();
1375
1376         /*      Draw root point if we have no IK parent */
1377         if (!(boneflag & BONE_IK_TOPARENT)){
1378                 if (id != -1)
1379                         glLoadName (id | BONESEL_ROOT);
1380                 if (armflag & ARM_EDITMODE){
1381                         if (boneflag & BONE_ROOTSEL)
1382                                 cpack (B_YELLOW);
1383                         else
1384                                 cpack (B_PURPLE);
1385                 }
1386                 draw_boneverti (0, 0, 0, pointsize, 0);
1387         }
1388
1389         /*      Draw tip point (for selection only )*/
1390
1391         if (id != -1)
1392                 glLoadName (id | BONESEL_TIP);
1393         
1394         if (armflag & ARM_EDITMODE){
1395                 if (boneflag & BONE_TIPSEL)
1396                         cpack (B_YELLOW);
1397                 else
1398                         cpack (B_PURPLE);
1399         }
1400         
1401         draw_boneverti (0, length, 0, pointsize, 0);
1402
1403         if (id != -1){
1404                 if (armflag & ARM_POSEMODE)
1405                         glLoadName((GLuint) id);
1406                 else{
1407 #if 1   /* Bones not selectable in editmode */  
1408                         glLoadName((GLuint) -1);
1409 #else
1410                         glLoadName ((GLuint) id|BONESEL_TIP|BONESEL_ROOT);
1411 #endif
1412                 }
1413         }
1414         
1415         
1416         if (armflag & ARM_EDITMODE){
1417                 if (boneflag & BONE_SELECTED)
1418                         cpack (B_YELLOW);
1419                 else
1420                         cpack (B_PURPLE);
1421         }
1422         
1423         /*      Draw additional axes */
1424         if (armflag & ARM_DRAWAXES){
1425                 drawaxes(length*0.25F);
1426         }
1427         
1428         /*      Section 1*/
1429         glBegin(GL_LINE_STRIP);
1430         vec[0]= vec[1]= 0;
1431         glVertex2fv(vec);
1432         
1433         vec[0]= -bulge; vec[1]= bulge;
1434         glVertex2fv(vec);
1435         
1436         vec[0]= 0; vec[1]= length;
1437         glVertex2fv(vec);
1438         
1439         vec[0]= bulge; vec[1]= bulge;
1440         glVertex2fv(vec);
1441         
1442         vec[0]= 0; vec[1]= 0;
1443         glVertex2fv(vec);
1444         glEnd();
1445         
1446         /*      Section 2*/
1447         glRotatef(90,0,1,0);
1448         glBegin(GL_LINE_STRIP);
1449         vec[0]= vec[1]= 0;
1450         glVertex2fv(vec);
1451         
1452         vec[0]= -bulge; vec[1]= bulge;
1453         glVertex2fv(vec);
1454         
1455         vec[0]= 0; vec[1]= length;
1456         glVertex2fv(vec);
1457         
1458         vec[0]= bulge; vec[1]= bulge;
1459         glVertex2fv(vec);
1460         
1461         vec[0]= 0; vec[1]= 0;
1462         glVertex2fv(vec);
1463         glEnd();
1464         
1465         /*      Square*/
1466         glTranslatef (0,bulge,0);
1467         glRotatef(45,0,1,0);
1468         glRotatef(90,1,0,0);
1469         glBegin(GL_LINE_STRIP);
1470         
1471         vec[0]= -bulge*.707;vec[1]=-bulge*.707;
1472         glVertex2fv(vec);
1473         
1474         vec[0]= bulge*.707;vec[1]= -bulge*.707;
1475         glVertex2fv(vec);
1476         
1477         vec[0]= bulge*.707;vec[1]= bulge*.707;
1478         glVertex2fv(vec);
1479         
1480         vec[0]= -bulge*.707;vec[1]= bulge*.707;
1481         glVertex2fv(vec);
1482         
1483         vec[0]= vec[1]= -bulge*.707;
1484         glVertex2fv(vec);
1485         glEnd();
1486         
1487
1488         glPopMatrix();
1489
1490         /*      Draw the bone name */
1491         if (armflag & ARM_DRAWNAMES){
1492                 glRasterPos3f(0,  length/2.0,  0);
1493                 BMF_DrawString(G.font, " ");
1494                 BMF_DrawString(G.font, name);
1495         }
1496 }
1497
1498
1499
1500 void add_primitiveArmature(int type)
1501 {
1502         if(G.scene->id.lib) return;
1503         
1504         /* this function also comes from an info window */
1505         if ELEM(curarea->spacetype, SPACE_VIEW3D, SPACE_INFO); else return;
1506         if(G.vd==NULL) return;
1507         
1508         G.f &= ~(G_VERTEXPAINT+G_FACESELECT+G_TEXTUREPAINT+G_WEIGHTPAINT);
1509         setcursor_space(SPACE_VIEW3D, CURSOR_STD);
1510
1511         check_editmode(OB_ARMATURE);
1512         
1513         /* If we're not the "obedit", make a new object and enter editmode */
1514         if(G.obedit==NULL) {
1515                 add_object(OB_ARMATURE);
1516                 base_init_from_view3d(BASACT, G.vd);
1517                 G.obedit= BASACT->object;
1518                 
1519                 where_is_object(G.obedit);
1520                 
1521                 make_editArmature();
1522                 setcursor_space(SPACE_VIEW3D, CURSOR_EDIT);
1523         }
1524         
1525         switch (type){
1526         default:
1527                 add_bone_input (G.obedit);      
1528                 break;
1529         };
1530         
1531         countall();
1532
1533         allqueue(REDRAWALL, 0);
1534 }
1535
1536 static void add_bone_input (Object *ob)
1537 /*
1538         FUNCTION: 
1539         Creates a bone chain under user input.
1540         As the user clicks to accept each bone,
1541         a new bone is started as the child and IK
1542         child of the previous bone.  Pressing ESC
1543         cancels the current bone and leaves bone
1544         adding mode.
1545
1546 */
1547 {
1548         float           *cursLoc, cent[3], dx, dy;
1549         float           mat[3][3], curs[3],     cmat[3][3], imat[3][3], rmat[4][4], itmat[4][4];
1550         short           xo, yo, mval[2], afbreek=0;
1551         short           val;
1552         float           restmat[4][4], tempVec[4];
1553         EditBone        *bone;
1554         EditBone        *parent;
1555         unsigned short          event;
1556         float           angle, scale;
1557         float           length, lengths;
1558         float   newEnd[4];
1559         int                     addbones=1;
1560         float           dvec[3], dvecp[3];
1561         
1562         cursLoc= give_cursor();
1563         
1564         VECCOPY (curs,cursLoc);
1565         
1566         while (addbones>0){
1567                 afbreek=0;
1568                 /*      Create an inverse matrix */
1569                 Mat3CpyMat4(mat, G.obedit->obmat);
1570                 VECCOPY(cent, curs);
1571                 cent[0]-= G.obedit->obmat[3][0];
1572                 cent[1]-= G.obedit->obmat[3][1];
1573                 cent[2]-= G.obedit->obmat[3][2];
1574                 
1575                 Mat3CpyMat4(imat, G.vd->viewmat);
1576                 Mat3MulVecfl(imat, cent);
1577                 
1578                 Mat3MulMat3(cmat, imat, mat);
1579                 Mat3Inv(imat,cmat);
1580                 
1581                 /*      Create a temporary bone */
1582                 bone= MEM_callocN(sizeof(EditBone), "eBone");
1583                 
1584                 /*      If we're the child of something, set that up now */
1585                 if (addbones>1){
1586                         parent=G.edbo.last;
1587                         bone->parent=parent;
1588                         bone->flag|=BONE_IK_TOPARENT;
1589                 }
1590                 
1591                 strcpy (bone->name,"Bone");
1592                 unique_editbone_name (bone->name);
1593         
1594                 BLI_addtail(&G.edbo, bone);
1595         
1596                 bone->flag |= BONE_QUATROT;
1597                 bone->flag |= (BONE_SELECTED);
1598                 deselectall_armature();
1599                 bone->flag |= BONE_SELECTED|BONE_HILIGHTED|BONE_TIPSEL|BONE_ROOTSEL;
1600                 
1601                 bone->weight= 1.0F;
1602                 bone->dist= 1.0F;
1603                 bone->boneclass = BONE_SKINNABLE;
1604
1605                 /*      Project cursor center to screenspace. */
1606                 getmouseco_areawin(mval);
1607                 xo= mval[0];
1608                 yo= mval[1];
1609                 window_to_3d(dvecp, xo, yo);
1610
1611                 while (1) {
1612
1613                         getmouseco_areawin(mval);
1614                         window_to_3d(dvec, mval[0], mval[1]);
1615
1616                         scale=1000;
1617
1618                         dx=     ((float)mval[0]-(float)xo)*scale;
1619                         dy= ((float)mval[1]-(float)yo)*scale;
1620         
1621                         /*              Calc bone length*/
1622                         lengths= sqrt((dx*dx)+(dy*dy));
1623                         length = sqrt(((dvec[0]-dvecp[0])*(dvec[0]-dvecp[0]))+((dvec[1]-dvecp[1])*(dvec[1]-dvecp[1]))+((dvec[2]-dvecp[2])*(dvec[2]-dvecp[2])));
1624
1625                         /*              Find rotation around screen normal */
1626                         if (lengths>0.0F) {
1627                                 angle= acos(dy/lengths);
1628                                 if (dx<0.0F)
1629                                         angle*= -1.0F;
1630                         }
1631                         else angle= 0.0F;
1632                         
1633                         /*              FIXME:  Is there a blender-defined way of making rot and trans matrices? */
1634                         rmat[0][0]= cos (angle);
1635                         rmat[0][1]= -sin (angle);
1636                         rmat[0][2]= 0.0F;
1637                         rmat[0][3]= 0.0F;
1638                         rmat[1][0]= sin (angle);
1639                         rmat[1][1]= cos (angle);
1640                         rmat[1][2]= 0.0F;
1641                         rmat[1][3]= 0.0F;
1642                         rmat[2][0]= 0.0F;
1643                         rmat[2][1]= 0.0F;
1644                         rmat[2][2]= 1.0F;
1645                         rmat[2][3]= 0.0F;
1646                         rmat[3][0]= cent[0];
1647                         rmat[3][1]= cent[1];
1648                         rmat[3][2]= cent[2];
1649                         rmat[3][3]= 1.0F;
1650                         
1651                         /*              Rotate object's inversemat by the bone's rotation
1652                         to get the coordinate space of the bone */
1653                         Mat4CpyMat3     (itmat, imat);
1654                         Mat4MulMat4 (restmat, rmat, itmat);
1655                         
1656                         /*      Find the bone head */
1657                         tempVec[0]=0; tempVec[1]=0.0F; tempVec[2]=0.0F; tempVec[3]=1.0F;
1658                         Mat4MulVec4fl (restmat, tempVec);
1659                         VECCOPY (bone->head, tempVec);
1660                         
1661                         /*      Find the bone tail */
1662                         tempVec[0]=0; tempVec[1]=length; tempVec[2]=0.0F; tempVec[3]=1.0F;
1663                         Mat4MulVec4fl (restmat, tempVec);
1664                         VECCOPY (bone->tail, tempVec);
1665                         
1666                         /*      IF we're a child of something, add the parents' translates      */
1667                         
1668                         /*      Offset of child is new cursor*/
1669
1670                         VECCOPY (newEnd,bone->tail); newEnd[3]=1;
1671
1672                         /*      Set the bone's transformations  */
1673                         Mat4One (bone->obmat);
1674                         bone->size[0]=bone->size[1]=bone->size[2]=1.0F;
1675
1676                         force_draw();
1677                         while(qtest()) {
1678                                 event= extern_qread(&val);
1679                                 if(val) {
1680                                         switch(event) {
1681                                         case ESCKEY:
1682                                         case RIGHTMOUSE:
1683                                                 BLI_freelinkN (&G.edbo,bone);
1684                                                 afbreek=1;
1685                                                 addbones=0;
1686                                                 break;
1687                                         case LEFTMOUSE:
1688                                         case MIDDLEMOUSE:
1689                                         case SPACEKEY:
1690                                         case RETKEY:
1691                                                 afbreek= 1;
1692                                                                                         
1693                                                 Mat4MulVec4fl (G.obedit->obmat,newEnd);
1694                                                 
1695                                                 curs[0]=newEnd[0];
1696                                                 curs[1]=newEnd[1];
1697                                                 curs[2]=newEnd[2];
1698                                                 addbones++;
1699                                                 break;
1700                                         }       /*      End of case*/
1701                                 }       /*      End of if (val)*/
1702                                 if(afbreek) break;
1703                         }       /*      Endd of Qtest loop      */
1704
1705                 if(afbreek) break;
1706                 }/*     End of positioning loop (while)*/
1707         }       /*      End of bone adding loop*/
1708         
1709         countall();
1710
1711 }
1712
1713 void attach_bone_to_parent_cb(void *bonev, void *arg2_unused)
1714 {
1715         EditBone *curBone= bonev;
1716         attach_bone_to_parent(curBone);
1717 }
1718
1719 void attach_bone_to_parent(EditBone *bone)
1720 {
1721         EditBone *curbone;
1722
1723         if (bone->flag & BONE_IK_TOPARENT) {
1724
1725                 /* See if there are any other bones that refer to the same 
1726                  * parent and disconnect them 
1727                  */
1728                 for (curbone = G.edbo.first; curbone; curbone=curbone->next){
1729                         if (curbone!=bone){
1730                                 if (curbone->parent && 
1731                                         (curbone->parent == bone->parent) && 
1732                                         (curbone->flag & BONE_IK_TOPARENT))
1733                                         curbone->flag &= ~BONE_IK_TOPARENT;
1734                         }
1735                 }
1736
1737         /* Attach this bone to its parent */
1738                 VECCOPY(bone->head, bone->parent->tail);
1739         }
1740 }
1741
1742 void deselectall_armature(void)
1743 /*      Actually, it toggles selection, deselecting
1744         everything if anything is selected */
1745 {
1746         EditBone        *eBone;
1747         int                     sel=1;
1748         
1749         
1750         /*      Determine if there are any selected bones
1751                 And therefore whether we are selecting or deselecting */
1752         for (eBone=G.edbo.first;eBone;eBone=eBone->next){
1753                 if (eBone->flag & (BONE_SELECTED | BONE_TIPSEL | BONE_ROOTSEL)){
1754                         sel=0;
1755                         break;
1756                 };
1757         };
1758         
1759         /*      Set the flags */
1760         for (eBone=G.edbo.first;eBone;eBone=eBone->next){
1761                 if (sel)
1762                         eBone->flag |= (BONE_SELECTED | BONE_TIPSEL | BONE_ROOTSEL);
1763                 else
1764                         eBone->flag &= ~(BONE_SELECTED | BONE_TIPSEL | BONE_ROOTSEL);
1765         };
1766         allqueue(REDRAWVIEW3D, 0);
1767         allqueue(REDRAWBUTSEDIT, 0);
1768         allqueue(REDRAWBUTSHEAD, 0);
1769         allqueue(REDRAWBUTSOBJECT, 0);
1770         countall();
1771 }
1772
1773 void join_armature(void)
1774 {
1775         
1776         Object  *ob;
1777         Base    *base, *nextbase;
1778         ListBase eblist;
1779         EditBone *curbone, *next;
1780         float   mat[4][4], imat[4][4];
1781         
1782         /*      Ensure we're not in editmode and that the active object is an armature*/
1783         if(G.obedit) return;
1784         
1785         ob= OBACT;
1786         if(ob->type!=OB_ARMATURE) return;
1787         
1788         /*      Make sure the user wants to continue*/
1789         if(okee("Join selected Armatures")==0) return;
1790         
1791         /*      Put the active armature into editmode and join the bones from the other one*/
1792 #if 1
1793         enter_editmode();
1794 #else
1795         baselist.first=baselist.last=0;
1796         make_boneList(&baselist, &((bArmature*)ob->data)->bonebase, NULL);
1797 #endif
1798         
1799         for (base=FIRSTBASE; base; base=nextbase) {
1800                 nextbase = base->next;
1801                 if (TESTBASE(base)){
1802                         if ((base->object->type==OB_ARMATURE) && (base->object!=ob)){
1803                                 /* Make a list of editbones */
1804                                 eblist.first=eblist.last=0;
1805                                 make_boneList (&eblist, &((bArmature*)base->object->data)->bonebase,NULL);
1806                                 /* Find the difference matrix */
1807                                 Mat4Invert(imat, ob->obmat);
1808                                 Mat4MulMat4(mat, base->object->obmat, imat);
1809                                 
1810                                 /* Copy bones from the object to the edit armature */
1811                                 for (curbone=eblist.first; curbone; curbone=next){
1812                                         next = curbone->next;
1813                                         
1814                                         /* Blank out tranformation data */
1815                                         curbone->loc[0]=curbone->loc[1]=curbone->loc[2]=0.0F;
1816                                         curbone->size[0]=curbone->size[1]=curbone->size[2]=1.0F;
1817                                         curbone->quat[0]=curbone->quat[1]=curbone->quat[2]=curbone->quat[3]=0.0F;
1818                                         
1819                                         unique_editbone_name (curbone->name);
1820                                         
1821                                         /* Transform the bone */
1822                                         {
1823                                                 float premat[4][4];
1824                                                 float postmat[4][4];
1825                                                 float difmat[4][4];
1826                                                 float imat[4][4];
1827                                                 float temp[4][4];
1828                                                 float delta[3];
1829
1830                                                 /* Get the premat */
1831                                                 VecSubf (delta, curbone->tail, curbone->head);
1832                                                 make_boneMatrixvr(temp, delta, curbone->roll);
1833                                                 Mat4MulMat4 (premat, temp, mat);
1834
1835                                                 Mat4MulVecfl(mat, curbone->head);
1836                                                 Mat4MulVecfl(mat, curbone->tail);
1837
1838                                                 /* Get the postmat */
1839                                                 VecSubf (delta, curbone->tail, curbone->head);
1840                                                 make_boneMatrixvr(postmat, delta, curbone->roll);
1841                                                 
1842                                                 /* Find the roll */
1843                                                 Mat4Invert (imat, premat);
1844                                                 Mat4MulMat4 (difmat, postmat, imat);
1845                                                 
1846                                                 curbone->roll -=atan(difmat[2][0]/difmat[2][2]);
1847                                                 
1848                                                 if (difmat[0][0]<0)
1849                                                         curbone->roll +=M_PI;
1850
1851                                         }
1852 #if 1
1853                                         BLI_remlink(&eblist, curbone);
1854                                         BLI_addtail(&G.edbo, curbone);
1855 #else
1856                                         BLI_remlink(&eblist, curbone);
1857                                         BLI_addtail(&baselist, curbone);
1858 #endif
1859                                 }
1860                                 
1861                                 free_and_unlink_base(base);
1862                         }
1863                 }
1864         }
1865         
1866 #if 1
1867         exit_editmode(1);
1868 #else
1869         editbones_to_armature(&baselist, ob);
1870         if (baselist.first){
1871                 BLI_freelistN (&baselist);
1872         }
1873 #endif
1874         allqueue(REDRAWVIEW3D, 0);
1875
1876 }
1877
1878
1879 static int      editbone_name_exists (char *name){
1880         EditBone        *eBone;
1881         
1882         for (eBone=G.edbo.first; eBone; eBone=eBone->next){
1883                 if (!strcmp (name, eBone->name))
1884                         return 1;
1885         }
1886         
1887         return 0;
1888                 
1889 }
1890
1891 void unique_editbone_name (char *name){
1892         char            tempname[64];
1893         int                     number;
1894         char            *dot;
1895         
1896         
1897         if (editbone_name_exists(name)){
1898                 /*      Strip off the suffix */
1899                 dot=strchr(name, '.');
1900                 if (dot)
1901                         *dot=0;
1902                 
1903                 for (number = 1; number <=999; number++){
1904                         sprintf (tempname, "%s.%03d", name, number);
1905                         if (!editbone_name_exists(tempname)){
1906                                 strcpy (name, tempname);
1907                                 return;
1908                         }
1909                 }
1910         }
1911 }
1912
1913 void extrude_armature(void)
1914 {
1915         EditBone *newbone, *curbone, *first=NULL, *partest;
1916         
1917         TEST_EDITARMATURE;
1918         
1919         
1920         if(okee("Extrude Bone Segments")==0) return;
1921         
1922         /* Duplicate the necessary bones */
1923         for (curbone = G.edbo.first; ((curbone) && (curbone!=first)); curbone=curbone->next){
1924                 if (curbone->flag & (BONE_TIPSEL|BONE_SELECTED)){
1925                         newbone = MEM_callocN(sizeof(EditBone), "extrudebone");
1926                         
1927                         
1928                         VECCOPY (newbone->head, curbone->tail);
1929                         VECCOPY (newbone->tail, newbone->head);
1930                         newbone->parent = curbone;
1931                         newbone->flag = BONE_TIPSEL;
1932                         newbone->flag |= BONE_QUATROT;
1933                         newbone->weight= curbone->weight;
1934                         newbone->dist= curbone->dist;
1935                         newbone->boneclass= curbone->boneclass;
1936
1937                         Mat4One(newbone->obmat);
1938                         
1939                         /* See if there are any ik children of the parent */
1940                         for (partest = G.edbo.first; partest; partest=partest->next){
1941                                 if ((partest->parent == curbone) && (partest->flag & BONE_IK_TOPARENT))
1942                                         break;
1943                         }
1944                         
1945                         if (!partest)
1946                                 newbone->flag |= BONE_IK_TOPARENT;
1947                         
1948                         strcpy (newbone->name, curbone->name);
1949                         unique_editbone_name(newbone->name);
1950                         
1951                         /* Add the new bone to the list */
1952                         BLI_addtail(&G.edbo, newbone);
1953                         if (!first)
1954                                 first = newbone;
1955                 }
1956                 
1957                 /* Deselect the old bone */
1958                 curbone->flag &= ~(BONE_TIPSEL|BONE_SELECTED|BONE_ROOTSEL);
1959                 
1960         }
1961         
1962         /* Transform the endpoints */
1963         countall();
1964         transform('g');         
1965         allqueue(REDRAWBUTSEDIT, 0);
1966         allqueue(REDRAWBUTSOBJECT, 0);
1967 }
1968
1969 void addvert_armature(void)
1970 {
1971 /*      
1972         I haven't decided if it will be possible to add bones in this way.
1973         For the moment, we'll use Extrude, or explicit parenting.
1974         */
1975 }
1976
1977
1978 EditBone *get_named_editbone(char *name)
1979 {
1980         EditBone  *eBone;
1981
1982         if (name)
1983                 for (eBone=G.edbo.first; eBone; eBone=eBone->next){
1984                         if (!strcmp (name, eBone->name))
1985                                 return eBone;
1986                 }
1987
1988         return NULL;
1989 }
1990
1991 void update_dup_subtarget(EditBone *dupBone)
1992 {
1993         /* If an edit bone has been duplicated, lets
1994          * update it's constraints if the subtarget
1995          * they point to has also been duplicated
1996          */
1997         EditBone     *oldtarget, *newtarget;
1998         bPoseChannel *chan;
1999         bConstraint  *curcon;
2000         ListBase     *conlist;
2001         char         *subname;
2002
2003
2004         if ( (chan = verify_pose_channel(OBACT->pose, dupBone->name)) )
2005                 if ( (conlist = &chan->constraints) )
2006                         for (curcon = conlist->first; curcon; curcon=curcon->next) {
2007                                 /* does this constraint have a subtarget in
2008                                  * this armature?
2009                                  */
2010                                 subname = get_con_subtarget_name(curcon, G.obedit);
2011                                 oldtarget = get_named_editbone(subname);
2012                                 if (oldtarget)
2013                                         /* was the subtarget bone duplicated too? If
2014                                          * so, update the constraint to point at the 
2015                                          * duplicate of the old subtarget.
2016                                          */
2017                                         if (oldtarget->flag & BONE_SELECTED){
2018                                                 newtarget = (EditBone*) oldtarget->temp;
2019                                                 strcpy(subname, newtarget->name);
2020                                         }
2021                         }
2022         
2023 }
2024
2025 void adduplicate_armature(void)
2026 {
2027         EditBone        *eBone = NULL;
2028         EditBone        *curBone;
2029         EditBone        *firstDup=NULL; /*      The beginning of the duplicated bones in the edbo list */
2030
2031         countall();
2032
2033         /*      Find the selected bones and duplicate them as needed */
2034         for (curBone=G.edbo.first; curBone && curBone!=firstDup; curBone=curBone->next){
2035                 if (curBone->flag & BONE_SELECTED){
2036
2037                         eBone=MEM_callocN(sizeof(EditBone), "addup_editbone");
2038                         eBone->flag |= BONE_SELECTED;
2039
2040                         /*      Copy data from old bone to new bone */
2041                         memcpy (eBone, curBone, sizeof(EditBone));
2042
2043                         /* Blank out tranformation data */
2044                         eBone->loc[0]=eBone->loc[1]=eBone->loc[2]=0.0F;
2045                         eBone->size[0]=eBone->size[1]=eBone->size[2]=1.0F;
2046                         eBone->quat[0]=eBone->quat[1]=eBone->quat[2]=eBone->quat[3]=0.0F;
2047
2048                         curBone->temp = eBone;
2049                         eBone->temp = curBone;
2050
2051                         unique_editbone_name (eBone->name);
2052                         BLI_addtail (&G.edbo, eBone);
2053                         if (!firstDup)
2054                                 firstDup=eBone;
2055
2056                         /* Lets duplicate the list of constraits that the
2057                          * current bone has.
2058                          */
2059                         if (OBACT->pose) {
2060                                 bPoseChannel *chanold, *channew;
2061                                 ListBase     *listold, *listnew;
2062
2063                                 chanold = verify_pose_channel (OBACT->pose, curBone->name);
2064                                 if (chanold) {
2065                                         listold = &chanold->constraints;
2066                                         if (listold){
2067                                                 channew = 
2068                                                         verify_pose_channel(OBACT->pose, eBone->name);
2069                                                 if (channew) {
2070                                                         listnew = &channew->constraints;
2071                                                         copy_constraints (listnew, listold);
2072                                                 }
2073                                         }
2074                                 }
2075                         }
2076                 }
2077         }
2078
2079         if (eBone){
2080                 /*      Fix the head and tail */        
2081                 if (eBone->parent && !eBone->parent->flag & BONE_SELECTED){
2082                         VecSubf (eBone->tail, eBone->tail, eBone->head);
2083                         VecSubf (eBone->head, eBone->head, eBone->head);
2084                 }
2085         }
2086
2087         /*      Run though the list and fix the pointers */
2088         for (curBone=G.edbo.first; curBone && curBone!=firstDup; curBone=curBone->next){
2089
2090                 if (curBone->flag & BONE_SELECTED){
2091                         eBone=(EditBone*) curBone->temp;
2092
2093                         /*      If this bone has no parent,
2094                                         Set the duplicate->parent to NULL
2095                         */
2096                         if (!curBone->parent){
2097                                 eBone->parent = NULL;
2098                         }
2099                         /*      If this bone has a parent that IS selected,
2100                                         Set the duplicate->parent to the curBone->parent->duplicate
2101                         */
2102                          else if (curBone->parent->flag & BONE_SELECTED){
2103                                 eBone->parent=(EditBone*) curBone->parent->temp;
2104                         }
2105                         /*      If this bone has a parent that IS not selected,
2106                                         Set the duplicate->parent to the curBone->parent
2107                         */
2108                          else {
2109                                 eBone->parent=(EditBone*) curBone->parent; 
2110                                 eBone->flag &= ~BONE_IK_TOPARENT;
2111                         }
2112
2113                         /* Lets try to fix any constraint subtargets that might
2114                            have been duplicated */
2115                         update_dup_subtarget(eBone);
2116                          
2117                 }
2118         } 
2119         
2120         /*      Deselect the old bones and select the new ones */
2121
2122         for (curBone=G.edbo.first; curBone && curBone!=firstDup; curBone=curBone->next){
2123                 curBone->flag &= ~(BONE_SELECTED | BONE_TIPSEL | BONE_ROOTSEL);
2124         }
2125
2126
2127         transform('g');
2128         allqueue(REDRAWBUTSEDIT, 0);
2129         allqueue(REDRAWBUTSOBJECT, 0);
2130 }
2131
2132 /*
2133  *
2134  *      POSING FUNCTIONS: Maybe move these to a separate file at some point
2135  *
2136  *
2137  */
2138
2139
2140 void clear_armature(Object *ob, char mode){
2141         Bone    *curBone;
2142         bArmature       *arm;
2143
2144         arm=get_armature(ob);
2145         
2146         if (!arm)
2147                 return;
2148
2149         for (curBone=arm->bonebase.first; curBone; curBone=curBone->next){
2150                 clear_armature_children (curBone, ob->pose, mode);
2151         }
2152
2153         where_is_armature (ob);
2154
2155 }
2156
2157 static void clear_armature_children (Bone *bone, bPose *pose, char mode){
2158         Bone                    *curBone;
2159         bPoseChannel    *chan;
2160         if (!bone)
2161                 return;
2162         
2163         chan = verify_pose_channel (pose, bone->name);
2164
2165         if (!chan)
2166                 return;
2167
2168         if (bone->flag & BONE_SELECTED){
2169                 switch (mode){
2170                 case 'r':
2171                         chan->quat[1]=chan->quat[2]=chan->quat[3]=0.0F; chan->quat[0]=1.0F;
2172                         break;
2173                 case 'g':
2174                         chan->loc[0]=chan->loc[1]=chan->loc[2]=0.0F;
2175                         break;
2176                 case 's':
2177                         chan->size[0]=chan->size[1]=chan->size[2]=1.0F;
2178                         break;
2179                         
2180                 }
2181         }
2182
2183         for (curBone=bone->childbase.first; curBone; curBone=curBone->next){
2184                 clear_armature_children (curBone, pose, mode);
2185         }
2186
2187 }
2188
2189 void mousepose_armature(void)
2190 /*
2191         Handles right-clicking for selection
2192         of bones in armature pose modes.
2193 */
2194 {
2195         Bone            *nearBone;
2196
2197         if (!G.obpose)
2198                 return;
2199
2200         nearBone = get_nearest_bone(1);
2201
2202         if (nearBone){
2203                 if (!(G.qual & LR_SHIFTKEY)){
2204                         deselectall_posearmature(0);
2205                         nearBone->flag|=BONE_SELECTED;
2206                         select_actionchannel_by_name(G.obpose->action, nearBone->name, 1);
2207                 }
2208                 else {
2209                         if (nearBone->flag & BONE_SELECTED){
2210                                 nearBone->flag &= ~BONE_SELECTED;
2211                                 select_actionchannel_by_name(G.obpose->action, nearBone->name, 0);
2212                         }
2213                         else{
2214                                 nearBone->flag |= BONE_SELECTED;
2215                                 select_actionchannel_by_name(G.obpose->action, nearBone->name, 1);
2216                         }
2217                 };
2218         }
2219
2220         allqueue(REDRAWVIEW3D, 0);
2221         allqueue(REDRAWACTION, 0);
2222         allqueue(REDRAWIPO, 0);         /* To force action ipo update */
2223         allqueue(REDRAWBUTSOBJECT, 0);
2224
2225 //      countall();
2226         rightmouse_transform();
2227         
2228 }
2229
2230 void make_trans_bones (char mode)
2231 /*      Used in pose mode       */
2232 {
2233         bArmature               *arm;
2234         Bone                    *curBone;
2235         int                             count=0;
2236
2237         transmain=NULL;
2238
2239         arm=get_armature (G.obpose);
2240         if (!arm)
2241                 return;
2242
2243         if (arm->flag & ARM_RESTPOS){
2244                 notice ("Transformation not possible while Rest Position is enabled");
2245                 return;
2246         }
2247
2248
2249         if (!(G.obpose->lay & G.vd->lay))
2250                 return;
2251
2252
2253         centroid[0]=centroid[1]=centroid[2]=0;
2254
2255         apply_pose_armature(arm, G.obpose->pose, 0);
2256         where_is_armature (G.obpose);
2257
2258         /*      Allocate memory for the transformation record */
2259         tottrans= count_bones (arm, BONE_SELECTED, 0);
2260
2261         if (!tottrans)
2262                 return;
2263
2264         transmain= MEM_callocN(tottrans*sizeof(TransOb), "bonetransmain");
2265
2266         for (curBone=arm->bonebase.first; curBone; curBone=curBone->next){
2267                 count = add_trans_bonechildren (G.obpose, curBone, transmain, count, mode);
2268         }
2269         
2270         tottrans=count;
2271         
2272         if (tottrans){
2273                 centroid[0]/=tottrans;
2274                 centroid[1]/=tottrans;
2275                 centroid[2]/=tottrans;
2276                 Mat4MulVecfl (G.obpose->obmat, centroid);
2277         }
2278         else{
2279                 MEM_freeN (transmain);
2280         }
2281         return;
2282
2283 }
2284
2285 static int      count_bones (bArmature *arm, int flagmask, int allbones)
2286 {
2287         int     count=0;
2288         Bone    *curBone;
2289
2290         if (!arm)
2291                 return 0;
2292
2293         for (curBone=arm->bonebase.first; curBone; curBone=curBone->next){
2294                 count = count_bonechildren (curBone, count, flagmask, allbones);
2295         }
2296
2297         return count;
2298
2299 }
2300
2301 static int count_bonechildren (Bone *bone, int incount, int flagmask, int allbones){
2302
2303         Bone    *curBone;
2304
2305         if (!bone)
2306                 return incount;
2307
2308         if (bone->flag & flagmask || flagmask == 0xFFFFFFFF){
2309                 incount++;
2310                 if (!allbones)
2311                         return incount;
2312         }
2313
2314         for (curBone=bone->childbase.first; curBone; curBone=curBone->next){
2315                 incount=count_bonechildren (curBone, incount, flagmask, allbones);
2316         }
2317
2318         return incount;
2319 }
2320
2321
2322 static int add_trans_bonechildren (Object* ob, Bone* bone, TransOb* buffer, int index, char mode)
2323 {
2324         Bone    *curBone;
2325         TransOb *curOb;
2326         float   parmat[4][4], tempmat[4][4];
2327         float tempobmat[4][4];
2328         float vec[3];
2329         if (!bone)
2330                 return index;
2331
2332         
2333         
2334         /* We don't let IK children get "grabbed" */
2335         if (bone->flag & BONE_SELECTED){
2336                 if (!((mode=='g' || mode=='G') && (bone->flag & BONE_IK_TOPARENT))){
2337                         
2338                         get_bone_root_pos (bone, vec, 1);
2339                 
2340                         VecAddf (centroid, centroid, vec);
2341                         
2342                         curOb=&buffer[index];
2343                         
2344                         curOb->ob = ob;
2345                         curOb->rot=NULL;
2346
2347                         curOb->quat= bone->quat;
2348                         curOb->size= bone->size;
2349                         curOb->loc = bone->loc;
2350
2351                         curOb->data = bone; //  FIXME: Dangerous
2352                         
2353                         memcpy (curOb->oldquat, bone->quat, sizeof (bone->quat));
2354                         memcpy (curOb->oldsize, bone->size, sizeof (bone->size));
2355                         memcpy (curOb->oldloc, bone->loc, sizeof (bone->loc));
2356
2357 #if 0
2358                         if (bone->parent)
2359                                 get_objectspace_bone_matrix(bone->parent, tempmat, 1, 1);
2360                         else
2361                                 Mat4One (tempmat);
2362 #else
2363                         /* Get the matrix of this bone minus the usertransform */
2364                         Mat4CpyMat4 (tempobmat, bone->obmat);
2365                         Mat4One (bone->obmat);
2366                         get_objectspace_bone_matrix(bone, tempmat, 1, 1);
2367                         Mat4CpyMat4 (bone->obmat, tempobmat);
2368
2369                         
2370 #endif
2371
2372 #if 1
2373                         Mat4MulMat4 (parmat, tempmat, ob->obmat);       /* Original */
2374
2375                         /* Get world transform */
2376                         get_objectspace_bone_matrix(bone, tempmat, 1, 1);
2377                         if (ob->parent){
2378                                 where_is_object(ob->parent);
2379                                 Mat4MulSerie (tempobmat, ob->parent->obmat, ob->obmat, tempmat, NULL, NULL, NULL, NULL, NULL);
2380                         }
2381                         else
2382                                 Mat4MulSerie (tempobmat, ob->obmat, tempmat, NULL, NULL, NULL, NULL, NULL, NULL);
2383                         Mat3CpyMat4 (curOb->axismat, tempobmat);
2384                         Mat3Ortho(curOb->axismat);
2385
2386 #else
2387                         Mat4MulMat4 (parmat, ob->obmat, tempmat);
2388 #endif
2389                         Mat3CpyMat4 (curOb->parmat, parmat);
2390                         Mat3Inv (curOb->parinv, curOb->parmat);
2391
2392                         Mat3CpyMat4 (curOb->obmat, bone->obmat);
2393                         Mat3Inv (curOb->obinv, curOb->obmat);
2394                         
2395                         index++;
2396                         return index;
2397                 }
2398
2399         }
2400         
2401         /*      Recursively search  */
2402         for (curBone = bone->childbase.first; curBone; curBone=curBone->next){
2403                 index=add_trans_bonechildren (ob, curBone, buffer, index, mode);
2404         }
2405
2406         return index;
2407 }
2408
2409 static void deselect_bonechildren (Bone *bone, int mode)
2410 {
2411         Bone    *curBone;
2412
2413         if (!bone)
2414                 return;
2415
2416         if (mode==0)
2417                 bone->flag &= ~BONE_SELECTED;
2418         else if (!(bone->flag & BONE_HIDDEN))
2419                 bone->flag |= BONE_SELECTED;
2420
2421         select_actionchannel_by_name(G.obpose->action, bone->name, mode);
2422
2423         for (curBone=bone->childbase.first; curBone; curBone=curBone->next){
2424                 deselect_bonechildren(curBone, mode);
2425         }
2426 }
2427
2428
2429 void deselectall_posearmature (int test){
2430         int     selectmode      =       0;
2431         Bone*   curBone;
2432         
2433         /*      Determine if we're selecting or deselecting     */
2434         if (test){
2435                 if (!count_bones (get_armature(G.obpose), BONE_SELECTED, 0))
2436                         selectmode = 1;
2437         }
2438         
2439         /*      Set the flags accordingly       */
2440         for (curBone=get_armature(G.obpose)->bonebase.first; curBone; curBone=curBone->next)
2441                 deselect_bonechildren (curBone, selectmode);
2442         
2443         allqueue(REDRAWVIEW3D, 0);
2444         allqueue(REDRAWACTION, 0);
2445
2446 }
2447
2448 void auto_align_armature(void)
2449 /* Sets the roll value of selected bones so that their zaxes point upwards */
2450 {
2451         EditBone *ebone;
2452         float   xaxis[3]={1.0, 0.0, 0.0}, yaxis[3], zaxis[3]={0.0, 0.0, 1.0};
2453         float   targetmat[4][4], imat[4][4];
2454         float   curmat[4][4], diffmat[4][4];
2455         float   delta[3];
2456
2457         for (ebone = G.edbo.first; ebone; ebone=ebone->next){
2458                 if (ebone->flag & BONE_SELECTED){
2459                         /* Find the current bone matrix */
2460                         VecSubf(delta, ebone->tail, ebone->head);
2461                         make_boneMatrixvr (curmat, delta, 0.0);
2462                         
2463                         /* Make new matrix based on y axis & z-up */
2464                         VECCOPY (yaxis, curmat[1]);
2465
2466                         Mat4One(targetmat);
2467                         VECCOPY (targetmat[0], xaxis);
2468                         VECCOPY (targetmat[1], yaxis);
2469                         VECCOPY (targetmat[2], zaxis);
2470                         Mat4Ortho(targetmat);
2471
2472                         /* Find the difference between the two matrices */
2473
2474                         Mat4Invert (imat, targetmat);
2475                         Mat4MulMat4(diffmat, curmat, imat);
2476
2477                         ebone->roll = atan(diffmat[2][0]/diffmat[2][2]);
2478                         
2479                 }
2480         }
2481
2482
2483 int bone_looper(Object *ob, Bone *bone, void *data,
2484                         int (*bone_func)(Object *, Bone *, void *)) {
2485
2486     /* We want to apply the function bone_func to every bone 
2487      * in an armature -- feed bone_looper the first bone and 
2488      * a pointer to the bone_func and watch it go!. The int count 
2489      * can be useful for counting bones with a certain property
2490      * (e.g. skinnable)
2491      */
2492     int count = 0;
2493
2494     if (bone) {
2495
2496         /* only do bone_func if the bone is non null
2497          */
2498         count += bone_func(ob, bone, data);
2499
2500         /* try to execute bone_func for the first child
2501          */
2502         count += bone_looper(ob, bone->childbase.first, data,
2503                                     bone_func);
2504
2505         /* try to execute bone_func for the next bone at this
2506          * depth of the recursion.
2507          */
2508         count += bone_looper(ob, bone->next, data, bone_func);
2509     }
2510
2511     return count;
2512 }
2513
2514 int ik_chain_looper(Object *ob, Bone *bone, void *data,
2515                                    int (*bone_func)(Object *, Bone *, void *)) {
2516
2517     /* We want to apply the function bone_func to every bone 
2518      * in an ik chain -- feed ikchain_looper a bone in the chain and 
2519      * a pointer to the bone_func and watch it go!. The int count 
2520      * can be useful for counting bones with a certain property
2521      * (e.g. skinnable)
2522      */
2523         Bone *curBone;
2524     int   count = 0;
2525
2526     if (bone) {
2527
2528         /* This bone */
2529         count += bone_func(ob, bone, data);
2530
2531         /* The parents */
2532                 for (curBone = bone; curBone; curBone=curBone->parent) {
2533                         if (!curBone->parent)
2534                                 break;
2535                         else if (!(curBone->flag & BONE_IK_TOPARENT))
2536                                 break;
2537                         count += bone_func(ob, curBone->parent, data);
2538                 }
2539
2540                 /* The children */
2541                 for (curBone = bone->childbase.first; curBone; curBone=curBone->next){
2542                         if (curBone->flag & BONE_IK_TOPARENT) {
2543                                 count += bone_func(ob, curBone, data);
2544                         }
2545                 }
2546     }
2547
2548     return count;
2549 }
2550
2551 int bone_skinnable(Object *ob, Bone *bone, void *data)
2552 {
2553     /* Bones that are not of boneclass BONE_UNSKINNABLE
2554      * are regarded to be "skinnable" and are eligible for
2555      * auto-skinning.
2556      *
2557      * This function performs 2 functions:
2558      *
2559      *   a) It returns 1 if the bone is skinnable.
2560      *      If we loop over all bones with this 
2561      *      function, we can count the number of
2562      *      skinnable bones.
2563      *   b) If the pointer data is non null,
2564      *      it is treated like a handle to a
2565      *      bone pointer -- the bone pointer
2566      *      is set to point at this bone, and
2567      *      the pointer the handle points to
2568      *      is incremented to point to the
2569      *      next member of an array of pointers
2570      *      to bones. This way we can loop using
2571      *      this function to construct an array of
2572      *      pointers to bones that point to all
2573      *      skinnable bones.
2574      */
2575     Bone ***hbone;
2576
2577     if ( bone->boneclass != BONE_UNSKINNABLE ) {
2578                 if (data != NULL) {
2579                         hbone = (Bone ***) data;
2580             **hbone = bone;
2581             ++*hbone;
2582         }
2583         return 1;
2584     }
2585     return 0;
2586 }
2587
2588 int add_defgroup_unique_bone(Object *ob, Bone *bone, void *data) {
2589     /* This group creates a vertex group to ob that has the
2590      * same name as bone (provided the bone is skinnable). 
2591          * If such a vertex group aleady exist the routine exits.
2592      */
2593         if ( bone_skinnable(ob, bone, NULL) ) {
2594                 if (!get_named_vertexgroup(ob,bone->name)) {
2595                         add_defgroup_name(ob, bone->name);
2596                         return 1;
2597                 }
2598     }
2599     return 0;
2600 }
2601
2602 int dgroup_skinnable(Object *ob, Bone *bone, void *data) {
2603     /* Bones that are not of boneclass BONE_UNSKINNABLE
2604      * are regarded to be "skinnable" and are eligible for
2605      * auto-skinning.
2606      *
2607      * This function performs 2 functions:
2608      *
2609      *   a) If the bone is skinnable, it creates 
2610      *      a vertex group for ob that has
2611      *      the name of the skinnable bone
2612      *      (if one doesn't exist already).
2613      *   b) If the pointer data is non null,
2614      *      it is treated like a handle to a
2615      *      bDeformGroup pointer -- the 
2616      *      bDeformGroup pointer is set to point
2617      *      to the deform group with the bone's
2618      *      name, and the pointer the handle 
2619      *      points to is incremented to point to the
2620      *      next member of an array of pointers
2621      *      to bDeformGroups. This way we can loop using
2622      *      this function to construct an array of
2623      *      pointers to bDeformGroups, all with names
2624      *      of skinnable bones.
2625      */
2626     bDeformGroup ***hgroup, *defgroup;
2627
2628     if ( bone->boneclass != BONE_UNSKINNABLE ) {
2629         if ( !(defgroup = get_named_vertexgroup(ob, bone->name)) ) {
2630             defgroup = add_defgroup_name(ob, bone->name);
2631         }
2632
2633         if (data != NULL) {
2634             hgroup = (bDeformGroup ***) data;
2635             **hgroup = defgroup;
2636             ++*hgroup;
2637         }
2638         return 1;
2639     }
2640     return 0;
2641 }
2642
2643 void add_verts_to_closest_dgroup(Object *ob, Object *par)
2644 {
2645     /* This function implements a crude form of 
2646      * auto-skinning: vertices are assigned to the
2647      * deformation groups associated with bones based
2648      * on thier proximity to a bone. Every vert is
2649      * given a weight of 1.0 to the weight group
2650      * cooresponding to the bone that it is
2651      * closest to. The vertex may also be assigned to
2652      * a deformation group associated to a bone
2653      * that is within 10% of the mninimum distance
2654      * between the bone and the nearest vert -- the
2655      * cooresponding weight will fall-off to zero
2656      * as the distance approaches the 10% tolerance mark.
2657          * If the mesh has subsurf enabled then the verts
2658          * on the subsurf limit surface is used to generate 
2659          * the weights rather than the verts on the cage
2660          * mesh.
2661      */
2662
2663     bArmature *arm;
2664     Bone **bonelist, **bonehandle, *bone;
2665     bDeformGroup **dgrouplist, **dgrouphandle, *defgroup;
2666     float *distance, mindist = 0.0, weight = 0.0;
2667     float   root[3];
2668     float   tip[3];
2669     float real_co[3];
2670         float *subverts = NULL;
2671     float *subvert;
2672     Mesh  *mesh;
2673     MVert *vert;
2674
2675     int numbones, i, j;
2676
2677     /* If the parent object is not an armature exit */
2678     arm = get_armature(par);
2679     if (!arm)
2680         return;
2681
2682     /* count the number of skinnable bones */
2683     numbones = bone_looper(ob, arm->bonebase.first, NULL,
2684                                   bone_skinnable);
2685
2686     /* create an array of pointer to bones that are skinnable
2687      * and fill it with all of the skinnable bones
2688      */
2689     bonelist = MEM_mallocN(numbones*sizeof(Bone *), "bonelist");
2690     bonehandle = bonelist;
2691     bone_looper(ob, arm->bonebase.first, &bonehandle,
2692                        bone_skinnable);
2693
2694     /* create an array of pointers to the deform groups that
2695      * coorespond to the skinnable bones (creating them
2696      * as necessary.
2697      */
2698     dgrouplist = MEM_mallocN(numbones*sizeof(bDeformGroup *), "dgrouplist");
2699     dgrouphandle = dgrouplist;
2700     bone_looper(ob, arm->bonebase.first, &dgrouphandle,
2701                        dgroup_skinnable);
2702
2703     /* create an array of floats that will be used for each vert
2704      * to hold the distance to each bone.
2705      */
2706     distance = MEM_mallocN(numbones*sizeof(float), "distance");
2707
2708     mesh = (Mesh*)ob->data;
2709
2710         /* Is subsurf on? Lets use the verts on the limit surface then */
2711         if (mesh->flag&ME_SUBSURF) {
2712                 subverts = MEM_mallocN(3*mesh->totvert*sizeof(float), "subverts");
2713                 subsurf_calculate_limit_positions(mesh, (void *)subverts);      /* (ton) made void*, dunno how to cast */
2714         }
2715
2716     /* for each vertex in the mesh ...
2717      */
2718     for ( i=0 ; i < mesh->totvert ; ++i ) {
2719         /* get the vert in global coords
2720          */
2721                 
2722                 if (subverts) {
2723                         subvert = subverts + i*3;
2724                         VECCOPY (real_co, subvert);
2725                 }
2726                 else {
2727                         vert = mesh->mvert + i;
2728                         VECCOPY (real_co, vert->co);
2729                 }
2730         Mat4MulVecfl(ob->obmat, real_co);
2731
2732
2733         /* for each skinnable bone ...
2734          */
2735         for (j=0; j < numbones; ++j) {
2736             bone = bonelist[j];
2737
2738             /* get the root of the bone in global coords
2739              */
2740             get_bone_root_pos (bone, root, 0);
2741             Mat4MulVecfl(par->obmat, root);
2742
2743             /* get the tip of the bone in global coords
2744              */
2745             get_bone_tip_pos (bone, tip, 0);
2746             Mat4MulVecfl(par->obmat, tip);
2747
2748             /* store the distance from the bone to
2749              * the vert
2750              */
2751             distance[j] = dist_to_bone(real_co, root, tip);
2752
2753             /* if this is the first bone, or if this
2754              * bone is less than mindist, then set this
2755              * distance to mindist
2756              */
2757             if (j == 0) {
2758                 mindist = distance[j];
2759             }
2760             else if (distance[j] < mindist) {
2761                 mindist = distance[j];
2762             }
2763         }
2764
2765         /* for each deform group ...
2766          */
2767         for (j=0; j < numbones; ++j) {
2768             defgroup = dgrouplist[j];
2769
2770             /* if the cooresponding bone is the closest one
2771              * add the vert to the deform group with weight 1
2772              */
2773             if (distance[j] <= mindist) {
2774                 add_vert_to_defgroup (ob, defgroup, i, 1.0, WEIGHT_REPLACE);
2775             }
2776
2777             /* if the cooresponding bone is within 10% of the
2778              * nearest distance, add the vert to the
2779              * deform group with a weight that declines with
2780              * distance
2781              */
2782             else if (distance[j] <= mindist*1.10) {
2783                 if (mindist > 0)
2784                     weight = 1.0 - (distance[j] - mindist) / (mindist * 0.10);
2785                 add_vert_to_defgroup (ob, defgroup, i, weight, WEIGHT_REPLACE);
2786             }
2787             
2788             /* if the cooresponding bone is outside of the 10% tolerance
2789              * then remove the vert from the weight group (if it is
2790              * in that group)
2791              */
2792             else {
2793                 remove_vert_defgroup (ob, defgroup, i);
2794             }
2795         }
2796     }
2797
2798     /* free the memory allocated
2799      */
2800     MEM_freeN(bonelist);
2801     MEM_freeN(dgrouplist);
2802     MEM_freeN(distance);
2803         if (subverts) MEM_freeN(subverts);
2804 }
2805
2806 void create_vgroups_from_armature(Object *ob, Object *par)
2807 {
2808         /* Lets try to create some vertex groups 
2809          * based on the bones of the parent armature.
2810          */
2811
2812         bArmature *arm;
2813         short mode;
2814
2815         /* If the parent object is not an armature exit */
2816         arm = get_armature(par);
2817         if (!arm)
2818                 return;
2819
2820         /* Prompt the user on whether/how they want the vertex groups
2821          * added to the child mesh */
2822     mode= pupmenu("Create Vertex Groups? %t|"
2823                                   "Don't Create Groups %x1|"
2824                                   "Name Groups %x2|"
2825                   "Create From Closest Bones %x3");
2826         switch (mode){
2827         case 2:
2828                 /* Traverse the bone list, trying to create empty vertex 
2829                  * groups cooresponding to the bone.
2830                  */
2831                 bone_looper(ob, arm->bonebase.first, NULL,
2832                                         add_defgroup_unique_bone);
2833                 if (ob->type == OB_MESH)
2834                         create_dverts((Mesh*)ob->data);
2835
2836                 break;
2837
2838         case 3:
2839                 /* Traverse the bone list, trying to create vertex groups 
2840                  * that are populated with the vertices for which the
2841                  * bone is closest.
2842                  */
2843                 add_verts_to_closest_dgroup(ob, par);
2844                 break;
2845
2846         }
2847
2848
2849 int hide_selected_pose_bone(Object *ob, Bone *bone, void *ptr) {
2850         if (bone->flag & BONE_SELECTED) {
2851                 bone->flag |= BONE_HIDDEN;
2852                 bone->flag &= ~BONE_SELECTED;
2853         }
2854         return 0;
2855 }
2856
2857 void hide_selected_pose_bones(void) {
2858         bArmature               *arm;
2859
2860         arm=get_armature (G.obpose);
2861
2862         if (!arm)
2863                 return;
2864
2865         bone_looper(G.obpose, arm->bonebase.first, NULL, 
2866                                 hide_selected_pose_bone);
2867
2868         force_draw();
2869 }
2870
2871 int hide_unselected_pose_bone(Object *ob, Bone *bone, void *ptr) {
2872         if (~bone->flag & BONE_SELECTED) {
2873                 bone->flag |= BONE_HIDDEN;
2874         }
2875         return 0;
2876 }
2877
2878 void hide_unselected_pose_bones(void) {
2879         bArmature               *arm;
2880
2881         arm=get_armature (G.obpose);
2882
2883         if (!arm)
2884                 return;
2885
2886         bone_looper(G.obpose, arm->bonebase.first, NULL, 
2887                                 hide_unselected_pose_bone);
2888
2889         force_draw();
2890 }
2891
2892 int show_pose_bone(Object *ob, Bone *bone, void *ptr) {
2893         if (bone->flag & BONE_HIDDEN) {
2894                 bone->flag &= ~BONE_HIDDEN;
2895                 bone->flag |= BONE_SELECTED;
2896         }
2897
2898         return 0;
2899 }
2900
2901 void show_all_pose_bones(void) {
2902         bArmature               *arm;
2903
2904         arm=get_armature (G.obpose);
2905
2906         if (!arm)
2907                 return;
2908
2909         bone_looper(G.obpose, arm->bonebase.first, NULL, 
2910                                 show_pose_bone);
2911
2912         force_draw();
2913 }
2914
2915 int is_delay_deform(void)
2916 {
2917         bArmature               *arm;
2918
2919         arm=get_armature (G.obpose);
2920
2921         if (!arm)
2922                 return 0;
2923
2924         return (arm->flag & ARM_DELAYDEFORM);
2925 }