=bmesh= merge from trunk at r36529
[blender.git] / source / blender / blenkernel / intern / object.c
index c761e9852bd356c89b881bef012b69b9af5b4e78..eb796b073d8d94ba6ed2ba3eb36c888bee946962 100644 (file)
@@ -98,6 +98,7 @@
 #include "BKE_scene.h"
 #include "BKE_sequencer.h"
 #include "BKE_softbody.h"
+#include "BKE_material.h"
 
 #include "LBM_fluidsim.h"
 
@@ -209,8 +210,8 @@ void object_link_modifiers(struct Object *ob, struct Object *from)
                BLI_addtail(&ob->modifiers, nmd);
        }
 
-       copy_object_particlesystems(from, ob);
-       copy_object_softbody(from, ob);
+       copy_object_particlesystems(ob, from);
+       copy_object_softbody(ob, from);
 
        // TODO: smoke?, cloth?
 }
@@ -737,51 +738,45 @@ void make_local_camera(Camera *cam)
 {
        Main *bmain= G.main;
        Object *ob;
-       Camera *camn;
        int local=0, lib=0;
 
        /* - only lib users: do nothing
-               * - only local users: set flag
-               * - mixed: make copy
-               */
+        * - only local users: set flag
+        * - mixed: make copy
+        */
        
        if(cam->id.lib==NULL) return;
        if(cam->id.us==1) {
                cam->id.lib= NULL;
                cam->id.flag= LIB_LOCAL;
-               new_id(NULL, (ID *)cam, NULL);
+               new_id(&bmain->camera, (ID *)cam, NULL);
                return;
        }
        
-       ob= bmain->object.first;
-       while(ob) {
+       for(ob= bmain->object.first; ob && ELEM(0, lib, local); ob= ob->id.next) {
                if(ob->data==cam) {
                        if(ob->id.lib) lib= 1;
                        else local= 1;
                }
-               ob= ob->id.next;
        }
        
        if(local && lib==0) {
                cam->id.lib= NULL;
                cam->id.flag= LIB_LOCAL;
-               new_id(NULL, (ID *)cam, NULL);
+               new_id(&bmain->camera, (ID *)cam, NULL);
        }
        else if(local && lib) {
-               camn= copy_camera(cam);
+               Camera *camn= copy_camera(cam);
                camn->id.us= 0;
                
-               ob= bmain->object.first;
-               while(ob) {
-                       if(ob->data==cam) {
-                               
+               for(ob= bmain->object.first; ob; ob= ob->id.next) {
+                       if(ob->data == cam) {
                                if(ob->id.lib==NULL) {
                                        ob->data= camn;
                                        camn->id.us++;
                                        cam->id.us--;
                                }
                        }
-                       ob= ob->id.next;
                }
        }
 }
@@ -898,7 +893,7 @@ void make_local_lamp(Lamp *la)
        if(la->id.us==1) {
                la->id.lib= NULL;
                la->id.flag= LIB_LOCAL;
-               new_id(NULL, (ID *)la, NULL);
+               new_id(&bmain->lamp, (ID *)la, NULL);
                return;
        }
        
@@ -914,7 +909,7 @@ void make_local_lamp(Lamp *la)
        if(local && lib==0) {
                la->id.lib= NULL;
                la->id.flag= LIB_LOCAL;
-               new_id(NULL, (ID *)la, NULL);
+               new_id(&bmain->lamp, (ID *)la, NULL);
        }
        else if(local && lib) {
                lan= copy_lamp(la);
@@ -1367,11 +1362,10 @@ Object *copy_object(Object *ob)
        return obn;
 }
 
-void expand_local_object(Object *ob)
+static void extern_local_object(Object *ob)
 {
        //bActionStrip *strip;
        ParticleSystem *psys;
-       int a;
 
 #if 0 // XXX old animation system
        id_lib_extern((ID *)ob->action);
@@ -1379,10 +1373,11 @@ void expand_local_object(Object *ob)
 #endif // XXX old animation system
        id_lib_extern((ID *)ob->data);
        id_lib_extern((ID *)ob->dup_group);
-       
-       for(a=0; a<ob->totcol; a++) {
-               id_lib_extern((ID *)ob->mat[a]);
-       }
+       id_lib_extern((ID *)ob->poselib);
+       id_lib_extern((ID *)ob->gpd);
+
+       extern_local_matarar(ob->mat, ob->totcol);
+
 #if 0 // XXX old animation system
        for (strip=ob->nlastrips.first; strip; strip=strip->next) {
                id_lib_extern((ID *)strip->act);
@@ -1395,16 +1390,15 @@ void expand_local_object(Object *ob)
 void make_local_object(Object *ob)
 {
        Main *bmain= G.main;
-       Object *obn;
        Scene *sce;
        Base *base;
        int local=0, lib=0;
 
        /* - only lib users: do nothing
-               * - only local users: set flag
-               * - mixed: make copy
-               */
-       
+        * - only local users: set flag
+        * - mixed: make copy
+        */
+
        if(ob->id.lib==NULL) return;
        
        ob->proxy= ob->proxy_from= NULL;
@@ -1412,31 +1406,23 @@ void make_local_object(Object *ob)
        if(ob->id.us==1) {
                ob->id.lib= NULL;
                ob->id.flag= LIB_LOCAL;
-               new_id(NULL, (ID *)ob, NULL);
-
+               new_id(&bmain->object, (ID *)ob, NULL);
        }
        else {
-               sce= bmain->scene.first;
-               while(sce) {
-                       base= sce->base.first;
-                       while(base) {
-                               if(base->object==ob) {
-                                       if(sce->id.lib) lib++;
-                                       else local++;
-                                       break;
-                               }
-                               base= base->next;
+               for(sce= bmain->scene.first; sce && ELEM(0, lib, local); sce= sce->id.next) {
+                       if(object_in_scene(ob, sce)) {
+                               if(sce->id.lib) lib= 1;
+                               else local= 1;
                        }
-                       sce= sce->id.next;
                }
-               
+
                if(local && lib==0) {
                        ob->id.lib= NULL;
                        ob->id.flag= LIB_LOCAL;
-                       new_id(NULL, (ID *)ob, NULL);
+                       new_id(&bmain->object, (ID *)ob, NULL);
                }
                else if(local && lib) {
-                       obn= copy_object(ob);
+                       Object *obn= copy_object(ob);
                        obn->id.us= 0;
                        
                        sce= bmain->scene.first;
@@ -1457,7 +1443,7 @@ void make_local_object(Object *ob)
                }
        }
        
-       expand_local_object(ob);
+       extern_local_object(ob);
 }
 
 /*
@@ -1565,7 +1551,10 @@ void object_make_proxy(Object *ob, Object *target, Object *gob)
                ob->rotmode= target->rotmode;
                mul_m4_m4m4(ob->obmat, target->obmat, gob->obmat);
                if(gob->dup_group) { /* should always be true */
-                       sub_v3_v3(ob->obmat[3], gob->dup_group->dupli_ofs);
+                       float tvec[3];
+                       copy_v3_v3(tvec, gob->dup_group->dupli_ofs);
+                       mul_mat3_m4_v3(ob->obmat, tvec);
+                       sub_v3_v3(ob->obmat[3], tvec);
                }
                object_apply_mat4(ob, ob->obmat, FALSE, TRUE);
        }
@@ -1615,6 +1604,10 @@ void object_make_proxy(Object *ob, Object *target, Object *gob)
                
                armature_set_id_extern(ob);
        }
+       else if (target->type == OB_EMPTY) {
+               ob->empty_drawtype = target->empty_drawtype;
+               ob->empty_drawsize = target->empty_drawsize;
+       }
 
        /* copy IDProperties */
        if(ob->id.properties) {
@@ -2284,7 +2277,7 @@ void what_does_parent(Scene *scene, Object *ob, Object *workob)
        workob->constraints.first = ob->constraints.first;
        workob->constraints.last = ob->constraints.last;
 
-       strcpy(workob->parsubstr, ob->parsubstr); 
+       BLI_strncpy(workob->parsubstr, ob->parsubstr, sizeof(workob->parsubstr));
 
        where_is_object(scene, workob);
 }
@@ -2832,6 +2825,16 @@ int object_insert_ptcache(Object *ob)
        return i;
 }
 
+void object_camera_mode(RenderData *rd, Object *camera)
+{
+       rd->mode &= ~(R_ORTHO|R_PANORAMA);
+       if(camera && camera->type==OB_CAMERA) {
+               Camera *cam= camera->data;
+               if(cam->type == CAM_ORTHO) rd->mode |= R_ORTHO;
+               if(cam->flag & CAM_PANORAMA) rd->mode |= R_PANORAMA;
+       }
+}
+
 /* 'lens' may be set for envmap only */
 void object_camera_matrix(
                RenderData *rd, Object *camera, int winx, int winy, short field_second,
@@ -2841,8 +2844,7 @@ void object_camera_matrix(
        Camera *cam=NULL;
        float pixsize;
        float shiftx=0.0, shifty=0.0, winside, viewfac;
-
-       rd->mode &= ~(R_ORTHO|R_PANORAMA);
+       short is_ortho= FALSE;
 
        /* question mark */
        (*ycor)= rd->yasp / rd->xasp;
@@ -2852,8 +2854,9 @@ void object_camera_matrix(
        if(camera->type==OB_CAMERA) {
                cam= camera->data;
 
-               if(cam->type==CAM_ORTHO) rd->mode |= R_ORTHO;
-               if(cam->flag & CAM_PANORAMA) rd->mode |= R_PANORAMA;
+               if(cam->type == CAM_ORTHO) {
+                       is_ortho= TRUE;
+               }
 
                /* solve this too... all time depending stuff is in convertblender.c?
                 * Need to update the camera early because it's used for projection matrices
@@ -2893,7 +2896,7 @@ void object_camera_matrix(
        }
 
        /* ortho only with camera available */
-       if(cam && rd->mode & R_ORTHO) {
+       if(cam && is_ortho) {
                if(rd->xasp*winx >= rd->yasp*winy) {
                        viewfac= winx;
                }
@@ -2936,7 +2939,7 @@ void object_camera_matrix(
        (*viewdx)= pixsize;
        (*viewdy)= (*ycor) * pixsize;
 
-       if(rd->mode & R_ORTHO)
+       if(is_ortho)
                orthographic_m4(winmat, viewplane->xmin, viewplane->xmax, viewplane->ymin, viewplane->ymax, *clipsta, *clipend);
        else
                perspective_m4(winmat, viewplane->xmin, viewplane->xmax, viewplane->ymin, viewplane->ymax, *clipsta, *clipend);