6941742a0c97ac802729bf40dc9871904536a717
[blender.git] / source / blender / blenkernel / intern / constraint.c
1 /**
2  * $Id$
3  *
4  * ***** BEGIN GPL 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.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software Foundation,
18  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
19  *
20  * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
21  * All rights reserved.
22  *
23  * The Original Code is: all of this file.
24  *
25  * Contributor(s): 2007, Joshua Leung, major recode
26  *
27  * ***** END GPL LICENSE BLOCK *****
28  */
29
30 #include <stdio.h> 
31 #include <stddef.h>
32 #include <string.h>
33 #include <math.h>
34 #include <float.h>
35
36 #include "MEM_guardedalloc.h"
37
38 #include "BLI_blenlib.h"
39 #include "BLI_math.h"
40 #include "BLI_editVert.h"
41
42 #include "DNA_armature_types.h"
43 #include "DNA_constraint_types.h"
44 #include "DNA_modifier_types.h"
45 #include "DNA_object_types.h"
46 #include "DNA_action_types.h"
47 #include "DNA_curve_types.h"
48 #include "DNA_mesh_types.h"
49 #include "DNA_meshdata_types.h"
50 #include "DNA_lattice_types.h"
51 #include "DNA_scene_types.h"
52 #include "DNA_text_types.h"
53
54 #include "BKE_utildefines.h"
55 #include "BKE_action.h"
56 #include "BKE_anim.h" /* for the curve calculation part */
57 #include "BKE_armature.h"
58 #include "BKE_blender.h"
59 #include "BKE_constraint.h"
60 #include "BKE_displist.h"
61 #include "BKE_deform.h"
62 #include "BKE_DerivedMesh.h"    /* for geometry targets */
63 #include "BKE_cdderivedmesh.h" /* for geometry targets */
64 #include "BKE_object.h"
65 #include "BKE_ipo.h"
66 #include "BKE_global.h"
67 #include "BKE_library.h"
68 #include "BKE_idprop.h"
69 #include "BKE_shrinkwrap.h"
70 #include "BKE_mesh.h"
71
72 #ifndef DISABLE_PYTHON
73 #include "BPY_extern.h"
74 #endif
75
76 #ifndef M_PI
77 #define M_PI            3.14159265358979323846
78 #endif
79
80
81
82 /* ************************ Constraints - General Utilities *************************** */
83 /* These functions here don't act on any specific constraints, and are therefore should/will
84  * not require any of the special function-pointers afforded by the relevant constraint 
85  * type-info structs.
86  */
87
88 /* -------------- Naming -------------- */
89
90 /* Find the first available, non-duplicate name for a given constraint */
91 void unique_constraint_name (bConstraint *con, ListBase *list)
92 {
93         BLI_uniquename(list, con, "Const", '.', offsetof(bConstraint, name), sizeof(con->name));
94 }
95
96 /* ----------------- Evaluation Loop Preparation --------------- */
97
98 /* package an object/bone for use in constraint evaluation */
99 /* This function MEM_calloc's a bConstraintOb struct, that will need to be freed after evaluation */
100 bConstraintOb *constraints_make_evalob (Scene *scene, Object *ob, void *subdata, short datatype)
101 {
102         bConstraintOb *cob;
103         
104         /* create regardless of whether we have any data! */
105         cob= MEM_callocN(sizeof(bConstraintOb), "bConstraintOb");
106         
107         /* for system time, part of deglobalization, code nicer later with local time (ton) */
108         cob->scene= scene;
109         
110         /* based on type of available data */
111         switch (datatype) {
112                 case CONSTRAINT_OBTYPE_OBJECT:
113                 {
114                         /* disregard subdata... calloc should set other values right */
115                         if (ob) {
116                                 cob->ob = ob;
117                                 cob->type = datatype;
118                                 cob->rotOrder = EULER_ORDER_DEFAULT; // TODO: when objects have rotation order too, use that
119                                 copy_m4_m4(cob->matrix, ob->obmat);
120                         }
121                         else
122                                 unit_m4(cob->matrix);
123                         
124                         copy_m4_m4(cob->startmat, cob->matrix);
125                 }
126                         break;
127                 case CONSTRAINT_OBTYPE_BONE:
128                 {
129                         /* only set if we have valid bone, otherwise default */
130                         if (ob && subdata) {
131                                 cob->ob = ob;
132                                 cob->pchan = (bPoseChannel *)subdata;
133                                 cob->type = datatype;
134                                 
135                                 if (cob->pchan->rotmode > 0) {
136                                         /* should be some type of Euler order */
137                                         cob->rotOrder= cob->pchan->rotmode; 
138                                 }
139                                 else {
140                                         /* Quats, so eulers should just use default order */
141                                         cob->rotOrder= EULER_ORDER_DEFAULT;
142                                 }
143                                 
144                                 /* matrix in world-space */
145                                 mul_m4_m4m4(cob->matrix, cob->pchan->pose_mat, ob->obmat);
146                         }
147                         else
148                                 unit_m4(cob->matrix);
149                                 
150                         copy_m4_m4(cob->startmat, cob->matrix);
151                 }
152                         break;
153                         
154                 default: /* other types not yet handled */
155                         unit_m4(cob->matrix);
156                         unit_m4(cob->startmat);
157                         break;
158         }
159         
160         return cob;
161 }
162
163 /* cleanup after constraint evaluation */
164 void constraints_clear_evalob (bConstraintOb *cob)
165 {
166         float delta[4][4], imat[4][4];
167         
168         /* prevent crashes */
169         if (cob == NULL) 
170                 return;
171         
172         /* calculate delta of constraints evaluation */
173         invert_m4_m4(imat, cob->startmat);
174         mul_m4_m4m4(delta, imat, cob->matrix);
175         
176         /* copy matrices back to source */
177         switch (cob->type) {
178                 case CONSTRAINT_OBTYPE_OBJECT:
179                 {
180                         /* cob->ob might not exist! */
181                         if (cob->ob) {
182                                 /* copy new ob-matrix back to owner */
183                                 copy_m4_m4(cob->ob->obmat, cob->matrix);
184                                 
185                                 /* copy inverse of delta back to owner */
186                                 invert_m4_m4(cob->ob->constinv, delta);
187                         }
188                 }
189                         break;
190                 case CONSTRAINT_OBTYPE_BONE:
191                 {
192                         /* cob->ob or cob->pchan might not exist */
193                         if (cob->ob && cob->pchan) {
194                                 /* copy new pose-matrix back to owner */
195                                 mul_m4_m4m4(cob->pchan->pose_mat, cob->matrix, cob->ob->imat);
196                                 
197                                 /* copy inverse of delta back to owner */
198                                 invert_m4_m4(cob->pchan->constinv, delta);
199                         }
200                 }
201                         break;
202         }
203         
204         /* free tempolary struct */
205         MEM_freeN(cob);
206 }
207
208 /* -------------- Space-Conversion API -------------- */
209
210 /* This function is responsible for the correct transformations/conversions 
211  * of a matrix from one space to another for constraint evaluation.
212  * For now, this is only implemented for Objects and PoseChannels.
213  */
214 void constraint_mat_convertspace (Object *ob, bPoseChannel *pchan, float mat[][4], short from, short to)
215 {
216         float tempmat[4][4];
217         float diff_mat[4][4];
218         float imat[4][4];
219         
220         /* prevent crashes in these unlikely events  */
221         if (ob==NULL || mat==NULL) return;
222         /* optimise trick - check if need to do anything */
223         if (from == to) return;
224         
225         /* are we dealing with pose-channels or objects */
226         if (pchan) {
227                 /* pose channels */
228                 switch (from) {
229                         case CONSTRAINT_SPACE_WORLD: /* ---------- FROM WORLDSPACE ---------- */
230                         {
231                                 /* world to pose */
232                                 invert_m4_m4(imat, ob->obmat);
233                                 copy_m4_m4(tempmat, mat);
234                                 mul_m4_m4m4(mat, tempmat, imat);
235                                 
236                                 /* use pose-space as stepping stone for other spaces... */
237                                 if (ELEM(to, CONSTRAINT_SPACE_LOCAL, CONSTRAINT_SPACE_PARLOCAL)) {
238                                         /* call self with slightly different values */
239                                         constraint_mat_convertspace(ob, pchan, mat, CONSTRAINT_SPACE_POSE, to);
240                                 }
241                         }
242                                 break;
243                         case CONSTRAINT_SPACE_POSE:     /* ---------- FROM POSESPACE ---------- */
244                         {
245                                 /* pose to world */
246                                 if (to == CONSTRAINT_SPACE_WORLD) {
247                                         copy_m4_m4(tempmat, mat);
248                                         mul_m4_m4m4(mat, tempmat, ob->obmat);
249                                 }
250                                 /* pose to local */
251                                 else if (to == CONSTRAINT_SPACE_LOCAL) {
252                                         if (pchan->bone) {
253                                                 if (pchan->parent) {
254                                                         float offs_bone[4][4];
255                                                                 
256                                                         /* construct offs_bone the same way it is done in armature.c */
257                                                         copy_m4_m3(offs_bone, pchan->bone->bone_mat);
258                                                         VECCOPY(offs_bone[3], pchan->bone->head);
259                                                         offs_bone[3][1]+= pchan->bone->parent->length;
260                                                         
261                                                         if (pchan->bone->flag & BONE_HINGE) {
262                                                                 /* pose_mat = par_pose-space_location * chan_mat */
263                                                                 float tmat[4][4];
264                                                                 
265                                                                 /* the rotation of the parent restposition */
266                                                                 copy_m4_m4(tmat, pchan->bone->parent->arm_mat);
267                                                                 
268                                                                 /* the location of actual parent transform */
269                                                                 VECCOPY(tmat[3], offs_bone[3]);
270                                                                 offs_bone[3][0]= offs_bone[3][1]= offs_bone[3][2]= 0.0f;
271                                                                 mul_m4_v3(pchan->parent->pose_mat, tmat[3]);
272                                                                 
273                                                                 mul_m4_m4m4(diff_mat, offs_bone, tmat);
274                                                                 invert_m4_m4(imat, diff_mat);
275                                                         }
276                                                         else {
277                                                                 /* pose_mat = par_pose_mat * bone_mat * chan_mat */
278                                                                 mul_m4_m4m4(diff_mat, offs_bone, pchan->parent->pose_mat);
279                                                                 invert_m4_m4(imat, diff_mat);
280                                                         }
281                                                 }
282                                                 else {
283                                                         /* pose_mat = chan_mat * arm_mat */
284                                                         invert_m4_m4(imat, pchan->bone->arm_mat);
285                                                 }
286                                                 
287                                                 copy_m4_m4(tempmat, mat);
288                                                 mul_m4_m4m4(mat, tempmat, imat);
289                                         }
290                                 }
291                                 /* pose to local with parent */
292                                 else if (to == CONSTRAINT_SPACE_PARLOCAL) {
293                                         if (pchan->bone) {
294                                                 invert_m4_m4(imat, pchan->bone->arm_mat);
295                                                 copy_m4_m4(tempmat, mat);
296                                                 mul_m4_m4m4(mat, tempmat, imat);
297                                         }
298                                 }
299                         }
300                                 break;
301                         case CONSTRAINT_SPACE_LOCAL: /* ------------ FROM LOCALSPACE --------- */
302                         {
303                                 /* local to pose - do inverse procedure that was done for pose to local */
304                                 if (pchan->bone) {
305                                         /* we need the posespace_matrix = local_matrix + (parent_posespace_matrix + restpos) */                                         
306                                         if (pchan->parent) {
307                                                 float offs_bone[4][4];
308                                                 
309                                                 /* construct offs_bone the same way it is done in armature.c */
310                                                 copy_m4_m3(offs_bone, pchan->bone->bone_mat);
311                                                 VECCOPY(offs_bone[3], pchan->bone->head);
312                                                 offs_bone[3][1]+= pchan->bone->parent->length;
313                                                 
314                                                 if (pchan->bone->flag & BONE_HINGE) {
315                                                         /* pose_mat = par_pose-space_location * chan_mat */
316                                                         float tmat[4][4];
317                                                         
318                                                         /* the rotation of the parent restposition */
319                                                         copy_m4_m4(tmat, pchan->bone->parent->arm_mat);
320                                                         
321                                                         /* the location of actual parent transform */
322                                                         VECCOPY(tmat[3], offs_bone[3]);
323                                                         offs_bone[3][0]= offs_bone[3][1]= offs_bone[3][2]= 0.0f;
324                                                         mul_m4_v3(pchan->parent->pose_mat, tmat[3]);
325                                                         
326                                                         mul_m4_m4m4(diff_mat, offs_bone, tmat);
327                                                         copy_m4_m4(tempmat, mat);
328                                                         mul_m4_m4m4(mat, tempmat, diff_mat);
329                                                 }
330                                                 else {
331                                                         /* pose_mat = par_pose_mat * bone_mat * chan_mat */
332                                                         mul_m4_m4m4(diff_mat, offs_bone, pchan->parent->pose_mat);
333                                                         copy_m4_m4(tempmat, mat);
334                                                         mul_m4_m4m4(mat, tempmat, diff_mat);
335                                                 }
336                                         }
337                                         else {
338                                                 copy_m4_m4(diff_mat, pchan->bone->arm_mat);
339                                                 
340                                                 copy_m4_m4(tempmat, mat);
341                                                 mul_m4_m4m4(mat, tempmat, diff_mat);
342                                         }
343                                 }
344                                 
345                                 /* use pose-space as stepping stone for other spaces */
346                                 if (ELEM(to, CONSTRAINT_SPACE_WORLD, CONSTRAINT_SPACE_PARLOCAL)) {
347                                         /* call self with slightly different values */
348                                         constraint_mat_convertspace(ob, pchan, mat, CONSTRAINT_SPACE_POSE, to);
349                                 }                               
350                         }
351                                 break;
352                         case CONSTRAINT_SPACE_PARLOCAL: /* -------------- FROM LOCAL WITH PARENT ---------- */
353                         {
354                                 /* local + parent to pose */
355                                 if (pchan->bone) {                                      
356                                         copy_m4_m4(diff_mat, pchan->bone->arm_mat);
357                                         copy_m4_m4(tempmat, mat);
358                                         mul_m4_m4m4(mat, diff_mat, tempmat);
359                                 }
360                                 
361                                 /* use pose-space as stepping stone for other spaces */
362                                 if (ELEM(to, CONSTRAINT_SPACE_WORLD, CONSTRAINT_SPACE_LOCAL)) {
363                                         /* call self with slightly different values */
364                                         constraint_mat_convertspace(ob, pchan, mat, CONSTRAINT_SPACE_POSE, to);
365                                 }
366                         }
367                                 break;
368                 }
369         }
370         else {
371                 /* objects */
372                 if (from==CONSTRAINT_SPACE_WORLD && to==CONSTRAINT_SPACE_LOCAL) {
373                         /* check if object has a parent - otherwise this won't work */
374                         if (ob->parent) {
375                                 /* 'subtract' parent's effects from owner */
376                                 mul_m4_m4m4(diff_mat, ob->parentinv, ob->parent->obmat);
377                                 invert_m4_m4(imat, diff_mat);
378                                 copy_m4_m4(tempmat, mat);
379                                 mul_m4_m4m4(mat, tempmat, imat);
380                         }
381                 }
382                 else if (from==CONSTRAINT_SPACE_LOCAL && to==CONSTRAINT_SPACE_WORLD) {
383                         /* check that object has a parent - otherwise this won't work */
384                         if (ob->parent) {
385                                 /* 'add' parent's effect back to owner */
386                                 copy_m4_m4(tempmat, mat);
387                                 mul_m4_m4m4(diff_mat, ob->parentinv, ob->parent->obmat);
388                                 mul_m4_m4m4(mat, tempmat, diff_mat);
389                         }
390                 }
391         }
392 }
393
394 /* ------------ General Target Matrix Tools ---------- */
395
396 /* function that sets the given matrix based on given vertex group in mesh */
397 static void contarget_get_mesh_mat (Scene *scene, Object *ob, char *substring, float mat[][4])
398 {
399         DerivedMesh *dm = NULL;
400         Mesh *me= ob->data;
401         EditMesh *em = BKE_mesh_get_editmesh(me);
402         float vec[3] = {0.0f, 0.0f, 0.0f}, tvec[3];
403         float normal[3] = {0.0f, 0.0f, 0.0f}, plane[3];
404         float imat[3][3], tmat[3][3];
405         int dgroup;
406         short freeDM = 0;
407         
408         /* initialize target matrix using target matrix */
409         copy_m4_m4(mat, ob->obmat);
410         
411         /* get index of vertex group */
412         dgroup = defgroup_name_index(ob, substring);
413         if (dgroup < 0) return;
414         
415         /* get DerivedMesh */
416         if (em) {
417                 /* target is in editmode, so get a special derived mesh */
418                 dm = CDDM_from_editmesh(em, ob->data);
419                 freeDM= 1;
420         }
421         else {
422                 /* when not in EditMode, use the 'final' derived mesh 
423                  *      - check if the custom data masks for derivedFinal mean that we can just use that
424                  *        (this is more effficient + sufficient for most cases)
425                  */
426                 if (!(ob->lastDataMask & CD_MASK_MDEFORMVERT)) {
427                         dm = mesh_get_derived_final(scene, ob, CD_MASK_MDEFORMVERT);
428                         freeDM= 1;
429                 }
430                 else 
431                         dm = (DerivedMesh *)ob->derivedFinal;
432         }
433         
434         /* only continue if there's a valid DerivedMesh */
435         if (dm) {
436                 MDeformVert *dvert = dm->getVertDataArray(dm, CD_MDEFORMVERT);
437                 int numVerts = dm->getNumVerts(dm);
438                 int i, j, count = 0;
439                 float co[3], nor[3];
440                 
441                 /* check that dvert is a valid pointers (just in case) */
442                 if (dvert) {
443                         /* get the average of all verts with that are in the vertex-group */
444                         for (i = 0; i < numVerts; i++) {        
445                                 for (j = 0; j < dvert[i].totweight; j++) {
446                                         /* does this vertex belong to nominated vertex group? */
447                                         if (dvert[i].dw[j].def_nr == dgroup) {
448                                                 dm->getVertCo(dm, i, co);
449                                                 dm->getVertNo(dm, i, nor);
450                                                 add_v3_v3(vec, co);
451                                                 add_v3_v3(normal, nor);
452                                                 count++;
453                                                 break;
454                                         }
455                                         
456                                 }
457                         }
458                         
459                         
460                         /* calculate averages of normal and coordinates */
461                         if (count > 0) {
462                                 mul_v3_fl(vec, 1.0f / count);
463                                 mul_v3_fl(normal, 1.0f / count);
464                         }
465                         
466                         
467                         /* derive the rotation from the average normal: 
468                          *              - code taken from transform_manipulator.c, 
469                          *                      calc_manipulator_stats, V3D_MANIP_NORMAL case
470                          */
471                         /*      we need the transpose of the inverse for a normal... */
472                         copy_m3_m4(imat, ob->obmat);
473                         
474                         invert_m3_m3(tmat, imat);
475                         transpose_m3(tmat);
476                         mul_m3_v3(tmat, normal);
477                         
478                         normalize_v3(normal);
479                         VECCOPY(plane, tmat[1]);
480                         
481                         VECCOPY(tmat[2], normal);
482                         cross_v3_v3v3(tmat[0], normal, plane);
483                         cross_v3_v3v3(tmat[1], tmat[2], tmat[0]);
484                         
485                         copy_m4_m3(mat, tmat);
486                         normalize_m4(mat);
487                         
488                         
489                         /* apply the average coordinate as the new location */
490                         mul_v3_m4v3(tvec, ob->obmat, vec);
491                         VECCOPY(mat[3], tvec);
492                 }
493         }
494         
495         /* free temporary DerivedMesh created (in EditMode case) */
496         if (dm && freeDM)
497                 dm->release(dm);
498         if (em)
499                 BKE_mesh_end_editmesh(me, em);
500 }
501
502 /* function that sets the given matrix based on given vertex group in lattice */
503 static void contarget_get_lattice_mat (Object *ob, char *substring, float mat[][4])
504 {
505         Lattice *lt= (Lattice *)ob->data;
506         
507         DispList *dl = find_displist(&ob->disp, DL_VERTS);
508         float *co = dl?dl->verts:NULL;
509         BPoint *bp = lt->def;
510         
511         MDeformVert *dvert = lt->dvert;
512         int tot_verts= lt->pntsu*lt->pntsv*lt->pntsw;
513         float vec[3]= {0.0f, 0.0f, 0.0f}, tvec[3];
514         int dgroup=0, grouped=0;
515         int i, n;
516         
517         /* initialize target matrix using target matrix */
518         copy_m4_m4(mat, ob->obmat);
519         
520         /* get index of vertex group */
521         dgroup = defgroup_name_index(ob, substring);
522         if (dgroup < 0) return;
523         if (dvert == NULL) return;
524         
525         /* 1. Loop through control-points checking if in nominated vertex-group.
526          * 2. If it is, add it to vec to find the average point.
527          */
528         for (i=0; i < tot_verts; i++, dvert++) {
529                 for (n= 0; n < dvert->totweight; n++) {
530                         /* found match - vert is in vgroup */
531                         if (dvert->dw[n].def_nr == dgroup) {
532                                 /* copy coordinates of point to temporary vector, then add to find average */
533                                 if (co)
534                                         memcpy(tvec, co, 3*sizeof(float));
535                                 else
536                                         memcpy(tvec, bp->vec, 3*sizeof(float));
537                                         
538                                 add_v3_v3(vec, tvec);
539                                 grouped++;
540                                 
541                                 break;
542                         }
543                 }
544                 
545                 /* advance pointer to coordinate data */
546                 if (co) co+= 3;
547                 else bp++;
548         }
549         
550         /* find average location, then multiply by ob->obmat to find world-space location */
551         if (grouped)
552                 mul_v3_fl(vec, 1.0f / grouped);
553         mul_v3_m4v3(tvec, ob->obmat, vec);
554         
555         /* copy new location to matrix */
556         VECCOPY(mat[3], tvec);
557 }
558
559 /* generic function to get the appropriate matrix for most target cases */
560 /* The cases where the target can be object data have not been implemented */
561 static void constraint_target_to_mat4 (Scene *scene, Object *ob, char *substring, float mat[][4], short from, short to, float headtail)
562 {
563         /*      Case OBJECT */
564         if (!strlen(substring)) {
565                 copy_m4_m4(mat, ob->obmat);
566                 constraint_mat_convertspace(ob, NULL, mat, from, to);
567         }
568         /*      Case VERTEXGROUP */
569         /* Current method just takes the average location of all the points in the
570          * VertexGroup, and uses that as the location value of the targets. Where 
571          * possible, the orientation will also be calculated, by calculating an
572          * 'average' vertex normal, and deriving the rotaation from that.
573          *
574          * NOTE: EditMode is not currently supported, and will most likely remain that
575          *              way as constraints can only really affect things on object/bone level.
576          */
577         else if (ob->type == OB_MESH) {
578                 contarget_get_mesh_mat(scene, ob, substring, mat);
579                 constraint_mat_convertspace(ob, NULL, mat, from, to);
580         }
581         else if (ob->type == OB_LATTICE) {
582                 contarget_get_lattice_mat(ob, substring, mat);
583                 constraint_mat_convertspace(ob, NULL, mat, from, to);
584         }
585         /*      Case BONE */
586         else {
587                 bPoseChannel *pchan;
588                 
589                 pchan = get_pose_channel(ob->pose, substring);
590                 if (pchan) {
591                         /* Multiply the PoseSpace accumulation/final matrix for this
592                          * PoseChannel by the Armature Object's Matrix to get a worldspace
593                          * matrix.
594                          */
595                         if (headtail < 0.000001) {
596                                 /* skip length interpolation if set to head */
597                                 mul_m4_m4m4(mat, pchan->pose_mat, ob->obmat);
598                         }
599                         else {
600                                 float tempmat[4][4], loc[3];
601                                 
602                                 /* interpolate along length of bone */
603                                 interp_v3_v3v3(loc, pchan->pose_head, pchan->pose_tail, headtail);      
604                                 
605                                 /* use interpolated distance for subtarget */
606                                 copy_m4_m4(tempmat, pchan->pose_mat);   
607                                 copy_v3_v3(tempmat[3], loc);
608                                 
609                                 mul_m4_m4m4(mat, tempmat, ob->obmat);
610                         }
611                 } 
612                 else
613                         copy_m4_m4(mat, ob->obmat);
614                         
615                 /* convert matrix space as required */
616                 constraint_mat_convertspace(ob, pchan, mat, from, to);
617         }
618 }
619
620 /* ************************* Specific Constraints ***************************** */
621 /* Each constraint defines a set of functions, which will be called at the appropriate
622  * times. In addition to this, each constraint should have a type-info struct, where
623  * its functions are attached for use. 
624  */
625  
626 /* Template for type-info data:
627  *      - make a copy of this when creating new constraints, and just change the functions
628  *        pointed to as necessary
629  *      - although the naming of functions doesn't matter, it would help for code
630  *        readability, to follow the same naming convention as is presented here
631  *      - any functions that a constraint doesn't need to define, don't define
632  *        for such cases, just use NULL 
633  *      - these should be defined after all the functions have been defined, so that
634  *        forward-definitions/prototypes don't need to be used!
635  *      - keep this copy #if-def'd so that future constraints can get based off this
636  */
637 #if 0
638 static bConstraintTypeInfo CTI_CONSTRNAME = {
639         CONSTRAINT_TYPE_CONSTRNAME, /* type */
640         sizeof(bConstrNameConstraint), /* size */
641         "ConstrName", /* name */
642         "bConstrNameConstraint", /* struct name */
643         constrname_free, /* free data */
644         constrname_relink, /* relink data */
645         constrname_id_looper, /* id looper */
646         constrname_copy, /* copy data */
647         constrname_new_data, /* new data */
648         constrname_get_tars, /* get constraint targets */
649         constrname_flush_tars, /* flush constraint targets */
650         constrname_get_tarmat, /* get target matrix */
651         constrname_evaluate /* evaluate */
652 };
653 #endif
654
655 /* This function should be used for the get_target_matrix member of all 
656  * constraints that are not picky about what happens to their target matrix.
657  */
658 static void default_get_tarmat (bConstraint *con, bConstraintOb *cob, bConstraintTarget *ct, float ctime)
659 {
660         if (VALID_CONS_TARGET(ct))
661                 constraint_target_to_mat4(cob->scene, ct->tar, ct->subtarget, ct->matrix, CONSTRAINT_SPACE_WORLD, ct->space, con->headtail);
662         else if (ct)
663                 unit_m4(ct->matrix);
664 }
665
666 /* This following macro should be used for all standard single-target *_get_tars functions 
667  * to save typing and reduce maintainance woes.
668  * (Hopefully all compilers will be happy with the lines with just a space on them. Those are
669  *  really just to help this code easier to read)
670  */
671 // TODO: cope with getting rotation order...
672 #define SINGLETARGET_GET_TARS(con, datatar, datasubtarget, ct, list) \
673         { \
674                 ct= MEM_callocN(sizeof(bConstraintTarget), "tempConstraintTarget"); \
675                  \
676                 ct->tar= datatar; \
677                 strcpy(ct->subtarget, datasubtarget); \
678                 ct->space= con->tarspace; \
679                 ct->flag= CONSTRAINT_TAR_TEMP; \
680                  \
681                 if (ct->tar) { \
682                         if ((ct->tar->type==OB_ARMATURE) && (ct->subtarget[0])) { \
683                                 bPoseChannel *pchan= get_pose_channel(ct->tar->pose, ct->subtarget); \
684                                 ct->type = CONSTRAINT_OBTYPE_BONE; \
685                                 ct->rotOrder= (pchan) ? (pchan->rotmode) : EULER_ORDER_DEFAULT; \
686                         }\
687                         else if (ELEM(ct->tar->type, OB_MESH, OB_LATTICE) && (ct->subtarget[0])) { \
688                                 ct->type = CONSTRAINT_OBTYPE_VERT; \
689                                 ct->rotOrder = EULER_ORDER_DEFAULT; \
690                         } \
691                         else {\
692                                 ct->type = CONSTRAINT_OBTYPE_OBJECT; \
693                                 ct->rotOrder= ct->tar->rotmode; \
694                         } \
695                 } \
696                  \
697                 BLI_addtail(list, ct); \
698         }
699         
700 /* This following macro should be used for all standard single-target *_get_tars functions 
701  * to save typing and reduce maintainance woes. It does not do the subtarget related operations
702  * (Hopefully all compilers will be happy with the lines with just a space on them. Those are
703  *  really just to help this code easier to read)
704  */
705 // TODO: cope with getting rotation order...
706 #define SINGLETARGETNS_GET_TARS(con, datatar, ct, list) \
707         { \
708                 ct= MEM_callocN(sizeof(bConstraintTarget), "tempConstraintTarget"); \
709                  \
710                 ct->tar= datatar; \
711                 ct->space= con->tarspace; \
712                 ct->flag= CONSTRAINT_TAR_TEMP; \
713                  \
714                 if (ct->tar) ct->type = CONSTRAINT_OBTYPE_OBJECT; \
715                  \
716                 BLI_addtail(list, ct); \
717         }
718
719 /* This following macro should be used for all standard single-target *_flush_tars functions
720  * to save typing and reduce maintainance woes.
721  * Note: the pointer to ct will be changed to point to the next in the list (as it gets removed)
722  * (Hopefully all compilers will be happy with the lines with just a space on them. Those are
723  *  really just to help this code easier to read)
724  */
725 #define SINGLETARGET_FLUSH_TARS(con, datatar, datasubtarget, ct, list, nocopy) \
726         { \
727                 if (ct) { \
728                         bConstraintTarget *ctn = ct->next; \
729                         if (nocopy == 0) { \
730                                 datatar= ct->tar; \
731                                 strcpy(datasubtarget, ct->subtarget); \
732                                 con->tarspace= (char)ct->space; \
733                         } \
734                          \
735                         BLI_freelinkN(list, ct); \
736                         ct= ctn; \
737                 } \
738         }
739         
740 /* This following macro should be used for all standard single-target *_flush_tars functions
741  * to save typing and reduce maintainance woes. It does not do the subtarget related operations.
742  * Note: the pointer to ct will be changed to point to the next in the list (as it gets removed)
743  * (Hopefully all compilers will be happy with the lines with just a space on them. Those are
744  *  really just to help this code easier to read)
745  */
746 #define SINGLETARGETNS_FLUSH_TARS(con, datatar, ct, list, nocopy) \
747         { \
748                 if (ct) { \
749                         bConstraintTarget *ctn = ct->next; \
750                         if (nocopy == 0) { \
751                                 datatar= ct->tar; \
752                                 con->tarspace= (char)ct->space; \
753                         } \
754                          \
755                         BLI_freelinkN(list, ct); \
756                         ct= ctn; \
757                 } \
758         }
759  
760 /* --------- ChildOf Constraint ------------ */
761
762 static void childof_new_data (void *cdata)
763 {
764         bChildOfConstraint *data= (bChildOfConstraint *)cdata;
765         
766         data->flag = (CHILDOF_LOCX | CHILDOF_LOCY | CHILDOF_LOCZ |
767                                         CHILDOF_ROTX |CHILDOF_ROTY | CHILDOF_ROTZ |
768                                         CHILDOF_SIZEX | CHILDOF_SIZEY | CHILDOF_SIZEZ);
769         unit_m4(data->invmat);
770 }
771
772 static void childof_id_looper (bConstraint *con, ConstraintIDFunc func, void *userdata)
773 {
774         bChildOfConstraint *data= con->data;
775         
776         /* target only */
777         func(con, (ID**)&data->tar, userdata);
778 }
779
780 static int childof_get_tars (bConstraint *con, ListBase *list)
781 {
782         if (con && list) {
783                 bChildOfConstraint *data= con->data;
784                 bConstraintTarget *ct;
785                 
786                 /* standard target-getting macro for single-target constraints */
787                 SINGLETARGET_GET_TARS(con, data->tar, data->subtarget, ct, list)
788                 
789                 return 1;
790         }
791         
792         return 0;
793 }
794
795 static void childof_flush_tars (bConstraint *con, ListBase *list, short nocopy)
796 {
797         if (con && list) {
798                 bChildOfConstraint *data= con->data;
799                 bConstraintTarget *ct= list->first;
800                 
801                 /* the following macro is used for all standard single-target constraints */
802                 SINGLETARGET_FLUSH_TARS(con, data->tar, data->subtarget, ct, list, nocopy)
803         }
804 }
805
806 static void childof_evaluate (bConstraint *con, bConstraintOb *cob, ListBase *targets)
807 {
808         bChildOfConstraint *data= con->data;
809         bConstraintTarget *ct= targets->first;
810         
811         /* only evaluate if there is a target */
812         if (VALID_CONS_TARGET(ct)) {
813                 float parmat[4][4], invmat[4][4], tempmat[4][4];
814                 float loc[3], eul[3], size[3];
815                 float loco[3], eulo[3], sizo[3];
816                 
817                 /* get offset (parent-inverse) matrix */
818                 copy_m4_m4(invmat, data->invmat);
819                 
820                 /* extract components of both matrices */
821                 VECCOPY(loc, ct->matrix[3]);
822                 mat4_to_eulO( eul, ct->rotOrder,ct->matrix);
823                 mat4_to_size( size,ct->matrix);
824                 
825                 VECCOPY(loco, invmat[3]);
826                 mat4_to_eulO( eulo, cob->rotOrder,invmat);
827                 mat4_to_size( sizo,invmat);
828                 
829                 /* disable channels not enabled */
830                 if (!(data->flag & CHILDOF_LOCX)) loc[0]= loco[0]= 0.0f;
831                 if (!(data->flag & CHILDOF_LOCY)) loc[1]= loco[1]= 0.0f;
832                 if (!(data->flag & CHILDOF_LOCZ)) loc[2]= loco[2]= 0.0f;
833                 if (!(data->flag & CHILDOF_ROTX)) eul[0]= eulo[0]= 0.0f;
834                 if (!(data->flag & CHILDOF_ROTY)) eul[1]= eulo[1]= 0.0f;
835                 if (!(data->flag & CHILDOF_ROTZ)) eul[2]= eulo[2]= 0.0f;
836                 if (!(data->flag & CHILDOF_SIZEX)) size[0]= sizo[0]= 1.0f;
837                 if (!(data->flag & CHILDOF_SIZEY)) size[1]= sizo[1]= 1.0f;
838                 if (!(data->flag & CHILDOF_SIZEZ)) size[2]= sizo[2]= 1.0f;
839                 
840                 /* make new target mat and offset mat */
841                 loc_eulO_size_to_mat4(ct->matrix, loc, eul, size, ct->rotOrder);
842                 loc_eulO_size_to_mat4(invmat, loco, eulo, sizo, cob->rotOrder);
843                 
844                 /* multiply target (parent matrix) by offset (parent inverse) to get 
845                  * the effect of the parent that will be exherted on the owner
846                  */
847                 mul_m4_m4m4(parmat, invmat, ct->matrix);
848                 
849                 /* now multiply the parent matrix by the owner matrix to get the 
850                  * the effect of this constraint (i.e.  owner is 'parented' to parent)
851                  */
852                 copy_m4_m4(tempmat, cob->matrix);
853                 mul_m4_m4m4(cob->matrix, tempmat, parmat); 
854         }
855 }
856
857 static bConstraintTypeInfo CTI_CHILDOF = {
858         CONSTRAINT_TYPE_CHILDOF, /* type */
859         sizeof(bChildOfConstraint), /* size */
860         "ChildOf", /* name */
861         "bChildOfConstraint", /* struct name */
862         NULL, /* free data */
863         NULL, /* relink data */
864         childof_id_looper, /* id looper */
865         NULL, /* copy data */
866         childof_new_data, /* new data */
867         childof_get_tars, /* get constraint targets */
868         childof_flush_tars, /* flush constraint targets */
869         default_get_tarmat, /* get a target matrix */
870         childof_evaluate /* evaluate */
871 };
872
873 /* -------- TrackTo Constraint ------- */
874
875 static void trackto_new_data (void *cdata)
876 {
877         bTrackToConstraint *data= (bTrackToConstraint *)cdata;
878         
879         data->reserved1 = TRACK_Y;
880         data->reserved2 = UP_Z;
881 }       
882
883 static void trackto_id_looper (bConstraint *con, ConstraintIDFunc func, void *userdata)
884 {
885         bTrackToConstraint *data= con->data;
886         
887         /* target only */
888         func(con, (ID**)&data->tar, userdata);
889 }
890
891 static int trackto_get_tars (bConstraint *con, ListBase *list)
892 {
893         if (con && list) {
894                 bTrackToConstraint *data= con->data;
895                 bConstraintTarget *ct;
896                 
897                 /* standard target-getting macro for single-target constraints */
898                 SINGLETARGET_GET_TARS(con, data->tar, data->subtarget, ct, list)
899                 
900                 return 1;
901         }
902         
903         return 0;
904 }
905
906 static void trackto_flush_tars (bConstraint *con, ListBase *list, short nocopy)
907 {
908         if (con && list) {
909                 bTrackToConstraint *data= con->data;
910                 bConstraintTarget *ct= list->first;
911                 
912                 /* the following macro is used for all standard single-target constraints */
913                 SINGLETARGET_FLUSH_TARS(con, data->tar, data->subtarget, ct, list, nocopy)
914         }
915 }
916
917
918 static int basis_cross (int n, int m)
919 {
920         switch (n-m) {
921                 case 1: 
922                 case -2:
923                         return 1;
924                         
925                 case -1: 
926                 case 2:
927                         return -1;
928                         
929                 default:
930                         return 0;
931         }
932 }
933
934 static void vectomat (float *vec, float *target_up, short axis, short upflag, short flags, float m[][3])
935 {
936         float n[3];
937         float u[3]; /* vector specifying the up axis */
938         float proj[3];
939         float right[3];
940         float neg = -1;
941         int right_index;
942         
943         copy_v3_v3(n, vec);
944         if (normalize_v3(n) == 0.0) { 
945                 n[0] = 0.0;
946                 n[1] = 0.0;
947                 n[2] = 1.0;
948         }
949         if (axis > 2) axis -= 3;
950         else negate_v3(n);
951
952         /* n specifies the transformation of the track axis */
953         if (flags & TARGET_Z_UP) { 
954                 /* target Z axis is the global up axis */
955                 u[0] = target_up[0];
956                 u[1] = target_up[1];
957                 u[2] = target_up[2];
958         }
959         else { 
960                 /* world Z axis is the global up axis */
961                 u[0] = 0;
962                 u[1] = 0;
963                 u[2] = 1;
964         }
965
966         /* project the up vector onto the plane specified by n */
967         project_v3_v3v3(proj, u, n); /* first u onto n... */
968         sub_v3_v3v3(proj, u, proj); /* then onto the plane */
969         /* proj specifies the transformation of the up axis */
970
971         if (normalize_v3(proj) == 0.0) { /* degenerate projection */
972                 proj[0] = 0.0;
973                 proj[1] = 1.0;
974                 proj[2] = 0.0;
975         }
976
977         /* Normalized cross product of n and proj specifies transformation of the right axis */
978         cross_v3_v3v3(right, proj, n);
979         normalize_v3(right);
980
981         if (axis != upflag) {
982                 right_index = 3 - axis - upflag;
983                 neg = (float)basis_cross(axis, upflag);
984                 
985                 /* account for up direction, track direction */
986                 m[right_index][0] = neg * right[0];
987                 m[right_index][1] = neg * right[1];
988                 m[right_index][2] = neg * right[2];
989                 
990                 m[upflag][0] = proj[0];
991                 m[upflag][1] = proj[1];
992                 m[upflag][2] = proj[2];
993                 
994                 m[axis][0] = n[0];
995                 m[axis][1] = n[1];
996                 m[axis][2] = n[2];
997         }
998         /* identity matrix - don't do anything if the two axes are the same */
999         else {
1000                 m[0][0]= m[1][1]= m[2][2]= 1.0;
1001                 m[0][1]= m[0][2]= 0.0;
1002                 m[1][0]= m[1][2]= 0.0;
1003                 m[2][0]= m[2][1]= 0.0;
1004         }
1005 }
1006
1007
1008 static void trackto_evaluate (bConstraint *con, bConstraintOb *cob, ListBase *targets)
1009 {
1010         bTrackToConstraint *data= con->data;
1011         bConstraintTarget *ct= targets->first;
1012         
1013         if (VALID_CONS_TARGET(ct)) {
1014                 float size[3], vec[3];
1015                 float totmat[3][3];
1016                 float tmat[4][4];
1017                 
1018                 /* Get size property, since ob->size is only the object's own relative size, not its global one */
1019                 mat4_to_size( size,cob->matrix);
1020                 
1021                 /* Clear the object's rotation */       
1022                 cob->matrix[0][0]=size[0];
1023                 cob->matrix[0][1]=0;
1024                 cob->matrix[0][2]=0;
1025                 cob->matrix[1][0]=0;
1026                 cob->matrix[1][1]=size[1];
1027                 cob->matrix[1][2]=0;
1028                 cob->matrix[2][0]=0;
1029                 cob->matrix[2][1]=0;
1030                 cob->matrix[2][2]=size[2];
1031                 
1032                 /* targetmat[2] instead of ownermat[2] is passed to vectomat
1033                  * for backwards compatability it seems... (Aligorith)
1034                  */
1035                 sub_v3_v3v3(vec, cob->matrix[3], ct->matrix[3]);
1036                 vectomat(vec, ct->matrix[2], 
1037                                 (short)data->reserved1, (short)data->reserved2, 
1038                                 data->flags, totmat);
1039                 
1040                 copy_m4_m4(tmat, cob->matrix);
1041                 mul_m4_m3m4(cob->matrix, totmat, tmat);
1042         }
1043 }
1044
1045 static bConstraintTypeInfo CTI_TRACKTO = {
1046         CONSTRAINT_TYPE_TRACKTO, /* type */
1047         sizeof(bTrackToConstraint), /* size */
1048         "TrackTo", /* name */
1049         "bTrackToConstraint", /* struct name */
1050         NULL, /* free data */
1051         NULL, /* relink data */
1052         trackto_id_looper, /* id looper */
1053         NULL, /* copy data */
1054         trackto_new_data, /* new data */
1055         trackto_get_tars, /* get constraint targets */
1056         trackto_flush_tars, /* flush constraint targets */
1057         default_get_tarmat, /* get target matrix */
1058         trackto_evaluate /* evaluate */
1059 };
1060
1061 /* --------- Inverse-Kinemetics --------- */
1062
1063 static void kinematic_new_data (void *cdata)
1064 {
1065         bKinematicConstraint *data= (bKinematicConstraint *)cdata;
1066         
1067         data->weight= (float)1.0;
1068         data->orientweight= (float)1.0;
1069         data->iterations = 500;
1070         data->dist= (float)1.0;
1071         data->flag= CONSTRAINT_IK_TIP|CONSTRAINT_IK_STRETCH|CONSTRAINT_IK_POS;
1072 }
1073
1074 static void kinematic_id_looper (bConstraint *con, ConstraintIDFunc func, void *userdata)
1075 {
1076         bKinematicConstraint *data= con->data;
1077         
1078         /* chain target */
1079         func(con, (ID**)&data->tar, userdata);
1080         
1081         /* poletarget */
1082         func(con, (ID**)&data->poletar, userdata);
1083 }
1084
1085 static int kinematic_get_tars (bConstraint *con, ListBase *list)
1086 {
1087         if (con && list) {
1088                 bKinematicConstraint *data= con->data;
1089                 bConstraintTarget *ct;
1090                 
1091                 /* standard target-getting macro for single-target constraints is used twice here */
1092                 SINGLETARGET_GET_TARS(con, data->tar, data->subtarget, ct, list)
1093                 SINGLETARGET_GET_TARS(con, data->poletar, data->polesubtarget, ct, list)
1094                 
1095                 return 2;
1096         }
1097         
1098         return 0;
1099 }
1100
1101 static void kinematic_flush_tars (bConstraint *con, ListBase *list, short nocopy)
1102 {
1103         if (con && list) {
1104                 bKinematicConstraint *data= con->data;
1105                 bConstraintTarget *ct= list->first;
1106                 
1107                 /* the following macro is used for all standard single-target constraints */
1108                 SINGLETARGET_FLUSH_TARS(con, data->tar, data->subtarget, ct, list, nocopy)
1109                 SINGLETARGET_FLUSH_TARS(con, data->poletar, data->polesubtarget, ct, list, nocopy)
1110         }
1111 }
1112
1113 static void kinematic_get_tarmat (bConstraint *con, bConstraintOb *cob, bConstraintTarget *ct, float ctime)
1114 {
1115         bKinematicConstraint *data= con->data;
1116         
1117         if (VALID_CONS_TARGET(ct)) 
1118                 constraint_target_to_mat4(cob->scene, ct->tar, ct->subtarget, ct->matrix, CONSTRAINT_SPACE_WORLD, ct->space, con->headtail);
1119         else if (ct) {
1120                 if (data->flag & CONSTRAINT_IK_AUTO) {
1121                         Object *ob= cob->ob;
1122                         
1123                         if (ob == NULL) {
1124                                 unit_m4(ct->matrix);
1125                         }
1126                         else {
1127                                 float vec[3];
1128                                 /* move grabtarget into world space */
1129                                 VECCOPY(vec, data->grabtarget);
1130                                 mul_m4_v3(ob->obmat, vec);
1131                                 copy_m4_m4(ct->matrix, ob->obmat);
1132                                 VECCOPY(ct->matrix[3], vec);
1133                         }
1134                 }
1135                 else
1136                         unit_m4(ct->matrix);
1137         }
1138 }
1139
1140 static bConstraintTypeInfo CTI_KINEMATIC = {
1141         CONSTRAINT_TYPE_KINEMATIC, /* type */
1142         sizeof(bKinematicConstraint), /* size */
1143         "IK", /* name */
1144         "bKinematicConstraint", /* struct name */
1145         NULL, /* free data */
1146         NULL, /* relink data */
1147         kinematic_id_looper, /* id looper */
1148         NULL, /* copy data */
1149         kinematic_new_data, /* new data */
1150         kinematic_get_tars, /* get constraint targets */
1151         kinematic_flush_tars, /* flush constraint targets */
1152         kinematic_get_tarmat, /* get target matrix */
1153         NULL /* evaluate - solved as separate loop */
1154 };
1155
1156 /* -------- Follow-Path Constraint ---------- */
1157
1158 static void followpath_new_data (void *cdata)
1159 {
1160         bFollowPathConstraint *data= (bFollowPathConstraint *)cdata;
1161         
1162         data->trackflag = TRACK_Y;
1163         data->upflag = UP_Z;
1164         data->offset = 0;
1165         data->followflag = 0;
1166 }
1167
1168 static void followpath_id_looper (bConstraint *con, ConstraintIDFunc func, void *userdata)
1169 {
1170         bFollowPathConstraint *data= con->data;
1171         
1172         /* target only */
1173         func(con, (ID**)&data->tar, userdata);
1174 }
1175
1176 static int followpath_get_tars (bConstraint *con, ListBase *list)
1177 {
1178         if (con && list) {
1179                 bFollowPathConstraint *data= con->data;
1180                 bConstraintTarget *ct;
1181                 
1182                 /* standard target-getting macro for single-target constraints without subtargets */
1183                 SINGLETARGETNS_GET_TARS(con, data->tar, ct, list)
1184                 
1185                 return 1;
1186         }
1187         
1188         return 0;
1189 }
1190
1191 static void followpath_flush_tars (bConstraint *con, ListBase *list, short nocopy)
1192 {
1193         if (con && list) {
1194                 bFollowPathConstraint *data= con->data;
1195                 bConstraintTarget *ct= list->first;
1196                 
1197                 /* the following macro is used for all standard single-target constraints */
1198                 SINGLETARGETNS_FLUSH_TARS(con, data->tar, ct, list, nocopy)
1199         }
1200 }
1201
1202 static void followpath_get_tarmat (bConstraint *con, bConstraintOb *cob, bConstraintTarget *ct, float ctime)
1203 {
1204         bFollowPathConstraint *data= con->data;
1205         
1206         if (VALID_CONS_TARGET(ct)) {
1207                 Curve *cu= ct->tar->data;
1208                 float q[4], vec[4], dir[3], quat[4], radius, x1;
1209                 float totmat[4][4];
1210                 float curvetime;
1211                 
1212                 unit_m4(totmat);
1213                 unit_m4(ct->matrix);
1214                 
1215                 /* note: when creating constraints that follow path, the curve gets the CU_PATH set now,
1216                  *              currently for paths to work it needs to go through the bevlist/displist system (ton) 
1217                  */
1218                 
1219                 /* only happens on reload file, but violates depsgraph still... fix! */
1220                 if (cu->path==NULL || cu->path->data==NULL)
1221                         makeDispListCurveTypes(cob->scene, ct->tar, 0);
1222                 
1223                 if (cu->path && cu->path->data) {
1224                         if ((data->followflag & FOLLOWPATH_STATIC) == 0) { 
1225                                 /* animated position along curve depending on time */
1226                                 if (cob->scene)
1227                                         curvetime= bsystem_time(cob->scene, ct->tar, cu->ctime, 0.0) - data->offset;
1228                                 else    
1229                                         curvetime= cu->ctime - data->offset;
1230                                 
1231                                 /* ctime is now a proper var setting of Curve which gets set by Animato like any other var that's animated,
1232                                  * but this will only work if it actually is animated... 
1233                                  *
1234                                  * we divide the curvetime calculated in the previous step by the length of the path, to get a time
1235                                  * factor, which then gets clamped to lie within 0.0 - 1.0 range
1236                                  */
1237                                 curvetime /= cu->pathlen;
1238                                 CLAMP(curvetime, 0.0, 1.0);
1239                         }
1240                         else {
1241                                 /* fixed position along curve */
1242                                 curvetime= data->offset_fac;
1243                         }
1244                         
1245                         if ( where_on_path(ct->tar, curvetime, vec, dir, NULL, &radius, NULL) ) {
1246                                 if (data->followflag & FOLLOWPATH_FOLLOW) {
1247                                         vec_to_quat(quat, dir, (short)data->trackflag, (short)data->upflag);
1248                                         
1249                                         normalize_v3(dir);
1250                                         q[0]= (float)cos(0.5*vec[3]);
1251                                         x1= (float)sin(0.5*vec[3]);
1252                                         q[1]= -x1*dir[0];
1253                                         q[2]= -x1*dir[1];
1254                                         q[3]= -x1*dir[2];
1255                                         mul_qt_qtqt(quat, q, quat);
1256                                         
1257                                         quat_to_mat4(totmat, quat);
1258                                 }
1259                                 
1260                                 if (data->followflag & FOLLOWPATH_RADIUS) {
1261                                         float tmat[4][4], rmat[4][4];
1262                                         scale_m4_fl(tmat, radius);
1263                                         mul_m4_m4m4(rmat, totmat, tmat);
1264                                         copy_m4_m4(totmat, rmat);
1265                                 }
1266                                 
1267                                 VECCOPY(totmat[3], vec);
1268                                 
1269                                 mul_serie_m4(ct->matrix, ct->tar->obmat, totmat, NULL, NULL, NULL, NULL, NULL, NULL);
1270                         }
1271                 }
1272         }
1273         else if (ct)
1274                 unit_m4(ct->matrix);
1275 }
1276
1277 static void followpath_evaluate (bConstraint *con, bConstraintOb *cob, ListBase *targets)
1278 {
1279         bConstraintTarget *ct= targets->first;
1280         
1281         /* only evaluate if there is a target */
1282         if (VALID_CONS_TARGET(ct)) {
1283                 float obmat[4][4];
1284                 float size[3];
1285                 bFollowPathConstraint *data= con->data;
1286                 
1287                 /* get Object transform (loc/rot/size) to determine transformation from path */
1288                 // TODO: this used to be local at one point, but is probably more useful as-is
1289                 copy_m4_m4(obmat, cob->matrix);
1290                 
1291                 /* get scaling of object before applying constraint */
1292                 mat4_to_size(size, cob->matrix);
1293                 
1294                 /* apply targetmat - containing location on path, and rotation */
1295                 mul_serie_m4(cob->matrix, ct->matrix, obmat, NULL, NULL, NULL, NULL, NULL, NULL);
1296                 
1297                 /* un-apply scaling caused by path */
1298                 if ((data->followflag & FOLLOWPATH_RADIUS)==0) { /* XXX - assume that scale correction means that radius will have some scale error in it - Campbell */
1299                         float obsize[3];
1300                         
1301                         mat4_to_size( obsize,cob->matrix);
1302                         if (obsize[0])
1303                                 mul_v3_fl(cob->matrix[0], size[0] / obsize[0]);
1304                         if (obsize[1])
1305                                 mul_v3_fl(cob->matrix[1], size[1] / obsize[1]);
1306                         if (obsize[2])
1307                                 mul_v3_fl(cob->matrix[2], size[2] / obsize[2]);
1308                 }
1309         }
1310 }
1311
1312 static bConstraintTypeInfo CTI_FOLLOWPATH = {
1313         CONSTRAINT_TYPE_FOLLOWPATH, /* type */
1314         sizeof(bFollowPathConstraint), /* size */
1315         "Follow Path", /* name */
1316         "bFollowPathConstraint", /* struct name */
1317         NULL, /* free data */
1318         NULL, /* relink data */
1319         followpath_id_looper, /* id looper */
1320         NULL, /* copy data */
1321         followpath_new_data, /* new data */
1322         followpath_get_tars, /* get constraint targets */
1323         followpath_flush_tars, /* flush constraint targets */
1324         followpath_get_tarmat, /* get target matrix */
1325         followpath_evaluate /* evaluate */
1326 };
1327
1328 /* --------- Limit Location --------- */
1329
1330
1331 static void loclimit_evaluate (bConstraint *con, bConstraintOb *cob, ListBase *targets)
1332 {
1333         bLocLimitConstraint *data = con->data;
1334         
1335         if (data->flag & LIMIT_XMIN) {
1336                 if (cob->matrix[3][0] < data->xmin)
1337                         cob->matrix[3][0] = data->xmin;
1338         }
1339         if (data->flag & LIMIT_XMAX) {
1340                 if (cob->matrix[3][0] > data->xmax)
1341                         cob->matrix[3][0] = data->xmax;
1342         }
1343         if (data->flag & LIMIT_YMIN) {
1344                 if (cob->matrix[3][1] < data->ymin)
1345                         cob->matrix[3][1] = data->ymin;
1346         }
1347         if (data->flag & LIMIT_YMAX) {
1348                 if (cob->matrix[3][1] > data->ymax)
1349                         cob->matrix[3][1] = data->ymax;
1350         }
1351         if (data->flag & LIMIT_ZMIN) {
1352                 if (cob->matrix[3][2] < data->zmin) 
1353                         cob->matrix[3][2] = data->zmin;
1354         }
1355         if (data->flag & LIMIT_ZMAX) {
1356                 if (cob->matrix[3][2] > data->zmax)
1357                         cob->matrix[3][2] = data->zmax;
1358         }
1359 }
1360
1361 static bConstraintTypeInfo CTI_LOCLIMIT = {
1362         CONSTRAINT_TYPE_LOCLIMIT, /* type */
1363         sizeof(bLocLimitConstraint), /* size */
1364         "Limit Location", /* name */
1365         "bLocLimitConstraint", /* struct name */
1366         NULL, /* free data */
1367         NULL, /* relink data */
1368         NULL, /* id looper */
1369         NULL, /* copy data */
1370         NULL, /* new data */
1371         NULL, /* get constraint targets */
1372         NULL, /* flush constraint targets */
1373         NULL, /* get target matrix */
1374         loclimit_evaluate /* evaluate */
1375 };
1376
1377 /* -------- Limit Rotation --------- */
1378
1379 static void rotlimit_evaluate (bConstraint *con, bConstraintOb *cob, ListBase *targets)
1380 {
1381         bRotLimitConstraint *data = con->data;
1382         float loc[3];
1383         float eul[3];
1384         float size[3];
1385         
1386         VECCOPY(loc, cob->matrix[3]);
1387         mat4_to_size( size,cob->matrix);
1388         
1389         mat4_to_eulO( eul, cob->rotOrder,cob->matrix);
1390         
1391         /* constraint data uses radians internally */
1392         
1393         /* limiting of euler values... */
1394         if (data->flag & LIMIT_XROT) {
1395                 if (eul[0] < data->xmin) 
1396                         eul[0] = data->xmin;
1397                         
1398                 if (eul[0] > data->xmax)
1399                         eul[0] = data->xmax;
1400         }
1401         if (data->flag & LIMIT_YROT) {
1402                 if (eul[1] < data->ymin)
1403                         eul[1] = data->ymin;
1404                         
1405                 if (eul[1] > data->ymax)
1406                         eul[1] = data->ymax;
1407         }
1408         if (data->flag & LIMIT_ZROT) {
1409                 if (eul[2] < data->zmin)
1410                         eul[2] = data->zmin;
1411                         
1412                 if (eul[2] > data->zmax)
1413                         eul[2] = data->zmax;
1414         }
1415                 
1416         loc_eulO_size_to_mat4(cob->matrix, loc, eul, size, cob->rotOrder);
1417 }
1418
1419 static bConstraintTypeInfo CTI_ROTLIMIT = {
1420         CONSTRAINT_TYPE_ROTLIMIT, /* type */
1421         sizeof(bRotLimitConstraint), /* size */
1422         "Limit Rotation", /* name */
1423         "bRotLimitConstraint", /* struct name */
1424         NULL, /* free data */
1425         NULL, /* relink data */
1426         NULL, /* id looper */
1427         NULL, /* copy data */
1428         NULL, /* new data */
1429         NULL, /* get constraint targets */
1430         NULL, /* flush constraint targets */
1431         NULL, /* get target matrix */
1432         rotlimit_evaluate /* evaluate */
1433 };
1434
1435 /* --------- Limit Scaling --------- */
1436
1437
1438 static void sizelimit_evaluate (bConstraint *con, bConstraintOb *cob, ListBase *targets)
1439 {
1440         bSizeLimitConstraint *data = con->data;
1441         float obsize[3], size[3];
1442         
1443         mat4_to_size( size,cob->matrix);
1444         mat4_to_size( obsize,cob->matrix);
1445         
1446         if (data->flag & LIMIT_XMIN) {
1447                 if (size[0] < data->xmin) 
1448                         size[0] = data->xmin;   
1449         }
1450         if (data->flag & LIMIT_XMAX) {
1451                 if (size[0] > data->xmax) 
1452                         size[0] = data->xmax;
1453         }
1454         if (data->flag & LIMIT_YMIN) {
1455                 if (size[1] < data->ymin) 
1456                         size[1] = data->ymin;   
1457         }
1458         if (data->flag & LIMIT_YMAX) {
1459                 if (size[1] > data->ymax) 
1460                         size[1] = data->ymax;
1461         }
1462         if (data->flag & LIMIT_ZMIN) {
1463                 if (size[2] < data->zmin) 
1464                         size[2] = data->zmin;   
1465         }
1466         if (data->flag & LIMIT_ZMAX) {
1467                 if (size[2] > data->zmax) 
1468                         size[2] = data->zmax;
1469         }
1470         
1471         if (obsize[0]) 
1472                 mul_v3_fl(cob->matrix[0], size[0]/obsize[0]);
1473         if (obsize[1]) 
1474                 mul_v3_fl(cob->matrix[1], size[1]/obsize[1]);
1475         if (obsize[2]) 
1476                 mul_v3_fl(cob->matrix[2], size[2]/obsize[2]);
1477 }
1478
1479 static bConstraintTypeInfo CTI_SIZELIMIT = {
1480         CONSTRAINT_TYPE_SIZELIMIT, /* type */
1481         sizeof(bSizeLimitConstraint), /* size */
1482         "Limit Scaling", /* name */
1483         "bSizeLimitConstraint", /* struct name */
1484         NULL, /* free data */
1485         NULL, /* relink data */
1486         NULL, /* id looper */
1487         NULL, /* copy data */
1488         NULL, /* new data */
1489         NULL, /* get constraint targets */
1490         NULL, /* flush constraint targets */
1491         NULL, /* get target matrix */
1492         sizelimit_evaluate /* evaluate */
1493 };
1494
1495 /* ----------- Copy Location ------------- */
1496
1497 static void loclike_new_data (void *cdata)
1498 {
1499         bLocateLikeConstraint *data= (bLocateLikeConstraint *)cdata;
1500         
1501         data->flag = LOCLIKE_X|LOCLIKE_Y|LOCLIKE_Z;
1502 }
1503
1504 static void loclike_id_looper (bConstraint *con, ConstraintIDFunc func, void *userdata)
1505 {
1506         bLocateLikeConstraint *data= con->data;
1507         
1508         /* target only */
1509         func(con, (ID**)&data->tar, userdata);
1510 }
1511
1512 static int loclike_get_tars (bConstraint *con, ListBase *list)
1513 {
1514         if (con && list) {
1515                 bLocateLikeConstraint *data= con->data;
1516                 bConstraintTarget *ct;
1517                 
1518                 /* standard target-getting macro for single-target constraints */
1519                 SINGLETARGET_GET_TARS(con, data->tar, data->subtarget, ct, list)
1520                 
1521                 return 1;
1522         }
1523         
1524         return 0;
1525 }
1526
1527 static void loclike_flush_tars (bConstraint *con, ListBase *list, short nocopy)
1528 {
1529         if (con && list) {
1530                 bLocateLikeConstraint *data= con->data;
1531                 bConstraintTarget *ct= list->first;
1532                 
1533                 /* the following macro is used for all standard single-target constraints */
1534                 SINGLETARGET_FLUSH_TARS(con, data->tar, data->subtarget, ct, list, nocopy)
1535         }
1536 }
1537
1538 static void loclike_evaluate (bConstraint *con, bConstraintOb *cob, ListBase *targets)
1539 {
1540         bLocateLikeConstraint *data= con->data;
1541         bConstraintTarget *ct= targets->first;
1542         
1543         if (VALID_CONS_TARGET(ct)) {
1544                 float offset[3] = {0.0f, 0.0f, 0.0f};
1545                 
1546                 if (data->flag & LOCLIKE_OFFSET)
1547                         VECCOPY(offset, cob->matrix[3]);
1548                         
1549                 if (data->flag & LOCLIKE_X) {
1550                         cob->matrix[3][0] = ct->matrix[3][0];
1551                         
1552                         if (data->flag & LOCLIKE_X_INVERT) cob->matrix[3][0] *= -1;
1553                         cob->matrix[3][0] += offset[0];
1554                 }
1555                 if (data->flag & LOCLIKE_Y) {
1556                         cob->matrix[3][1] = ct->matrix[3][1];
1557                         
1558                         if (data->flag & LOCLIKE_Y_INVERT) cob->matrix[3][1] *= -1;
1559                         cob->matrix[3][1] += offset[1];
1560                 }
1561                 if (data->flag & LOCLIKE_Z) {
1562                         cob->matrix[3][2] = ct->matrix[3][2];
1563                         
1564                         if (data->flag & LOCLIKE_Z_INVERT) cob->matrix[3][2] *= -1;
1565                         cob->matrix[3][2] += offset[2];
1566                 }
1567         }
1568 }
1569
1570 static bConstraintTypeInfo CTI_LOCLIKE = {
1571         CONSTRAINT_TYPE_LOCLIKE, /* type */
1572         sizeof(bLocateLikeConstraint), /* size */
1573         "Copy Location", /* name */
1574         "bLocateLikeConstraint", /* struct name */
1575         NULL, /* free data */
1576         NULL, /* relink data */
1577         loclike_id_looper, /* id looper */
1578         NULL, /* copy data */
1579         loclike_new_data, /* new data */
1580         loclike_get_tars, /* get constraint targets */
1581         loclike_flush_tars, /* flush constraint targets */
1582         default_get_tarmat, /* get target matrix */
1583         loclike_evaluate /* evaluate */
1584 };
1585
1586 /* ----------- Copy Rotation ------------- */
1587
1588 static void rotlike_new_data (void *cdata)
1589 {
1590         bRotateLikeConstraint *data= (bRotateLikeConstraint *)cdata;
1591         
1592         data->flag = ROTLIKE_X|ROTLIKE_Y|ROTLIKE_Z;
1593 }
1594
1595 static void rotlike_id_looper (bConstraint *con, ConstraintIDFunc func, void *userdata)
1596 {
1597         bChildOfConstraint *data= con->data;
1598         
1599         /* target only */
1600         func(con, (ID**)&data->tar, userdata);
1601 }
1602
1603 static int rotlike_get_tars (bConstraint *con, ListBase *list)
1604 {
1605         if (con && list) {
1606                 bRotateLikeConstraint *data= con->data;
1607                 bConstraintTarget *ct;
1608                 
1609                 /* standard target-getting macro for single-target constraints */
1610                 SINGLETARGET_GET_TARS(con, data->tar, data->subtarget, ct, list)
1611                 
1612                 return 1;
1613         }
1614         
1615         return 0;
1616 }
1617
1618 static void rotlike_flush_tars (bConstraint *con, ListBase *list, short nocopy)
1619 {
1620         if (con && list) {
1621                 bRotateLikeConstraint *data= con->data;
1622                 bConstraintTarget *ct= list->first;
1623                 
1624                 /* the following macro is used for all standard single-target constraints */
1625                 SINGLETARGET_FLUSH_TARS(con, data->tar, data->subtarget, ct, list, nocopy)
1626         }
1627 }
1628
1629 static void rotlike_evaluate (bConstraint *con, bConstraintOb *cob, ListBase *targets)
1630 {
1631         bRotateLikeConstraint *data= con->data;
1632         bConstraintTarget *ct= targets->first;
1633         
1634         if (VALID_CONS_TARGET(ct)) {
1635                 float   loc[3];
1636                 float   eul[3], obeul[3];
1637                 float   size[3];
1638                 
1639                 VECCOPY(loc, cob->matrix[3]);
1640                 mat4_to_size( size,cob->matrix);
1641                 
1642                 /* to allow compatible rotations, must get both rotations in the order of the owner... */
1643                 mat4_to_eulO( eul, cob->rotOrder,ct->matrix);
1644                 mat4_to_eulO( obeul, cob->rotOrder,cob->matrix);
1645                 
1646                 if ((data->flag & ROTLIKE_X)==0)
1647                         eul[0] = obeul[0];
1648                 else {
1649                         if (data->flag & ROTLIKE_OFFSET)
1650                                 rotate_eulO(eul, cob->rotOrder, 'X', obeul[0]);
1651                         
1652                         if (data->flag & ROTLIKE_X_INVERT)
1653                                 eul[0] *= -1;
1654                 }
1655                 
1656                 if ((data->flag & ROTLIKE_Y)==0)
1657                         eul[1] = obeul[1];
1658                 else {
1659                         if (data->flag & ROTLIKE_OFFSET)
1660                                 rotate_eulO(eul, cob->rotOrder, 'Y', obeul[1]);
1661                         
1662                         if (data->flag & ROTLIKE_Y_INVERT)
1663                                 eul[1] *= -1;
1664                 }
1665                 
1666                 if ((data->flag & ROTLIKE_Z)==0)
1667                         eul[2] = obeul[2];
1668                 else {
1669                         if (data->flag & ROTLIKE_OFFSET)
1670                                 rotate_eulO(eul, cob->rotOrder, 'Z', obeul[2]);
1671                         
1672                         if (data->flag & ROTLIKE_Z_INVERT)
1673                                 eul[2] *= -1;
1674                 }
1675                 
1676                 compatible_eul(eul, obeul);
1677                 loc_eulO_size_to_mat4(cob->matrix, loc, eul, size, cob->rotOrder);
1678         }
1679 }
1680
1681 static bConstraintTypeInfo CTI_ROTLIKE = {
1682         CONSTRAINT_TYPE_ROTLIKE, /* type */
1683         sizeof(bRotateLikeConstraint), /* size */
1684         "Copy Rotation", /* name */
1685         "bRotateLikeConstraint", /* struct name */
1686         NULL, /* free data */
1687         NULL, /* relink data */
1688         rotlike_id_looper, /* id looper */
1689         NULL, /* copy data */
1690         rotlike_new_data, /* new data */
1691         rotlike_get_tars, /* get constraint targets */
1692         rotlike_flush_tars, /* flush constraint targets */
1693         default_get_tarmat, /* get target matrix */
1694         rotlike_evaluate /* evaluate */
1695 };
1696
1697 /* ---------- Copy Scaling ---------- */
1698
1699 static void sizelike_new_data (void *cdata)
1700 {
1701         bSizeLikeConstraint *data= (bSizeLikeConstraint *)cdata;
1702         
1703         data->flag = SIZELIKE_X|SIZELIKE_Y|SIZELIKE_Z;
1704 }
1705
1706 static void sizelike_id_looper (bConstraint *con, ConstraintIDFunc func, void *userdata)
1707 {
1708         bSizeLikeConstraint *data= con->data;
1709         
1710         /* target only */
1711         func(con, (ID**)&data->tar, userdata);
1712 }
1713
1714 static int sizelike_get_tars (bConstraint *con, ListBase *list)
1715 {
1716         if (con && list) {
1717                 bSizeLikeConstraint *data= con->data;
1718                 bConstraintTarget *ct;
1719                 
1720                 /* standard target-getting macro for single-target constraints */
1721                 SINGLETARGET_GET_TARS(con, data->tar, data->subtarget, ct, list)
1722                 
1723                 return 1;
1724         }
1725         
1726         return 0;
1727 }
1728
1729 static void sizelike_flush_tars (bConstraint *con, ListBase *list, short nocopy)
1730 {
1731         if (con && list) {
1732                 bSizeLikeConstraint *data= con->data;
1733                 bConstraintTarget *ct= list->first;
1734                 
1735                 /* the following macro is used for all standard single-target constraints */
1736                 SINGLETARGET_FLUSH_TARS(con, data->tar, data->subtarget, ct, list, nocopy)
1737         }
1738 }
1739
1740 static void sizelike_evaluate (bConstraint *con, bConstraintOb *cob, ListBase *targets)
1741 {
1742         bSizeLikeConstraint *data= con->data;
1743         bConstraintTarget *ct= targets->first;
1744         
1745         if (VALID_CONS_TARGET(ct)) {
1746                 float obsize[3], size[3];
1747                 
1748                 mat4_to_size(size, ct->matrix);
1749                 mat4_to_size(obsize, cob->matrix);
1750                 
1751                 if ((data->flag & SIZELIKE_X) && (obsize[0] != 0)) {
1752                         if (data->flag & SIZELIKE_OFFSET) {
1753                                 size[0] += (obsize[0] - 1.0f);
1754                                 mul_v3_fl(cob->matrix[0], size[0] / obsize[0]);
1755                         }
1756                         else
1757                                 mul_v3_fl(cob->matrix[0], size[0] / obsize[0]);
1758                 }
1759                 if ((data->flag & SIZELIKE_Y) && (obsize[1] != 0)) {
1760                         if (data->flag & SIZELIKE_OFFSET) {
1761                                 size[1] += (obsize[1] - 1.0f);
1762                                 mul_v3_fl(cob->matrix[1], size[1] / obsize[1]);
1763                         }
1764                         else
1765                                 mul_v3_fl(cob->matrix[1], size[1] / obsize[1]);
1766                 }
1767                 if ((data->flag & SIZELIKE_Z) && (obsize[2] != 0)) {
1768                         if (data->flag & SIZELIKE_OFFSET) {
1769                                 size[2] += (obsize[2] - 1.0f);
1770                                 mul_v3_fl(cob->matrix[2], size[2] / obsize[2]);
1771                         }
1772                         else
1773                                 mul_v3_fl(cob->matrix[2], size[2] / obsize[2]);
1774                 }
1775         }
1776 }
1777
1778 static bConstraintTypeInfo CTI_SIZELIKE = {
1779         CONSTRAINT_TYPE_SIZELIKE, /* type */
1780         sizeof(bSizeLikeConstraint), /* size */
1781         "Copy Scale", /* name */
1782         "bSizeLikeConstraint", /* struct name */
1783         NULL, /* free data */
1784         NULL, /* relink data */
1785         sizelike_id_looper, /* id looper */
1786         NULL, /* copy data */
1787         sizelike_new_data, /* new data */
1788         sizelike_get_tars, /* get constraint targets */
1789         sizelike_flush_tars, /* flush constraint targets */
1790         default_get_tarmat, /* get target matrix */
1791         sizelike_evaluate /* evaluate */
1792 };
1793
1794 /* ----------- Copy Transforms ------------- */
1795
1796 static void translike_id_looper (bConstraint *con, ConstraintIDFunc func, void *userdata)
1797 {
1798         bTransLikeConstraint *data= con->data;
1799         
1800         /* target only */
1801         func(con, (ID**)&data->tar, userdata);
1802 }
1803
1804 static int translike_get_tars (bConstraint *con, ListBase *list)
1805 {
1806         if (con && list) {
1807                 bTransLikeConstraint *data= con->data;
1808                 bConstraintTarget *ct;
1809                 
1810                 /* standard target-getting macro for single-target constraints */
1811                 SINGLETARGET_GET_TARS(con, data->tar, data->subtarget, ct, list)
1812                 
1813                 return 1;
1814         }
1815         
1816         return 0;
1817 }
1818
1819 static void translike_flush_tars (bConstraint *con, ListBase *list, short nocopy)
1820 {
1821         if (con && list) {
1822                 bTransLikeConstraint *data= con->data;
1823                 bConstraintTarget *ct= list->first;
1824                 
1825                 /* the following macro is used for all standard single-target constraints */
1826                 SINGLETARGET_FLUSH_TARS(con, data->tar, data->subtarget, ct, list, nocopy)
1827         }
1828 }
1829
1830 static void translike_evaluate (bConstraint *con, bConstraintOb *cob, ListBase *targets)
1831 {
1832         bConstraintTarget *ct= targets->first;
1833         
1834         if (VALID_CONS_TARGET(ct)) {
1835                 /* just copy the entire transform matrix of the target */
1836                 copy_m4_m4(cob->matrix, ct->matrix);
1837         }
1838 }
1839
1840 static bConstraintTypeInfo CTI_TRANSLIKE = {
1841         CONSTRAINT_TYPE_TRANSLIKE, /* type */
1842         sizeof(bTransLikeConstraint), /* size */
1843         "Copy Transforms", /* name */
1844         "bTransLikeConstraint", /* struct name */
1845         NULL, /* free data */
1846         NULL, /* relink data */
1847         translike_id_looper, /* id looper */
1848         NULL, /* copy data */
1849         NULL, /* new data */
1850         translike_get_tars, /* get constraint targets */
1851         translike_flush_tars, /* flush constraint targets */
1852         default_get_tarmat, /* get target matrix */
1853         translike_evaluate /* evaluate */
1854 };
1855
1856 /* ---------- Maintain Volume ---------- */
1857
1858 static void samevolume_new_data (void *cdata)
1859 {
1860         bSameVolumeConstraint *data= (bSameVolumeConstraint *)cdata;
1861
1862         data->flag = SAMEVOL_Y;
1863         data->volume = 1.0f;
1864 }
1865
1866 static void samevolume_evaluate (bConstraint *con, bConstraintOb *cob, ListBase *targets)
1867 {
1868         bSameVolumeConstraint *data= con->data;
1869
1870         float obsize[3];
1871         float volume=data->volume;
1872
1873         mat4_to_size(obsize, cob->matrix);
1874
1875         switch (data->flag) {
1876                 case SAMEVOL_X:
1877                         if (obsize[0]!=0) {
1878                                 mul_v3_fl(cob->matrix[1], sqrt(volume/obsize[0])/obsize[0]);
1879                                 mul_v3_fl(cob->matrix[2], sqrt(volume/obsize[0])/obsize[0]);
1880                         }
1881                         break;
1882                 case SAMEVOL_Y:
1883                         if (obsize[1]!=0) {
1884                                 mul_v3_fl(cob->matrix[0], sqrt(volume/obsize[1])/obsize[1]);
1885                                 mul_v3_fl(cob->matrix[2], sqrt(volume/obsize[1])/obsize[1]);
1886                         }
1887                         break;
1888                 case SAMEVOL_Z:
1889                         if (obsize[2]!=0) {
1890                                 mul_v3_fl(cob->matrix[0], sqrt(volume/obsize[2])/obsize[2]);
1891                                 mul_v3_fl(cob->matrix[1], sqrt(volume/obsize[2])/obsize[2]);
1892                         }
1893                         break;
1894         }
1895 }
1896
1897 static bConstraintTypeInfo CTI_SAMEVOL = {
1898         CONSTRAINT_TYPE_SAMEVOL, /* type */
1899         sizeof(bSameVolumeConstraint), /* size */
1900         "Maintain Volume", /* name */
1901         "bSameVolumeConstraint", /* struct name */
1902         NULL, /* free data */
1903         NULL, /* relink data */
1904         NULL, /* id looper */
1905         NULL, /* copy data */
1906         samevolume_new_data, /* new data */
1907         NULL, /* get constraint targets */
1908         NULL, /* flush constraint targets */
1909         NULL, /* get target matrix */
1910         samevolume_evaluate /* evaluate */
1911 };
1912
1913 /* ----------- Python Constraint -------------- */
1914
1915 static void pycon_free (bConstraint *con)
1916 {
1917         bPythonConstraint *data= con->data;
1918         
1919         /* id-properties */
1920         IDP_FreeProperty(data->prop);
1921         MEM_freeN(data->prop);
1922         
1923         /* multiple targets */
1924         BLI_freelistN(&data->targets);
1925 }       
1926
1927 static void pycon_relink (bConstraint *con)
1928 {
1929         bPythonConstraint *data= con->data;
1930         
1931         ID_NEW(data->text);
1932 }
1933
1934 static void pycon_copy (bConstraint *con, bConstraint *srccon)
1935 {
1936         bPythonConstraint *pycon = (bPythonConstraint *)con->data;
1937         bPythonConstraint *opycon = (bPythonConstraint *)srccon->data;
1938         
1939         pycon->prop = IDP_CopyProperty(opycon->prop);
1940         BLI_duplicatelist(&pycon->targets, &opycon->targets);
1941 }
1942
1943 static void pycon_new_data (void *cdata)
1944 {
1945         bPythonConstraint *data= (bPythonConstraint *)cdata;
1946         
1947         /* everything should be set correctly by calloc, except for the prop->type constant.*/
1948         data->prop = MEM_callocN(sizeof(IDProperty), "PyConstraintProps");
1949         data->prop->type = IDP_GROUP;
1950 }
1951
1952 static int pycon_get_tars (bConstraint *con, ListBase *list)
1953 {
1954         if (con && list) {
1955                 bPythonConstraint *data= con->data;
1956                 
1957                 list->first = data->targets.first;
1958                 list->last = data->targets.last;
1959                 
1960                 return data->tarnum;
1961         }
1962         
1963         return 0;
1964 }
1965
1966 static void pycon_id_looper (bConstraint *con, ConstraintIDFunc func, void *userdata)
1967 {
1968         bPythonConstraint *data= con->data;
1969         bConstraintTarget *ct;
1970         
1971         /* targets */
1972         for (ct= data->targets.first; ct; ct= ct->next)
1973                 func(con, (ID**)&ct->tar, userdata);
1974                 
1975         /* script */
1976         func(con, (ID**)&data->text, userdata);
1977 }
1978
1979 /* Whether this approach is maintained remains to be seen (aligorith) */
1980 static void pycon_get_tarmat (bConstraint *con, bConstraintOb *cob, bConstraintTarget *ct, float ctime)
1981 {
1982 #ifndef DISABLE_PYTHON
1983         bPythonConstraint *data= con->data;
1984 #endif
1985
1986         if (VALID_CONS_TARGET(ct)) {
1987                 /* special exception for curves - depsgraph issues */
1988                 if (ct->tar->type == OB_CURVE) {
1989                         Curve *cu= ct->tar->data;
1990                         
1991                         /* this check is to make sure curve objects get updated on file load correctly.*/
1992                         if (cu->path==NULL || cu->path->data==NULL) /* only happens on reload file, but violates depsgraph still... fix! */
1993                                 makeDispListCurveTypes(cob->scene, ct->tar, 0);                         
1994                 }
1995                 
1996                 /* firstly calculate the matrix the normal way, then let the py-function override
1997                  * this matrix if it needs to do so
1998                  */
1999                 constraint_target_to_mat4(cob->scene, ct->tar, ct->subtarget, ct->matrix, CONSTRAINT_SPACE_WORLD, ct->space, con->headtail);
2000                 
2001                 /* only execute target calculation if allowed */
2002 #ifndef DISABLE_PYTHON
2003                 if (G.f & G_SCRIPT_AUTOEXEC)
2004                         BPY_pyconstraint_target(data, ct);
2005 #endif
2006         }
2007         else if (ct)
2008                 unit_m4(ct->matrix);
2009 }
2010
2011 static void pycon_evaluate (bConstraint *con, bConstraintOb *cob, ListBase *targets)
2012 {
2013 #ifdef DISABLE_PYTHON
2014         return;
2015 #else
2016         bPythonConstraint *data= con->data;
2017         
2018         /* only evaluate in python if we're allowed to do so */
2019         if ((G.f & G_SCRIPT_AUTOEXEC)==0)  return;
2020         
2021 /* currently removed, until I this can be re-implemented for multiple targets */
2022 #if 0
2023         /* Firstly, run the 'driver' function which has direct access to the objects involved 
2024          * Technically, this is potentially dangerous as users may abuse this and cause dependency-problems,
2025          * but it also allows certain 'clever' rigging hacks to work.
2026          */
2027         BPY_pyconstraint_driver(data, cob, targets);
2028 #endif
2029         
2030         /* Now, run the actual 'constraint' function, which should only access the matrices */
2031         BPY_pyconstraint_eval(data, cob, targets);
2032 #endif /* DISABLE_PYTHON */
2033 }
2034
2035 static bConstraintTypeInfo CTI_PYTHON = {
2036         CONSTRAINT_TYPE_PYTHON, /* type */
2037         sizeof(bPythonConstraint), /* size */
2038         "Script", /* name */
2039         "bPythonConstraint", /* struct name */
2040         pycon_free, /* free data */
2041         pycon_relink, /* relink data */
2042         pycon_id_looper, /* id looper */
2043         pycon_copy, /* copy data */
2044         pycon_new_data, /* new data */
2045         pycon_get_tars, /* get constraint targets */
2046         NULL, /* flush constraint targets */
2047         pycon_get_tarmat, /* get target matrix */
2048         pycon_evaluate /* evaluate */
2049 };
2050
2051 /* -------- Action Constraint ----------- */
2052
2053 static void actcon_relink (bConstraint *con)
2054 {
2055         bActionConstraint *data= con->data;
2056         ID_NEW(data->act);
2057 }
2058
2059 static void actcon_new_data (void *cdata)
2060 {
2061         bActionConstraint *data= (bActionConstraint *)cdata;
2062         
2063         /* set type to 20 (Loc X), as 0 is Rot X for backwards compatability */
2064         data->type = 20;
2065 }
2066
2067 static void actcon_id_looper (bConstraint *con, ConstraintIDFunc func, void *userdata)
2068 {
2069         bActionConstraint *data= con->data;
2070         
2071         /* target */
2072         func(con, (ID**)&data->tar, userdata);
2073         
2074         /* action */
2075         func(con, (ID**)&data->act, userdata);
2076 }
2077
2078 static int actcon_get_tars (bConstraint *con, ListBase *list)
2079 {
2080         if (con && list) {
2081                 bActionConstraint *data= con->data;
2082                 bConstraintTarget *ct;
2083                 
2084                 /* standard target-getting macro for single-target constraints */
2085                 SINGLETARGET_GET_TARS(con, data->tar, data->subtarget, ct, list)
2086                 
2087                 return 1;
2088         }
2089         
2090         return 0;
2091 }
2092
2093 static void actcon_flush_tars (bConstraint *con, ListBase *list, short nocopy)
2094 {
2095         if (con && list) {
2096                 bActionConstraint *data= con->data;
2097                 bConstraintTarget *ct= list->first;
2098                 
2099                 /* the following macro is used for all standard single-target constraints */
2100                 SINGLETARGET_FLUSH_TARS(con, data->tar, data->subtarget, ct, list, nocopy)
2101         }
2102 }
2103
2104 static void actcon_get_tarmat (bConstraint *con, bConstraintOb *cob, bConstraintTarget *ct, float ctime)
2105 {
2106         extern void chan_calc_mat(bPoseChannel *chan);
2107         bActionConstraint *data = con->data;
2108         
2109         if (VALID_CONS_TARGET(ct)) {
2110                 float tempmat[4][4], vec[3];
2111                 float s, t;
2112                 short axis;
2113                 
2114                 /* initialise return matrix */
2115                 unit_m4(ct->matrix);
2116                 
2117                 /* get the transform matrix of the target */
2118                 constraint_target_to_mat4(cob->scene, ct->tar, ct->subtarget, tempmat, CONSTRAINT_SPACE_WORLD, ct->space, con->headtail);
2119                 
2120                 /* determine where in transform range target is */
2121                 /* data->type is mapped as follows for backwards compatability:
2122                  *      00,01,02        - rotation (it used to be like this)
2123                  *      10,11,12        - scaling
2124                  *      20,21,22        - location
2125                  */
2126                 if (data->type < 10) {
2127                         /* extract rotation (is in whatever space target should be in) */
2128                         mat4_to_eul(vec, tempmat);
2129                         vec[0] *= (float)(180.0/M_PI);
2130                         vec[1] *= (float)(180.0/M_PI);
2131                         vec[2] *= (float)(180.0/M_PI);
2132                         axis= data->type;
2133                 }
2134                 else if (data->type < 20) {
2135                         /* extract scaling (is in whatever space target should be in) */
2136                         mat4_to_size(vec, tempmat);
2137                         axis= data->type - 10;
2138                 }
2139                 else {
2140                         /* extract location */
2141                         VECCOPY(vec, tempmat[3]);
2142                         axis= data->type - 20;
2143                 }
2144                 
2145                 /* Target defines the animation */
2146                 s = (vec[axis]-data->min) / (data->max-data->min);
2147                 CLAMP(s, 0, 1);
2148                 t = (s * (data->end-data->start)) + data->start;
2149                 
2150                 if (G.f & G_DEBUG)
2151                         printf("do Action Constraint %s - Ob %s Pchan %s \n", con->name, cob->ob->id.name+2, (cob->pchan)?cob->pchan->name:NULL);
2152                 
2153                 /* Get the appropriate information from the action */
2154                 if (cob->type == CONSTRAINT_OBTYPE_BONE) {
2155                         Object workob;
2156                         bPose *pose;
2157                         bPoseChannel *pchan, *tchan;
2158                         
2159                         /* make a temporary pose and evaluate using that */
2160                         pose = MEM_callocN(sizeof(bPose), "pose");
2161                         
2162                         /* make a copy of the bone of interest in the temp pose before evaluating action, so that it can get set 
2163                          *      - we need to manually copy over a few settings, including rotation order, otherwise this fails
2164                          */
2165                         pchan = cob->pchan;
2166                         
2167                         tchan= verify_pose_channel(pose, pchan->name);
2168                         tchan->rotmode= pchan->rotmode;
2169                         
2170                         /* evaluate action using workob (it will only set the PoseChannel in question) */
2171                         what_does_obaction(cob->scene, cob->ob, &workob, pose, data->act, pchan->name, t);
2172                         
2173                         /* convert animation to matrices for use here */
2174                         chan_calc_mat(tchan);
2175                         copy_m4_m4(ct->matrix, tchan->chan_mat);
2176                         
2177                         /* Clean up */
2178                         free_pose(pose);
2179                 }
2180                 else if (cob->type == CONSTRAINT_OBTYPE_OBJECT) {
2181                         Object workob;
2182                         
2183                         /* evaluate using workob */
2184                         // FIXME: we don't have any consistent standards on limiting effects on object...
2185                         what_does_obaction(cob->scene, cob->ob, &workob, NULL, data->act, NULL, t);
2186                         object_to_mat4(&workob, ct->matrix);
2187                 }
2188                 else {
2189                         /* behaviour undefined... */
2190                         puts("Error: unknown owner type for Action Constraint");
2191                 }
2192         }
2193 }
2194
2195 static void actcon_evaluate (bConstraint *con, bConstraintOb *cob, ListBase *targets)
2196 {
2197         bConstraintTarget *ct= targets->first;
2198         
2199         if (VALID_CONS_TARGET(ct)) {
2200                 float temp[4][4];
2201                 
2202                 /* Nice and simple... we just need to multiply the matrices, as the get_target_matrix
2203                  * function has already taken care of everything else.
2204                  */
2205                 copy_m4_m4(temp, cob->matrix);
2206                 mul_m4_m4m4(cob->matrix, ct->matrix, temp);
2207         }
2208 }
2209
2210 static bConstraintTypeInfo CTI_ACTION = {
2211         CONSTRAINT_TYPE_ACTION, /* type */
2212         sizeof(bActionConstraint), /* size */
2213         "Action", /* name */
2214         "bActionConstraint", /* struct name */
2215         NULL, /* free data */
2216         actcon_relink, /* relink data */
2217         actcon_id_looper, /* id looper */
2218         NULL, /* copy data */
2219         actcon_new_data, /* new data */
2220         actcon_get_tars, /* get constraint targets */
2221         actcon_flush_tars, /* flush constraint targets */
2222         actcon_get_tarmat, /* get target matrix */
2223         actcon_evaluate /* evaluate */
2224 };
2225
2226 /* --------- Locked Track ---------- */
2227
2228 static void locktrack_new_data (void *cdata)
2229 {
2230         bLockTrackConstraint *data= (bLockTrackConstraint *)cdata;
2231         
2232         data->trackflag = TRACK_Y;
2233         data->lockflag = LOCK_Z;
2234 }       
2235
2236 static void locktrack_id_looper (bConstraint *con, ConstraintIDFunc func, void *userdata)
2237 {
2238         bLockTrackConstraint *data= con->data;
2239         
2240         /* target only */
2241         func(con, (ID**)&data->tar, userdata);
2242 }
2243
2244 static int locktrack_get_tars (bConstraint *con, ListBase *list)
2245 {
2246         if (con && list) {
2247                 bLockTrackConstraint *data= con->data;
2248                 bConstraintTarget *ct;
2249                 
2250                 /* the following macro is used for all standard single-target constraints */
2251                 SINGLETARGET_GET_TARS(con, data->tar, data->subtarget, ct, list)
2252                 
2253                 return 1;
2254         }
2255         
2256         return 0;
2257 }
2258
2259 static void locktrack_flush_tars (bConstraint *con, ListBase *list, short nocopy)
2260 {
2261         if (con && list) {
2262                 bLockTrackConstraint *data= con->data;
2263                 bConstraintTarget *ct= list->first;
2264                 
2265                 /* the following macro is used for all standard single-target constraints */
2266                 SINGLETARGET_FLUSH_TARS(con, data->tar, data->subtarget, ct, list, nocopy)
2267         }
2268 }
2269
2270 static void locktrack_evaluate (bConstraint *con, bConstraintOb *cob, ListBase *targets)
2271 {
2272         bLockTrackConstraint *data= con->data;
2273         bConstraintTarget *ct= targets->first;
2274         
2275         if (VALID_CONS_TARGET(ct)) {
2276                 float vec[3],vec2[3];
2277                 float totmat[3][3];
2278                 float tmpmat[3][3];
2279                 float invmat[3][3];
2280                 float tmat[4][4];
2281                 float mdet;
2282                 
2283                 /* Vector object -> target */
2284                 sub_v3_v3v3(vec, ct->matrix[3], cob->matrix[3]);
2285                 switch (data->lockflag){
2286                 case LOCK_X: /* LOCK X */
2287                 {
2288                         switch (data->trackflag) {
2289                                 case TRACK_Y: /* LOCK X TRACK Y */
2290                                 {
2291                                         /* Projection of Vector on the plane */
2292                                         project_v3_v3v3(vec2, vec, cob->matrix[0]);
2293                                         sub_v3_v3v3(totmat[1], vec, vec2);
2294                                         normalize_v3(totmat[1]);
2295                                         
2296                                         /* the x axis is fixed */
2297                                         totmat[0][0] = cob->matrix[0][0];
2298                                         totmat[0][1] = cob->matrix[0][1];
2299                                         totmat[0][2] = cob->matrix[0][2];
2300                                         normalize_v3(totmat[0]);
2301                                         
2302                                         /* the z axis gets mapped onto a third orthogonal vector */
2303                                         cross_v3_v3v3(totmat[2], totmat[0], totmat[1]);
2304                                 }
2305                                         break;
2306                                 case TRACK_Z: /* LOCK X TRACK Z */
2307                                 {
2308                                         /* Projection of Vector on the plane */
2309                                         project_v3_v3v3(vec2, vec, cob->matrix[0]);
2310                                         sub_v3_v3v3(totmat[2], vec, vec2);
2311                                         normalize_v3(totmat[2]);
2312                                         
2313                                         /* the x axis is fixed */
2314                                         totmat[0][0] = cob->matrix[0][0];
2315                                         totmat[0][1] = cob->matrix[0][1];
2316                                         totmat[0][2] = cob->matrix[0][2];
2317                                         normalize_v3(totmat[0]);
2318                                         
2319                                         /* the z axis gets mapped onto a third orthogonal vector */
2320                                         cross_v3_v3v3(totmat[1], totmat[2], totmat[0]);
2321                                 }
2322                                         break;
2323                                 case TRACK_nY: /* LOCK X TRACK -Y */
2324                                 {
2325                                         /* Projection of Vector on the plane */
2326                                         project_v3_v3v3(vec2, vec, cob->matrix[0]);
2327                                         sub_v3_v3v3(totmat[1], vec, vec2);
2328                                         normalize_v3(totmat[1]);
2329                                         negate_v3(totmat[1]);
2330                                         
2331                                         /* the x axis is fixed */
2332                                         totmat[0][0] = cob->matrix[0][0];
2333                                         totmat[0][1] = cob->matrix[0][1];
2334                                         totmat[0][2] = cob->matrix[0][2];
2335                                         normalize_v3(totmat[0]);
2336                                         
2337                                         /* the z axis gets mapped onto a third orthogonal vector */
2338                                         cross_v3_v3v3(totmat[2], totmat[0], totmat[1]);
2339                                 }
2340                                         break;
2341                                 case TRACK_nZ: /* LOCK X TRACK -Z */
2342                                 {
2343                                         /* Projection of Vector on the plane */
2344                                         project_v3_v3v3(vec2, vec, cob->matrix[0]);
2345                                         sub_v3_v3v3(totmat[2], vec, vec2);
2346                                         normalize_v3(totmat[2]);
2347                                         negate_v3(totmat[2]);
2348                                                 
2349                                         /* the x axis is fixed */
2350                                         totmat[0][0] = cob->matrix[0][0];
2351                                         totmat[0][1] = cob->matrix[0][1];
2352                                         totmat[0][2] = cob->matrix[0][2];
2353                                         normalize_v3(totmat[0]);
2354                                                 
2355                                         /* the z axis gets mapped onto a third orthogonal vector */
2356                                         cross_v3_v3v3(totmat[1], totmat[2], totmat[0]);
2357                                 }
2358                                         break;
2359                                 default:
2360                                 {
2361                                         totmat[0][0] = 1;totmat[0][1] = 0;totmat[0][2] = 0;
2362                                         totmat[1][0] = 0;totmat[1][1] = 1;totmat[1][2] = 0;
2363                                         totmat[2][0] = 0;totmat[2][1] = 0;totmat[2][2] = 1;
2364                                 }
2365                                         break;
2366                         }
2367                 }
2368                         break;
2369                 case LOCK_Y: /* LOCK Y */
2370                 {
2371                         switch (data->trackflag) {
2372                                 case TRACK_X: /* LOCK Y TRACK X */
2373                                 {
2374                                         /* Projection of Vector on the plane */
2375                                         project_v3_v3v3(vec2, vec, cob->matrix[1]);
2376                                         sub_v3_v3v3(totmat[0], vec, vec2);
2377                                         normalize_v3(totmat[0]);
2378                                         
2379                                         /* the y axis is fixed */
2380                                         totmat[1][0] = cob->matrix[1][0];
2381                                         totmat[1][1] = cob->matrix[1][1];
2382                                         totmat[1][2] = cob->matrix[1][2];
2383                                         normalize_v3(totmat[1]);
2384                                         
2385                                         /* the z axis gets mapped onto a third orthogonal vector */
2386                                         cross_v3_v3v3(totmat[2], totmat[0], totmat[1]);
2387                                 }
2388                                         break;
2389                                 case TRACK_Z: /* LOCK Y TRACK Z */
2390                                 {
2391                                         /* Projection of Vector on the plane */
2392                                         project_v3_v3v3(vec2, vec, cob->matrix[1]);
2393                                         sub_v3_v3v3(totmat[2], vec, vec2);
2394                                         normalize_v3(totmat[2]);
2395                                         
2396                                         /* the y axis is fixed */
2397                                         totmat[1][0] = cob->matrix[1][0];
2398                                         totmat[1][1] = cob->matrix[1][1];
2399                                         totmat[1][2] = cob->matrix[1][2];
2400                                         normalize_v3(totmat[1]);
2401                                         
2402                                         /* the z axis gets mapped onto a third orthogonal vector */
2403                                         cross_v3_v3v3(totmat[0], totmat[1], totmat[2]);
2404                                 }
2405                                         break;
2406                                 case TRACK_nX: /* LOCK Y TRACK -X */
2407                                 {
2408                                         /* Projection of Vector on the plane */
2409                                         project_v3_v3v3(vec2, vec, cob->matrix[1]);
2410                                         sub_v3_v3v3(totmat[0], vec, vec2);
2411                                         normalize_v3(totmat[0]);
2412                                         negate_v3(totmat[0]);
2413                                         
2414                                         /* the y axis is fixed */
2415                                         totmat[1][0] = cob->matrix[1][0];
2416                                         totmat[1][1] = cob->matrix[1][1];
2417                                         totmat[1][2] = cob->matrix[1][2];
2418                                         normalize_v3(totmat[1]);
2419                                         
2420                                         /* the z axis gets mapped onto a third orthogonal vector */
2421                                         cross_v3_v3v3(totmat[2], totmat[0], totmat[1]);
2422                                 }
2423                                         break;
2424                                 case TRACK_nZ: /* LOCK Y TRACK -Z */
2425                                 {
2426                                         /* Projection of Vector on the plane */
2427                                         project_v3_v3v3(vec2, vec, cob->matrix[1]);
2428                                         sub_v3_v3v3(totmat[2], vec, vec2);
2429                                         normalize_v3(totmat[2]);
2430                                         negate_v3(totmat[2]);
2431                                         
2432                                         /* the y axis is fixed */
2433                                         totmat[1][0] = cob->matrix[1][0];
2434                                         totmat[1][1] = cob->matrix[1][1];
2435                                         totmat[1][2] = cob->matrix[1][2];
2436                                         normalize_v3(totmat[1]);
2437                                         
2438                                         /* the z axis gets mapped onto a third orthogonal vector */
2439                                         cross_v3_v3v3(totmat[0], totmat[1], totmat[2]);
2440                                 }
2441                                         break;
2442                                 default:
2443                                 {
2444                                         totmat[0][0] = 1;totmat[0][1] = 0;totmat[0][2] = 0;
2445                                         totmat[1][0] = 0;totmat[1][1] = 1;totmat[1][2] = 0;
2446                                         totmat[2][0] = 0;totmat[2][1] = 0;totmat[2][2] = 1;
2447                                 }
2448                                         break;
2449                         }
2450                 }
2451                         break;
2452                 case LOCK_Z: /* LOCK Z */
2453                 {
2454                         switch (data->trackflag) {
2455                                 case TRACK_X: /* LOCK Z TRACK X */
2456                                 {
2457                                         /* Projection of Vector on the plane */
2458                                         project_v3_v3v3(vec2, vec, cob->matrix[2]);
2459                                         sub_v3_v3v3(totmat[0], vec, vec2);
2460                                         normalize_v3(totmat[0]);
2461                                         
2462                                         /* the z axis is fixed */
2463                                         totmat[2][0] = cob->matrix[2][0];
2464                                         totmat[2][1] = cob->matrix[2][1];
2465                                         totmat[2][2] = cob->matrix[2][2];
2466                                         normalize_v3(totmat[2]);
2467                                         
2468                                         /* the x axis gets mapped onto a third orthogonal vector */
2469                                         cross_v3_v3v3(totmat[1], totmat[2], totmat[0]);
2470                                 }
2471                                         break;
2472                                 case TRACK_Y: /* LOCK Z TRACK Y */
2473                                 {
2474                                         /* Projection of Vector on the plane */
2475                                         project_v3_v3v3(vec2, vec, cob->matrix[2]);
2476                                         sub_v3_v3v3(totmat[1], vec, vec2);
2477                                         normalize_v3(totmat[1]);
2478                                         
2479                                         /* the z axis is fixed */
2480                                         totmat[2][0] = cob->matrix[2][0];
2481                                         totmat[2][1] = cob->matrix[2][1];
2482                                         totmat[2][2] = cob->matrix[2][2];
2483                                         normalize_v3(totmat[2]);
2484                                                 
2485                                         /* the x axis gets mapped onto a third orthogonal vector */
2486                                         cross_v3_v3v3(totmat[0], totmat[1], totmat[2]);
2487                                 }
2488                                         break;
2489                                 case TRACK_nX: /* LOCK Z TRACK -X */
2490                                 {
2491                                         /* Projection of Vector on the plane */
2492                                         project_v3_v3v3(vec2, vec, cob->matrix[2]);
2493                                         sub_v3_v3v3(totmat[0], vec, vec2);
2494                                         normalize_v3(totmat[0]);
2495                                         negate_v3(totmat[0]);
2496                                         
2497                                         /* the z axis is fixed */
2498                                         totmat[2][0] = cob->matrix[2][0];
2499                                         totmat[2][1] = cob->matrix[2][1];
2500                                         totmat[2][2] = cob->matrix[2][2];
2501                                         normalize_v3(totmat[2]);
2502                                         
2503                                         /* the x axis gets mapped onto a third orthogonal vector */
2504                                         cross_v3_v3v3(totmat[1], totmat[2], totmat[0]);
2505                                 }
2506                                         break;
2507                                 case TRACK_nY: /* LOCK Z TRACK -Y */
2508                                 {
2509                                         /* Projection of Vector on the plane */
2510                                         project_v3_v3v3(vec2, vec, cob->matrix[2]);
2511                                         sub_v3_v3v3(totmat[1], vec, vec2);
2512                                         normalize_v3(totmat[1]);
2513                                         negate_v3(totmat[1]);
2514                                         
2515                                         /* the z axis is fixed */
2516                                         totmat[2][0] = cob->matrix[2][0];
2517                                         totmat[2][1] = cob->matrix[2][1];
2518                                         totmat[2][2] = cob->matrix[2][2];
2519                                         normalize_v3(totmat[2]);
2520                                                 
2521                                         /* the x axis gets mapped onto a third orthogonal vector */
2522                                         cross_v3_v3v3(totmat[0], totmat[1], totmat[2]);
2523                                 }
2524                                         break;
2525                                 default:
2526                                 {
2527                                         totmat[0][0] = 1;totmat[0][1] = 0;totmat[0][2] = 0;
2528                                         totmat[1][0] = 0;totmat[1][1] = 1;totmat[1][2] = 0;
2529                                         totmat[2][0] = 0;totmat[2][1] = 0;totmat[2][2] = 1;
2530                                 }
2531                                         break;
2532                         }
2533                 }
2534                         break;
2535                 default:
2536                 {
2537                         totmat[0][0] = 1;totmat[0][1] = 0;totmat[0][2] = 0;
2538                         totmat[1][0] = 0;totmat[1][1] = 1;totmat[1][2] = 0;
2539                         totmat[2][0] = 0;totmat[2][1] = 0;totmat[2][2] = 1;
2540                 }
2541                         break;
2542                 }
2543                 /* Block to keep matrix heading */
2544                 tmpmat[0][0] = cob->matrix[0][0];tmpmat[0][1] = cob->matrix[0][1];tmpmat[0][2] = cob->matrix[0][2];
2545                 tmpmat[1][0] = cob->matrix[1][0];tmpmat[1][1] = cob->matrix[1][1];tmpmat[1][2] = cob->matrix[1][2];
2546                 tmpmat[2][0] = cob->matrix[2][0];tmpmat[2][1] = cob->matrix[2][1];tmpmat[2][2] = cob->matrix[2][2];
2547                 normalize_v3(tmpmat[0]);
2548                 normalize_v3(tmpmat[1]);
2549                 normalize_v3(tmpmat[2]);
2550                 invert_m3_m3(invmat, tmpmat);
2551                 mul_m3_m3m3(tmpmat, totmat, invmat);
2552                 totmat[0][0] = tmpmat[0][0];totmat[0][1] = tmpmat[0][1];totmat[0][2] = tmpmat[0][2];
2553                 totmat[1][0] = tmpmat[1][0];totmat[1][1] = tmpmat[1][1];totmat[1][2] = tmpmat[1][2];
2554                 totmat[2][0] = tmpmat[2][0];totmat[2][1] = tmpmat[2][1];totmat[2][2] = tmpmat[2][2];
2555                 
2556                 copy_m4_m4(tmat, cob->matrix);
2557                 
2558                 mdet = determinant_m3(  totmat[0][0],totmat[0][1],totmat[0][2],
2559                                                 totmat[1][0],totmat[1][1],totmat[1][2],
2560                                                 totmat[2][0],totmat[2][1],totmat[2][2]);
2561                 if (mdet==0) {
2562                         totmat[0][0] = 1;totmat[0][1] = 0;totmat[0][2] = 0;
2563                         totmat[1][0] = 0;totmat[1][1] = 1;totmat[1][2] = 0;
2564                         totmat[2][0] = 0;totmat[2][1] = 0;totmat[2][2] = 1;
2565                 }
2566                 
2567                 /* apply out transformaton to the object */
2568                 mul_m4_m3m4(cob->matrix, totmat, tmat);
2569         }
2570 }
2571
2572 static bConstraintTypeInfo CTI_LOCKTRACK = {
2573         CONSTRAINT_TYPE_LOCKTRACK, /* type */
2574         sizeof(bLockTrackConstraint), /* size */
2575         "Locked Track", /* name */
2576         "bLockTrackConstraint", /* struct name */
2577         NULL, /* free data */
2578         NULL, /* relink data */
2579         locktrack_id_looper, /* id looper */
2580         NULL, /* copy data */
2581         locktrack_new_data, /* new data */
2582         locktrack_get_tars, /* get constraint targets */
2583         locktrack_flush_tars, /* flush constraint targets */
2584         default_get_tarmat, /* get target matrix */
2585         locktrack_evaluate /* evaluate */
2586 };
2587
2588 /* ---------- Limit Distance Constraint ----------- */
2589
2590 static void distlimit_new_data (void *cdata)
2591 {
2592         bDistLimitConstraint *data= (bDistLimitConstraint *)cdata;
2593         
2594         data->dist= 0.0f;
2595 }
2596
2597 static void distlimit_id_looper (bConstraint *con, ConstraintIDFunc func, void *userdata)
2598 {
2599         bDistLimitConstraint *data= con->data;
2600         
2601         /* target only */
2602         func(con, (ID**)&data->tar, userdata);
2603 }
2604
2605 static int distlimit_get_tars (bConstraint *con, ListBase *list)
2606 {
2607         if (con && list) {
2608                 bDistLimitConstraint *data= con->data;
2609                 bConstraintTarget *ct;
2610                 
2611                 /* standard target-getting macro for single-target constraints */
2612                 SINGLETARGET_GET_TARS(con, data->tar, data->subtarget, ct, list)
2613                 
2614                 return 1;
2615         }
2616         
2617         return 0;
2618 }
2619
2620 static void distlimit_flush_tars (bConstraint *con, ListBase *list, short nocopy)
2621 {
2622         if (con && list) {
2623                 bDistLimitConstraint *data= con->data;
2624                 bConstraintTarget *ct= list->first;
2625                 
2626                 /* the following macro is used for all standard single-target constraints */
2627                 SINGLETARGET_FLUSH_TARS(con, data->tar, data->subtarget, ct, list, nocopy)
2628         }
2629 }
2630
2631 static void distlimit_evaluate (bConstraint *con, bConstraintOb *cob, ListBase *targets)
2632 {
2633         bDistLimitConstraint *data= con->data;
2634         bConstraintTarget *ct= targets->first;
2635         
2636         /* only evaluate if there is a target */
2637         if (VALID_CONS_TARGET(ct)) {
2638                 float dvec[3], dist=0.0f, sfac=1.0f;
2639                 short clamp_surf= 0;
2640                 
2641                 /* calculate our current distance from the target */
2642                 dist= len_v3v3(cob->matrix[3], ct->matrix[3]);
2643                 
2644                 /* set distance (flag is only set when user demands it) */
2645                 if (data->dist == 0)
2646                         data->dist= dist;
2647                 
2648                 /* check if we're which way to clamp from, and calculate interpolation factor (if needed) */
2649                 if (data->mode == LIMITDIST_OUTSIDE) {
2650                         /* if inside, then move to surface */
2651                         if (dist <= data->dist) {
2652                                 clamp_surf= 1;
2653                                 sfac= data->dist / dist;
2654                         }
2655                         /* if soft-distance is enabled, start fading once owner is dist+softdist from the target */
2656                         else if (data->flag & LIMITDIST_USESOFT) {
2657                                 if (dist <= (data->dist + data->soft)) {
2658                                         
2659                                 }
2660                         }
2661                 }
2662                 else if (data->mode == LIMITDIST_INSIDE) {
2663                         /* if outside, then move to surface */
2664                         if (dist >= data->dist) {
2665                                 clamp_surf= 1;
2666                                 sfac= data->dist / dist;
2667                         }
2668                         /* if soft-distance is enabled, start fading once owner is dist-soft from the target */
2669                         else if (data->flag & LIMITDIST_USESOFT) {
2670                                 // FIXME: there's a problem with "jumping" when this kicks in
2671                                 if (dist >= (data->dist - data->soft)) {
2672                                         sfac = (float)( data->soft*(1.0 - exp(-(dist - data->dist)/data->soft)) + data->dist );
2673                                         sfac /= dist;
2674                                         
2675                                         clamp_surf= 1;
2676                                 }
2677                         }
2678                 }
2679                 else {
2680                         if (IS_EQ(dist, data->dist)==0) {
2681                                 clamp_surf= 1;
2682                                 sfac= data->dist / dist;
2683                         }
2684                 }
2685                 
2686                 /* clamp to 'surface' (i.e. move owner so that dist == data->dist) */
2687                 if (clamp_surf) {
2688                         /* simply interpolate along line formed by target -> owner */
2689                         interp_v3_v3v3(dvec, ct->matrix[3], cob->matrix[3], sfac);
2690                         
2691                         /* copy new vector onto owner */
2692                         VECCOPY(cob->matrix[3], dvec);
2693                 }
2694         }
2695 }
2696
2697 static bConstraintTypeInfo CTI_DISTLIMIT = {
2698         CONSTRAINT_TYPE_DISTLIMIT, /* type */
2699         sizeof(bDistLimitConstraint), /* size */
2700         "Limit Distance", /* name */
2701         "bDistLimitConstraint", /* struct name */
2702         NULL, /* free data */
2703         NULL, /* relink data */
2704         distlimit_id_looper, /* id looper */
2705         NULL, /* copy data */
2706         distlimit_new_data, /* new data */
2707         distlimit_get_tars, /* get constraint targets */
2708         distlimit_flush_tars, /* flush constraint targets */
2709         default_get_tarmat, /* get a target matrix */
2710         distlimit_evaluate /* evaluate */
2711 };
2712
2713 /* ---------- Stretch To ------------ */
2714
2715 static void stretchto_new_data (void *cdata)
2716 {
2717         bStretchToConstraint *data= (bStretchToConstraint *)cdata;
2718         
2719         data->volmode = 0;
2720         data->plane = 0;
2721         data->orglength = 0.0; 
2722         data->bulge = 1.0;
2723 }
2724
2725 static void stretchto_id_looper (bConstraint *con, ConstraintIDFunc func, void *userdata)
2726 {
2727         bStretchToConstraint *data= con->data;
2728         
2729         /* target only */
2730         func(con, (ID**)&data->tar, userdata);
2731 }
2732
2733 static int stretchto_get_tars (bConstraint *con, ListBase *list)
2734 {
2735         if (con && list) {
2736                 bStretchToConstraint *data= con->data;
2737                 bConstraintTarget *ct;
2738                 
2739                 /* standard target-getting macro for single-target constraints */
2740                 SINGLETARGET_GET_TARS(con, data->tar, data->subtarget, ct, list)
2741                 
2742                 return 1;
2743         }
2744         
2745         return 0;
2746 }
2747
2748 static void stretchto_flush_tars (bConstraint *con, ListBase *list, short nocopy)
2749 {
2750         if (con && list) {
2751                 bStretchToConstraint *data= con->data;
2752                 bConstraintTarget *ct= list->first;
2753                 
2754                 /* the following macro is used for all standard single-target constraints */
2755                 SINGLETARGET_FLUSH_TARS(con, data->tar, data->subtarget, ct, list, nocopy)
2756         }
2757 }
2758
2759 static void stretchto_evaluate (bConstraint *con, bConstraintOb *cob, ListBase *targets)
2760 {
2761         bStretchToConstraint *data= con->data;
2762         bConstraintTarget *ct= targets->first;
2763         
2764         /* only evaluate if there is a target */
2765         if (VALID_CONS_TARGET(ct)) {
2766                 float size[3], scale[3], vec[3], xx[3], zz[3], orth[3];
2767                 float totmat[3][3];
2768                 float tmat[4][4];
2769                 float dist;
2770                 
2771                 /* store scaling before destroying obmat */
2772                 mat4_to_size( size,cob->matrix);
2773                 
2774                 /* store X orientation before destroying obmat */
2775                 xx[0] = cob->matrix[0][0];
2776                 xx[1] = cob->matrix[0][1];
2777                 xx[2] = cob->matrix[0][2];
2778                 normalize_v3(xx);
2779                 
2780                 /* store Z orientation before destroying obmat */
2781                 zz[0] = cob->matrix[2][0];
2782                 zz[1] = cob->matrix[2][1];
2783                 zz[2] = cob->matrix[2][2];
2784                 normalize_v3(zz);
2785                 
2786                 sub_v3_v3v3(vec, cob->matrix[3], ct->matrix[3]);
2787                 vec[0] /= size[0];
2788                 vec[1] /= size[1];
2789                 vec[2] /= size[2];
2790                 
2791                 dist = normalize_v3(vec);
2792                 //dist = len_v3v3( ob->obmat[3], targetmat[3]);
2793                 
2794                 /* data->orglength==0 occurs on first run, and after 'R' button is clicked */
2795                 if (data->orglength == 0)  
2796                         data->orglength = dist;
2797                 if (data->bulge == 0) 
2798                         data->bulge = 1.0;
2799                 
2800                 scale[1] = dist/data->orglength;
2801                 switch (data->volmode) {
2802                 /* volume preserving scaling */
2803                 case VOLUME_XZ :
2804                         scale[0] = 1.0f - (float)sqrt(data->bulge) + (float)sqrt(data->bulge*(data->orglength/dist));
2805                         scale[2] = scale[0];
2806                         break;
2807                 case VOLUME_X:
2808                         scale[0] = 1.0f + data->bulge * (data->orglength /dist - 1);
2809                         scale[2] = 1.0;
2810                         break;
2811                 case VOLUME_Z:
2812                         scale[0] = 1.0;
2813                         scale[2] = 1.0f + data->bulge * (data->orglength /dist - 1);
2814                         break;
2815                         /* don't care for volume */
2816                 case NO_VOLUME:
2817                         scale[0] = 1.0;
2818                         scale[2] = 1.0;
2819                         break;
2820                 default: /* should not happen, but in case*/
2821                         return;    
2822                 } /* switch (data->volmode) */
2823
2824                 /* Clear the object's rotation and scale */
2825                 cob->matrix[0][0]=size[0]*scale[0];
2826                 cob->matrix[0][1]=0;
2827                 cob->matrix[0][2]=0;
2828                 cob->matrix[1][0]=0;
2829                 cob->matrix[1][1]=size[1]*scale[1];
2830                 cob->matrix[1][2]=0;
2831                 cob->matrix[2][0]=0;
2832                 cob->matrix[2][1]=0;
2833                 cob->matrix[2][2]=size[2]*scale[2];
2834                 
2835                 sub_v3_v3v3(vec, cob->matrix[3], ct->matrix[3]);
2836                 normalize_v3(vec);
2837                 
2838                 /* new Y aligns  object target connection*/
2839                 totmat[1][0] = -vec[0];
2840                 totmat[1][1] = -vec[1];
2841                 totmat[1][2] = -vec[2];
2842                 switch (data->plane) {
2843                 case PLANE_X:
2844                         /* build new Z vector */
2845                         /* othogonal to "new Y" "old X! plane */
2846                         cross_v3_v3v3(orth, vec, xx);
2847                         normalize_v3(orth);
2848                         
2849                         /* new Z*/
2850                         totmat[2][0] = orth[0];
2851                         totmat[2][1] = orth[1];
2852                         totmat[2][2] = orth[2];
2853                         
2854                         /* we decided to keep X plane*/
2855                         cross_v3_v3v3(xx, orth, vec);
2856                         normalize_v3(xx);
2857                         totmat[0][0] = xx[0];
2858                         totmat[0][1] = xx[1];
2859                         totmat[0][2] = xx[2];
2860                         break;
2861                 case PLANE_Z:
2862                         /* build new X vector */
2863                         /* othogonal to "new Y" "old Z! plane */
2864                         cross_v3_v3v3(orth, vec, zz);
2865                         normalize_v3(orth);
2866                         
2867                         /* new X */
2868                         totmat[0][0] = -orth[0];
2869                         totmat[0][1] = -orth[1];
2870                         totmat[0][2] = -orth[2];
2871                         
2872                         /* we decided to keep Z */
2873                         cross_v3_v3v3(zz, orth, vec);
2874                         normalize_v3(zz);
2875                         totmat[2][0] = zz[0];
2876                         totmat[2][1] = zz[1];
2877                         totmat[2][2] = zz[2];
2878                         break;
2879                 } /* switch (data->plane) */
2880                 
2881                 copy_m4_m4(tmat, cob->matrix);
2882                 mul_m4_m3m4(cob->matrix, totmat, tmat);
2883         }
2884 }
2885
2886 static bConstraintTypeInfo CTI_STRETCHTO = {
2887         CONSTRAINT_TYPE_STRETCHTO, /* type */
2888         sizeof(bStretchToConstraint), /* size */
2889         "Stretch To", /* name */
2890         "bStretchToConstraint", /* struct name */
2891         NULL, /* free data */
2892         NULL, /* relink data */
2893         stretchto_id_looper, /* id looper */
2894         NULL, /* copy data */
2895         stretchto_new_data, /* new data */
2896         stretchto_get_tars, /* get constraint targets */
2897         stretchto_flush_tars, /* flush constraint targets */
2898         default_get_tarmat, /* get target matrix */
2899         stretchto_evaluate /* evaluate */
2900 };
2901
2902 /* ---------- Floor ------------ */
2903
2904 static void minmax_new_data (void *cdata)
2905 {
2906         bMinMaxConstraint *data= (bMinMaxConstraint *)cdata;
2907         
2908         data->minmaxflag = TRACK_Z;
2909         data->offset = 0.0f;
2910         data->cache[0] = data->cache[1] = data->cache[2] = 0.0f;
2911         data->flag = 0;
2912 }
2913
2914 static void minmax_id_looper (bConstraint *con, ConstraintIDFunc func, void *userdata)
2915 {
2916         bMinMaxConstraint *data= con->data;
2917         
2918         /* target only */
2919         func(con, (ID**)&data->tar, userdata);
2920 }
2921
2922 static int minmax_get_tars (bConstraint *con, Lis