90b25e8fd49460a2b24c80cccb2052859fa02836
[blender.git] / source / blender / blenkernel / intern / material.c
1 /*
2  * This program is free software; you can redistribute it and/or
3  * modify it under the terms of the GNU General Public License
4  * as published by the Free Software Foundation; either version 2
5  * of the License, or (at your option) any later version.
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * along with this program; if not, write to the Free Software Foundation,
14  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
15  *
16  * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
17  * All rights reserved.
18  */
19
20 /** \file
21  * \ingroup bke
22  */
23
24
25 #include <string.h>
26 #include <math.h>
27 #include <stddef.h>
28
29 #include "CLG_log.h"
30
31 #include "MEM_guardedalloc.h"
32
33 #include "DNA_anim_types.h"
34 #include "DNA_collection_types.h"
35 #include "DNA_curve_types.h"
36 #include "DNA_material_types.h"
37 #include "DNA_mesh_types.h"
38 #include "DNA_meshdata_types.h"
39 #include "DNA_customdata_types.h"
40 #include "DNA_gpencil_types.h"
41 #include "DNA_ID.h"
42 #include "DNA_meta_types.h"
43 #include "DNA_node_types.h"
44 #include "DNA_object_types.h"
45 #include "DNA_scene_types.h"
46
47 #include "BLI_math.h"
48 #include "BLI_listbase.h"
49 #include "BLI_utildefines.h"
50 #include "BLI_array_utils.h"
51
52 #include "BKE_animsys.h"
53 #include "BKE_brush.h"
54 #include "BKE_displist.h"
55 #include "BKE_gpencil.h"
56 #include "BKE_icons.h"
57 #include "BKE_image.h"
58 #include "BKE_library.h"
59 #include "BKE_main.h"
60 #include "BKE_material.h"
61 #include "BKE_mesh.h"
62 #include "BKE_scene.h"
63 #include "BKE_node.h"
64 #include "BKE_curve.h"
65 #include "BKE_editmesh.h"
66 #include "BKE_font.h"
67
68 #include "DEG_depsgraph.h"
69 #include "DEG_depsgraph_build.h"
70
71 #include "GPU_material.h"
72
73 /* used in UI and render */
74 Material defmaterial;
75
76 static CLG_LogRef LOG = {"bke.material"};
77
78 /* called on startup, creator.c */
79 void init_def_material(void)
80 {
81         BKE_material_init(&defmaterial);
82 }
83
84 /** Free (or release) any data used by this material (does not free the material itself). */
85 void BKE_material_free(Material *ma)
86 {
87         BKE_animdata_free((ID *)ma, false);
88
89         /* Free gpu material before the ntree */
90         GPU_material_free(&ma->gpumaterial);
91
92         /* is no lib link block, but material extension */
93         if (ma->nodetree) {
94                 ntreeFreeNestedTree(ma->nodetree);
95                 MEM_freeN(ma->nodetree);
96                 ma->nodetree = NULL;
97         }
98
99         MEM_SAFE_FREE(ma->texpaintslot);
100
101         MEM_SAFE_FREE(ma->gp_style);
102
103         BKE_icon_id_delete((ID *)ma);
104         BKE_previewimg_free(&ma->preview);
105 }
106
107 void BKE_material_init_gpencil_settings(Material *ma)
108 {
109         if ((ma) && (ma->gp_style == NULL)) {
110                 ma->gp_style = MEM_callocN(sizeof(MaterialGPencilStyle), "Grease Pencil Material Settings");
111
112                 MaterialGPencilStyle *gp_style = ma->gp_style;
113                 /* set basic settings */
114                 gp_style->stroke_rgba[3] = 1.0f;
115                 gp_style->fill_rgba[3] = 1.0f;
116                 gp_style->pattern_gridsize = 0.1f;
117                 gp_style->gradient_radius = 0.5f;
118                 ARRAY_SET_ITEMS(gp_style->mix_rgba, 1.0f, 1.0f, 1.0f, 0.2f);
119                 ARRAY_SET_ITEMS(gp_style->gradient_scale, 1.0f, 1.0f);
120                 ARRAY_SET_ITEMS(gp_style->texture_scale, 1.0f, 1.0f);
121                 gp_style->texture_opacity = 1.0f;
122                 gp_style->texture_pixsize = 100.0f;
123
124                 gp_style->flag |= GP_STYLE_STROKE_SHOW;
125         }
126 }
127
128 void BKE_material_init(Material *ma)
129 {
130         BLI_assert(MEMCMP_STRUCT_AFTER_IS_ZERO(ma, id));
131
132         ma->r = ma->g = ma->b = 0.8;
133         ma->specr = ma->specg = ma->specb = 1.0;
134         ma->a = 1.0f;
135         ma->spec = 0.5;
136
137         ma->roughness = 0.25f;
138
139         ma->pr_type = MA_SPHERE;
140
141         ma->preview = NULL;
142
143         ma->alpha_threshold = 0.5f;
144
145 }
146
147 Material *BKE_material_add(Main *bmain, const char *name)
148 {
149         Material *ma;
150
151         ma = BKE_libblock_alloc(bmain, ID_MA, name, 0);
152
153         BKE_material_init(ma);
154
155         return ma;
156 }
157
158 Material *BKE_material_add_gpencil(Main *bmain, const char *name)
159 {
160         Material *ma;
161
162         ma = BKE_material_add(bmain, name);
163
164         /* grease pencil settings */
165         if (ma != NULL) {
166                 BKE_material_init_gpencil_settings(ma);
167                 BKE_brush_update_material(bmain, ma, NULL);
168         }
169         return ma;
170 }
171
172
173 /**
174  * Only copy internal data of Material ID from source to already allocated/initialized destination.
175  * You probably never want to use that directly, use BKE_id_copy or BKE_id_copy_ex for typical needs.
176  *
177  * WARNING! This function will not handle ID user count!
178  *
179  * \param flag: Copying options (see BKE_library.h's LIB_ID_COPY_... flags for more).
180  */
181 void BKE_material_copy_data(Main *bmain, Material *ma_dst, const Material *ma_src, const int flag)
182 {
183         if (ma_src->nodetree) {
184                 /* Note: nodetree is *not* in bmain, however this specific case is handled at lower level
185                  *       (see BKE_libblock_copy_ex()). */
186                 BKE_id_copy_ex(bmain, (ID *)ma_src->nodetree, (ID **)&ma_dst->nodetree, flag);
187         }
188
189         if ((flag & LIB_ID_COPY_NO_PREVIEW) == 0) {
190                 BKE_previewimg_id_copy(&ma_dst->id, &ma_src->id);
191         }
192         else {
193                 ma_dst->preview = NULL;
194         }
195
196         if (ma_src->texpaintslot != NULL) {
197                 ma_dst->texpaintslot = MEM_dupallocN(ma_src->texpaintslot);
198         }
199
200         if (ma_src->gp_style != NULL) {
201                 ma_dst->gp_style = MEM_dupallocN(ma_src->gp_style);
202         }
203
204         BLI_listbase_clear(&ma_dst->gpumaterial);
205
206         /* TODO Duplicate Engine Settings and set runtime to NULL */
207 }
208
209 Material *BKE_material_copy(Main *bmain, const Material *ma)
210 {
211         Material *ma_copy;
212         BKE_id_copy(bmain, &ma->id, (ID **)&ma_copy);
213         return ma_copy;
214 }
215
216 /* XXX (see above) material copy without adding to main dbase */
217 Material *BKE_material_localize(Material *ma)
218 {
219         /* TODO(bastien): Replace with something like:
220          *
221          *   Material *ma_copy;
222          *   BKE_id_copy_ex(bmain, &ma->id, (ID **)&ma_copy,
223          *                  LIB_ID_COPY_NO_MAIN | LIB_ID_COPY_NO_PREVIEW | LIB_ID_COPY_NO_USER_REFCOUNT,
224          *                  false);
225          *   return ma_copy;
226          *
227          * NOTE: Only possible once nested node trees are fully converted to that too. */
228
229         Material *man = BKE_libblock_copy_for_localize(&ma->id);
230
231         man->texpaintslot = NULL;
232         man->preview = NULL;
233
234         if (ma->nodetree != NULL) {
235                 man->nodetree = ntreeLocalize(ma->nodetree);
236         }
237
238         if (ma->gp_style != NULL) {
239                 man->gp_style = MEM_dupallocN(ma->gp_style);
240         }
241
242         BLI_listbase_clear(&man->gpumaterial);
243
244         /* TODO Duplicate Engine Settings and set runtime to NULL */
245
246         man->id.tag |= LIB_TAG_LOCALIZED;
247
248         return man;
249 }
250
251 void BKE_material_make_local(Main *bmain, Material *ma, const bool lib_local)
252 {
253         BKE_id_make_local_generic(bmain, &ma->id, true, lib_local);
254 }
255
256 Material ***give_matarar(Object *ob)
257 {
258         Mesh *me;
259         Curve *cu;
260         MetaBall *mb;
261         bGPdata *gpd;
262
263         if (ob->type == OB_MESH) {
264                 me = ob->data;
265                 return &(me->mat);
266         }
267         else if (ELEM(ob->type, OB_CURVE, OB_FONT, OB_SURF)) {
268                 cu = ob->data;
269                 return &(cu->mat);
270         }
271         else if (ob->type == OB_MBALL) {
272                 mb = ob->data;
273                 return &(mb->mat);
274         }
275         else if (ob->type == OB_GPENCIL) {
276                 gpd = ob->data;
277                 return &(gpd->mat);
278         }
279         return NULL;
280 }
281
282 short *give_totcolp(Object *ob)
283 {
284         Mesh *me;
285         Curve *cu;
286         MetaBall *mb;
287         bGPdata *gpd;
288
289         if (ob->type == OB_MESH) {
290                 me = ob->data;
291                 return &(me->totcol);
292         }
293         else if (ELEM(ob->type, OB_CURVE, OB_FONT, OB_SURF)) {
294                 cu = ob->data;
295                 return &(cu->totcol);
296         }
297         else if (ob->type == OB_MBALL) {
298                 mb = ob->data;
299                 return &(mb->totcol);
300         }
301         else if (ob->type == OB_GPENCIL) {
302                 gpd = ob->data;
303                 return &(gpd->totcol);
304         }
305         return NULL;
306 }
307
308 /* same as above but for ID's */
309 Material ***give_matarar_id(ID *id)
310 {
311         /* ensure we don't try get materials from non-obdata */
312         BLI_assert(OB_DATA_SUPPORT_ID(GS(id->name)));
313
314         switch (GS(id->name)) {
315                 case ID_ME:
316                         return &(((Mesh *)id)->mat);
317                 case ID_CU:
318                         return &(((Curve *)id)->mat);
319                 case ID_MB:
320                         return &(((MetaBall *)id)->mat);
321                 case ID_GD:
322                         return &(((bGPdata *)id)->mat);
323                 default:
324                         break;
325         }
326         return NULL;
327 }
328
329 short *give_totcolp_id(ID *id)
330 {
331         /* ensure we don't try get materials from non-obdata */
332         BLI_assert(OB_DATA_SUPPORT_ID(GS(id->name)));
333
334         switch (GS(id->name)) {
335                 case ID_ME:
336                         return &(((Mesh *)id)->totcol);
337                 case ID_CU:
338                         return &(((Curve *)id)->totcol);
339                 case ID_MB:
340                         return &(((MetaBall *)id)->totcol);
341                 case ID_GD:
342                         return &(((bGPdata *)id)->totcol);
343                 default:
344                         break;
345         }
346         return NULL;
347 }
348
349 static void material_data_index_remove_id(ID *id, short index)
350 {
351         /* ensure we don't try get materials from non-obdata */
352         BLI_assert(OB_DATA_SUPPORT_ID(GS(id->name)));
353
354         switch (GS(id->name)) {
355                 case ID_ME:
356                         BKE_mesh_material_index_remove((Mesh *)id, index);
357                         break;
358                 case ID_CU:
359                         BKE_curve_material_index_remove((Curve *)id, index);
360                         break;
361                 case ID_MB:
362                         /* meta-elems don't have materials atm */
363                         break;
364                 case ID_GD:
365                         BKE_gpencil_material_index_remove((bGPdata *)id, index);
366                         break;
367                 default:
368                         break;
369         }
370 }
371
372 static void material_data_index_clear_id(ID *id)
373 {
374         /* ensure we don't try get materials from non-obdata */
375         BLI_assert(OB_DATA_SUPPORT_ID(GS(id->name)));
376
377         switch (GS(id->name)) {
378                 case ID_ME:
379                         BKE_mesh_material_index_clear((Mesh *)id);
380                         break;
381                 case ID_CU:
382                         BKE_curve_material_index_clear((Curve *)id);
383                         break;
384                 case ID_MB:
385                         /* meta-elems don't have materials atm */
386                         break;
387                 default:
388                         break;
389         }
390 }
391
392 void BKE_material_resize_id(Main *bmain, ID *id, short totcol, bool do_id_user)
393 {
394         Material ***matar = give_matarar_id(id);
395         short *totcolp = give_totcolp_id(id);
396
397         if (matar == NULL) {
398                 return;
399         }
400
401         if (do_id_user && totcol < (*totcolp)) {
402                 short i;
403                 for (i = totcol; i < (*totcolp); i++) {
404                         id_us_min((ID *)(*matar)[i]);
405                 }
406         }
407
408         if (totcol == 0) {
409                 if (*totcolp) {
410                         MEM_freeN(*matar);
411                         *matar = NULL;
412                 }
413         }
414         else {
415                 *matar = MEM_recallocN(*matar, sizeof(void *) * totcol);
416         }
417         *totcolp = totcol;
418
419         DEG_id_tag_update(id, ID_RECALC_COPY_ON_WRITE);
420         DEG_relations_tag_update(bmain);
421 }
422
423 void BKE_material_append_id(Main *bmain, ID *id, Material *ma)
424 {
425         Material ***matar;
426         if ((matar = give_matarar_id(id))) {
427                 short *totcol = give_totcolp_id(id);
428                 Material **mat = MEM_callocN(sizeof(void *) * ((*totcol) + 1), "newmatar");
429                 if (*totcol) memcpy(mat, *matar, sizeof(void *) * (*totcol));
430                 if (*matar) MEM_freeN(*matar);
431
432                 *matar = mat;
433                 (*matar)[(*totcol)++] = ma;
434
435                 id_us_plus((ID *)ma);
436                 test_all_objects_materials(bmain, id);
437
438                 DEG_id_tag_update(id, ID_RECALC_COPY_ON_WRITE);
439                 DEG_relations_tag_update(bmain);
440         }
441 }
442
443 Material *BKE_material_pop_id(Main *bmain, ID *id, int index_i, bool update_data)
444 {
445         short index = (short)index_i;
446         Material *ret = NULL;
447         Material ***matar;
448         if ((matar = give_matarar_id(id))) {
449                 short *totcol = give_totcolp_id(id);
450                 if (index >= 0 && index < (*totcol)) {
451                         ret = (*matar)[index];
452                         id_us_min((ID *)ret);
453
454                         if (*totcol <= 1) {
455                                 *totcol = 0;
456                                 MEM_freeN(*matar);
457                                 *matar = NULL;
458                         }
459                         else {
460                                 if (index + 1 != (*totcol))
461                                         memmove((*matar) + index, (*matar) + (index + 1), sizeof(void *) * ((*totcol) - (index + 1)));
462
463                                 (*totcol)--;
464                                 *matar = MEM_reallocN(*matar, sizeof(void *) * (*totcol));
465                                 test_all_objects_materials(bmain, id);
466                         }
467
468                         if (update_data) {
469                                 /* decrease mat_nr index */
470                                 material_data_index_remove_id(id, index);
471                         }
472
473                         DEG_id_tag_update(id, ID_RECALC_COPY_ON_WRITE);
474                         DEG_relations_tag_update(bmain);
475                 }
476         }
477
478         return ret;
479 }
480
481 void BKE_material_clear_id(Main *bmain, ID *id, bool update_data)
482 {
483         Material ***matar;
484         if ((matar = give_matarar_id(id))) {
485                 short *totcol = give_totcolp_id(id);
486
487                 while ((*totcol)--) {
488                         id_us_min((ID *)((*matar)[*totcol]));
489                 }
490                 *totcol = 0;
491                 if (*matar) {
492                         MEM_freeN(*matar);
493                         *matar = NULL;
494                 }
495
496                 if (update_data) {
497                         /* decrease mat_nr index */
498                         material_data_index_clear_id(id);
499                 }
500
501                 DEG_id_tag_update(id, ID_RECALC_COPY_ON_WRITE);
502                 DEG_relations_tag_update(bmain);
503         }
504 }
505
506 Material **give_current_material_p(Object *ob, short act)
507 {
508         Material ***matarar, **ma_p;
509         const short *totcolp;
510
511         if (ob == NULL) return NULL;
512
513         /* if object cannot have material, (totcolp == NULL) */
514         totcolp = give_totcolp(ob);
515         if (totcolp == NULL || ob->totcol == 0) return NULL;
516
517         /* return NULL for invalid 'act', can happen for mesh face indices */
518         if (act > ob->totcol)
519                 return NULL;
520         else if (act <= 0) {
521                 if (act < 0) {
522                         CLOG_ERROR(&LOG, "Negative material index!");
523                 }
524                 return NULL;
525         }
526
527         if (ob->matbits && ob->matbits[act - 1]) {    /* in object */
528                 ma_p = &ob->mat[act - 1];
529         }
530         else {                              /* in data */
531
532                 /* check for inconsistency */
533                 if (*totcolp < ob->totcol)
534                         ob->totcol = *totcolp;
535                 if (act > ob->totcol) act = ob->totcol;
536
537                 matarar = give_matarar(ob);
538
539                 if (matarar && *matarar) {
540                         ma_p = &(*matarar)[act - 1];
541                 }
542                 else {
543                         ma_p = NULL;
544                 }
545         }
546
547         return ma_p;
548 }
549
550 Material *give_current_material(Object *ob, short act)
551 {
552         Material **ma_p = give_current_material_p(ob, act);
553         return ma_p ? *ma_p : NULL;
554 }
555
556 MaterialGPencilStyle *BKE_material_gpencil_settings_get(Object *ob, short act)
557 {
558         Material *ma = give_current_material(ob, act);
559         if (ma != NULL) {
560                 if (ma->gp_style == NULL) {
561                         BKE_material_init_gpencil_settings(ma);
562                 }
563
564                 return ma->gp_style;
565         }
566         else {
567                 return NULL;
568         }
569 }
570
571 Material *give_node_material(Material *ma)
572 {
573         if (ma && ma->use_nodes && ma->nodetree) {
574                 bNode *node = nodeGetActiveID(ma->nodetree, ID_MA);
575
576                 if (node)
577                         return (Material *)node->id;
578         }
579
580         return NULL;
581 }
582
583 void BKE_material_resize_object(Main *bmain, Object *ob, const short totcol, bool do_id_user)
584 {
585         Material **newmatar;
586         char *newmatbits;
587
588         if (do_id_user && totcol < ob->totcol) {
589                 short i;
590                 for (i = totcol; i < ob->totcol; i++) {
591                         id_us_min((ID *)ob->mat[i]);
592                 }
593         }
594
595         if (totcol == 0) {
596                 if (ob->totcol) {
597                         MEM_freeN(ob->mat);
598                         MEM_freeN(ob->matbits);
599                         ob->mat = NULL;
600                         ob->matbits = NULL;
601                 }
602         }
603         else if (ob->totcol < totcol) {
604                 newmatar = MEM_callocN(sizeof(void *) * totcol, "newmatar");
605                 newmatbits = MEM_callocN(sizeof(char) * totcol, "newmatbits");
606                 if (ob->totcol) {
607                         memcpy(newmatar, ob->mat, sizeof(void *) * ob->totcol);
608                         memcpy(newmatbits, ob->matbits, sizeof(char) * ob->totcol);
609                         MEM_freeN(ob->mat);
610                         MEM_freeN(ob->matbits);
611                 }
612                 ob->mat = newmatar;
613                 ob->matbits = newmatbits;
614         }
615         /* XXX, why not realloc on shrink? - campbell */
616
617         ob->totcol = totcol;
618         if (ob->totcol && ob->actcol == 0) ob->actcol = 1;
619         if (ob->actcol > ob->totcol) ob->actcol = ob->totcol;
620
621         DEG_id_tag_update(&ob->id, ID_RECALC_COPY_ON_WRITE | ID_RECALC_GEOMETRY);
622         DEG_relations_tag_update(bmain);
623 }
624
625 void test_object_materials(Main *bmain, Object *ob, ID *id)
626 {
627         /* make the ob mat-array same size as 'ob->data' mat-array */
628         const short *totcol;
629
630         if (id == NULL || (totcol = give_totcolp_id(id)) == NULL) {
631                 return;
632         }
633
634         BKE_material_resize_object(bmain, ob, *totcol, false);
635 }
636
637 void test_all_objects_materials(Main *bmain, ID *id)
638 {
639         /* make the ob mat-array same size as 'ob->data' mat-array */
640         Object *ob;
641         const short *totcol;
642
643         if (id == NULL || (totcol = give_totcolp_id(id)) == NULL) {
644                 return;
645         }
646
647         BKE_main_lock(bmain);
648         for (ob = bmain->objects.first; ob; ob = ob->id.next) {
649                 if (ob->data == id) {
650                         BKE_material_resize_object(bmain, ob, *totcol, false);
651                 }
652         }
653         BKE_main_unlock(bmain);
654 }
655
656 void assign_material_id(Main *bmain, ID *id, Material *ma, short act)
657 {
658         Material *mao, **matar, ***matarar;
659         short *totcolp;
660
661         if (act > MAXMAT) return;
662         if (act < 1) act = 1;
663
664         /* test arraylens */
665
666         totcolp = give_totcolp_id(id);
667         matarar = give_matarar_id(id);
668
669         if (totcolp == NULL || matarar == NULL) return;
670
671         if (act > *totcolp) {
672                 matar = MEM_callocN(sizeof(void *) * act, "matarray1");
673
674                 if (*totcolp) {
675                         memcpy(matar, *matarar, sizeof(void *) * (*totcolp));
676                         MEM_freeN(*matarar);
677                 }
678
679                 *matarar = matar;
680                 *totcolp = act;
681         }
682
683         /* in data */
684         mao = (*matarar)[act - 1];
685         if (mao)
686                 id_us_min(&mao->id);
687         (*matarar)[act - 1] = ma;
688
689         if (ma)
690                 id_us_plus(&ma->id);
691
692         test_all_objects_materials(bmain, id);
693 }
694
695 void assign_material(Main *bmain, Object *ob, Material *ma, short act, int assign_type)
696 {
697         Material *mao, **matar, ***matarar;
698         short *totcolp;
699         char bit = 0;
700
701         if (act > MAXMAT) return;
702         if (act < 1) act = 1;
703
704         /* prevent crashing when using accidentally */
705         BLI_assert(!ID_IS_LINKED(ob));
706         if (ID_IS_LINKED(ob)) return;
707
708         /* test arraylens */
709
710         totcolp = give_totcolp(ob);
711         matarar = give_matarar(ob);
712
713         if (totcolp == NULL || matarar == NULL) return;
714
715         if (act > *totcolp) {
716                 matar = MEM_callocN(sizeof(void *) * act, "matarray1");
717
718                 if (*totcolp) {
719                         memcpy(matar, *matarar, sizeof(void *) * (*totcolp));
720                         MEM_freeN(*matarar);
721                 }
722
723                 *matarar = matar;
724                 *totcolp = act;
725         }
726
727         if (act > ob->totcol) {
728                 /* Need more space in the material arrays */
729                 ob->mat = MEM_recallocN_id(ob->mat, sizeof(void *) * act, "matarray2");
730                 ob->matbits = MEM_recallocN_id(ob->matbits, sizeof(char) * act, "matbits1");
731                 ob->totcol = act;
732         }
733
734         /* Determine the object/mesh linking */
735         if (assign_type == BKE_MAT_ASSIGN_EXISTING) {
736                 /* keep existing option (avoid confusion in scripts),
737                  * intentionally ignore userpref (default to obdata). */
738                 bit = ob->matbits[act - 1];
739         }
740         else if (assign_type == BKE_MAT_ASSIGN_USERPREF && ob->totcol && ob->actcol) {
741                 /* copy from previous material */
742                 bit = ob->matbits[ob->actcol - 1];
743         }
744         else {
745                 switch (assign_type) {
746                         case BKE_MAT_ASSIGN_OBDATA:
747                                 bit = 0;
748                                 break;
749                         case BKE_MAT_ASSIGN_OBJECT:
750                                 bit = 1;
751                                 break;
752                         case BKE_MAT_ASSIGN_USERPREF:
753                         default:
754                                 bit = (U.flag & USER_MAT_ON_OB) ? 1 : 0;
755                                 break;
756                 }
757         }
758
759         /* do it */
760
761         ob->matbits[act - 1] = bit;
762         if (bit == 1) {   /* in object */
763                 mao = ob->mat[act - 1];
764                 if (mao)
765                         id_us_min(&mao->id);
766                 ob->mat[act - 1] = ma;
767                 test_object_materials(bmain, ob, ob->data);
768         }
769         else {  /* in data */
770                 mao = (*matarar)[act - 1];
771                 if (mao)
772                         id_us_min(&mao->id);
773                 (*matarar)[act - 1] = ma;
774                 test_all_objects_materials(bmain, ob->data);  /* Data may be used by several objects... */
775         }
776
777         if (ma)
778                 id_us_plus(&ma->id);
779 }
780
781
782 void BKE_material_remap_object(Object *ob, const unsigned int *remap)
783 {
784         Material ***matar = give_matarar(ob);
785         const short *totcol_p = give_totcolp(ob);
786
787         BLI_array_permute(ob->mat, ob->totcol, remap);
788
789         if (ob->matbits) {
790                 BLI_array_permute(ob->matbits, ob->totcol, remap);
791         }
792
793         if (matar) {
794                 BLI_array_permute(*matar, *totcol_p, remap);
795         }
796
797         if (ob->type == OB_MESH) {
798                 BKE_mesh_material_remap(ob->data, remap, ob->totcol);
799         }
800         else if (ELEM(ob->type, OB_CURVE, OB_SURF, OB_FONT)) {
801                 BKE_curve_material_remap(ob->data, remap, ob->totcol);
802         }
803         else if (ob->type == OB_GPENCIL) {
804                 BKE_gpencil_material_remap(ob->data, remap, ob->totcol);
805         }
806         else {
807                 /* add support for this object data! */
808                 BLI_assert(matar == NULL);
809         }
810 }
811
812 /**
813  * Calculate a material remapping from \a ob_src to \a ob_dst.
814  *
815  * \param remap_src_to_dst: An array the size of `ob_src->totcol`
816  * where index values are filled in which map to \a ob_dst materials.
817  */
818 void BKE_material_remap_object_calc(
819         Object *ob_dst, Object *ob_src,
820         short *remap_src_to_dst)
821 {
822         if (ob_src->totcol == 0) {
823                 return;
824         }
825
826         GHash *gh_mat_map = BLI_ghash_ptr_new_ex(__func__, ob_src->totcol);
827
828         for (int i = 0; i < ob_dst->totcol; i++) {
829                 Material *ma_src = give_current_material(ob_dst, i + 1);
830                 BLI_ghash_reinsert(gh_mat_map, ma_src, POINTER_FROM_INT(i), NULL, NULL);
831         }
832
833         /* setup default mapping (when materials don't match) */
834         {
835                 int i = 0;
836                 if (ob_dst->totcol >= ob_src->totcol) {
837                         for (; i < ob_src->totcol; i++) {
838                                 remap_src_to_dst[i] = i;
839                         }
840                 }
841                 else {
842                         for (; i < ob_dst->totcol; i++) {
843                                 remap_src_to_dst[i] = i;
844                         }
845                         for (; i < ob_src->totcol; i++) {
846                                 remap_src_to_dst[i] = 0;
847                         }
848                 }
849         }
850
851         for (int i = 0; i < ob_src->totcol; i++) {
852                 Material *ma_src = give_current_material(ob_src, i + 1);
853
854                 if ((i < ob_dst->totcol) && (ma_src == give_current_material(ob_dst, i + 1))) {
855                         /* when objects have exact matching materials - keep existing index */
856                 }
857                 else {
858                         void **index_src_p = BLI_ghash_lookup_p(gh_mat_map, ma_src);
859                         if (index_src_p) {
860                                 remap_src_to_dst[i] = POINTER_AS_INT(*index_src_p);
861                         }
862                 }
863         }
864
865         BLI_ghash_free(gh_mat_map, NULL, NULL);
866 }
867
868
869 /* XXX - this calls many more update calls per object then are needed, could be optimized */
870 void assign_matarar(Main *bmain, struct Object *ob, struct Material ***matar, short totcol)
871 {
872         int actcol_orig = ob->actcol;
873         short i;
874
875         while ((ob->totcol > totcol) &&
876                BKE_object_material_slot_remove(bmain, ob))
877         {
878                 /* pass */
879         }
880
881         /* now we have the right number of slots */
882         for (i = 0; i < totcol; i++)
883                 assign_material(bmain, ob, (*matar)[i], i + 1, BKE_MAT_ASSIGN_USERPREF);
884
885         if (actcol_orig > ob->totcol)
886                 actcol_orig = ob->totcol;
887
888         ob->actcol = actcol_orig;
889 }
890
891
892 short BKE_object_material_slot_find_index(Object *ob, Material *ma)
893 {
894         Material ***matarar;
895         short a, *totcolp;
896
897         if (ma == NULL) return 0;
898
899         totcolp = give_totcolp(ob);
900         matarar = give_matarar(ob);
901
902         if (totcolp == NULL || matarar == NULL) return 0;
903
904         for (a = 0; a < *totcolp; a++)
905                 if ((*matarar)[a] == ma)
906                         break;
907         if (a < *totcolp)
908                 return a + 1;
909         return 0;
910 }
911
912 bool BKE_object_material_slot_add(Main *bmain, Object *ob)
913 {
914         if (ob == NULL) return false;
915         if (ob->totcol >= MAXMAT) return false;
916
917         assign_material(bmain, ob, NULL, ob->totcol + 1, BKE_MAT_ASSIGN_USERPREF);
918         ob->actcol = ob->totcol;
919         return true;
920 }
921
922 /* ****************** */
923
924 bool BKE_object_material_slot_remove(Main *bmain, Object *ob)
925 {
926         Material *mao, ***matarar;
927         short *totcolp;
928         short a, actcol;
929
930         if (ob == NULL || ob->totcol == 0) {
931                 return false;
932         }
933
934         /* this should never happen and used to crash */
935         if (ob->actcol <= 0) {
936                 CLOG_ERROR(&LOG, "invalid material index %d, report a bug!", ob->actcol);
937                 BLI_assert(0);
938                 return false;
939         }
940
941         /* take a mesh/curve/mball as starting point, remove 1 index,
942          * AND with all objects that share the ob->data
943          *
944          * after that check indices in mesh/curve/mball!!!
945          */
946
947         totcolp = give_totcolp(ob);
948         matarar = give_matarar(ob);
949
950         if (ELEM(NULL, matarar, *matarar)) {
951                 return false;
952         }
953
954         /* can happen on face selection in editmode */
955         if (ob->actcol > ob->totcol) {
956                 ob->actcol = ob->totcol;
957         }
958
959         /* we delete the actcol */
960         mao = (*matarar)[ob->actcol - 1];
961         if (mao)
962                 id_us_min(&mao->id);
963
964         for (a = ob->actcol; a < ob->totcol; a++)
965                 (*matarar)[a - 1] = (*matarar)[a];
966         (*totcolp)--;
967
968         if (*totcolp == 0) {
969                 MEM_freeN(*matarar);
970                 *matarar = NULL;
971         }
972
973         actcol = ob->actcol;
974
975         for (Object *obt = bmain->objects.first; obt; obt = obt->id.next) {
976                 if (obt->data == ob->data) {
977                         /* Can happen when object material lists are used, see: T52953 */
978                         if (actcol > obt->totcol) {
979                                 continue;
980                         }
981                         /* WATCH IT: do not use actcol from ob or from obt (can become zero) */
982                         mao = obt->mat[actcol - 1];
983                         if (mao)
984                                 id_us_min(&mao->id);
985
986                         for (a = actcol; a < obt->totcol; a++) {
987                                 obt->mat[a - 1] = obt->mat[a];
988                                 obt->matbits[a - 1] = obt->matbits[a];
989                         }
990                         obt->totcol--;
991                         if (obt->actcol > obt->totcol) obt->actcol = obt->totcol;
992
993                         if (obt->totcol == 0) {
994                                 MEM_freeN(obt->mat);
995                                 MEM_freeN(obt->matbits);
996                                 obt->mat = NULL;
997                                 obt->matbits = NULL;
998                         }
999                 }
1000         }
1001
1002         /* check indices from mesh */
1003         if (ELEM(ob->type, OB_MESH, OB_CURVE, OB_SURF, OB_FONT, OB_GPENCIL)) {
1004                 material_data_index_remove_id((ID *)ob->data, actcol - 1);
1005                 if (ob->runtime.curve_cache) {
1006                         BKE_displist_free(&ob->runtime.curve_cache->disp);
1007                 }
1008         }
1009
1010         return true;
1011 }
1012
1013 static bNode *nodetree_uv_node_recursive(bNode *node)
1014 {
1015         bNode *inode;
1016         bNodeSocket *sock;
1017
1018         for (sock = node->inputs.first; sock; sock = sock->next) {
1019                 if (sock->link) {
1020                         inode = sock->link->fromnode;
1021                         if (inode->typeinfo->nclass == NODE_CLASS_INPUT && inode->typeinfo->type == SH_NODE_UVMAP) {
1022                                 return inode;
1023                         }
1024                         else {
1025                                 return nodetree_uv_node_recursive(inode);
1026                         }
1027                 }
1028         }
1029
1030         return NULL;
1031 }
1032
1033 static int count_texture_nodes_recursive(bNodeTree *nodetree)
1034 {
1035         int tex_nodes = 0;
1036
1037         for (bNode *node = nodetree->nodes.first; node; node = node->next) {
1038                 if (node->typeinfo->nclass == NODE_CLASS_TEXTURE && node->typeinfo->type == SH_NODE_TEX_IMAGE && node->id) {
1039                         tex_nodes++;
1040                 }
1041                 else if (node->type == NODE_GROUP && node->id) {
1042                         /* recurse into the node group and see if it contains any textures */
1043                         tex_nodes += count_texture_nodes_recursive((bNodeTree *)node->id);
1044                 }
1045         }
1046
1047         return tex_nodes;
1048 }
1049
1050 static void fill_texpaint_slots_recursive(bNodeTree *nodetree, bNode *active_node, Material *ma, int *index)
1051 {
1052         for (bNode *node = nodetree->nodes.first; node; node = node->next) {
1053                 if (node->typeinfo->nclass == NODE_CLASS_TEXTURE && node->typeinfo->type == SH_NODE_TEX_IMAGE && node->id) {
1054                         if (active_node == node) {
1055                                 ma->paint_active_slot = *index;
1056                         }
1057
1058                         ma->texpaintslot[*index].ima = (Image *)node->id;
1059                         ma->texpaintslot[*index].interp = ((NodeTexImage *)node->storage)->interpolation;
1060
1061                         /* for new renderer, we need to traverse the treeback in search of a UV node */
1062                         bNode *uvnode = nodetree_uv_node_recursive(node);
1063
1064                         if (uvnode) {
1065                                 NodeShaderUVMap *storage = (NodeShaderUVMap *)uvnode->storage;
1066                                 ma->texpaintslot[*index].uvname = storage->uv_map;
1067                                 /* set a value to index so UI knows that we have a valid pointer for the mesh */
1068                                 ma->texpaintslot[*index].valid = true;
1069                         }
1070                         else {
1071                                 /* just invalidate the index here so UV map does not get displayed on the UI */
1072                                 ma->texpaintslot[*index].valid = false;
1073                         }
1074                         (*index)++;
1075                 }
1076                 else if (node->type == NODE_GROUP && node->id) {
1077                         /* recurse into the node group and see if it contains any textures */
1078                         fill_texpaint_slots_recursive((bNodeTree *)node->id, active_node, ma, index);
1079                 }
1080         }
1081 }
1082
1083 void BKE_texpaint_slot_refresh_cache(Scene *scene, Material *ma)
1084 {
1085         int count = 0;
1086         int index = 0;
1087
1088         if (!ma)
1089                 return;
1090
1091         /* COW needed when adding texture slot on an object with no materials. */
1092         DEG_id_tag_update(&ma->id, ID_RECALC_SHADING | ID_RECALC_COPY_ON_WRITE);
1093
1094         if (ma->texpaintslot) {
1095                 MEM_freeN(ma->texpaintslot);
1096                 ma->tot_slots = 0;
1097                 ma->texpaintslot = NULL;
1098         }
1099
1100         if (scene->toolsettings->imapaint.mode == IMAGEPAINT_MODE_IMAGE) {
1101                 ma->paint_active_slot = 0;
1102                 ma->paint_clone_slot = 0;
1103                 return;
1104         }
1105
1106         if (!(ma->nodetree)) {
1107                 ma->paint_active_slot = 0;
1108                 ma->paint_clone_slot = 0;
1109                 return;
1110         }
1111
1112         count = count_texture_nodes_recursive(ma->nodetree);
1113
1114         if (count == 0) {
1115                 ma->paint_active_slot = 0;
1116                 ma->paint_clone_slot = 0;
1117                 return;
1118         }
1119
1120         ma->texpaintslot = MEM_callocN(sizeof(*ma->texpaintslot) * count, "texpaint_slots");
1121
1122         bNode *active_node = nodeGetActiveTexture(ma->nodetree);
1123
1124         fill_texpaint_slots_recursive(ma->nodetree, active_node, ma, &index);
1125
1126         ma->tot_slots = count;
1127
1128
1129         if (ma->paint_active_slot >= count) {
1130                 ma->paint_active_slot = count - 1;
1131         }
1132
1133         if (ma->paint_clone_slot >= count) {
1134                 ma->paint_clone_slot = count - 1;
1135         }
1136
1137         return;
1138 }
1139
1140 void BKE_texpaint_slots_refresh_object(Scene *scene, struct Object *ob)
1141 {
1142         int i;
1143
1144         for (i = 1; i < ob->totcol + 1; i++) {
1145                 Material *ma = give_current_material(ob, i);
1146                 BKE_texpaint_slot_refresh_cache(scene, ma);
1147         }
1148 }
1149
1150
1151 /* r_col = current value, col = new value, (fac == 0) is no change */
1152 void ramp_blend(int type, float r_col[3], const float fac, const float col[3])
1153 {
1154         float tmp, facm = 1.0f - fac;
1155
1156         switch (type) {
1157                 case MA_RAMP_BLEND:
1158                         r_col[0] = facm * (r_col[0]) + fac * col[0];
1159                         r_col[1] = facm * (r_col[1]) + fac * col[1];
1160                         r_col[2] = facm * (r_col[2]) + fac * col[2];
1161                         break;
1162                 case MA_RAMP_ADD:
1163                         r_col[0] += fac * col[0];
1164                         r_col[1] += fac * col[1];
1165                         r_col[2] += fac * col[2];
1166                         break;
1167                 case MA_RAMP_MULT:
1168                         r_col[0] *= (facm + fac * col[0]);
1169                         r_col[1] *= (facm + fac * col[1]);
1170                         r_col[2] *= (facm + fac * col[2]);
1171                         break;
1172                 case MA_RAMP_SCREEN:
1173                         r_col[0] = 1.0f - (facm + fac * (1.0f - col[0])) * (1.0f - r_col[0]);
1174                         r_col[1] = 1.0f - (facm + fac * (1.0f - col[1])) * (1.0f - r_col[1]);
1175                         r_col[2] = 1.0f - (facm + fac * (1.0f - col[2])) * (1.0f - r_col[2]);
1176                         break;
1177                 case MA_RAMP_OVERLAY:
1178                         if (r_col[0] < 0.5f)
1179                                 r_col[0] *= (facm + 2.0f * fac * col[0]);
1180                         else
1181                                 r_col[0] = 1.0f - (facm + 2.0f * fac * (1.0f - col[0])) * (1.0f - r_col[0]);
1182                         if (r_col[1] < 0.5f)
1183                                 r_col[1] *= (facm + 2.0f * fac * col[1]);
1184                         else
1185                                 r_col[1] = 1.0f - (facm + 2.0f * fac * (1.0f - col[1])) * (1.0f - r_col[1]);
1186                         if (r_col[2] < 0.5f)
1187                                 r_col[2] *= (facm + 2.0f * fac * col[2]);
1188                         else
1189                                 r_col[2] = 1.0f - (facm + 2.0f * fac * (1.0f - col[2])) * (1.0f - r_col[2]);
1190                         break;
1191                 case MA_RAMP_SUB:
1192                         r_col[0] -= fac * col[0];
1193                         r_col[1] -= fac * col[1];
1194                         r_col[2] -= fac * col[2];
1195                         break;
1196                 case MA_RAMP_DIV:
1197                         if (col[0] != 0.0f)
1198                                 r_col[0] = facm * (r_col[0]) + fac * (r_col[0]) / col[0];
1199                         if (col[1] != 0.0f)
1200                                 r_col[1] = facm * (r_col[1]) + fac * (r_col[1]) / col[1];
1201                         if (col[2] != 0.0f)
1202                                 r_col[2] = facm * (r_col[2]) + fac * (r_col[2]) / col[2];
1203                         break;
1204                 case MA_RAMP_DIFF:
1205                         r_col[0] = facm * (r_col[0]) + fac * fabsf(r_col[0] - col[0]);
1206                         r_col[1] = facm * (r_col[1]) + fac * fabsf(r_col[1] - col[1]);
1207                         r_col[2] = facm * (r_col[2]) + fac * fabsf(r_col[2] - col[2]);
1208                         break;
1209                 case MA_RAMP_DARK:
1210                         r_col[0] = min_ff(r_col[0], col[0]) * fac + r_col[0] * facm;
1211                         r_col[1] = min_ff(r_col[1], col[1]) * fac + r_col[1] * facm;
1212                         r_col[2] = min_ff(r_col[2], col[2]) * fac + r_col[2] * facm;
1213                         break;
1214                 case MA_RAMP_LIGHT:
1215                         tmp = fac * col[0];
1216                         if (tmp > r_col[0]) r_col[0] = tmp;
1217                         tmp = fac * col[1];
1218                         if (tmp > r_col[1]) r_col[1] = tmp;
1219                         tmp = fac * col[2];
1220                         if (tmp > r_col[2]) r_col[2] = tmp;
1221                         break;
1222                 case MA_RAMP_DODGE:
1223                         if (r_col[0] != 0.0f) {
1224                                 tmp = 1.0f - fac * col[0];
1225                                 if (tmp <= 0.0f)
1226                                         r_col[0] = 1.0f;
1227                                 else if ((tmp = (r_col[0]) / tmp) > 1.0f)
1228                                         r_col[0] = 1.0f;
1229                                 else
1230                                         r_col[0] = tmp;
1231                         }
1232                         if (r_col[1] != 0.0f) {
1233                                 tmp = 1.0f - fac * col[1];
1234                                 if (tmp <= 0.0f)
1235                                         r_col[1] = 1.0f;
1236                                 else if ((tmp = (r_col[1]) / tmp) > 1.0f)
1237                                         r_col[1] = 1.0f;
1238                                 else
1239                                         r_col[1] = tmp;
1240                         }
1241                         if (r_col[2] != 0.0f) {
1242                                 tmp = 1.0f - fac * col[2];
1243                                 if (tmp <= 0.0f)
1244                                         r_col[2] = 1.0f;
1245                                 else if ((tmp = (r_col[2]) / tmp) > 1.0f)
1246                                         r_col[2] = 1.0f;
1247                                 else
1248                                         r_col[2] = tmp;
1249                         }
1250                         break;
1251                 case MA_RAMP_BURN:
1252                         tmp = facm + fac * col[0];
1253
1254                         if (tmp <= 0.0f)
1255                                 r_col[0] = 0.0f;
1256                         else if ((tmp = (1.0f - (1.0f - (r_col[0])) / tmp)) < 0.0f)
1257                                 r_col[0] = 0.0f;
1258                         else if (tmp > 1.0f)
1259                                 r_col[0] = 1.0f;
1260                         else
1261                                 r_col[0] = tmp;
1262
1263                         tmp = facm + fac * col[1];
1264                         if (tmp <= 0.0f)
1265                                 r_col[1] = 0.0f;
1266                         else if ((tmp = (1.0f - (1.0f - (r_col[1])) / tmp)) < 0.0f)
1267                                 r_col[1] = 0.0f;
1268                         else if (tmp > 1.0f)
1269                                 r_col[1] = 1.0f;
1270                         else
1271                                 r_col[1] = tmp;
1272
1273                         tmp = facm + fac * col[2];
1274                         if (tmp <= 0.0f)
1275                                 r_col[2] = 0.0f;
1276                         else if ((tmp = (1.0f - (1.0f - (r_col[2])) / tmp)) < 0.0f)
1277                                 r_col[2] = 0.0f;
1278                         else if (tmp > 1.0f)
1279                                 r_col[2] = 1.0f;
1280                         else
1281                                 r_col[2] = tmp;
1282                         break;
1283                 case MA_RAMP_HUE:
1284                 {
1285                         float rH, rS, rV;
1286                         float colH, colS, colV;
1287                         float tmpr, tmpg, tmpb;
1288                         rgb_to_hsv(col[0], col[1], col[2], &colH, &colS, &colV);
1289                         if (colS != 0) {
1290                                 rgb_to_hsv(r_col[0], r_col[1], r_col[2], &rH, &rS, &rV);
1291                                 hsv_to_rgb(colH, rS, rV, &tmpr, &tmpg, &tmpb);
1292                                 r_col[0] = facm * (r_col[0]) + fac * tmpr;
1293                                 r_col[1] = facm * (r_col[1]) + fac * tmpg;
1294                                 r_col[2] = facm * (r_col[2]) + fac * tmpb;
1295                         }
1296                         break;
1297                 }
1298                 case MA_RAMP_SAT:
1299                 {
1300                         float rH, rS, rV;
1301                         float colH, colS, colV;
1302                         rgb_to_hsv(r_col[0], r_col[1], r_col[2], &rH, &rS, &rV);
1303                         if (rS != 0) {
1304                                 rgb_to_hsv(col[0], col[1], col[2], &colH, &colS, &colV);
1305                                 hsv_to_rgb(rH, (facm * rS + fac * colS), rV, r_col + 0, r_col + 1, r_col + 2);
1306                         }
1307                         break;
1308                 }
1309                 case MA_RAMP_VAL:
1310                 {
1311                         float rH, rS, rV;
1312                         float colH, colS, colV;
1313                         rgb_to_hsv(r_col[0], r_col[1], r_col[2], &rH, &rS, &rV);
1314                         rgb_to_hsv(col[0], col[1], col[2], &colH, &colS, &colV);
1315                         hsv_to_rgb(rH, rS, (facm * rV + fac * colV), r_col + 0, r_col + 1, r_col + 2);
1316                         break;
1317                 }
1318                 case MA_RAMP_COLOR:
1319                 {
1320                         float rH, rS, rV;
1321                         float colH, colS, colV;
1322                         float tmpr, tmpg, tmpb;
1323                         rgb_to_hsv(col[0], col[1], col[2], &colH, &colS, &colV);
1324                         if (colS != 0) {
1325                                 rgb_to_hsv(r_col[0], r_col[1], r_col[2], &rH, &rS, &rV);
1326                                 hsv_to_rgb(colH, colS, rV, &tmpr, &tmpg, &tmpb);
1327                                 r_col[0] = facm * (r_col[0]) + fac * tmpr;
1328                                 r_col[1] = facm * (r_col[1]) + fac * tmpg;
1329                                 r_col[2] = facm * (r_col[2]) + fac * tmpb;
1330                         }
1331                         break;
1332                 }
1333                 case MA_RAMP_SOFT:
1334                 {
1335                         float scr, scg, scb;
1336
1337                         /* first calculate non-fac based Screen mix */
1338                         scr = 1.0f - (1.0f - col[0]) * (1.0f - r_col[0]);
1339                         scg = 1.0f - (1.0f - col[1]) * (1.0f - r_col[1]);
1340                         scb = 1.0f - (1.0f - col[2]) * (1.0f - r_col[2]);
1341
1342                         r_col[0] = facm * (r_col[0]) + fac * (((1.0f - r_col[0]) * col[0] * (r_col[0])) + (r_col[0] * scr));
1343                         r_col[1] = facm * (r_col[1]) + fac * (((1.0f - r_col[1]) * col[1] * (r_col[1])) + (r_col[1] * scg));
1344                         r_col[2] = facm * (r_col[2]) + fac * (((1.0f - r_col[2]) * col[2] * (r_col[2])) + (r_col[2] * scb));
1345                         break;
1346                 }
1347                 case MA_RAMP_LINEAR:
1348                         if (col[0] > 0.5f)
1349                                 r_col[0] = r_col[0] + fac * (2.0f * (col[0] - 0.5f));
1350                         else
1351                                 r_col[0] = r_col[0] + fac * (2.0f * (col[0]) - 1.0f);
1352                         if (col[1] > 0.5f)
1353                                 r_col[1] = r_col[1] + fac * (2.0f * (col[1] - 0.5f));
1354                         else
1355                                 r_col[1] = r_col[1] + fac * (2.0f * (col[1]) - 1.0f);
1356                         if (col[2] > 0.5f)
1357                                 r_col[2] = r_col[2] + fac * (2.0f * (col[2] - 0.5f));
1358                         else
1359                                 r_col[2] = r_col[2] + fac * (2.0f * (col[2]) - 1.0f);
1360                         break;
1361         }
1362 }
1363
1364 /**
1365  * \brief copy/paste buffer, if we had a proper py api that would be better
1366  * \note matcopybuf.nodetree does _NOT_ use ID's
1367  * \todo matcopybuf.nodetree's  node->id's are NOT validated, this will crash!
1368  */
1369 static Material matcopybuf;
1370 static short matcopied = 0;
1371
1372 void clear_matcopybuf(void)
1373 {
1374         memset(&matcopybuf, 0, sizeof(Material));
1375         matcopied = 0;
1376 }
1377
1378 void free_matcopybuf(void)
1379 {
1380         if (matcopybuf.nodetree) {
1381                 ntreeFreeLocalTree(matcopybuf.nodetree);
1382                 MEM_freeN(matcopybuf.nodetree);
1383                 matcopybuf.nodetree = NULL;
1384         }
1385
1386         matcopied = 0;
1387 }
1388
1389 void copy_matcopybuf(Main *bmain, Material *ma)
1390 {
1391         if (matcopied)
1392                 free_matcopybuf();
1393
1394         memcpy(&matcopybuf, ma, sizeof(Material));
1395
1396         if (ma->nodetree != NULL) {
1397                 matcopybuf.nodetree = ntreeCopyTree_ex(ma->nodetree, bmain, false);
1398         }
1399
1400         matcopybuf.preview = NULL;
1401         BLI_listbase_clear(&matcopybuf.gpumaterial);
1402         /* TODO Duplicate Engine Settings and set runtime to NULL */
1403         matcopied = 1;
1404 }
1405
1406 void paste_matcopybuf(Main *bmain, Material *ma)
1407 {
1408         ID id;
1409
1410         if (matcopied == 0)
1411                 return;
1412
1413         /* Free gpu material before the ntree */
1414         GPU_material_free(&ma->gpumaterial);
1415
1416         if (ma->nodetree) {
1417                 ntreeFreeNestedTree(ma->nodetree);
1418                 MEM_freeN(ma->nodetree);
1419         }
1420
1421         id = (ma->id);
1422         memcpy(ma, &matcopybuf, sizeof(Material));
1423         (ma->id) = id;
1424
1425         if (matcopybuf.nodetree != NULL) {
1426                 ma->nodetree = ntreeCopyTree_ex(matcopybuf.nodetree, bmain, false);
1427         }
1428 }
1429
1430 void BKE_material_eval(struct Depsgraph *depsgraph, Material *material)
1431 {
1432         DEG_debug_print_eval(depsgraph, __func__, material->id.name, material);
1433         GPU_material_free(&material->gpumaterial);
1434 }