4 * ***** BEGIN GPL LICENSE BLOCK *****
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.
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.
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., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
20 * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
21 * All rights reserved.
23 * The Original Code is: not all of this file anymore. :)
27 * ***** END GPL LICENSE BLOCK *****
39 #include "IMB_imbuf_types.h"
40 #include "IMB_imbuf.h"
42 #include "MEM_guardedalloc.h"
44 #include "DNA_brush_types.h"
45 #include "DNA_curve_types.h"
46 #include "DNA_customdata_types.h"
47 #include "DNA_image_types.h"
48 #include "DNA_lamp_types.h"
49 #include "DNA_material_types.h"
50 #include "DNA_mesh_types.h"
51 #include "DNA_meshdata_types.h"
52 #include "DNA_object_types.h"
53 #include "DNA_node_types.h"
54 #include "DNA_packedFile_types.h"
55 #include "DNA_particle_types.h"
56 #include "DNA_radio_types.h"
57 #include "DNA_screen_types.h"
58 #include "DNA_space_types.h"
59 #include "DNA_scene_types.h"
60 #include "DNA_texture_types.h"
61 #include "DNA_userdef_types.h"
62 #include "DNA_view3d_types.h"
63 #include "DNA_world_types.h"
65 #include "BKE_colortools.h"
66 #include "BKE_depsgraph.h"
67 #include "BKE_displist.h"
68 #include "BKE_effect.h"
69 #include "BKE_global.h"
70 #include "BKE_library.h"
73 #include "BKE_material.h"
74 #include "BKE_particle.h"
75 #include "BKE_utildefines.h"
76 #include "BKE_texture.h"
78 #include "BKE_packedFile.h"
79 #include "BKE_plugin_types.h"
80 #include "BKE_image.h"
82 #include "BLI_blenlib.h"
85 #include "BSE_filesel.h"
86 #include "BSE_headerbuttons.h"
89 #include "BDR_drawmesh.h"
91 #include "BIF_drawimage.h"
93 #include "BIF_graphics.h"
94 #include "BIF_keyval.h"
95 #include "BIF_mainqueue.h"
96 #include "BIF_resources.h"
97 #include "BIF_screen.h"
98 #include "BIF_mywindow.h"
99 #include "BIF_space.h"
100 #include "BIF_glutil.h"
101 #include "BIF_imasel.h"
102 #include "BIF_interface.h"
103 #include "BIF_toolbox.h"
104 #include "BIF_space.h"
105 #include "BIF_previewrender.h"
106 #include "BIF_butspace.h"
107 #include "BIF_writeimage.h"
108 #include "BIF_toets.h"
110 #include "mydevice.h"
114 #include "RE_pipeline.h"
116 /* -----includes for this file specific----- */
118 #include "butspace.h" // own module
121 static MTex emptytex;
122 static int packdummy = 0;
124 static char *mapto_blendtype_pup(void)
126 static char formatstr[] = "|%s %%x%d";
127 static char string[1024];
130 str += sprintf(str, formatstr, "Mix", MTEX_BLEND);
132 str += sprintf(str, formatstr, "Add", MTEX_ADD);
133 str += sprintf(str, formatstr, "Subtract", MTEX_SUB);
135 str += sprintf(str, formatstr, "Multiply", MTEX_MUL);
136 str += sprintf(str, formatstr, "Screen", MTEX_SCREEN);
137 str += sprintf(str, formatstr, "Overlay", MTEX_OVERLAY);
139 str += sprintf(str, formatstr, "Difference", MTEX_DIFF);
140 str += sprintf(str, formatstr, "Divide", MTEX_DIV);
142 str += sprintf(str, formatstr, "Darken", MTEX_DARK);
143 str += sprintf(str, formatstr, "Lighten", MTEX_LIGHT);
145 str += sprintf(str, formatstr, "Hue", MTEX_BLEND_HUE);
146 str += sprintf(str, formatstr, "Saturation", MTEX_BLEND_SAT);
147 str += sprintf(str, formatstr, "Value", MTEX_BLEND_VAL);
148 str += sprintf(str, formatstr, "Color", MTEX_BLEND_COLOR);
153 void shade_buttons_change_3d(void)
160 for(sa= G.curscreen->areabase.first; sa; sa= sa->next) {
161 if(sa->spacetype==SPACE_VIEW3D) {
162 View3D *v3d= sa->spacedata.first;
164 if(v3d->drawtype >= OB_SOLID) addqueue(sa->win, REDRAW, 0);
165 if(v3d->drawtype == OB_SHADED) {
166 if(ob->type==OB_LAMP) reshadeall_displist();
168 /* all objects using material */
169 Base *base= FIRSTBASE;
170 Material *ma= give_current_material(ob, ob->actcol);
174 if(base->lay & G.vd->lay) {
175 for(a=1; a<=ob->totcol; a++) {
176 if(ma == give_current_material(base->object, a)) {
177 freedisplist(&(base->object->disp));
190 /* *************************** TEXTURE ******************************** */
192 static void load_image_cb(char *str, void *ima_pp_v, void *iuser_v) /* called from fileselect or button */
194 Image **ima_pp= (Image **)ima_pp_v;
197 ima= BKE_add_image_file(str);
204 BKE_image_signal(ima, iuser_v, IMA_SIGNAL_RELOAD);
206 /* button event gets lost when it goes via filewindow */
207 if(G.buts && G.buts->lockpoin) {
208 Tex *tex= G.buts->lockpoin;
209 if(GS(tex->id.name)==ID_TE) {
210 BIF_preview_changed(ID_TE);
211 allqueue(REDRAWBUTSSHADING, 0);
212 allqueue(REDRAWOOPS, 0);
217 BIF_undo_push("Load image");
220 static void load_plugin_tex(char *str, void *tex_v, void *unused) /* called from fileselect */
224 if(tex->type!=TEX_PLUGIN) return;
226 if(tex->plugin) free_plugin_tex(tex->plugin);
229 tex->plugin= add_plugin_tex(str);
231 allqueue(REDRAWBUTSSHADING, 0);
232 BIF_preview_changed(ID_TE);
235 static void save_env(char *name)
241 BLI_convertstringcode(str, G.sce, G.scene->r.cfra);
242 tex= G.buts->lockpoin;
244 if(tex && GS(tex->id.name)==ID_TE) {
245 if(tex->env && tex->env->ok && saveover(str)) {
247 BIF_save_envmap(tex->env, str);
255 static int vergcband(const void *a1, const void *a2)
257 const CBData *x1=a1, *x2=a2;
259 if( x1->pos > x2->pos ) return 1;
260 else if( x1->pos < x2->pos) return -1;
264 void do_texbuts(unsigned short event)
270 tex= G.buts->lockpoin;
274 BIF_preview_changed(ID_TE);
275 allqueue(REDRAWBUTSSHADING, 0);
277 if(tex && G.scene->nodetree) {
278 NodeTagIDChanged(G.scene->nodetree, &tex->id);
279 allqueue(RECALC_COMPOSITE, 0);
283 scrarea_queue_headredraw(curarea);
284 BIF_preview_changed(ID_TE);
285 allqueue(REDRAWBUTSSHADING, 0);
286 if(G.buts->texfrom == 3) /* brush texture */
287 allqueue(REDRAWIMAGE, 0);
290 if(tex==NULL) return;
292 allqueue(REDRAWBUTSSHADING, 0);
293 BIF_preview_changed(ID_TE);
295 if(tex && G.scene->nodetree) {
296 NodeTagIDChanged(G.scene->nodetree, &tex->id);
297 allqueue(RECALC_COMPOSITE, 0);
301 if(tex==NULL) return;
303 BIF_undo_push("Default texture vars");
304 allqueue(REDRAWBUTSSHADING, 0);
305 BIF_preview_changed(ID_TE);
309 BIF_preview_changed(ID_TE);
310 allqueue(REDRAWBUTSSHADING, 0);
313 if(G.scene->nodetree) {
314 NodeTagIDChanged(G.scene->nodetree, &tex->id);
315 allqueue(RECALC_COMPOSITE, 0);
317 if(tex->ima && (tex->imaflag & TEX_MIPMAP) && (tex->ima->flag & IMA_FIELDS)) {
318 error("Cannot combine fields and mipmap");
319 tex->imaflag -= TEX_MIPMAP;
322 BKE_free_envmapdata(tex->env);
328 allqueue(REDRAWBUTSSHADING, 0);
329 BIF_preview_changed(ID_TE);
330 shade_buttons_change_3d();
335 if(tex==NULL) return;
337 sa= closest_bigger_area();
339 if(tex->plugin) strcpy(str, tex->plugin->name);
341 strcpy(str, U.plugtexdir);
343 activate_fileselect_args(FILE_SPECIAL, "SELECT PLUGIN", str, load_plugin_tex, tex, NULL);
348 if(tex==NULL || tex->plugin==NULL) return;
349 strcpy(str, tex->plugin->name);
350 free_plugin_tex(tex->plugin);
352 tex->plugin= add_plugin_tex(str);
353 allqueue(REDRAWBUTSSHADING, 0);
354 BIF_preview_changed(ID_TE);
358 if(tex==NULL) return;
359 if(tex->coba==NULL) tex->coba= add_colorband(0);
360 allqueue(REDRAWBUTSSHADING, 0);
361 BIF_preview_changed(ID_TE); // also ramps, so we do this
366 BKE_free_envmap(tex->env);
368 allqueue(REDRAWBUTSSHADING, 0);
369 BIF_preview_changed(ID_TE);
374 BKE_free_envmapdata(tex->env);
375 allqueue(REDRAWBUTSSHADING, 0);
376 BIF_preview_changed(ID_TE);
380 tex= G.main->tex.first;
382 if(tex->id.us && tex->type==TEX_ENVMAP) {
384 if(tex->env->stype!=ENV_LOAD) BKE_free_envmapdata(tex->env);
389 allqueue(REDRAWBUTSSHADING, 0);
390 BIF_preview_changed(ID_TE);
393 if(tex->env && tex->env->ok) {
394 if(tex->env->type==ENV_PLANE) {
395 notice("Sorry, not implemented yet");
398 sa= closest_bigger_area();
400 save_image_filesel_str(str);
401 activate_fileselect(FILE_SPECIAL, str, G.ima, save_env);
406 if(tex->env && tex->env->object) {
407 BIF_preview_changed(ID_TE);
408 if ELEM(tex->env->object->type, OB_CAMERA, OB_LAMP) {
409 error("Camera or Lamp not allowed");
410 tex->env->object= NULL;
416 if(event>=B_PLUGBUT && event<=B_PLUGBUT+23) {
417 PluginTex *pit= tex->plugin;
418 if(pit && pit->callback) {
419 pit->callback(event - B_PLUGBUT);
420 BIF_preview_changed(ID_TE);
421 allqueue(REDRAWBUTSSHADING, 0);
427 static void texture_panel_plugin(Tex *tex)
434 block= uiNewBlock(&curarea->uiblocks, "texture_panel_plugin", UI_EMBOSS, UI_HELV, curarea->win);
435 if(uiNewPanel(curarea, block, "Plugin", "Texture", 640, 0, 318, 204)==0) return;
436 uiSetButLock(tex->id.lib!=0, ERROR_LIBDATA_MESSAGE);
438 if(tex->plugin && tex->plugin->doit) {
442 for(a=0; a<pit->stypes; a++) {
443 uiDefButS(block, ROW, B_TEXREDR_PRV, pit->stnames+16*a, (76*a), 152, 75, 20, &tex->stype, 2.0, (float)a, 0, 0, "");
448 for(a=0; a<pit->vars; a++, varstr++) {
450 yco= 125 - 20*(a % 6)+1;
451 uiDefBut(block, varstr->type, B_PLUGBUT+a, varstr->name, xco,yco,137,19, &(pit->data[a]), varstr->min, varstr->max, 100, 0, varstr->tip);
454 uiDefBut(block, TEX, B_NAMEPLUGIN, "", 0,180,318,24, pit->name, 0.0, 159.0, 0, 0, "");
457 uiDefBut(block, BUT, B_LOADPLUGIN, "Load Plugin", 0,204,137,24, 0, 0, 0, 0, 0, "");
462 static void texture_panel_magic(Tex *tex)
466 block= uiNewBlock(&curarea->uiblocks, "texture_panel_magic", UI_EMBOSS, UI_HELV, curarea->win);
467 if(uiNewPanel(curarea, block, "Magic", "Texture", 640, 0, 318, 204)==0) return;
468 uiSetButLock(tex->id.lib!=0, ERROR_LIBDATA_MESSAGE);
470 uiBlockBeginAlign(block);
471 uiDefButS(block, NUM, B_TEXPRV, "Depth:", 10, 90, 150, 19, &tex->noisedepth, 0.0, 10.0, 0, 0, "Sets the depth of the pattern");
472 uiDefButF(block, NUM, B_TEXPRV, "Turbulence:", 10, 70, 150, 19, &tex->turbul, 0.0, 200.0, 10, 0, "Sets the strength of the pattern");
475 static void texture_panel_blend(Tex *tex)
479 block= uiNewBlock(&curarea->uiblocks, "texture_panel_blend", UI_EMBOSS, UI_HELV, curarea->win);
480 if(uiNewPanel(curarea, block, "Blend", "Texture", 640, 0, 318, 204)==0) return;
481 uiSetButLock(tex->id.lib!=0, ERROR_LIBDATA_MESSAGE);
483 uiBlockBeginAlign(block);
484 uiDefButS(block, ROW, B_TEXPRV, "Lin", 10, 180, 75, 19, &tex->stype, 2.0, (float)TEX_LIN, 0, 0, "Creates a linear progresion");
485 uiDefButS(block, ROW, B_TEXPRV, "Quad", 85, 180, 75, 19, &tex->stype, 2.0, (float)TEX_QUAD, 0, 0, "Creates a quadratic progression");
486 uiDefButS(block, ROW, B_TEXPRV, "Ease", 160, 180, 75, 19, &tex->stype, 2.0, (float)TEX_EASE, 0, 0, "Creates a progression easing from one step to the next");
487 uiDefButBitS(block, TOG, TEX_FLIPBLEND, B_TEXPRV, "Flip XY", 235, 180, 75, 19, &tex->flag, 0, 0, 0, 0, "Flips the direction of the progression 90 degrees");
489 uiDefButS(block, ROW, B_TEXPRV, "Diag", 10, 160, 75, 19, &tex->stype, 2.0, (float)TEX_DIAG, 0, 0, "Use a diagonal progression");
490 uiDefButS(block, ROW, B_TEXPRV, "Sphere", 85, 160, 75, 19, &tex->stype, 2.0, (float)TEX_SPHERE, 0, 0, "Use progression with the shape of a sphere");
491 uiDefButS(block, ROW, B_TEXPRV, "Halo", 160, 160, 75, 19, &tex->stype, 2.0, (float)TEX_HALO, 0, 0, "Use a quadratic progression with the shape of a sphere");
492 uiDefButS(block, ROW, B_TEXPRV, "Radial", 235, 160, 75, 19, &tex->stype, 2.0, (float)TEX_RAD, 0, 0, "Use a polar progression");
496 /* newnoise: noisebasis menu string */
497 static char* noisebasis_menu()
499 static char nbmenu[256];
500 sprintf(nbmenu, "Noise Basis %%t|Blender Original %%x%d|Original Perlin %%x%d|Improved Perlin %%x%d|Voronoi F1 %%x%d|Voronoi F2 %%x%d|Voronoi F3 %%x%d|Voronoi F4 %%x%d|Voronoi F2-F1 %%x%d|Voronoi Crackle %%x%d|CellNoise %%x%d", TEX_BLENDER, TEX_STDPERLIN, TEX_NEWPERLIN, TEX_VORONOI_F1, TEX_VORONOI_F2, TEX_VORONOI_F3, TEX_VORONOI_F4, TEX_VORONOI_F2F1, TEX_VORONOI_CRACKLE, TEX_CELLNOISE);
504 static void texture_panel_wood(Tex *tex)
508 block= uiNewBlock(&curarea->uiblocks, "texture_panel_wood", UI_EMBOSS, UI_HELV, curarea->win);
509 if(uiNewPanel(curarea, block, "Wood", "Texture", 640, 0, 318, 204)==0) return;
510 uiSetButLock(tex->id.lib!=0, ERROR_LIBDATA_MESSAGE);
512 uiBlockBeginAlign(block);
513 uiDefButS(block, ROW, B_TEXPRV, "Bands", 10, 180, 75, 18, &tex->stype, 2.0, (float)TEX_BAND, 0, 0, "Uses standard wood texture in bands");
514 uiDefButS(block, ROW, B_TEXPRV, "Rings", 85, 180, 75, 18, &tex->stype, 2.0, (float)TEX_RING, 0, 0, "Uses wood texture in rings");
515 uiDefButS(block, ROW, B_TEXPRV, "BandNoise", 160, 180, 75, 18, &tex->stype, 2.0, (float)TEX_BANDNOISE, 0, 0, "Adds noise to standard wood");
516 uiDefButS(block, ROW, B_TEXPRV, "RingNoise", 235, 180, 75, 18, &tex->stype, 2.0, (float)TEX_RINGNOISE, 0, 0, "Adds noise to rings");
518 uiDefButS(block, ROW, B_TEXPRV, "Sin", 10, 160, 50, 19, &tex->noisebasis2, 8.0, (float)TEX_SIN, 0, 0, "Uses a sine wave to produce bands");
519 uiDefButS(block, ROW, B_TEXPRV, "Saw", 60, 160, 50, 19, &tex->noisebasis2, 8.0, (float)TEX_SAW, 0, 0, "Uses a saw wave to produce bands");
520 uiDefButS(block, ROW, B_TEXPRV, "Tri", 110, 160, 50, 19, &tex->noisebasis2, 8.0, (float)TEX_TRI, 0, 0, "Uses a triangle wave to produce bands");
521 uiDefButS(block, ROW, B_TEXPRV, "Soft noise", 160, 160, 75, 19, &tex->noisetype, 12.0, (float)TEX_NOISESOFT, 0, 0, "Generates soft noise");
522 uiDefButS(block, ROW, B_TEXPRV, "Hard noise", 235, 160, 75, 19, &tex->noisetype, 12.0, (float)TEX_NOISEPERL, 0, 0, "Generates hard noise");
524 uiBlockBeginAlign(block);
525 uiDefButF(block, NUM, B_TEXPRV, "NoiseSize :", 10, 130, 150, 19, &tex->noisesize, 0.0001, 2.0, 10, 0, "Sets scaling for noise input");
526 uiDefButF(block, NUM, B_TEXPRV, "Turbulence:", 160, 130, 150, 19, &tex->turbul, 0.0, 200.0, 10, 0, "Sets the turbulence of the bandnoise and ringnoise types");
527 uiBlockEndAlign(block);
529 /* newnoise: noisebasis menu */
530 uiDefBut(block, LABEL, 0, "Noise Basis", 10, 30, 150, 19, 0, 0.0, 0.0, 0, 0, "");
531 uiDefButS(block, MENU, B_TEXPRV, noisebasis_menu(), 10, 10, 150, 19, &tex->noisebasis, 0,0,0,0, "Sets the noise basis used for turbulence");
532 uiDefButF(block, NUM, B_NOP, "Nabla: ", 160, 10, 150, 19, &tex->nabla, 0.001, 0.1, 1, 0, "Defines size of derivative offset used for calculating normal");
536 static void texture_panel_stucci(Tex *tex)
540 block= uiNewBlock(&curarea->uiblocks, "texture_panel_stucci", UI_EMBOSS, UI_HELV, curarea->win);
541 if(uiNewPanel(curarea, block, "Stucci", "Texture", 640, 0, 318, 204)==0) return;
542 uiSetButLock(tex->id.lib!=0, ERROR_LIBDATA_MESSAGE);
544 uiBlockBeginAlign(block);
545 uiDefButS(block, ROW, B_TEXPRV, "Plastic", 10, 180, 100, 19, &tex->stype, 2.0, (float)TEX_PLASTIC, 0, 0, "Uses standard stucci");
546 uiDefButS(block, ROW, B_TEXPRV, "Wall In", 110, 180, 100, 19, &tex->stype, 2.0, (float)TEX_WALLIN, 0, 0, "Creates Dimples");
547 uiDefButS(block, ROW, B_TEXPRV, "Wall Out", 210, 180, 100, 19, &tex->stype, 2.0, (float)TEX_WALLOUT, 0, 0, "Creates Ridges");
549 uiDefButS(block, ROW, B_TEXPRV, "Soft noise", 10, 160, 150, 19, &tex->noisetype, 12.0, (float)TEX_NOISESOFT, 0, 0, "Generates soft noise");
550 uiDefButS(block, ROW, B_TEXPRV, "Hard noise", 160, 160, 150, 19, &tex->noisetype, 12.0, (float)TEX_NOISEPERL, 0, 0, "Generates hard noise");
552 uiBlockBeginAlign(block);
553 uiDefButF(block, NUM, B_TEXPRV, "NoiseSize :", 10, 110, 150, 19, &tex->noisesize, 0.0001, 2.0, 10, 0, "Sets scaling for noise input");
554 uiDefButF(block, NUM, B_TEXPRV, "Turbulence:", 10, 90, 150, 19, &tex->turbul, 0.0, 200.0, 10, 0, "Sets the depth of the stucci");
555 uiBlockEndAlign(block);
557 /* newnoise: noisebasis menu */
558 uiDefBut(block, LABEL, 0, "Noise Basis", 10, 30, 150, 19, 0, 0.0, 0.0, 0, 0, "");
559 uiDefButS(block, MENU, B_TEXPRV, noisebasis_menu(), 10, 10, 150, 19, &tex->noisebasis, 0,0,0,0, "Sets the noise basis used for turbulence");
560 // note, nabla not supported here!
561 // uiDefButF(block, NUM, B_NOP, "Nabla: ", 160, 10, 150, 19, &tex->nabla, 0.001, 0.1, 1, 0, "Defines size of derivative offset used for calculating normal");
565 static void texture_panel_marble(Tex *tex)
569 block= uiNewBlock(&curarea->uiblocks, "texture_panel_marble", UI_EMBOSS, UI_HELV, curarea->win);
570 if(uiNewPanel(curarea, block, "Marble", "Texture", 640, 0, 318, 204)==0) return;
571 uiSetButLock(tex->id.lib!=0, ERROR_LIBDATA_MESSAGE);
573 uiBlockBeginAlign(block);
574 uiDefButS(block, ROW, B_TEXPRV, "Soft", 10, 180, 100, 18, &tex->stype, 2.0, (float)TEX_SOFT, 0, 0, "Uses soft marble");
575 uiDefButS(block, ROW, B_TEXPRV, "Sharp", 110, 180, 100, 18, &tex->stype, 2.0, (float)TEX_SHARP, 0, 0, "Uses more clearly defined marble");
576 uiDefButS(block, ROW, B_TEXPRV, "Sharper", 210, 180, 100, 18, &tex->stype, 2.0, (float)TEX_SHARPER, 0, 0, "Uses very clearly defined marble");
578 uiDefButS(block, ROW, B_TEXPRV, "Soft noise", 10, 160, 150, 19, &tex->noisetype, 12.0, (float)TEX_NOISESOFT, 0, 0, "Generates soft noise");
579 uiDefButS(block, ROW, B_TEXPRV, "Hard noise", 160, 160, 150, 19, &tex->noisetype, 12.0, (float)TEX_NOISEPERL, 0, 0, "Generates hard noise");
581 uiDefButS(block, ROW, B_TEXPRV, "Sin", 10, 140, 100, 18, &tex->noisebasis2, 8.0, 0.0, 0, 0, "Uses a sine wave to produce bands.");
582 uiDefButS(block, ROW, B_TEXPRV, "Saw", 110, 140, 100, 18, &tex->noisebasis2, 8.0, 1.0, 0, 0, "Uses a saw wave to produce bands");
583 uiDefButS(block, ROW, B_TEXPRV, "Tri", 210, 140, 100, 18, &tex->noisebasis2, 8.0, 2.0, 0, 0, "Uses a triangle wave to produce bands");
585 uiBlockBeginAlign(block);
586 uiDefButF(block, NUM, B_TEXPRV, "NoiseSize :", 10, 110, 150, 19, &tex->noisesize, 0.0001, 2.0, 10, 0, "Sets scaling for noise input");
587 uiDefButS(block, NUM, B_TEXPRV, "NoiseDepth:", 10, 90, 150, 19, &tex->noisedepth, 0.0, 6.0, 0, 0, "Sets the depth of the marble calculation");
588 uiDefButF(block, NUM, B_TEXPRV, "Turbulence:", 10, 70, 150, 19, &tex->turbul, 0.0, 200.0, 10, 0, "Sets the turbulence of the sine bands");
589 uiBlockEndAlign(block);
591 /* newnoise: noisebasis menu */
592 uiDefBut(block, LABEL, 0, "Noise Basis", 10, 30, 150, 19, 0, 0.0, 0.0, 0, 0, "");
593 uiDefButS(block, MENU, B_TEXPRV, noisebasis_menu(), 10, 10, 150, 19, &tex->noisebasis, 0,0,0,0, "Sets the noise basis used for turbulence");
594 uiDefButF(block, NUM, B_NOP, "Nabla: ", 160, 10, 150, 19, &tex->nabla, 0.001, 0.1, 1, 0, "Defines size of derivative offset used for calculating normal");
598 static void texture_panel_clouds(Tex *tex)
602 block= uiNewBlock(&curarea->uiblocks, "texture_panel_clouds", UI_EMBOSS, UI_HELV, curarea->win);
603 if(uiNewPanel(curarea, block, "Clouds", "Texture", 640, 0, 318, 204)==0) return;
604 uiSetButLock(tex->id.lib!=0, ERROR_LIBDATA_MESSAGE);
606 uiBlockBeginAlign(block);
607 uiDefButS(block, ROW, B_TEXPRV, "Default", 10, 180, 70, 18, &tex->stype, 2.0, (float)TEX_DEFAULT, 0, 0, "Uses standard noise");
608 uiDefButS(block, ROW, B_TEXPRV, "Color", 80, 180, 70, 18, &tex->stype, 2.0, (float)TEX_COLOR, 0, 0, "Lets Noise return RGB value");
609 uiDefButS(block, ROW, B_TEXPRV, "Soft noise", 155, 180, 75, 18, &tex->noisetype, 12.0, (float)TEX_NOISESOFT, 0, 0, "Generates soft noise");
610 uiDefButS(block, ROW, B_TEXPRV, "Hard noise", 230, 180, 80, 18, &tex->noisetype, 12.0, (float)TEX_NOISEPERL, 0, 0, "Generates hard noise");
611 uiBlockBeginAlign(block);
612 uiDefButF(block, NUM, B_TEXPRV, "NoiseSize :", 10, 130, 150, 19, &tex->noisesize, 0.0001, 2.0, 10, 0, "Sets scaling for noise input");
613 uiDefButS(block, NUM, B_TEXPRV, "NoiseDepth:", 160, 130, 150, 19, &tex->noisedepth, 0.0, 6.0, 0, 0, "Sets the depth of the cloud calculation");
614 uiBlockEndAlign(block);
616 /* newnoise: noisebasis menu */
617 uiDefBut(block, LABEL, 0, "Noise Basis", 10, 30, 150, 19, 0, 0.0, 0.0, 0, 0, "");
618 uiDefButS(block, MENU, B_TEXPRV, noisebasis_menu(), 10, 10, 150, 19, &tex->noisebasis, 0,0,0,0, "Sets the noise basis used for turbulence");
619 uiDefButF(block, NUM, B_NOP, "Nabla: ", 160, 10, 150, 19, &tex->nabla, 0.001, 0.1, 1, 0, "Defines size of derivative offset used for calculating normal");
623 /*****************************************/
624 /* newnoise: panel(s) for musgrave types */
625 /*****************************************/
627 static void texture_panel_musgrave(Tex *tex)
632 block= uiNewBlock(&curarea->uiblocks, "texture_panel_musgrave", UI_EMBOSS, UI_HELV, curarea->win);
633 if(uiNewPanel(curarea, block, "Musgrave", "Texture", 640, 0, 318, 204)==0) return;
634 uiSetButLock(tex->id.lib!=0, ERROR_LIBDATA_MESSAGE);
636 /* TEX_MFRACTAL, TEX_RIDGEDMF, TEX_HYBRIDMF, TEX_FBM, TEX_HTERRAIN */
637 str= "Multifractal %x0|Ridged Multifractal %x1|Hybrid Multifractal %x2|Hetero Terrain %x4|fBm %x3";
638 uiDefButS(block, MENU, B_TEXREDR_PRV, str, 10, 160, 150, 19, &tex->stype, 0.0, 0.0, 0, 0, "Sets Musgrave type");
640 uiBlockBeginAlign(block);
641 uiDefButF(block, NUMSLI, B_TEXPRV, "H: ", 10, 130, 150, 19, &tex->mg_H, 0.0001, 2.0, 10, 0, "Sets the highest fractal dimension");
642 uiDefButF(block, NUMSLI, B_TEXPRV, "Lacu: ", 160, 130, 150, 19, &tex->mg_lacunarity, 0.0, 6.0, 10, 0, "Sets the gap between succesive frequencies");
643 uiDefButF(block, NUMSLI, B_TEXPRV, "Octs: ", 10, 110, 150, 19, &tex->mg_octaves, 0.0, 8.0, 10, 0, "Sets the number of frequencies used");
644 if ((tex->stype==TEX_RIDGEDMF) || (tex->stype==TEX_HYBRIDMF) || (tex->stype==TEX_HTERRAIN)) {
645 uiDefButF(block, NUMSLI, B_TEXPRV, "Ofst: ", 160, 110, 150, 19, &tex->mg_offset, 0.0, 6.0, 10, 0, "Sets the fractal offset");
646 if ((tex->stype==TEX_RIDGEDMF) || (tex->stype==TEX_HYBRIDMF))
647 uiDefButF(block, NUMSLI, B_TEXPRV, "Gain: ", 10, 90, 150, 19, &tex->mg_gain, 0.0, 6.0, 10, 0, "Sets the gain multiplier");
650 uiBlockBeginAlign(block);
651 /* noise output scale */
652 uiDefButF(block, NUM, B_TEXPRV, "iScale: ", 10, 60, 150, 19, &tex->ns_outscale, 0.0, 10.0, 10, 0, "Scales intensity output");
653 /* frequency scale */
654 uiDefButF(block, NUM, B_TEXPRV, "NoiseSize: ", 160, 60, 150, 19, &tex->noisesize, 0.0001, 2.0, 10, 0, "Sets scaling for noise input");
655 uiBlockEndAlign(block);
657 /* noisebasis menu */
658 uiDefBut(block, LABEL, 0, "Noise Basis", 10, 30, 150, 19, 0, 0.0, 0.0, 0, 0, "");
659 uiDefButS(block, MENU, B_TEXPRV, noisebasis_menu(), 10, 10, 150, 19, &tex->noisebasis, 0,0,0,0, "Sets the noise basis used for turbulence");
660 uiDefButF(block, NUM, B_NOP, "Nabla: ", 160, 10, 150, 19, &tex->nabla, 0.001, 0.1, 1, 0, "Defines size of derivative offset used for calculating normal");
665 static void texture_panel_distnoise(Tex *tex)
668 block= uiNewBlock(&curarea->uiblocks, "texture_panel_distnoise", UI_EMBOSS, UI_HELV, curarea->win);
669 if(uiNewPanel(curarea, block, "Distorted Noise", "Texture", 640, 0, 318, 204)==0) return;
670 uiSetButLock(tex->id.lib!=0, ERROR_LIBDATA_MESSAGE);
672 uiBlockBeginAlign(block);
673 /* distortion amount */
674 uiDefButF(block, NUM, B_TEXPRV, "DistAmnt: ", 10, 130, 150, 19, &tex->dist_amount, 0.0, 10.0, 10, 0, "Sets amount of distortion");
675 /* frequency scale */
676 uiDefButF(block, NUM, B_TEXPRV, "NoiseSize: ", 160, 130, 150, 19, &tex->noisesize, 0.0001, 2.0, 10, 0, "Sets scaling for noise input");
677 uiBlockEndAlign(block);
679 uiDefBut(block, LABEL, 0, "Distortion Noise", 10, 100, 150, 19, 0, 0.0, 0.0, 0, 0, "");
680 uiDefBut(block, LABEL, 0, "Noise Basis", 160, 100, 150, 19, 0, 0.0, 0.0, 0, 0, "");
682 uiBlockBeginAlign(block);
683 /* noisebasis used for the distortion */
684 uiDefButS(block, MENU, B_TEXPRV, noisebasis_menu(), 10, 80, 150, 19, &tex->noisebasis, 0,0,0,0, "Sets the noise basis which does the distortion");
685 /* noisebasis to distort */
686 uiDefButS(block, MENU, B_TEXPRV, noisebasis_menu(), 160, 80, 150, 19, &tex->noisebasis2, 0,0,0,0, "Sets the noise basis to distort");
687 uiBlockEndAlign(block);
689 uiDefButF(block, NUM, B_NOP, "Nabla: ", 10, 50, 150, 19, &tex->nabla, 0.001, 0.1, 1, 0, "Defines size of derivative offset used for calculating normal");
693 static void texture_panel_voronoi(Tex *tex)
697 block= uiNewBlock(&curarea->uiblocks, "texture_panel_voronoi", UI_EMBOSS, UI_HELV, curarea->win);
698 if(uiNewPanel(curarea, block, "Voronoi", "Texture", 640, 0, 318, 204)==0) return;
699 uiSetButLock(tex->id.lib!=0, ERROR_LIBDATA_MESSAGE);
702 uiBlockBeginAlign(block);
703 uiDefButS(block, ROW, B_TEXPRV, "Int", 10, 180, 75, 18, &tex->vn_coltype, 1.0, 0.0, 0, 0, "Only calculate intensity");
704 uiDefButS(block, ROW, B_TEXPRV, "Col1", 85, 180, 75, 18, &tex->vn_coltype, 1.0, 1.0, 0, 0, "Color cells by position");
705 uiDefButS(block, ROW, B_TEXPRV, "Col2", 160, 180, 75, 18, &tex->vn_coltype, 1.0, 2.0, 0, 0, "Same as Col1 + outline based on F2-F1");
706 uiDefButS(block, ROW, B_TEXPRV, "Col3", 235, 180, 75, 18, &tex->vn_coltype, 1.0, 3.0, 0, 0, "Same as Col2 * intensity");
707 uiBlockEndAlign(block);
709 /* distance metric */
710 sprintf(dm_menu, "Distance Metric %%t|Actual Distance %%x%d|Distance Squared %%x%d|Manhattan %%x%d|Chebychev %%x%d|Minkovsky 1/2 %%x%d|Minkovsky 4 %%x%d|Minkovsky %%x%d", TEX_DISTANCE, TEX_DISTANCE_SQUARED, TEX_MANHATTAN, TEX_CHEBYCHEV, TEX_MINKOVSKY_HALF, TEX_MINKOVSKY_FOUR, TEX_MINKOVSKY);
711 uiDefBut(block, LABEL, B_TEXPRV, "Distance Metric", 10, 160, 150, 19, 0, 0, 0, 0, 0, "");
712 uiDefButS(block, MENU, B_TEXPRV, dm_menu, 10, 140, 150, 19, &tex->vn_distm, 0,0,0,0, "Sets the distance metric to be used");
714 if (tex->vn_distm==TEX_MINKOVSKY)
715 uiDefButF(block, NUMSLI, B_TEXPRV, "Exp: ", 10, 120, 150, 19, &tex->vn_mexp, 0.01, 10.0, 10, 0, "Sets minkovsky exponent");
717 uiBlockBeginAlign(block);
718 uiDefButF(block, NUM, B_TEXPRV, "iScale: ", 160, 140, 150, 19, &tex->ns_outscale, 0.01, 10.0, 10, 0, "Scales intensity output");
719 uiDefButF(block, NUM, B_TEXPRV, "Size: ", 160, 120, 150, 19, &tex->noisesize, 0.0001, 2.0, 10, 0, "Sets scaling for noise input");
720 uiBlockBeginAlign(block);
721 uiDefButF(block, NUM, B_NOP, "Nabla: ", 160, 70, 150, 19, &tex->nabla, 0.001, 0.1, 1, 0, "Defines size of derivative offset used for calculating normal");
724 uiBlockBeginAlign(block);
725 uiDefButF(block, NUMSLI, B_TEXPRV, "W1: ", 10, 70, 150, 19, &tex->vn_w1, -2.0, 2.0, 10, 0, "Sets feature weight 1");
726 uiDefButF(block, NUMSLI, B_TEXPRV, "W2: ", 10, 50, 150, 19, &tex->vn_w2, -2.0, 2.0, 10, 0, "Sets feature weight 2");
727 uiDefButF(block, NUMSLI, B_TEXPRV, "W3: ", 10, 30, 150, 19, &tex->vn_w3, -2.0, 2.0, 10, 0, "Sets feature weight 3");
728 uiDefButF(block, NUMSLI, B_TEXPRV, "W4: ", 10, 10, 150, 19, &tex->vn_w4, -2.0, 2.0, 10, 0, "Sets feature weight 4");
732 static char *layer_menu(RenderResult *rr, short *curlay)
735 int len= 64 + 32*BLI_countlist(&rr->layers);
737 char *str= MEM_callocN(len, "menu layers");
739 strcpy(str, "Layer %t");
744 a+= sprintf(str+a, "|Composite %%x0");
747 for(rl= rr->layers.first; rl; rl= rl->next, nr++) {
748 a+= sprintf(str+a, "|%s %%x%d", rl->name, nr);
751 /* no curlay clip here, on render (redraws) the amount of layers can be 1 fir single-layer render */
756 /* rl==NULL means composite result */
757 static char *pass_menu(RenderLayer *rl, short *curpass)
760 int len= 64 + 32*(rl?BLI_countlist(&rl->passes):1);
762 char *str= MEM_callocN(len, "menu layers");
764 strcpy(str, "Pass %t");
767 /* rendered results don't have a Combined pass */
768 if(rl==NULL || rl->rectf) {
769 a+= sprintf(str+a, "|Combined %%x0");
774 for(rpass= rl->passes.first; rpass; rpass= rpass->next, nr++)
775 a+= sprintf(str+a, "|%s %%x%d", rpass->name, nr);
783 static void set_frames_cb(void *ima_v, void *iuser_v)
786 ImageUser *iuser= iuser_v;
789 iuser->frames = IMB_anim_get_duration(ima->anim);
790 BKE_image_user_calc_imanr(iuser, G.scene->r.cfra, 0);
794 static void image_src_change_cb(void *ima_v, void *iuser_v)
796 BKE_image_signal(ima_v, iuser_v, IMA_SIGNAL_SRC_CHANGE);
799 /* buttons have 2 arg callbacks, filewindow has 3 args... so thats why the wrapper below */
800 static void image_browse_cb1(char *unused, void *ima_pp_v, void *iuser_v)
802 Image **ima_pp= (Image **)ima_pp_v;
803 ImageUser *iuser= iuser_v;
808 if(iuser->menunr== -2) {
809 activate_databrowse_args(&ima->id, ID_IM, 0, &iuser->menunr, image_browse_cb1, ima_pp, iuser);
811 else if (iuser->menunr>0) {
812 Image *newima= (Image*) BLI_findlink(&G.main->image, iuser->menunr-1);
814 if (newima && newima!=ima) {
816 id_us_plus(&newima->id);
817 if(ima) ima->id.us--;
819 BKE_image_signal(newima, iuser, IMA_SIGNAL_USER_NEW_IMAGE);
821 BIF_undo_push("Browse image");
827 static void image_browse_cb(void *ima_pp_v, void *iuser_v)
829 image_browse_cb1(NULL, ima_pp_v, iuser_v);
832 static void image_reload_cb(void *ima_v, void *iuser_v)
835 BKE_image_signal(ima_v, iuser_v, IMA_SIGNAL_RELOAD);
839 static void image_field_test(void *ima_v, void *iuser_v)
844 ImBuf *ibuf= BKE_image_get_ibuf(ima, iuser_v);
847 if( !(ima->flag & IMA_FIELDS) && (ibuf->flags & IB_fields) ) nr= 1;
848 if( (ima->flag & IMA_FIELDS) && !(ibuf->flags & IB_fields) ) nr= 1;
850 BKE_image_signal(ima, iuser_v, IMA_SIGNAL_FREE);
856 static void image_unlink_cb(void *ima_pp_v, void *unused)
858 Image **ima_pp= (Image **)ima_pp_v;
860 if(ima_pp && *ima_pp) {
867 static void image_load_fs_cb(void *ima_pp_v, void *iuser_v)
869 Image **ima_pp= (Image **)ima_pp_v;
873 if(ima_pp==NULL) return;
875 sa= closest_bigger_area();
877 if(*ima_pp) name= (*ima_pp)->name;
880 if (strcmp (U.textudir, "/") == 0)
886 else name = U.textudir;
888 if (G.qual & LR_CTRLKEY) {
889 activate_imageselect_args(FILE_SPECIAL, "SELECT IMAGE", name, load_image_cb, ima_pp_v, iuser_v);
892 activate_fileselect_args(FILE_SPECIAL, "SELECT IMAGE", name, load_image_cb, ima_pp_v, iuser_v);
896 /* 5 layer button callbacks... */
897 static void image_multi_cb(void *rr_v, void *iuser_v)
899 BKE_image_multilayer_index(rr_v, iuser_v);
901 static void image_multi_inclay_cb(void *rr_v, void *iuser_v)
903 RenderResult *rr= rr_v;
904 ImageUser *iuser= iuser_v;
905 int tot= BLI_countlist(&rr->layers) + (rr->rectf?1:0); /* fake compo result layer */
906 if(iuser->layer<tot-1)
908 BKE_image_multilayer_index(rr, iuser);
910 static void image_multi_declay_cb(void *rr_v, void *iuser_v)
912 ImageUser *iuser= iuser_v;
915 BKE_image_multilayer_index(rr_v, iuser);
917 static void image_multi_incpass_cb(void *rr_v, void *iuser_v)
919 RenderResult *rr= rr_v;
920 ImageUser *iuser= iuser_v;
921 RenderLayer *rl= BLI_findlink(&rr->layers, iuser->layer);
923 int tot= BLI_countlist(&rl->passes) + (rl->rectf?1:0); /* builtin render result has no combined pass in list */
924 if(iuser->pass<tot-1) {
926 BKE_image_multilayer_index(rr, iuser);
930 static void image_multi_decpass_cb(void *rr_v, void *iuser_v)
932 ImageUser *iuser= iuser_v;
935 BKE_image_multilayer_index(rr_v, iuser);
939 static void image_pack_cb(void *ima_v, void *iuser_v)
943 if(ima->source!=IMA_SRC_SEQUENCE && ima->source!=IMA_SRC_MOVIE) {
944 if (ima->packedfile) {
945 if (G.fileflags & G_AUTOPACK) {
946 if (okee("Disable AutoPack ?")) {
947 G.fileflags &= ~G_AUTOPACK;
951 if ((G.fileflags & G_AUTOPACK) == 0) {
952 unpackImage(ima, PF_ASK);
953 BIF_undo_push("Unpack image");
957 ImBuf *ibuf= BKE_image_get_ibuf(ima, iuser_v);
958 if (ibuf && (ibuf->userflags & IB_BITMAPDIRTY)) {
959 error("Can't pack painted image. Save image or use Repack as PNG.");
961 ima->packedfile = newPackedFile(ima->name);
962 BIF_undo_push("Pack image");
969 static void image_load_cb(void *ima_pp_v, void *iuser_v)
972 Image *ima= *((Image **)ima_pp_v);
973 ImBuf *ibuf= BKE_image_get_ibuf(ima, iuser_v);
976 /* name in ima has been changed by button! */
977 BLI_strncpy(str, ima->name, FILE_MAX);
978 if(ibuf) BLI_strncpy(ima->name, ibuf->name, FILE_MAX);
980 load_image_cb(str, ima_pp_v, iuser_v);
984 static void image_freecache_cb(void *ima_v, void *unused)
986 BKE_image_free_anim_ibufs(ima_v, G.scene->r.cfra);
987 allqueue(REDRAWIMAGE, 0);
990 static void image_generated_change_cb(void *ima_v, void *iuser_v)
992 BKE_image_signal(ima_v, iuser_v, IMA_SIGNAL_FREE);
995 static void image_user_change(void *iuser_v, void *unused)
997 BKE_image_user_calc_imanr(iuser_v, G.scene->r.cfra, 0);
1000 void uiblock_layer_pass_buttons(uiBlock *block, RenderResult *rr, ImageUser *iuser, int event, int x, int y, int w)
1003 RenderLayer *rl= NULL;
1007 /* layer menu is 1/3 larger than pass */
1012 strp= layer_menu(rr, &iuser->layer);
1013 but= uiDefButS(block, MENU, event, strp, x, y, wmenu1, 20, &iuser->layer, 0,0,0,0, "Select Layer");
1014 uiButSetFunc(but, image_multi_cb, rr, iuser);
1017 rl= BLI_findlink(&rr->layers, iuser->layer - (rr->rectf?1:0)); /* fake compo layer, return NULL is meant to be */
1018 strp= pass_menu(rl, &iuser->pass);
1019 but= uiDefButS(block, MENU, event, strp, x+wmenu1, y, wmenu2, 20, &iuser->pass, 0,0,0,0, "Select Pass");
1020 uiButSetFunc(but, image_multi_cb, rr, iuser);
1024 static void uiblock_layer_pass_arrow_buttons(uiBlock *block, RenderResult *rr, ImageUser *iuser, int imagechanged)
1028 if(rr==NULL || iuser==NULL)
1030 if(rr->layers.first==NULL) {
1031 uiDefBut(block, LABEL, 0, "No Layers in Render Result,", 10, 107, 300, 20, NULL, 1, 0, 0, 0, "");
1035 uiBlockBeginAlign(block);
1037 /* decrease, increase arrows */
1038 but= uiDefIconBut(block, BUT, imagechanged, ICON_TRIA_LEFT, 10,107,17,20, NULL, 0, 0, 0, 0, "Previous Layer");
1039 uiButSetFunc(but, image_multi_declay_cb, rr, iuser);
1040 but= uiDefIconBut(block, BUT, imagechanged, ICON_TRIA_RIGHT, 27,107,18,20, NULL, 0, 0, 0, 0, "Next Layer");
1041 uiButSetFunc(but, image_multi_inclay_cb, rr, iuser);
1043 uiblock_layer_pass_buttons(block, rr, iuser, imagechanged, 45, 107, 230);
1045 /* decrease, increase arrows */
1046 but= uiDefIconBut(block, BUT, imagechanged, ICON_TRIA_LEFT, 275,107,17,20, NULL, 0, 0, 0, 0, "Previous Pass");
1047 uiButSetFunc(but, image_multi_decpass_cb, rr, iuser);
1048 but= uiDefIconBut(block, BUT, imagechanged, ICON_TRIA_RIGHT, 292,107,18,20, NULL, 0, 0, 0, 0, "Next Pass");
1049 uiButSetFunc(but, image_multi_incpass_cb, rr, iuser);
1051 uiBlockEndAlign(block);
1055 /* The general Image panel with the loadsa callbacks! */
1056 void uiblock_image_panel(uiBlock *block, Image **ima_pp, ImageUser *iuser,
1057 short redraw, short imagechanged)
1059 Image *ima= *ima_pp;
1061 char str[128], *strp;
1063 /* different stuff when we show viewer */
1064 if(ima && ima->source==IMA_SRC_VIEWER) {
1065 ImBuf *ibuf= BKE_image_get_ibuf(ima, iuser);
1067 image_info(ima, ibuf, str);
1068 uiDefBut(block, LABEL, 0, ima->id.name+2, 10, 180, 300, 20, NULL, 1, 0, 0, 0, "");
1069 uiDefBut(block, LABEL, 0, str, 10, 160, 300, 20, NULL, 1, 0, 0, 0, "");
1071 if(ima->type==IMA_TYPE_COMPOSITE) {
1072 iuser= ntree_get_active_iuser(G.scene->nodetree);
1074 uiBlockBeginAlign(block);
1075 uiDefIconTextBut(block, BUT, B_SIMA_RECORD, ICON_REC, "Record", 10,120,100,20, 0, 0, 0, 0, 0, "");
1076 uiDefIconTextBut(block, BUT, B_SIMA_PLAY, ICON_PLAY, "Play", 110,120,100,20, 0, 0, 0, 0, 0, "");
1077 but= uiDefBut(block, BUT, B_NOP, "Free Cache", 210,120,100,20, 0, 0, 0, 0, 0, "");
1078 uiButSetFunc(but, image_freecache_cb, ima, NULL);
1081 sprintf(str, "(%d) Frames:", iuser->framenr);
1082 else strcpy(str, "Frames:");
1083 uiBlockBeginAlign(block);
1084 uiDefButI(block, NUM, imagechanged, str, 10, 90,150, 20, &iuser->frames, 0.0, MAXFRAMEF, 0, 0, "Sets the number of images of a movie to use");
1085 uiDefButI(block, NUM, imagechanged, "StartFr:", 160,90,150,20, &iuser->sfra, 1.0, MAXFRAMEF, 0, 0, "Sets the global starting frame of the movie");
1088 else if(ima->type==IMA_TYPE_R_RESULT) {
1089 /* browse layer/passes */
1090 uiblock_layer_pass_arrow_buttons(block, RE_GetResult(RE_GetRender(G.scene->id.name)), iuser, imagechanged);
1095 /* the main ima source types */
1097 uiSetButLock(ima->id.lib!=NULL, ERROR_LIBDATA_MESSAGE);
1098 uiBlockBeginAlign(block);
1099 uiBlockSetFunc(block, image_src_change_cb, ima, iuser);
1100 uiDefButS(block, ROW, imagechanged, "Still", 10, 180, 60, 20, &ima->source, 0.0, IMA_SRC_FILE, 0, 0, "Single Image file");
1101 uiDefButS(block, ROW, imagechanged, "Movie", 70, 180, 60, 20, &ima->source, 0.0, IMA_SRC_MOVIE, 0, 0, "Movie file");
1102 uiDefButS(block, ROW, imagechanged, "Sequence", 130, 180, 90, 20, &ima->source, 0.0, IMA_SRC_SEQUENCE, 0, 0, "Multiple Image files, as a sequence");
1103 uiDefButS(block, ROW, imagechanged, "Generated", 220, 180, 90, 20, &ima->source, 0.0, IMA_SRC_GENERATED, 0, 0, "Generated Image");
1104 uiBlockSetFunc(block, NULL, NULL, NULL);
1107 uiDefBut(block, LABEL, 0, " ", 10, 180, 300, 20, 0, 0, 0, 0, 0, ""); /* for align in panel */
1110 IMAnames_to_pupstring(&strp, NULL, NULL, &(G.main->image), NULL, &iuser->menunr);
1112 uiBlockBeginAlign(block);
1113 but= uiDefButS(block, MENU, imagechanged, strp, 10,155,23,20, &iuser->menunr, 0, 0, 0, 0, "Selects an existing Image or Movie");
1114 uiButSetFunc(but, image_browse_cb, ima_pp, iuser);
1118 /* name + options, or only load */
1120 int drawpack= (ima->source!=IMA_SRC_SEQUENCE && ima->source!=IMA_SRC_MOVIE && ima->ok);
1122 but= uiDefBut(block, TEX, B_IDNAME, "IM:", 33, 155, 177, 20, ima->id.name+2, 0.0, 21.0, 0, 0, "Current Image Datablock name.");
1123 uiButSetFunc(but, test_idbutton_cb, ima->id.name, NULL);
1124 but= uiDefBut(block, BUT, imagechanged, "Reload", 210, 155, 60, 20, NULL, 0, 0, 0, 0, "Reloads Image or Movie");
1125 uiButSetFunc(but, image_reload_cb, ima, iuser);
1127 but= uiDefIconBut(block, BUT, imagechanged, ICON_X, 270,155,20,20, 0, 0, 0, 0, 0, "Unlink Image block");
1128 uiButSetFunc(but, image_unlink_cb, ima_pp, NULL);
1129 sprintf(str, "%d", ima->id.us);
1130 uiDefBut(block, BUT, B_NOP, str, 290,155,20,20, 0, 0, 0, 0, 0, "Only displays number of users of Image block");
1132 but= uiDefIconBut(block, BUT, imagechanged, ICON_FILESEL, 10, 135, 23, 20, 0, 0, 0, 0, 0, "Open Fileselect to load new Image");
1133 uiButSetFunc(but, image_load_fs_cb, ima_pp, iuser);
1134 but= uiDefBut(block, TEX, imagechanged, "", 33,135,257+(drawpack?0:20),20, ima->name, 0.0, 239.0, 0, 0, "Image/Movie file name, change to load new");
1135 uiButSetFunc(but, image_load_cb, ima_pp, iuser);
1138 if (ima->packedfile) packdummy = 1;
1140 but= uiDefIconButBitI(block, TOG, 1, redraw, ICON_PACKAGE, 290,135,20,20, &packdummy, 0, 0, 0, 0, "Toggles Packed status of this Image");
1141 uiButSetFunc(but, image_pack_cb, ima, iuser);
1146 but= uiDefBut(block, BUT, imagechanged, "Load", 33, 155, 100,20, NULL, 0, 0, 0, 0, "Load new Image of Movie");
1147 uiButSetFunc(but, image_load_fs_cb, ima_pp, iuser);
1149 uiBlockEndAlign(block);
1152 ImBuf *ibuf= BKE_image_get_ibuf(ima, iuser);
1154 /* check for re-render, only buttons */
1155 if(imagechanged==B_IMAGECHANGED) {
1156 if(iuser->flag & IMA_ANIM_REFRESHED) {
1157 iuser->flag &= ~IMA_ANIM_REFRESHED;
1158 BIF_preview_changed(ID_TE);
1163 if(ima->type==IMA_TYPE_MULTILAYER && ima->rr) {
1164 uiblock_layer_pass_arrow_buttons(block, ima->rr, iuser, imagechanged);
1167 image_info(ima, ibuf, str);
1168 uiDefBut(block, LABEL, 0, str, 10, 112, 300, 20, NULL, 1, 0, 0, 0, "");
1171 /* exception, let's do because we only use this panel 3 times in blender... but not real good code! */
1172 if( (FACESEL_PAINT_TEST) && G.sima && &G.sima->iuser==iuser)
1174 /* left side default per-image options, right half the additional options */
1177 uiBlockBeginAlign(block);
1178 but= uiDefButBitS(block, TOG, IMA_FIELDS, imagechanged, "Fields", 10, 70, 65, 20, &ima->flag, 0, 0, 0, 0, "Click to enable use of fields in Image");
1179 uiButSetFunc(but, image_field_test, ima, iuser);
1180 uiDefButBitS(block, TOG, IMA_STD_FIELD, B_NOP, "Odd", 75, 70, 45, 20, &ima->flag, 0, 0, 0, 0, "Standard Field Toggle");
1182 uiBlockSetFunc(block, image_reload_cb, ima, iuser);
1183 uiDefButBitS(block, TOG, IMA_ANTIALI, B_NOP, "Anti", 10, 50, 45, 20, &ima->flag, 0, 0, 0, 0, "Toggles Image anti-aliasing, only works with solid colors");
1184 uiDefButBitS(block, TOG, IMA_DO_PREMUL, imagechanged, "Premul", 55, 50, 65, 20, &ima->flag, 0, 0, 0, 0, "Toggles premultiplying alpha");
1185 uiBlockEndAlign(block);
1187 if( ELEM(ima->source, IMA_SRC_MOVIE, IMA_SRC_SEQUENCE)) {
1188 sprintf(str, "(%d) Frames:", iuser->framenr);
1190 uiBlockBeginAlign(block);
1191 uiBlockSetFunc(block, image_user_change, iuser, NULL);
1192 uiDefButBitS(block, TOG, IMA_ANIM_ALWAYS, B_NOP, "Auto Refresh", 120, 70, 190, 20, &iuser->flag, 0, 0, 0, 0, "Always refresh Image on frame changes");
1195 uiDefButI(block, NUM, imagechanged, str, 120, 50,170, 20, &iuser->frames, 0.0, MAXFRAMEF, 0, 0, "Sets the number of images of a movie to use");
1196 but= uiDefBut(block, BUT, redraw, "<", 290, 50, 20, 20, 0, 0, 0, 0, 0, "Copies number of frames in movie file to Frames: button");
1197 uiButSetFunc(but, set_frames_cb, ima, iuser);
1200 uiDefButI(block, NUM, imagechanged, str, 120, 50,190, 20, &iuser->frames, 0.0, MAXFRAMEF, 0, 0, "Sets the number of images of a movie to use");
1202 uiDefButI(block, NUM, imagechanged, "Offs:", 120,30,100,20, &iuser->offset, -MAXFRAMEF, MAXFRAMEF, 0, 0, "Offsets the number of the frame to use in the animation");
1203 uiDefButS(block, NUM, imagechanged, "Fie/Ima:", 220,30,90,20, &iuser->fie_ima, 1.0, 200.0, 0, 0, "The number of fields per rendered frame (2 fields is 1 image)");
1205 uiDefButI(block, NUM, imagechanged, "StartFr:", 120,10,100,20, &iuser->sfra, 1.0, MAXFRAMEF, 0, 0, "Sets the global starting frame of the movie");
1206 uiDefButS(block, TOG, imagechanged, "Cyclic", 220,10,90,20, &iuser->cycl, 0.0, 1.0, 0, 0, "Cycle the images in the movie");
1208 uiBlockSetFunc(block, NULL, iuser, NULL);
1210 else if(ima->source==IMA_SRC_GENERATED) {
1212 uiBlockBeginAlign(block);
1213 uiBlockSetFunc(block, image_generated_change_cb, ima, iuser);
1214 uiDefButS(block, NUM, imagechanged, "SizeX:", 120,70,100,20, &ima->gen_x, 1.0, 5000.0, 0, 0, "Image size x");
1215 uiDefButS(block, NUM, imagechanged, "SizeY:", 220,70,90,20, &ima->gen_y, 1.0, 5000.0, 0, 0, "Image size y");
1216 uiDefButS(block, TOG, imagechanged, "UV Test grid",120,50,190,20, &ima->gen_type, 0.0, 1.0, 0, 0, "");
1217 uiBlockSetFunc(block, NULL, NULL, NULL);
1220 uiBlockEndAlign(block);
1223 static void texture_panel_image(Image **ima, ImageUser *iuser)
1227 block= uiNewBlock(&curarea->uiblocks, "texture_panel_image", UI_EMBOSS, UI_HELV, curarea->win);
1228 if(uiNewPanel(curarea, block, "Image", "Texture", 960, 0, 318, 204)==0) return;
1230 uiblock_image_panel(block, ima, iuser, B_REDR, B_IMAGECHANGED);
1233 static void texture_panel_image_map(Tex *tex, MTex *mtex)
1237 block= uiNewBlock(&curarea->uiblocks, "texture_panel_image_map", UI_EMBOSS, UI_HELV, curarea->win);
1238 if(uiNewPanel(curarea, block, "Map Image", "Texture", 640, 0, 318, 204)==0) return;
1239 uiSetButLock(tex->id.lib!=0, ERROR_LIBDATA_MESSAGE);
1242 uiBlockBeginAlign(block);
1243 uiDefButBitS(block, TOG, TEX_MIPMAP, B_IMAGECHANGED, "MipMap", 10, 180, 75, 20, &tex->imaflag, 0, 0, 0, 0, "Generates and uses mipmaps");
1244 uiDefButBitS(block, TOG, TEX_GAUSS_MIP, 0, "Gauss", 85, 180, 75, 20, &tex->imaflag, 0, 0, 0, 0, "Enable Gauss filter to sample down mipmaps");
1245 uiDefButBitS(block, TOG, TEX_INTERPOL, 0, "Interpol", 160, 180, 75, 20, &tex->imaflag, 0, 0, 0, 0, "Interpolates pixels using Area filter");
1246 uiDefButBitS(block, TOG, TEX_IMAROT, B_TEXPRV, "Rot90", 235, 180, 75, 20, &tex->imaflag, 0, 0, 0, 0, "Actually flips X and Y for rendering, rotates and mirrors");
1248 uiDefButBitS(block, TOG, TEX_USEALPHA, B_TEXPRV, "UseAlpha", 10, 160, 100, 20, &tex->imaflag, 0, 0, 0, 0, "Click to use Image's alpha channel");
1249 uiDefButBitS(block, TOG, TEX_CALCALPHA, B_TEXPRV, "CalcAlpha", 110, 160, 100, 20, &tex->imaflag, 0, 0, 0, 0, "Click to calculate an alpha channel based on Image RGB values");
1250 uiDefButBitS(block, TOG, TEX_NEGALPHA, B_TEXPRV, "NegAlpha", 210, 160, 100, 20, &tex->flag, 0, 0, 0, 0, "Click to invert the alpha values");
1252 uiBlockBeginAlign(block);
1253 uiDefButBitS(block, TOG, TEX_FILTER_MIN, B_TEXPRV, "Min", 10, 120, 30, 20, &tex->imaflag, 0, 0, 0, 0, "Use Filtersize as a minimal filter value in pixels");
1254 uiDefButF(block, NUM, B_TEXPRV, "Filter: ", 40,120,120,20, &tex->filtersize, 0.1, 50.0, 10, 3, "Multiplies the filter size used by mipmap and interpol");
1256 uiBlockBeginAlign(block);
1257 uiDefButBitS(block, TOG, TEX_NORMALMAP, B_NOP, "Normal Map", 160,120,(mtex)? 75: 150,20, &tex->imaflag,
1258 0, 0, 0, 0, "Use image RGB values for normal mapping");
1260 uiDefButS(block, MENU, B_DIFF, "Normal Space %t|Camera %x0|World %x1|Object %x2|Tangent %x3",
1261 235,120,75,20, &mtex->normapspace, 0, 0, 0, 0, "Sets space of normal map image");
1262 uiBlockEndAlign(block);
1264 /* crop extend clip */
1266 uiBlockBeginAlign(block);
1267 uiDefButS(block, ROW, B_TEXREDR_PRV, "Extend", 10,90,63,19, &tex->extend, 4.0, 1.0, 0, 0, "Extends the color of the edge pixels");
1268 uiDefButS(block, ROW, B_TEXREDR_PRV, "Clip", 73,90,48,19, &tex->extend, 4.0, 2.0, 0, 0, "Sets alpha 0.0 outside Image edges");
1269 uiDefButS(block, ROW, B_TEXREDR_PRV, "ClipCube", 121,90,63,19, &tex->extend, 4.0, 4.0, 0, 0, "Sets alpha to 0.0 outside cubeshaped area around Image");
1270 uiDefButS(block, ROW, B_TEXREDR_PRV, "Repeat", 184,90,63,19, &tex->extend, 4.0, 3.0, 0, 0, "Causes Image to repeat horizontally and vertically");
1271 uiDefButS(block, ROW, B_TEXREDR_PRV, "Checker", 247,90,63,19, &tex->extend, 4.0, 5.0, 0, 0, "Causes Image to repeat in checker pattern");
1273 if(tex->extend==TEX_REPEAT) {
1274 uiBlockBeginAlign(block);
1275 uiDefButBitS(block, TOG, TEX_REPEAT_XMIR, B_TEXPRV, "Mirr", 10,60,30,19, &tex->flag, 0.0, 0.0, 0, 0, "Mirrors X direction repeat");
1276 uiDefButS(block, NUM, B_TEXPRV, "Xrepeat:", 40,60,120,19, &tex->xrepeat, 1.0, 512.0, 0, 0, "Sets a repetition multiplier in the X direction");
1277 uiDefButBitS(block, TOG, TEX_REPEAT_YMIR, B_TEXPRV, "Mirr", 160,60,30,19, &tex->flag, 0.0, 0.0, 0, 0, "Mirrors Y direction repeat");
1278 uiDefButS(block, NUM, B_TEXPRV, "Yrepeat:", 190,60,120,19, &tex->yrepeat, 1.0, 512.0, 0, 0, "Sets a repetition multiplier in the Y direction");
1280 else if(tex->extend==TEX_CHECKER) {
1281 uiBlockBeginAlign(block);
1282 uiDefButBitS(block, TOG, TEX_CHECKER_ODD, B_TEXPRV, "Odd", 10,60,100,19, &tex->flag, 0.0, 0.0, 0, 0, "Sets odd checker tiles");
1283 uiDefButBitS(block, TOG, TEX_CHECKER_EVEN, B_TEXPRV, "Even", 110,60,100,19, &tex->flag, 0.0, 0.0, 0, 0, "Sets even checker tiles");
1284 uiDefButF(block, NUM, B_TEXPRV, "Mortar:", 210,60,100,19, &tex->checkerdist, 0.0, 0.99, 0, 0, "Set checkers distance (like mortar)");
1286 uiBlockBeginAlign(block);
1287 uiDefButF(block, NUM, B_TEXPRV, "MinX ", 10,30,150,19, &tex->cropxmin, -10.0, 10.0, 10, 0, "Sets minimum X value to crop Image");
1288 uiDefButF(block, NUM, B_TEXPRV, "MinY ", 10,10,150,19, &tex->cropymin, -10.0, 10.0, 10, 0, "Sets minimum Y value to crop Image");
1290 uiBlockBeginAlign(block);
1291 uiDefButF(block, NUM, B_TEXPRV, "MaxX ", 160,30,150,19, &tex->cropxmax, -10.0, 10.0, 10, 0, "Sets maximum X value to crop Image");
1292 uiDefButF(block, NUM, B_TEXPRV, "MaxY ", 160,10,150,19, &tex->cropymax, -10.0, 10.0, 10, 0, "Sets maximum Y value to crop Image");
1293 uiBlockEndAlign(block);
1297 /***************************************/
1299 static void texture_panel_envmap(Tex *tex)
1305 short a, xco, yco, dx, dy;
1306 char *strp, str[32];
1308 block= uiNewBlock(&curarea->uiblocks, "texture_panel_envmap", UI_EMBOSS, UI_HELV, curarea->win);
1309 if(uiNewPanel(curarea, block, "Envmap", "Texture", 640, 0, 318, 204)==0) return;
1310 uiSetButLock(tex->id.lib!=0, ERROR_LIBDATA_MESSAGE);
1312 if(tex->env==NULL) {
1313 tex->env= BKE_add_envmap();
1314 tex->env->object= OBACT;
1319 uiBlockBeginAlign(block);
1320 uiDefButS(block, ROW, B_REDR, "Static", 10, 180, 100, 19, &env->stype, 2.0, (float)ENV_STATIC, 0, 0, "Calculates environment map only once");
1321 uiDefButS(block, ROW, B_REDR, "Anim", 110, 180, 100, 19, &env->stype, 2.0, (float)ENV_ANIM, 0, 0, "Calculates environment map at each rendering");
1322 uiDefButS(block, ROW, B_ENV_FREE, "Load", 210, 180, 100, 19, &env->stype, 2.0, (float)ENV_LOAD, 0, 0, "Loads saved environment map from disk");
1323 uiBlockEndAlign(block);
1325 if(env->stype==ENV_LOAD) {
1328 IMAnames_to_pupstring(&strp, NULL, NULL, &(G.main->image), id, &(G.buts->menunr));
1330 uiBlockBeginAlign(block);
1332 but= uiDefButS(block, MENU, B_TEXPRV, strp, 10,145,23,20, &tex->iuser.menunr, 0, 0, 0, 0, "Selects an existing environment map");
1333 uiButSetFunc(but, image_browse_cb, &tex->ima, &tex->iuser);
1336 but= uiDefBut(block, TEX, B_NAMEIMA, "", 35,145,255,20, tex->ima->name, 0.0, 79.0, 0, 0, "Displays environment map name: click to change");
1337 uiButSetFunc(but, image_load_cb, &tex->ima, &tex->iuser);
1339 sprintf(str, "%d", tex->ima->id.us);
1340 uiDefBut(block, BUT, 0, str, 290,145,20,20, 0, 0, 0, 0, 0, "Displays number of users of environment map: click to make single user");
1341 uiBlockEndAlign(block);
1343 but= uiDefBut(block, BUT, B_IMAGECHANGED, "Reload", 230,125,80,20, 0, 0, 0, 0, 0, "Reloads saved environment map");
1344 uiButSetFunc(but, image_reload_cb, tex->ima, NULL);
1346 if (tex->ima->packedfile) packdummy = 1;
1348 but= uiDefIconButBitI(block, TOG, 1, B_REDR, ICON_PACKAGE, 205,125,24,20, &packdummy, 0, 0, 0, 0, "Toggles Packed status of this environment map");
1349 uiButSetFunc(but, image_pack_cb, tex->ima, &tex->iuser);
1351 else uiBlockEndAlign(block);
1355 but= uiDefBut(block, BUT, B_IMAGECHANGED, "Load Image", 10,125,150,20, 0, 0, 0, 0, 0, "Loads saved environment map - file select");
1356 uiButSetFunc(but, image_load_fs_cb, &tex->ima, &tex->iuser);
1359 uiBlockBeginAlign(block);
1360 uiDefBut(block, BUT, B_ENV_FREE, "Free Data", 10,145,100,20, 0, 0, 0, 0, 0, "Releases all images associated with this environment map");
1361 uiDefBut(block, BUT, B_ENV_SAVE, "Save EnvMap", 110,145,100,20, 0, 0, 0, 0, 0, "Saves current environment map");
1362 uiDefBut(block, BUT, B_ENV_FREE_ALL, "Free all EnvMaps", 210,145,100,20, 0, 0, 0, 0, 0, "Frees all rendered environment maps for all materials");
1364 uiBlockBeginAlign(block);
1365 uiDefButS(block, ROW, B_NOP, "Cube", 10,120,100,20, &env->type, 3.0f, (float)ENV_CUBE, 0, 0, "Use environment map with six cube sides");
1366 uiDefButS(block, ROW, B_NOP, "Plane", 110,120,100,20, &env->type, 3.0f, (float)ENV_PLANE, 0, 0, "Only one side is rendered, with Z axis pointing in direction of image");
1367 uiDefButF(block, NUM, B_NOP, "Zoom: ", 210,120,100,20, &env->viewscale, 0.5f, 5.0f, 100, 2, "Zoom factor for planar environment map");
1368 uiBlockEndAlign(block);
1371 uiDefIDPoinBut(block, test_obpoin_but, ID_OB, B_ENV_OB, "Ob:", 10,90,150,20, &(env->object), "Displays object to use as viewpoint for environment map: click to change");
1372 if(env->stype!=ENV_LOAD)
1373 uiDefButS(block, NUM, B_ENV_FREE, "CubeRes", 160,90,150,20, &env->cuberes, 50, 4096.0, 0, 0, "Sets the pixel resolution of the rendered environment map");
1375 uiBlockBeginAlign(block);
1376 uiDefButBitS(block, TOG, TEX_FILTER_MIN, B_TEXPRV, "Min", 10, 65, 30, 20, &tex->imaflag, 0, 0, 0, 0, "Use Filtersize as a minimal filter value in pixels");
1377 uiDefButF(block, NUM, B_TEXPRV, "Filter :", 40,65,120,20, &tex->filtersize, 0.1, 25.0, 0, 3, "Adjusts sharpness or blurriness of the reflection"),
1378 uiDefButS(block, NUM, B_ENV_FREE, "Depth:", 160,65,150,20, &env->depth, 0, 5.0, 0, 0, "Sets the number of times a map will be rendered recursively mirror effects"),
1379 uiDefButF(block, NUM, REDRAWVIEW3D, "ClipSta", 10,40,150,20, &env->clipsta, 0.01, 50.0, 100, 0, "Sets start value for clipping: objects nearer than this are not visible to map");
1380 uiDefButF(block, NUM, B_NOP, "ClipEnd", 160,40,150,20, &env->clipend, 0.1, 20000.0, 1000, 0, "Sets end value for clipping beyond which objects are not visible to map");
1381 uiBlockEndAlign(block);
1383 uiDefBut(block, LABEL, 0, "Don't render layer:", 10,10,140,22, 0, 0.0, 0.0, 0, 0, "");
1389 uiBlockBeginAlign(block);
1391 uiDefButBitI(block, TOG, 1<<a, 0, "", (xco+a*(dx/2)), (yco+dy/2), (dx/2), (1+dy/2), (int *)&env->notlay, 0, 0, 0, 0, "Toggles layer visibility to environment map");
1393 uiDefButBitI(block, TOG, 1<<(a+10), 0, "",(xco+a*(dx/2)), yco, (dx/2), (dy/2), (int *)&env->notlay, 0, 0, 0, 0, "Toggles layer visibility to environment map");
1395 uiBlockBeginAlign(block);
1398 uiDefButBitI(block, TOG, 1<<a, 0, "", (xco+a*(dx/2)), (yco+dy/2), (dx/2), (1+dy/2), (int *)&env->notlay, 0, 0, 0, 0, "Toggles layer visibility to environment map");
1400 uiDefButBitI(block, TOG, 1<<(a+10), 0, "",(xco+a*(dx/2)), yco, (dx/2), (dy/2), (int *)&env->notlay, 0, 0, 0, 0, "Toggles layer visibility to environment map");
1405 static void colorband_pos_cb(void *coba_v, void *unused_v)
1407 ColorBand *coba= coba_v;
1410 if(coba->tot<2) return;
1412 for(a=0; a<coba->tot; a++) coba->data[a].cur= a;
1413 qsort(coba->data, coba->tot, sizeof(CBData), vergcband);
1414 for(a=0; a<coba->tot; a++) {
1415 if(coba->data[a].cur==coba->cur) {
1416 if(coba->cur!=a) addqueue(curarea->win, REDRAW, 0); /* button cur */
1423 static void colorband_add_cb(void *coba_v, void *unused_v)
1425 ColorBand *coba= coba_v;
1427 if(coba->tot < MAXCOLORBAND-1) coba->tot++;
1428 coba->cur= coba->tot-1;
1430 colorband_pos_cb(coba, NULL);
1431 BIF_undo_push("Add colorband");
1435 static void colorband_del_cb(void *coba_v, void *unused_v)
1437 ColorBand *coba= coba_v;
1440 if(coba->tot<2) return;
1442 for(a=coba->cur; a<coba->tot; a++) {
1443 coba->data[a]= coba->data[a+1];
1445 if(coba->cur) coba->cur--;
1448 BIF_undo_push("Delete colorband");
1449 BIF_preview_changed(ID_TE);
1453 /* offset aligns from bottom, standard width 300, height 115 */
1454 static void draw_colorband_buts(uiBlock *block, ColorBand *coba, int xoffs, int yoffs, int redraw)
1459 if(coba==NULL) return;
1461 bt= uiDefBut(block, BUT, redraw, "Add", 80+xoffs,95+yoffs,37,20, 0, 0, 0, 0, 0, "Adds a new color position to the colorband");
1462 uiButSetFunc(bt, colorband_add_cb, coba, NULL);
1463 uiDefButS(block, NUM, redraw, "Cur:", 117+xoffs,95+yoffs,81,20, &coba->cur, 0.0, (float)(coba->tot-1), 0, 0, "Displays the active color from the colorband");
1464 bt= uiDefBut(block, BUT, redraw, "Del", 199+xoffs,95+yoffs,37,20, 0, 0, 0, 0, 0, "Deletes the active position");
1465 uiButSetFunc(bt, colorband_del_cb, coba, NULL);
1466 uiDefButS(block, ROW, redraw, "E", 236+xoffs,95+yoffs,16,20, &coba->ipotype, 5.0, 1.0, 0, 0, "Sets interpolation type 'Ease' (quadratic) ");
1467 uiDefButS(block, ROW, redraw, "C", 252+xoffs,95+yoffs,16,20, &coba->ipotype, 5.0, 3.0, 0, 0, "Sets interpolation type Cardinal");
1468 uiDefButS(block, ROW, redraw, "L", 268+xoffs,95+yoffs,16,20, &coba->ipotype, 5.0, 0.0, 0, 0, "Sets interpolation type Linear");
1469 uiDefButS(block, ROW, redraw, "S", 284+xoffs,95+yoffs,16,20, &coba->ipotype, 5.0, 2.0, 0, 0, "Sets interpolation type B-Spline");
1471 uiDefBut(block, BUT_COLORBAND, redraw, "", xoffs,65+yoffs,300,30, coba, 0, 0, 0, 0, "");
1473 cbd= coba->data + coba->cur;
1475 uiBlockBeginAlign(block);
1476 bt= uiDefButF(block, NUM, redraw, "Pos", xoffs,40+yoffs,110,20, &cbd->pos, 0.0, 1.0, 10, 0, "Sets the position of the active color");
1477 uiButSetFunc(bt, colorband_pos_cb, coba, NULL);
1478 uiDefButF(block, COL, redraw, "", xoffs,20+yoffs,110,20, &(cbd->r), 0, 0, 0, B_BANDCOL, "");
1479 uiDefButF(block, NUMSLI, redraw, "A ", xoffs,yoffs,110,20, &cbd->a, 0.0, 1.0, 10, 0, "Sets the alpha value for this position");
1481 uiBlockBeginAlign(block);
1482 uiDefButF(block, NUMSLI, redraw, "R ", 115+xoffs,40+yoffs,185,20, &cbd->r, 0.0, 1.0, B_BANDCOL, 0, "Sets the red value for the active color");
1483 uiDefButF(block, NUMSLI, redraw, "G ", 115+xoffs,20+yoffs,185,20, &cbd->g, 0.0, 1.0, B_BANDCOL, 0, "Sets the green value for the active color");
1484 uiDefButF(block, NUMSLI, redraw, "B ", 115+xoffs,yoffs,185,20, &cbd->b, 0.0, 1.0, B_BANDCOL, 0, "Sets the blue value for the active color");
1485 uiBlockEndAlign(block);
1488 void draw_colorband_buts_small(uiBlock *block, ColorBand *coba, rctf *butr, int event)
1492 float unit= (butr->xmax-butr->xmin)/14.0f;
1493 float xs= butr->xmin;
1495 cbd= coba->data + coba->cur;
1497 uiBlockBeginAlign(block);
1498 uiDefButF(block, COL, event, "", xs,butr->ymin+20.0f,2.0f*unit,20, &(cbd->r), 0, 0, 0, B_BANDCOL, "");
1499 uiDefButF(block, NUM, event, "A:", xs+2.0f*unit,butr->ymin+20.0f,4.0f*unit,20, &(cbd->a), 0.0f, 1.0f, 10, 2, "");
1500 bt= uiDefBut(block, BUT, event, "Add", xs+6.0f*unit,butr->ymin+20.0f,2.0f*unit,20, NULL, 0, 0, 0, 0, "Adds a new color position to the colorband");
1501 uiButSetFunc(bt, colorband_add_cb, coba, NULL);
1502 bt= uiDefBut(block, BUT, event, "Del", xs+8.0f*unit,butr->ymin+20.0f,2.0f*unit,20, NULL, 0, 0, 0, 0, "Deletes the active position");
1503 uiButSetFunc(bt, colorband_del_cb, coba, NULL);
1504 uiDefButS(block, ROW, event, "E", xs+10.0f*unit,butr->ymin+20.0f,unit,20, &coba->ipotype, 5.0, 1.0, 0, 0, "Sets interpolation type 'Ease' (quadratic) ");
1505 uiDefButS(block, ROW, event, "C", xs+11.0f*unit,butr->ymin+20.0f,unit,20, &coba->ipotype, 5.0, 3.0, 0, 0, "Sets interpolation type Cardinal");
1506 uiDefButS(block, ROW, event, "L", xs+12.0f*unit,butr->ymin+20.0f,unit,20, &coba->ipotype, 5.0, 0.0, 0, 0, "Sets interpolation type Linear");
1507 uiDefButS(block, ROW, event, "S", xs+13.0f*unit,butr->ymin+20.0f,unit,20, &coba->ipotype, 5.0, 2.0, 0, 0, "Sets interpolation type B-Spline");
1509 uiDefBut(block, BUT_COLORBAND, event, "", xs,butr->ymin,butr->xmax-butr->xmin,20.0f, coba, 0, 0, 0, 0, "");
1510 uiBlockEndAlign(block);
1514 static void texture_panel_colors(Tex *tex)
1518 block= uiNewBlock(&curarea->uiblocks, "texture_panel_colors", UI_EMBOSS, UI_HELV, curarea->win);
1519 uiNewPanelTabbed("Texture", "Texture");
1520 if(uiNewPanel(curarea, block, "Colors", "Texture", 1280, 0, 318, 204)==0) return;
1522 uiSetButLock(tex->id.lib!=NULL, ERROR_LIBDATA_MESSAGE);
1525 uiBlockBeginAlign(block);
1526 uiDefButBitS(block, TOG, TEX_COLORBAND, B_COLORBAND, "Colorband",10,180,80,20, &tex->flag, 0, 0, 0, 0, "Toggles colorband operations");
1528 if(tex->flag & TEX_COLORBAND) {
1529 draw_colorband_buts(block, tex->coba, 10, 85, B_TEXREDR_PRV);
1533 if((tex->flag & TEX_COLORBAND)==0) {
1534 uiBlockBeginAlign(block);
1535 uiDefButF(block, NUMSLI, B_TEXPRV, "R ", 60,80,200,20, &tex->rfac, 0.0, 2.0, 0, 0, "Changes the red value of the texture");
1536 uiDefButF(block, NUMSLI, B_TEXPRV, "G ", 60,60,200,20, &tex->gfac, 0.0, 2.0, 0, 0, "Changes the green value of the texture");
1537 uiDefButF(block, NUMSLI, B_TEXPRV, "B ", 60,40,200,20, &tex->bfac, 0.0, 2.0, 0, 0, "Changes the blue value of the texture");
1540 uiBlockBeginAlign(block);
1541 uiDefButF(block, NUMSLI, B_TEXPRV, "Bright", 10,10,150,20, &tex->bright, 0.0, 2.0, 0, 0, "Changes the brightness of the color or intensity of a texture");
1542 uiDefButF(block, NUMSLI, B_TEXPRV, "Contr", 160,10,150,20, &tex->contrast, 0.01, 5.0, 0, 0, "Changes the contrast of the color or intensity of a texture");
1546 static void texture_panel_texture(MTex *mtex, Material *ma, World *wrld, Lamp *la, bNode *node, Brush *br, SculptData *sd)
1550 ID *id=NULL, *idfrom;
1555 block= uiNewBlock(&curarea->uiblocks, "texture_panel_texture", UI_EMBOSS, UI_HELV, curarea->win);
1556 if(uiNewPanel(curarea, block, "Texture", "Texture", 320, 0, 318, 204)==0) return;
1558 /* first do the browse but */
1560 id= (ID *)mtex->tex;
1564 if(ma) idfrom= &ma->id;
1565 else if(wrld) idfrom= &wrld->id;
1566 else if(la) idfrom= &la->id;
1567 else if(br) idfrom= &br->id;
1568 else if(sd) idfrom= NULL; /* Not sure what this does */
1571 uiBlockSetCol(block, TH_BUT_SETTING2);
1573 std_libbuttons(block, 10, 180, 0, NULL, B_TEXBROWSE, ID_TE, 0, id, idfrom, &(G.buts->texnr), B_TEXALONE, B_TEXLOCAL, B_TEXDELETE, B_AUTOTEXNAME, B_KEEPDATA);
1576 std_libbuttons(block, 10, 180, 0, NULL, B_WTEXBROWSE, ID_TE, 0, id, idfrom, &(G.buts->texnr), B_TEXALONE, B_TEXLOCAL, B_TEXDELETE, B_AUTOTEXNAME, B_KEEPDATA);
1579 std_libbuttons(block, 10, 180, 0, NULL, B_LTEXBROWSE, ID_TE, 0, id, idfrom, &(G.buts->texnr), B_TEXALONE, B_TEXLOCAL, B_TEXDELETE, B_AUTOTEXNAME, B_KEEPDATA);
1582 std_libbuttons(block, 10, 180, 0, NULL, B_BTEXBROWSE, ID_TE, 0, id, idfrom, &(G.buts->menunr), B_TEXALONE, B_TEXLOCAL, B_TEXDELETE, B_AUTOTEXNAME, B_KEEPDATA);
1585 std_libbuttons(block, 10, 180, 0, NULL, B_SCULPT_TEXBROWSE, ID_TE, 0, id, idfrom, &(G.buts->texnr), B_TEXALONE, B_TEXLOCAL, B_TEXDELETE, B_AUTOTEXNAME, B_KEEPDATA);
1590 uiBlockSetCol(block, TH_BUT_NEUTRAL);
1594 /* From button: removed */
1598 uiBlockBeginAlign(block);
1600 for(a= 0; a<MAX_MTEX; a++) {
1602 if(ma) mt= ma->mtex[a];
1603 else if(wrld) mt= wrld->mtex[a];
1604 else if(la) mt= la->mtex[a];
1605 else if(br) mt= br->mtex[a];
1606 else if(sd) mt= sd->mtex[a];
1608 if(mt && mt->tex) splitIDname(mt->tex->id.name+2, str, &loos);
1609 else strcpy(str, "");
1613 uiDefButC(block, ROW, B_TEXCHANNEL, str, 10,yco,140,19, &(ma->texact), 0.0, (float)a, 0, 0, "Click to select texture channel");
1617 uiDefButS(block, ROW, B_TEXCHANNEL, str, 10,yco,140,19, &(wrld->texact), 0.0, (float)a, 0, 0, "");
1621 uiDefButS(block, ROW, B_TEXCHANNEL, str, 10,yco,140,19, &(la->texact), 0.0, (float)a, 0, 0, "");
1625 uiDefButS(block, ROW, B_TEXCHANNEL, str, 10,yco,140,19, &(br->texact), 0.0, (float)a, 0, 0, "");
1629 uiDefButS(block, ROW, B_TEXCHANNEL, str, 10,yco,140,19, &(sd->texact), 0.0, (float)a, 0, 0, "");
1633 uiBlockEndAlign(block);
1635 uiBlockSetCol(block, TH_AUTO);
1640 Tex *tex= (Tex *)id;
1642 uiSetButLock(tex->id.lib!=0, ERROR_LIBDATA_MESSAGE);
1644 /* newnoise: all texture types as menu, not enough room for more buttons.
1645 * Can widen panel, but looks ugly when other panels overlap it */
1647 sprintf(textypes, "Texture Type %%t|None %%x%d|Image %%x%d|EnvMap %%x%d|Clouds %%x%d|Marble %%x%d|Stucci %%x%d|Wood %%x%d|Magic %%x%d|Blend %%x%d|Noise %%x%d|Plugin %%x%d|Musgrave %%x%d|Voronoi %%x%d|DistortedNoise %%x%d", 0, TEX_IMAGE, TEX_ENVMAP, TEX_CLOUDS, TEX_MARBLE, TEX_STUCCI, TEX_WOOD, TEX_MAGIC, TEX_BLEND, TEX_NOISE, TEX_PLUGIN, TEX_MUSGRAVE, TEX_VORONOI, TEX_DISTNOISE);
1648 uiDefBut(block, LABEL, 0, "Texture Type", 160, 150, 140, 20, 0, 0.0, 0.0, 0, 0, "");
1649 uiDefButS(block, MENU, B_TEXTYPE, textypes, 160, 125, 140, 25, &tex->type, 0,0,0,0, "Select texture type");
1653 // label to avoid centering
1654 uiDefBut(block, LABEL, 0, " ", 160, 10, 140, 20, 0, 0, 0, 0, 0, "");
1658 static void texture_panel_preview(MTex *mtex, int preview)
1662 block= uiNewBlock(&curarea->uiblocks, "texture_panel_preview", UI_EMBOSS, UI_HELV, curarea->win);
1663 if(uiNewPanel(curarea, block, "Preview", "Texture", 0, 0, 318, 204)==0) return;
1665 if(preview) uiBlockSetDrawExtraFunc(block, BIF_previewdraw);
1667 // label to force a boundbox for buttons not to be centered
1668 uiDefBut(block, LABEL, 0, " ", 20,20,10,10, 0, 0, 0, 0, 0, "");
1670 uiBlockBeginAlign(block);
1671 uiDefButC(block, ROW, B_TEXREDR_PRV, "Mat", 200,175,80,25, &G.buts->texfrom, 3.0, 0.0, 0, 0, "Displays the textures of the active material");
1672 uiDefButC(block, ROW, B_TEXREDR_PRV, "World", 200,150,80,25, &G.buts->texfrom, 3.0, 1.0, 0, 0, "Displays the textures of the world block");
1673 uiDefButC(block, ROW, B_TEXREDR_PRV, "Lamp", 200,125,80,25, &G.buts->texfrom, 3.0, 2.0, 0, 0, "Displays the textures of the selected lamp");
1674 uiDefButC(block, ROW, B_TEXREDR_PRV, "Brush", 200,100,80,25, &G.buts->texfrom, 3.0, 3.0, 0, 0, "Displays the textures of the selected brush");
1675 uiBlockEndAlign(block);
1677 if(mtex && mtex->tex) {
1678 uiDefButBitS(block, TOG, TEX_PRV_ALPHA, B_TEXREDR_PRV, "Alpha", 200,60,80,20, &mtex->tex->flag, 0, 0, 0, 0, "Show alpha in preview");
1679 uiSetButLock(mtex->tex->id.lib!=NULL, ERROR_LIBDATA_MESSAGE);
1680 uiDefBut(block, BUT, B_DEFTEXVAR, "Default Vars",200,10,80,20, 0, 0, 0, 0, 0, "Sets all values to defaults");
1686 /* *************************** RADIO ******************************** */
1688 void do_radiobuts(unsigned short event)
1694 rad= G.scene->radio;
1699 BIF_undo_push("Add radiosity");
1700 allqueue(REDRAWBUTSSHADING, 0);
1701 allqueue(REDRAWVIEW3D, 0);
1705 BIF_undo_push("Delete radiosity");
1706 allqueue(REDRAWBUTSSHADING, 0);
1707 allqueue(REDRAWVIEW3D, 0);
1711 allqueue(REDRAWBUTSSHADING, 0);
1712 allqueue(REDRAWVIEW3D, 0);
1715 rad_collect_meshes();
1716 allqueue(REDRAWBUTSSHADING, 0);
1717 allqueue(REDRAWVIEW3D, 0);
1720 if(phase==RAD_PHASE_PATCHES) {
1721 rad_limit_subdivide();
1722 allqueue(REDRAWBUTSSHADING, 0);
1723 allqueue(REDRAWVIEW3D, 0);
1727 if(phase==RAD_PHASE_PATCHES) {
1729 rad_subdivshootpatch();
1730 allqueue(REDRAWBUTSSHADING, 0);
1731 allqueue(REDRAWVIEW3D, 0);
1736 if(phase==RAD_PHASE_PATCHES) {
1738 rad_subdivshootelem();
1739 allqueue(REDRAWBUTSSHADING, 0);
1740 allqueue(REDRAWVIEW3D, 0);
1745 if(phase==RAD_PHASE_PATCHES) {
1749 allqueue(REDRAWBUTSSHADING, 0);
1750 allqueue(REDRAWVIEW3D, 0);
1755 allqueue(REDRAWVIEW3D, 0);
1756 allqueue(REDRAWBUTSSHADING, 0);
1760 if(phase & RAD_PHASE_FACES) make_face_tab();
1761 else make_node_display(); /* radio solver also uses nodes, different ones :) */
1762 allqueue(REDRAWVIEW3D, 0);
1765 if(phase & RAD_PHASE_FACES) {
1767 removeEqualNodes(rad->nodelim);
1769 allqueue(REDRAWVIEW3D, 0);
1770 allqueue(REDRAWBUTSSHADING, 0);
1773 case B_RAD_NODEFILT:
1774 if(phase & RAD_PHASE_FACES) {
1778 allqueue(REDRAWVIEW3D, 0);
1781 case B_RAD_FACEFILT:
1782 if(phase & RAD_PHASE_FACES) {
1784 allqueue(REDRAWVIEW3D, 0);
1789 allqueue(REDRAWVIEW3D, 0);
1792 if(phase & RAD_PHASE_FACES) rad_addmesh();
1793 BIF_undo_push("Radiosity add mesh");
1794 allqueue(REDRAWVIEW3D, 0);
1797 if(phase & RAD_PHASE_FACES) rad_replacemesh();
1798 BIF_undo_push("Radiosity replace mesh");
1799 allqueue(REDRAWVIEW3D, 0);
1806 static void radio_panel_calculation(Radio *rad, int flag)
1810 block= uiNewBlock(&curarea->uiblocks, "radio_panel_calculation", UI_EMBOSS, UI_HELV, curarea->win);
1811 if(uiNewPanel(curarea, block, "Calculation", "Radio", 640, 0, 318, 204)==0) return;
1812 uiAutoBlock(block, 10, 10, 300, 200, UI_BLOCK_ROWS);
1814 if(flag != RAD_PHASE_PATCHES) uiBlockSetCol(block, TH_BUT_NEUTRAL);
1815 uiDefBut(block, BUT, B_RAD_GO, "GO", 0, 0, 10, 15, NULL, 0, 0, 0, 0, "Starts the radiosity simulation");
1817 uiBlockSetCol(block, TH_AUTO);
1818 uiDefButS(block, NUM, B_NOP, "SubSh Patch:", 1, 0, 10, 10, &rad->subshootp, 0.0, 10.0, 0, 0, "Sets the number of times the environment is tested to detect pathes");
1819 uiDefButS(block, NUM, B_NOP, "SubSh Element:", 1, 0, 10, 10, &rad->subshoote, 0.0, 10.0, 0, 0, "Sets the number of times the environment is tested to detect elements");
1821 if(flag != RAD_PHASE_PATCHES) uiBlockSetCol(block, TH_BUT_NEUTRAL);
1822 uiDefBut(block, BUT, B_RAD_SHOOTE, "Subdiv Shoot Element", 2, 0, 10, 10, NULL, 0, 0, 0, 0, "For pre-subdivision, Detects high energy changes and subdivide Elements");
1823 uiDefBut(block, BUT, B_RAD_SHOOTP, "Subdiv Shoot Patch", 2, 0, 10, 10, NULL, 0, 0, 0, 0, "For pre-subdivision, Detects high energy changes and subdivide Patches");
1825 uiBlockSetCol(block, TH_AUTO);
1826 uiDefButI(block, NUM, B_NOP, "MaxEl:", 3, 0, 10, 10, &rad->maxnode, 1.0, 250000.0, 0, 0, "Sets the maximum allowed number of elements");
1827 uiDefButS(block, NUM, B_NOP, "Max Subdiv Shoot:", 3, 0, 10, 10, &rad->maxsublamp, 1.0, 250.0, 0, 0, "Sets the maximum number of initial shoot patches that are evaluated");
1829 if(flag & RAD_PHASE_FACES);
1830 else uiBlockSetCol(block, TH_BUT_NEUTRAL);
1831 uiDefBut(block, BUT, B_RAD_FACEFILT, "FaceFilter", 4, 0, 10, 10, NULL, 0, 0, 0, 0, "Forces an extra smoothing");
1832 uiDefBut(block, BUT, B_RAD_NODEFILT, "Element Filter", 4, 0, 10, 10, NULL, 0, 0, 0, 0, "Filters elements to remove aliasing artefacts");
1834 uiDefBut(block, BUT, B_RAD_NODELIM, "RemoveDoubles", 5, 0, 30, 10, NULL, 0.0, 50.0, 0, 0, "Joins elements which differ less than 'Lim'");
1835 uiBlockSetCol(block, TH_AUTO);
1836 uiDefButS(block, NUM, B_NOP, "Lim:", 5, 0, 10, 10, &rad->nodelim, 0.0, 50.0, 0, 0, "Sets the range for removing doubles");
1841 static void radio_panel_tool(Radio *rad, int flag)
1845 block= uiNewBlock(&curarea->uiblocks, "radio_panel_tool", UI_EMBOSS, UI_HELV, curarea->win);
1846 if(uiNewPanel(curarea, block, "Radio Tool", "Radio", 320, 0, 318, 204)==0) return;
1847 uiAutoBlock(block, 10, 10, 300, 200, UI_BLOCK_ROWS);
1849 if(flag & RAD_PHASE_PATCHES) uiBlockSetCol(block, TH_BUT_SETTING1);
1850 uiDefBut(block, BUT, B_RAD_COLLECT, "Collect Meshes", 0, 0, 10, 15, NULL, 0, 0, 0, 0, "Converts selected visible meshes to patches");
1852 if(flag & RAD_PHASE_PATCHES)uiBlockSetCol(block, TH_AUTO);
1853 else uiBlockSetCol(block, TH_BUT_NEUTRAL);
1854 uiDefBut(block, BUT, B_RAD_FREE, "Free Radio Data", 0, 0, 10, 15, NULL, 0, 0, 0, 0, "Releases all memory used by Radiosity");
1856 if(flag & RAD_PHASE_FACES) uiBlockSetCol(block, TH_AUTO);
1857 else uiBlockSetCol(block, TH_BUT_NEUTRAL);
1858 uiDefBut(block, BUT, B_RAD_REPLACE, "Replace Meshes", 1, 0, 10, 12, NULL, 0, 0, 0, 0, "Converts meshes to Mesh objects with vertex colors, changing input-meshes");
1859 uiDefBut(block, BUT, B_RAD_ADDMESH, "Add new Meshes", 1, 0, 10, 12, NULL, 0, 0, 0, 0, "Converts meshes to Mesh objects with vertex colors, unchanging input-meshes");
1861 uiBlockSetCol(block, TH_AUTO);
1862 uiDefButS(block, ROW, B_RAD_DRAW, "Wire", 2, 0, 10, 10, &rad->drawtype, 0.0, 0.0, 0, 0, "Enables wireframe drawmode");
1863 uiDefButS(block, ROW, B_RAD_DRAW, "Solid", 2, 0, 10, 10, &rad->drawtype, 0.0, 1.0, 0, 0, "Enables solid drawmode");
1864 uiDefButS(block, ROW, B_RAD_DRAW, "Gour", 2, 0, 10, 10, &rad->drawtype, 0.0, 2.0, 0, 0, "Enables Gourad drawmode");
1865 uiDefButBitS(block, TOG, 1, B_RAD_DRAW, "ShowLim", 2, 0, 10, 10, &rad->flag, 0, 0, 0, 0, "Draws patch and element limits");
1866 uiDefButBitS(block, TOG, 2, B_RAD_DRAW, "Z", 2, 0, 3, 10, &rad->flag, 0, 0, 0, 0, "Draws limits differently");
1868 uiDefButS(block, NUM, B_RAD_LIMITS, "ElMax:", 3, 0, 10, 10, &rad->elma, 1.0, 500.0, 0, 0, "Sets maximum size of an element");
1869 uiDefButS(block, NUM, B_RAD_LIMITS, "ElMin:", 3, 0, 10, 10, &rad->elmi, 1.0, 100.0, 0, 0, "Sets minimum size of an element");
1870 uiDefButS(block, NUM, B_RAD_LIMITS, "PaMax:", 3, 0, 10, 10, &rad->pama, 10.0, 1000.0, 0, 0, "Sets maximum size of a patch");
1871 uiDefButS(block, NUM, B_RAD_LIMITS, "PaMin:", 3, 0, 10, 10, &rad->pami, 10.0, 1000.0, 0, 0, "Sets minimum size of a patch");
1873 uiDefBut(block, BUT, B_RAD_INIT, "Limit Subdivide", 5, 0, 10, 10, NULL, 0, 0, 0, 0, "Subdivides patches");
1877 static void radio_panel_render(Radio *rad)
1881 block= uiNewBlock(&curarea->uiblocks, "radio_panel_render", UI_EMBOSS, UI_HELV, curarea->win);
1882 if(uiNewPanel(curarea, block, "Radio Render", "Radio", 0, 0, 318, 204)==0) return;
1883 uiAutoBlock(block, 210, 30, 230, 150, UI_BLOCK_ROWS);
1885 uiDefButS(block, NUMSLI, B_RAD_LIMITS, "Hemires:", 0, 0, 10, 10, &rad->hemires, 100.0, 1000.0, 100, 0, "Sets the size of a hemicube");
1886 uiDefButS(block, NUM, B_NOP, "Max Iterations:", 2, 0, 10, 15, &rad->maxiter, 0.0, 10000.0, 0, 0, "Limits the maximum number of radiosity rounds");
1887 uiDefButF(block, NUM, B_RAD_FAC, "Mult:", 3, 0, 10, 15, &rad->radfac, 0.001, 250.0, 100, 0, "Mulitplies the energy values");
1888 uiDefButF(block, NUM, B_RAD_FAC, "Gamma:", 3, 0, 10, 15, &rad->gamma, 0.2, 10.0, 10, 0, "Changes the contrast of the energy values");
1889 uiDefButF(block, NUMSLI, B_NOP, "Convergence:", 5, 0, 10, 10, &rad->convergence, 0.0, 1.0, 10, 0, "Sets the lower threshold of unshot energy");
1893 /* ***************************** WORLD ************************** */
1895 void do_worldbuts(unsigned short event)
1897 static short mtexcopied=0;
1898 static MTex mtexcopybuf;
1904 case B_TEXCLEARWORLD:
1905 wrld= G.buts->lockpoin;
1906 mtex= wrld->mtex[ wrld->texact ];
1908 if(mtex->tex) mtex->tex->id.us--;
1910 wrld->mtex[ wrld->texact ]= 0;
1911 allqueue(REDRAWBUTSSHADING, 0);
1912 allqueue(REDRAWOOPS, 0);
1913 BIF_undo_push("Unlink world texture");
1914 BIF_preview_changed(ID_WO);
1918 wrld= G.buts->lockpoin;
1919 if(wrld && wrld->mtex[(int)wrld->texact] ) {
1920 mtex= wrld->mtex[(int)wrld->texact];
1921 if(mtex->tex==NULL) {
1922 error("No texture available");
1925 memcpy(&mtexcopybuf, wrld->mtex[(int)wrld->texact], sizeof(MTex));
1931 wrld= G.buts->lockpoin;
1932 if(wrld && mtexcopied && mtexcopybuf.tex) {
1933 if(wrld->mtex[(int)wrld->texact]==NULL )
1934 wrld->mtex[(int)wrld->texact]= MEM_mallocN(sizeof(MTex), "mtex");
1935 else if(wrld->mtex[(int)wrld->texact]->tex)
1936 wrld->mtex[(int)wrld->texact]->tex->id.us--;
1938 memcpy(wrld->mtex[(int)wrld->texact], &mtexcopybuf, sizeof(MTex));
1940 id_us_plus((ID *)mtexcopybuf.tex);
1941 BIF_undo_push("Paste mapping settings");
1942 BIF_preview_changed(ID_WO);
1943 scrarea_queue_winredraw(curarea);
1947 wrld= G.buts->lockpoin;
1948 if(wrld && (int)wrld->texact > 0) {
1949 mtexswap = wrld->mtex[(int)wrld->texact];
1950 wrld->mtex[(int)wrld->texact] = wrld->mtex[((int)wrld->texact)-1];
1951 wrld->mtex[((int)wrld->texact)-1] = mtexswap;
1953 allqueue(REDRAWBUTSSHADING, 0);
1956 case B_WMTEXMOVEDOWN:
1957 wrld= G.buts->lockpoin;
1958 if(wrld && (int)wrld->texact < MAX_MTEX-1) {
1959 mtexswap = wrld->mtex[(int)wrld->texact];
1960 wrld->mtex[(int)wrld->texact] = wrld->mtex[((int)wrld->texact)+1];
1961 wrld->mtex[((int)wrld->texact)+1] = mtexswap;
1963 allqueue(REDRAWBUTSSHADING, 0);
1967 /* falloff distances option only supports plain */
1968 wrld= G.buts->lockpoin;
1970 wrld->aocolor= WO_AOPLAIN;
1971 scrarea_queue_winredraw(curarea);
1976 static void world_panel_mapto(World *wrld)
1981 block= uiNewBlock(&curarea->uiblocks, "world_panel_mapto", UI_EMBOSS, UI_HELV, curarea->win);
1982 uiNewPanelTabbed("Texture and Input", "World");
1983 if(uiNewPanel(curarea, block, "Map To", "World", 1280, 0, 318, 204)==0) return;
1985 uiSetButLock(wrld->id.lib!=0, ERROR_LIBDATA_MESSAGE);
1987 mtex= wrld->mtex[ wrld->texact ];
1991 mtex->texco= TEXCO_VIEW;
1994 /* TEXTURE OUTPUT */
1995 uiBlockBeginAlign(block);
1996 uiDefButBitS(block, TOG, MTEX_STENCIL, B_WORLDPRV, "Stencil", 10,125,45,19, &(mtex->texflag), 0, 0, 0, 0, "Use this texture as a blending value on the next texture");
1997 uiDefButBitS(block, TOG, MTEX_NEGATIVE, B_WORLDPRV, "Neg", 55,125,30,19, &(mtex->texflag), 0, 0, 0, 0, "Inverts the values of the texture to reverse its effect");
1998 uiDefButBitS(block, TOG, MTEX_RGBTOINT, B_WORLDPRV, "No RGB", 85,125,60,19, &(mtex->texflag), 0, 0, 0, 0, "Converts texture RGB values to intensity (gray) values");
1999 uiBlockEndAlign(block);
2001 uiBlockBeginAlign(block);
2002 uiDefButF(block, COL, B_WORLDPRV, "", 10,100,135,19, &(mtex->r), 0, 0, 0, B_MTEXCOL, "");
2003 uiDefButF(block, NUMSLI, B_WORLDPRV, "R ", 10,80,135,19, &(mtex->r), 0.0, 1.0, B_MTEXCOL, 0, "The default color for textures that don't return RGB");
2004 uiDefButF(block, NUMSLI, B_WORLDPRV, "G ", 10,60,135,19, &(mtex->g), 0.0, 1.0, B_MTEXCOL, 0, "The default color for textures that don't return RGB");
2005 uiDefButF(block, NUMSLI, B_WORLDPRV, "B ", 10,40,135,19, &(mtex->b), 0.0, 1.0, B_MTEXCOL, 0, "The default color for textures that don't return RGB");
2006 uiBlockEndAlign(block);
2007 uiDefButF(block, NUMSLI, B_WORLDPRV, "DVar ", 10,10,135,19, &(mtex->def_var), 0.0, 1.0, 0, 0, "Value to use for Ref, Spec, Amb, Emit, Alpha, RayMir, TransLu and Hard");
2010 uiBlockBeginAlign(block);
2011 uiDefButBitS(block, TOG, WOMAP_BLEND, B_WORLDPRV, "Blend", 10,180,75,19, &(mtex->mapto), 0, 0, 0, 0, "Causes the texture to affect the color progression of the background");
2012 uiDefButBitS(block, TOG, WOMAP_HORIZ, B_WORLDPRV, "Hori", 85,180,75,19, &(mtex->mapto), 0, 0, 0, 0, "Causes the texture to affect the color of the horizon");
2013 uiDefButBitS(block, TOG, WOMAP_ZENUP, B_WORLDPRV, "ZenUp", 160,180,75,19, &(mtex->mapto), 0, 0, 0, 0, "Causes the texture to affect the color of the zenith above");
2014 uiDefButBitS(block, TOG, WOMAP_ZENDOWN, B_WORLDPRV, "ZenDo", 235,180,75,19, &(mtex->mapto), 0, 0, 0, 0, "Causes the texture to affect the color of the zenith below");
2015 uiBlockEndAlign(block);
2017 uiBlockBeginAlign(block);
2018 uiDefButS(block, MENU, B_WORLDPRV, mapto_blendtype_pup(),155,125,155,19, &(mtex->blendtype), 0, 0, 0, 0, "Texture blending mode");
2019 uiBlockEndAlign(block);
2021 uiBlockBeginAlign(block);
2022 uiDefButF(block, NUMSLI, B_WORLDPRV, "Col ", 155,100,155,19, &(mtex->colfac), 0.0, 1.0, 0, 0, "Sets the amount the texture affects color values");
2023 uiDefButF(block, NUMSLI, B_WORLDPRV, "Nor ", 155,80,155,19, &(mtex->norfac), 0.0, 1.0, 0, 0, "Sets the amount the texture affects normal values");
2024 uiDefButF(block, NUMSLI, B_WORLDPRV, "Var ", 155,60,155,19, &(mtex->varfac), 0.0, 1.0, 0, 0, "Sets the amount the texture affects other values");
2028 static void world_panel_texture(World *wrld)
2034 char str[64], *strp;
2036 block= uiNewBlock(&curarea->uiblocks, "world_panel_texture", UI_EMBOSS, UI_HELV, curarea->win);
2037 if(uiNewPanel(curarea, block, "Texture and Input", "World", 960, 0, 318, 204)==0) return;
2039 uiSetButLock(wrld->id.lib!=0, ERROR_LIBDATA_MESSAGE);
2042 uiBlockSetCol(block, TH_BUT_NEUTRAL);
2043 uiBlockBeginAlign(block);
2044 for(a= 0; a<MAX_MTEX; a++) {
2045 mtex= wrld->mtex[a];
2046 if(mtex && mtex->tex) splitIDname(mtex->tex->id.name+2, str, &loos);
2047 else strcpy(str, "");
2049 uiDefButS(block, ROW, REDRAWBUTSSHADING, str,10, 160-18*a, 80, 20, &(wrld->texact), 3.0, (float)a, 0, 0, "Texture channel");
2051 uiBlockEndAlign(block);
2053 mtex= wrld->mtex[ wrld->texact ];
2057 mtex->texco= TEXCO_VIEW;
2060 /* TEXTUREBLOCK SELECT */
2061 uiBlockSetCol(block, TH_BUT_SETTING2);
2062 id= (ID *)mtex->tex;
2063 IDnames_to_pupstring(&strp, NULL, "ADD NEW %x 32767", &(G.main->tex), id, &(G.buts->texnr));
2064 uiDefButS(block, MENU, B_WTEXBROWSE, strp, 100,140,20,19, &(G.buts->texnr), 0, 0, 0, 0, "Selects an existing texture or creates new");
2068 uiDefBut(block, TEX, B_IDNAME, "TE:", 100,160,200,19, id->name+2, 0.0, 21.0, 0, 0, "Displays name of the texture block: click to change");
2069 sprintf(str, "%d", id->us);
2070 uiDefBut(block, BUT, 0, str, 177,140,21,19, 0, 0, 0, 0, 0, "Displays number of users of texture: click to make single user");
2071 uiDefIconBut(block, BUT, B_AUTOTEXNAME, ICON_AUTO, 155,140,21,19, 0, 0, 0, 0, 0, "Auto-assigns name to texture");
2073 if(wrld->id.lib) uiDefIconBut(block, BUT, 0, ICON_DATALIB, 219,140,21,19, 0, 0, 0, 0, 0, "");
2074 else uiDefIconBut(block, BUT, 0, ICON_PARLIB, 219,140,21,19, 0, 0, 0, 0, 0, "");
2076 uiBlockSetCol(block, TH_AUTO);
2077 uiDefBut(block, BUT, B_TEXCLEARWORLD, "Clear", 122, 140, 32, 19, 0, 0, 0, 0, 0, "Erases link to texture");
2080 uiDefButS(block, TOG, B_WTEXBROWSE, "Add New" ,100, 160, 200, 19, &(G.buts->texnr), -1.0, 32767.0, 0, 0, "Adds a new texture datablock");
2082 uiBlockSetCol(block, TH_AUTO);
2084 /* copy/paste/up/down */
2085 uiBlockBeginAlign(block);
2086 uiDefIconBut(block, BUT, B_WMTEXCOPY, ICON_COPYUP, 200,140,25,19, 0, 0, 0, 0, 0, "Copies the mapping settings to the buffer");
2087 uiDefIconBut(block, BUT, B_WMTEXPASTE, ICON_PASTEUP, 225,140,25,19, 0, 0, 0, 0, 0, "Pastes the mapping settings from the buffer");
2088 uiDefIconBut(block, BUT, B_WMTEXMOVEUP, VICON_MOVE_UP, 250,140,25,19, 0, 0, 0, 0, 0, "Move texture channel up");
2089 uiDefIconBut(block, BUT, B_WMTEXMOVEDOWN, VICON_MOVE_DOWN, 275,140,25,19, 0, 0, 0, 0, 0, "Move texture channel down");
2092 uiBlockBeginAlign(block);
2093 uiDefButS(block, ROW, B_WORLDPRV, "View", 100,110,100,20, &(mtex->texco), 4.0, (float)TEXCO_VIEW, 0, 0, "Uses view vector for the texture coordinates");
2094 uiDefButS(block, ROW, B_WORLDPRV, "Global", 200,110,100,20, &(mtex->texco), 4.0, (float)TEXCO_GLOB, 0, 0, "Uses global coordinates for the texture coordinates (interior mist)");
2096 uiDefButS(block, ROW, B_WORLDPRV, "AngMap", 100,90,70,20, &(mtex->texco), 4.0, (float)TEXCO_ANGMAP, 0, 0, "Uses 360 degree angular coordinates, e.g. for spherical light probes");
2097 uiDefButS(block, ROW, B_WORLDPRV, "Sphere", 170,90,65,20, &(mtex->texco), 4.0, (float)TEXCO_H_SPHEREMAP, 0, 0, "For 360 degree panorama sky, spherical mapped, only top half");
2098 uiDefButS(block, ROW, B_WORLDPRV, "Tube", 235,90,65,20, &(mtex->texco), 4.0, (float)TEXCO_H_TUBEMAP, 0, 0, "For 360 degree panorama sky, cylindrical mapped, only top half");
2100 uiDefButS(block, ROW, B_WORLDPRV, "Object", 100,70,70,20, &(mtex->texco), 4.0, (float)TEXCO_OBJECT, 0, 0, "Uses linked object's coordinates for texture coordinates");
2101 uiDefIDPoinBut(block, test_obpoin_but, ID_OB, B_WORLDPRV, "OB:", 170,70,130,20, &(mtex->object), "Object name to use for mapping");
2103 uiBlockBeginAlign(block);
2104 uiDefButF(block, NUM, B_WORLDPRV, "dX", 100,40,100,19, mtex->ofs, -20.0, 20.0, 10, 0, "Fine tunes texture mapping X coordinate");
2105 uiDefButF(block, NUM, B_WORLDPRV, "dY", 100,20,100,19, mtex->ofs+1, -20.0, 20.0, 10, 0, "Fine tunes texture mapping Y coordinate");
2106 uiDefButF(block, NUM, B_WORLDPRV, "dZ", 100, 0,100,19, mtex->ofs+2, -20.0, 20.0, 10, 0, "Fine tunes texture mapping Z coordinate");
2107 uiBlockBeginAlign(block);
2108 uiDefButF(block, NUM, B_WORLDPRV, "sizeX", 200,40,100,19, mtex->size, -10.0, 10.0, 10, 0, "Sets scaling for the texture's X size");
2109 uiDefButF(block, NUM, B_WORLDPRV, "sizeY", 200,20,100,19, mtex->size+1, -10.0, 10.0, 10, 0, "Sets scaling for the texture's Y size");
2110 uiDefButF(block, NUM, B_WORLDPRV, "sizeZ", 200, 0,100,19, mtex->size+2, -10.0, 10.0, 10, 0, "Sets scaling for the texture's Z size");
2114 static void world_panel_mistaph(World *wrld)
2118 block= uiNewBlock(&curarea->uiblocks, "world_panel_mistaph", UI_EMBOSS, UI_HELV, curarea->win);
2119 if(uiNewPanel(curarea, block, "Mist / Stars / Physics", "World", 640, 0, 318, 204)==0) return;
2121 uiSetButLock(wrld->id.lib!=0, ERROR_LIBDATA_MESSAGE);
2123 #if GAMEBLENDER == 1
2124 uiDefButI(block, MENU, 1,
2126 "Physics %t|None %x0|Sumo %x2|Ode %x4 |Bullet %x5",
2128 //"Physics %t|None %x0|Sumo %x2|Bullet %x5", //disable Sumo, until too many people complain ;-)
2129 "Physics %t|None %x0|Sumo (deprecated) %x2|Bullet %x5",
2131 10,180,140,19, &wrld->physicsEngine, 0, 0, 0, 0,
2134 /* Gravitation for the game worlds */
2135 uiDefButF(block, NUMSLI,0, "Grav ", 150,180,150,19, &(wrld->gravity), 0.0, 25.0, 0, 0, "Sets the gravitation constant of the game world");
2138 uiBlockSetCol(block, TH_BUT_SETTING1);
2139 uiDefButBitS(block, TOG, WO_MIST, B_WORLDPRV2,"Mist", 10,120,140,19, &wrld->mode, 0, 0, 0, 0, "Toggles mist simulation");
2140 uiBlockSetCol(block, TH_AUTO);
2142 uiBlockBeginAlign(block);
2143 uiDefButS(block, ROW, B_WORLDPRV2, "Quad", 10, 90, 40, 19, &wrld->mistype, 1.0, 0.0, 0, 0, "Mist uses quadratic progression");
2144 uiDefButS(block, ROW, B_WORLDPRV2, "Lin", 50, 90, 50, 19, &wrld->mistype, 1.0, 1.0, 0, 0, "Mist uses linear progression");
2145 uiDefButS(block, ROW, B_WORLDPRV2, "Sqr", 100, 90, 50, 19, &wrld->mistype, 1.0, 2.0, 0, 0, "Mist uses inverse quadratic progression");
2146 uiBlockBeginAlign(block);
2147 uiDefButF(block, NUM,B_WORLDPRV2, "Start:",10,70,140,19, &wrld->miststa, 0.0, 10000.0, 10, 0, "Specifies the starting distance of the mist");
2148 uiDefButF(block, NUM,B_WORLDPRV2, "Dist:",10,50,140,19, &wrld->mistdist, 0.0,10000.0, 10, 00, "Specifies the depth of the mist");
2149 uiDefButF(block, NUM,B_WORLDPRV2,"Height:", 10,30,140,19, &wrld->misthi,0.0,100.0, 10, 0, "Specifies the factor for a less dense mist with increasing height");
2150 uiDefButF(block, NUMSLI, B_WORLDPRV2, "Misi ", 10,10,140,19, &(wrld->misi), 0., 1.0, 0, 0, "Sets the mist intensity");
2151 uiBlockEndAlign(block);
2153 uiBlockSetCol(block, TH_BUT_SETTING1);
2154 uiDefButBitS(block, TOG, WO_STARS, B_WORLDPRV2, "Stars",160,120,140,19, &wrld->mode, 0, 0, 0, 0, "Toggles starfield generation");
2155 uiBlockSetCol(block, TH_AUTO);
2157 uiBlockBeginAlign(block);
2158 uiDefButF(block, NUM,B_WORLDPRV2,"StarDist:", 160,70,140,19, &(wrld->stardist), 2.0, 1000.0, 100, 0, "Specifies the average distance between any two stars");
2159 uiDefButF(block, NUM,B_WORLDPRV2,"MinDist:", 160,50,140,19, &(wrld->starmindist), 0.0, 1000.0, 100, 0, "Specifies the minimum distance to the camera for stars");
2160 uiDefButF(block, NUMSLI,B_WORLDPRV2,"Size:", 160,30,140,19, &(wrld->starsize), 0.0, 10.0, 10, 0, "Specifies the average screen dimension of stars");
2161 uiDefButF(block, NUMSLI,B_WORLDPRV2,"Colnoise:", 160,10,140,19, &(wrld->starcolnoise), 0.0, 1.0, 100, 0, "Randomizes star color");
2162 uiBlockEndAlign(block);
2166 static void world_panel_amb_occ(World *wrld)
2169 short yco=PANEL_YMAX;
2171 block= uiNewBlock(&curarea->uiblocks, "world_panel_amb_oc", UI_EMBOSS, UI_HELV, curarea->win);
2172 uiNewPanelTabbed("Mist / Stars / Physics", "World");
2173 if(uiNewPanel(curarea, block, "Amb Occ", "World", PANELX, PANELY, PANELW, PANELH)==0) return;
2174 uiSetButLock(wrld->id.lib!=0, ERROR_LIBDATA_MESSAGE);
2177 uiBlockSetCol(block, TH_BUT_SETTING1);
2178 uiDefButBitS(block, TOG, WO_AMB_OCC, B_REDR, "Ambient Occlusion",
2179 X2CLM1, yco-=BUTH, BUTW1, BUTH, &wrld->mode, 0, 0, 0, 0, "Toggles ambient occlusion (soft shadows)");
2180 uiBlockSetCol(block, TH_AUTO);
2182 if(!(wrld->mode & WO_AMB_OCC)) return;
2186 if(wrld->ao_gather_method == WO_AOGATHER_RAYTRACE) {
2187 uiDefButS(block, NUM, B_REDR, "Samples:",
2188 X2CLM1, yco-=BUTH, BUTW2, BUTH, &wrld->aosamp, 1.0, 32.0, 100, 0, "Sets the number of samples used for AO (actual number: squared)");
2192 uiDefButF(block, NUM, B_REDR, "Max Dist:",
2193 X2CLM1, yco-=BUTH, BUTW2, BUTH, &wrld->aodist, 0.001, 5000.0, 100, 0, "Sets length of AO rays, defines how far away other faces give occlusion effect");
2196 uiDefButS(block, NUM, B_REDR, "Passes:",
2197 X2CLM1, yco-=BUTH, BUTW2, BUTH, &wrld->ao_approx_passes, 0.0, 10.0, 0, 0, "Sets the number of preprocessing passes to reduce overocclusion");
2201 uiDefButF(block, NUM, B_REDR, "Correction:",
2202 X2CLM1, yco-=BUTH, BUTW2, BUTH, &wrld->ao_approx_correction, 0.0, 1.0, 0, 0, "Ad-hoc correction for over-occlusion due to the approximation.");
2205 uiBlockBeginAlign(block);
2206 uiDefButBitS(block, TOG, WO_AODIST, B_AO_FALLOFF, "Use Falloff",
2207 X2CLM1, yco-=BUTH, BUTW2, BUTH, &wrld->aomode, 0, 0, 0, 0, "When enabled, distances to objects will be used to attenuate shadows. Only for Plain AO.");
2208 if (wrld->aomode & WO_AODIST)
2209 uiDefButF(block, NUM, B_REDR, "Strength:",
2210 X2CLM1, yco-=BUTH, BUTW2, BUTH, &wrld->aodistfac, 0.00001, 10.0, 100, 0, "Distance attenuation factor, the higher, the 'shorter' the shadows");
2211 uiBlockEndAlign(block);
2214 yco = PANEL_YMAX - BUTH - YSPACE;
2216 uiDefButS(block, MENU, B_REDR, "Gather Method%t|Raytrace %x0|Approximate %x1",
2217 X2CLM2, yco-=BUTH, BUTW2, BUTH, &wrld->ao_gather_method, 0, 0, 0, 0, "Method for occlusion gathering: Raytrace: slow when noise free results are required, but accurate, Approximate: faster and without noise, but inaccurate");
2221 if(wrld->ao_gather_method == WO_AOGATHER_RAYTRACE) {
2222 uiDefButS(block, MENU, B_REDR, "Constant QMC %x2|Adaptive QMC %x1|Constant Jittered %x0",
2223 X2CLM2, yco-=BUTH, BUTW2, BUTH, &wrld->ao_samp_method, 0, 0, 0, 0, "Method for generating shadow samples: Constant QMC: best quality, Adaptive QMC: fast in high contrast areas");
2227 if (wrld->ao_samp_method == WO_AOSAMP_HALTON) {
2228 uiBlockBeginAlign(block);
2229 uiDefButF(block, NUM, B_REDR, "Threshold:",
2230 X2CLM2, yco-=BUTH, BUTW2, BUTH, &wrld->ao_adapt_thresh, 0.0, 1.0, 100, 0, "Samples below this threshold will be considered fully shadowed/unshadowed and skipped");
2231 uiDefButF(block, NUMSLI, B_REDR, "Adapt Vec:",
2232 X2CLM2, yco-=BUTH, BUTW2, BUTH, &wrld->ao_adapt_speed_fac, 0.0, 1.0, 100, 0, "Use the speed vector pass to reduce AO samples in fast moving pixels. The higher the value, the more aggressive the sample reduction. Requires Vec pass enabled.");
2233 uiBlockEndAlign(block);
2234 } else if (wrld->ao_samp_method == WO_AOSAMP_CONSTANT) {
2235 uiDefButF(block, NUMSLI, B_REDR, "Bias:",
2236 X2CLM2, yco-=BUTH, BUTW2, BUTH, &wrld->aobias, 0.0, 0.5, 10, 0, "Sets bias to prevent smoothed faces to show banding (in radians)");
2240 uiBlockBeginAlign(block);
2241 uiDefButF(block, NUM, B_REDR, "Error:",
2242 X2CLM2, yco-=BUTH, BUTW2, BUTH, &wrld->ao_approx_error, 0.0001, 10.0, 0, 0, "Error tolerance (low values are slower and higher quality)");
2244 uiDefButBitS(block, TOG, WO_AOCACHE, B_REDR, "Pixel Cache",
2245 X2CLM2, yco-=BUTH, BUTW2, BUTH, &wrld->aomode, 0, 0, 0, 0, "Cache AO results in pixels and interpolate over neighbouring pixels for speedup.");
2246 uiBlockEndAlign(block);
2249 yco = PANEL_YMAX - (5*BUTH+4*YSPACE);
2251 /* result mix modes */
2252 uiBlockBeginAlign(block);
2253 uiDefButS(block, ROW, B_REDR, "Add",
2254 X3CLM1, yco-=BUTH, BUTW3, BUTH, &wrld->aomix, 1.0, (float)WO_AOADD, 0, 0, "adds light/shadows");
2255 uiDefButS(block, ROW, B_REDR, "Sub",
2256 X3CLM2, yco, BUTW3, BUTH, &wrld->aomix, 1.0, (float)WO_AOSUB, 0, 0, "subtracts light/shadows (needs at least one normal light to make anything visible)");
2257 uiDefButS(block, ROW, B_REDR, "Both",
2258 X3CLM3, yco, BUTW3, BUTH, &wrld->aomix, 1.0, (float)WO_AOADDSUB, 0, 0, "both lightens & darkens");
2259 uiBlockEndAlign(block);
2263 /* color treatment */
2264 uiBlockBeginAlign(block);
2265 uiDefButS(block, ROW, B_REDR, "Plain",
2266 X3CLM1, yco-=BUTH, BUTW3, BUTH, &wrld->aocolor, 2.0, (float)WO_AOPLAIN, 0, 0, "Plain diffuse energy (white)");
2267 uiDefButS(block, ROW, B_REDR, "Sky Color",
2268 X3CLM2, yco, BUTW3, BUTH, &wrld->aocolor, 2.0, (float)WO_AOSKYCOL, 0, 0, "Use horizon and zenith color for diffuse energy");
2269 if(wrld->ao_gather_method == WO_AOGATHER_RAYTRACE)
2270 uiDefButS(block, ROW, B_REDR, "Sky Texture",
2271 X3CLM3, yco, BUTW3, BUTH, &wrld->aocolor, 2.0, (float)WO_AOSKYTEX, 0, 0, "Does full Sky texture render for diffuse energy");
2272 uiBlockEndAlign(block);
2276 uiDefButF(block, NUMSLI, B_REDR, "Energy:",
2277 X2CLM1, yco-=BUTH, BUTW2, BUTH, &wrld->aoenergy, 0.01, 3.0, 100, 0, "Sets global energy scale for AO");
2280 static void world_panel_world(World *wrld)
2284 block= uiNewBlock(&curarea->uiblocks, "world_panel_world", UI_EMBOSS, UI_HELV, curarea->win);
2285 if(uiNewPanel(curarea, block, "World", "World", 320, 0, 318, 204)==0) return;
2287 uiBlockSetCol(block, TH_BUT_SETTING2);
2288 std_libbuttons(block, 10, 180, 0, NULL, B_WORLDBROWSE, ID_WO, 0, (ID *)wrld, (ID *)G.scene, &(G.buts->menunr), B_WORLDALONE, B_WORLDLOCAL, B_WORLDDELETE, 0, B_KEEPDATA);
2290 if(wrld==NULL) return;
2292 uiSetButLock(wrld->id.lib!=0, ERROR_LIBDATA_MESSAGE);
2293 uiBlockSetCol(block, TH_AUTO);
2295 uiBlockBeginAlign(block);
2296 uiDefButF(block, COL, B_WORLDPRV, "", 10,150,145,19, &wrld->horr, 0, 0, 0, B_COLHOR, "");
2297 uiDefButF(block, NUMSLI,B_WORLDPRV,"HoR ", 10,130,145,19, &(wrld->horr), 0.0, 1.0, B_COLHOR,0, "Sets the amount of red color at the horizon");
2298 uiDefButF(block, NUMSLI,B_WORLDPRV,"HoG ", 10,110,145,19, &(wrld->horg), 0.0, 1.0, B_COLHOR,0, "Sets the amount of green color at the horizon");
2299 uiDefButF(block, NUMSLI,B_WORLDPRV,"HoB ", 10,90,145,19, &(wrld->horb), 0.0, 1.0, B_COLHOR,0, "Sets the amount of blue color at the horizon");
2301 uiBlockBeginAlign(block);
2302 uiDefButF(block, COL, B_WORLDPRV, "", 160,150,145,19, &wrld->zenr, 0, 0, 0, B_COLZEN, "");
2303 uiDefButF(block, NUMSLI,B_WORLDPRV,"ZeR ", 160,130,145,19, &(wrld->zenr), 0.0, 1.0, B_COLZEN,0, "Sets the amount of red color at the zenith");
2304 uiDefButF(block, NUMSLI,B_WORLDPRV,"ZeG ", 160,110,145,19, &(wrld->zeng), 0.0, 1.0, B_COLZEN,0, "Sets the amount of green color at the zenith");
2305 uiDefButF(block, NUMSLI,B_WORLDPRV,"ZeB ", 160,90,145,19, &(wrld->zenb), 0.0, 1.0, B_COLZEN,0, "Sets the amount of blue color at the zenith");
2307 uiBlockBeginAlign(block);
2308 uiDefButF(block, COL, B_WORLDPRV, "", 10,70,145,19, &wrld->ambr, 0, 0, 0, 0, "");
2309 uiDefButF(block, NUMSLI,B_WORLDPRV,"AmbR ", 10,50,145,19, &(wrld->ambr), 0.0, 1.0 ,0,0, "Sets the amount of red ambient color");
2310 uiDefButF(block, NUMSLI,B_WORLDPRV,"AmbG ", 10,30,145,19, &(wrld->ambg), 0.0, 1.0 ,0,0, "Sets the amount of green ambient color");
2311 uiDefButF(block, NUMSLI,B_WORLDPRV,"AmbB ", 10,10,145,19, &(wrld->ambb), 0.0, 1.0 ,0,0, "Sets the amount of blue ambient color");
2313 uiBlockBeginAlign(block);
2314 uiBlockSetCol(block, TH_BUT_SETTING1);
2315 uiDefButF(block, NUMSLI,B_WORLDPRV2, "Exp ", 160,30,145,19, &(wrld->exp), 0.0, 1.0, 0, 2, "Sets amount of exponential color correction for light");
2316 uiDefButF(block, NUMSLI,B_WORLDPRV2, "Range ", 160,10,145,19, &(wrld->range), 0.2, 5.0, 0, 2, "Sets the color amount that will be mapped on color 1.0");
2321 static void world_panel_preview(World *wrld)
2325 /* name "Preview" is abused to detect previewrender offset panel */
2326 block= uiNewBlock(&curarea->uiblocks, "world_panel_preview", UI_EMBOSS, UI_HELV, curarea->win);
2327 if(uiNewPanel(curarea, block, "Preview", "World", 0, 0, 318, 204)==0) return;
2329 if(wrld==NULL) return;
2331 uiSetButLock(wrld->id.lib!=0, ERROR_LIBDATA_MESSAGE);
2333 uiBlockSetDrawExtraFunc(block, BIF_previewdraw);
2335 // label to force a boundbox for buttons not to be centered
2336 uiDefBut(block, LABEL, 0, " ", 20,20,10,10, 0, 0, 0, 0, 0, "");
2338 uiBlockBeginAlign(block);
2339 uiDefButBitS(block, TOG, WO_SKYREAL, B_WORLDPRV,"Real", 200,175,80,25, &wrld->skytype, 0, 0, 0, 0, "Renders background with a real horizon");
2340 uiDefButBitS(block, TOG, WO_SKYBLEND, B_WORLDPRV,"Blend",200,150,80,25, &wrld->skytype, 0, 0, 0, 0, "Renders background with natural progression from horizon to zenith");
2341 uiDefButBitS(block, TOG,WO_SKYPAPER, B_WORLDPRV,"Paper",200,125,80,25, &wrld->skytype, 0, 0, 0, 0, "Flattens blend or texture coordinates");
2342 uiBlockEndAlign(block);
2346 /* ************************ LAMP *************************** */
2348 void do_lampbuts(unsigned short event)
2350 static short mtexcopied=0;
2351 static MTex mtexcopybuf;
2358 BIF_preview_changed(ID_LA);
2359 allqueue(REDRAWVIEW3D, 0);
2360 allqueue(REDRAWBUTSSHADING, 0);
2362 case B_TEXCLEARLAMP:
2363 la= G.buts->lockpoin;
2364 mtex= la->mtex[ la->texact ];
2366 if(mtex->tex) mtex->tex->id.us--;
2368 la->mtex[ la->texact ]= 0;
2369 BIF_undo_push("Unlink world texture");
2370 allqueue(REDRAWBUTSSHADING, 0);
2371 allqueue(REDRAWOOPS, 0);
2372 BIF_preview_changed(ID_LA);
2376 la= G.buts->lockpoin;
2377 la->bufsize = la->bufsize&=(~15);
2378 allqueue(REDRAWBUTSSHADING, 0);
2379 allqueue(REDRAWOOPS, 0);
2382 la= G.buts->lockpoin;
2383 la->mode &= ~LA_SHAD_RAY;
2384 allqueue(REDRAWBUTSSHADING, 0);
2385 allqueue(REDRAWVIEW3D, 0);
2388 la= G.buts->lockpoin;
2389 la->mode &= ~LA_SHAD_BUF;
2390 /* yafray: 'softlight' uses it's own shadbuf. flag.
2391 Must be cleared here too when switching from ray shadow */
2392 la->mode &= ~LA_YF_SOFT;
2393 allqueue(REDRAWBUTSSHADING, 0);
2394 allqueue(REDRAWVIEW3D, 0);
2397 la= G.buts->lockpoin;
2398 if(la && la->mtex[(int)la->texact] ) {
2399 mtex= la->mtex[(int)la->texact];
2400 if(mtex->tex==NULL) {
2401 error("No texture available");
2404 memcpy(&mtexcopybuf, la->mtex[(int)la->texact], sizeof(MTex));
2410 la= G.buts->lockpoin;
2411 if(la && mtexcopied && mtexcopybuf.tex) {
2412 if(la->mtex[(int)la->texact]==NULL )
2413 la->mtex[(int)la->texact]= MEM_mallocN(sizeof(MTex), "mtex");
2414 else if(la->mtex[(int)la->texact]->tex)
2415 la->mtex[(int)la->texact]->tex->id.us--;
2417 memcpy(la->mtex[(int)la->texact], &mtexcopybuf, sizeof(MTex));
2419 id_us_plus((ID *)mtexcopybuf.tex);
2420 BIF_undo_push("Paste mapping settings");
2421 BIF_preview_changed(ID_LA);
2422 scrarea_queue_winredraw(curarea);
2426 la= G.buts->lockpoin;
2427 if(la && (int)la->texact > 0) {
2428 mtexswap = la->mtex[(int)la->texact];
2429 la->mtex[(int)la->texact] = la->mtex[((int)la->texact)-1];
2430 la->mtex[((int)la->texact)-1] = mtexswap;
2432 allqueue(REDRAWBUTSSHADING, 0);
2435 case B_LMTEXMOVEDOWN:
2436 la= G.buts->lockpoin;
2437 if(la && (int)la->texact < MAX_MTEX-1) {
2438 mtexswap = la->mtex[(int)la->texact];
2439 la->mtex[(int)la->texact] = la->mtex[((int)la->texact)+1];
2440 la->mtex[((int)la->texact)+1] = mtexswap;
2442 allqueue(REDRAWBUTSSHADING, 0);
2445 case B_LFALLOFFCHANGED:
2446 la= G.buts->lockpoin;
2447 curvemapping_changed(la->curfalloff, 1);
2448 BIF_undo_push("Edit Lamp falloff curve");
2449 BIF_preview_changed(ID_LA);
2450 scrarea_queue_winredraw(curarea);
2457 static void lamp_panel_mapto(Object *ob, Lamp *la)
2462 block= uiNewBlock(&curarea->uiblocks, "lamp_panel_mapto", UI_EMBOSS, UI_HELV, curarea->win);
2463 uiNewPanelTabbed("Texture and Input", "Lamp");
2464 if(uiNewPanel(curarea, block, "Map To", "Lamp", 1280, 0, 318, 204)==0) return;
2466 uiSetButLock(la->id.lib!=0, ERROR_LIBDATA_MESSAGE);
2468 mtex= la->mtex[ la->texact ];
2472 mtex->texco= TEXCO_VIEW;
2475 /* TEXTURE OUTPUT */
2476 uiBlockBeginAlign(block);
2477 uiDefButBitS(block, TOG, MTEX_STENCIL, B_LAMPPRV, "Stencil", 10,125,45,19, &(mtex->texflag), 0, 0, 0, 0, "Use this texture as a blending value on the next texture");
2478 uiDefButBitS(block, TOG, MTEX_NEGATIVE, B_LAMPPRV, "Neg", 55,125,30,19, &(mtex->texflag), 0, 0, 0, 0, "Inverts the values of the texture to reverse its effect");
2479 uiDefButBitS(block, TOG, MTEX_RGBTOINT, B_LAMPPRV, "No RGB", 85,125,60,19, &(mtex->texflag), 0, 0, 0, 0, "Converts texture RGB values to intensity (gray) values");
2480 uiBlockEndAlign(block);
2482 uiBlockBeginAlign(block);
2483 uiDefButF(block, COL, B_LAMPPRV, "", 10,100,135,19, &(mtex->r), 0, 0, 0, B_MTEXCOL, "");
2484 uiDefButF(block, NUMSLI, B_LAMPPRV, "R ", 10,80,135,19, &(mtex->r), 0.0, 1.0, B_MTEXCOL, 0, "The default color for textures that don't return RGB");
2485 uiDefButF(block, NUMSLI, B_LAMPPRV, "G ", 10,60,135,19, &(mtex->g), 0.0, 1.0, B_MTEXCOL, 0, "The default color for textures that don't return RGB");
2486 uiDefButF(block, NUMSLI, B_LAMPPRV, "B ", 10,40,135,19, &(mtex->b), 0.0, 1.0, B_MTEXCOL, 0, "The default color for textures that don't return RGB");
2487 uiBlockEndAlign(block);
2488 uiDefButF(block, NUMSLI, B_LAMPPRV, "DVar ", 10,10,135,19, &(mtex->def_var), 0.0, 1.0, 0, 0, "Value to use for Ref, Spec, Amb, Emit, Alpha, RayMir, TransLu and Hard");
2491 uiDefButBitS(block, TOG, MAP_COL, B_LAMPPRV, "Col", 10,180,135,19, &(mtex->mapto), 0, 0, 0, 0, "Lets the texture affect the basic color of the lamp");
2493 uiBlockBeginAlign(block);
2494 uiDefButS(block, MENU, B_LAMPPRV, mapto_blendtype_pup(),155,125,155,19, &(mtex->blendtype), 0, 0, 0, 0, "Texture blending mode");
2495 uiBlockEndAlign(block);
2497 uiDefButF(block, NUMSLI, B_LAMPPRV, "Col ", 155,100,155,19, &(mtex->colfac), 0.0, 1.0, 0, 0, "Sets the amount the texture affects color values");
2502 static void lamp_panel_texture(Object *ob, Lamp *la)
2508 char *strp, str[64];
2510 block= uiNewBlock(&curarea->uiblocks, "lamp_panel_texture", UI_EMBOSS, UI_HELV, curarea->win);
2511 if(uiNewPanel(curarea, block, "Texture and Input", "Lamp", 960, 0, 318, 204)==0) return;
2513 uiSetButLock(la->id.lib!=0, ERROR_LIBDATA_MESSAGE);
2516 uiBlockSetCol(block, TH_BUT_NEUTRAL);
2517 uiBlockBeginAlign(block);
2518 for(a= 0; a<MAX_MTEX; a++) {
2520 if(mtex && mtex->tex) splitIDname(mtex->tex->id.name+2, str, &loos);
2521 else strcpy(str, "");
2523 uiDefButS(block, ROW, B_REDR, str, 10, 160-18*a, 80, 20, &(la->texact), 3.0, (float)a, 0, 0, "");
2525 uiBlockEndAlign(block);
2527 mtex= la->mtex[ la->texact ];
2531 mtex->texco= TEXCO_VIEW;
2534 /* TEXTUREBLOK SELECT */
2535 uiBlockSetCol(block, TH_BUT_SETTING2);
2536 id= (ID *)mtex->tex;
2537 IDnames_to_pupstring(&strp, NULL, "ADD NEW %x 32767", &(G.main->tex), id, &(G.buts->texnr));
2539 /* doesnt work, because lockpoin points to lamp, not to texture */
2540 uiDefButS(block, MENU, B_LTEXBROWSE, strp, 100,140,20,19, &(G.buts->texnr), 0, 0, 0, 0, "Selects an existing texture or creates new");
2544 uiDefBut(block, TEX, B_IDNAME, "TE:", 100,160,200,19, id->name+2, 0.0, 21.0, 0, 0, "Displays name of the texture block: click to change");
2545 sprintf(str, "%d", id->us);
2546 uiDefBut(block, BUT, 0, str, 155,140,21,19, 0, 0, 0, 0, 0, "Displays number of users of texture: click to make single user");
2547 uiDefIconBut(block, BUT, B_AUTOTEXNAME, ICON_AUTO, 177,140,21,19, 0, 0, 0, 0, 0, "Auto-assigns name to texture");
2549 if(la->id.lib) uiDefIconBut(block, BUT, 0, ICON_DATALIB, 219,140,21,19, 0, 0, 0, 0, 0, "");
2550 else uiDefIconBut(block, BUT, 0, ICON_PARLIB, 219,140,21,19, 0, 0, 0, 0, 0, "");
2552 uiBlockSetCol(block, TH_AUTO);
2553 uiDefBut(block, BUT, B_TEXCLEARLAMP, "Clear", 122, 140, 32, 19, 0, 0, 0, 0, 0, "Erases link to texture");
2556 uiDefButS(block, TOG, B_LTEXBROWSE, "Add New" ,100, 160, 200, 19, &(G.buts->texnr), -1.0, 32767.0, 0, 0, "Adds a new texture datablock");
2558 /* copy/paste/up/down */
2559 uiBlockBeginAlign(block);
2560 uiDefIconBut(block, BUT, B_LMTEXCOPY, ICON_COPYUP, 200,140,25,19, 0, 0, 0, 0, 0, "Copies the mapping settings to the buffer");
2561 uiDefIconBut(block, BUT, B_LMTEXPASTE, ICON_PASTEUP, 225,140,25,19, 0, 0, 0, 0, 0, "Pastes the mapping settings from the buffer");
2562 uiDefIconBut(block, BUT, B_LMTEXMOVEUP, VICON_MOVE_UP, 250,140,25,19, 0, 0, 0, 0, 0, "Move texture channel up");
2563 uiDefIconBut(block, BUT, B_LMTEXMOVEDOWN, VICON_MOVE_DOWN, 275,140,25,19, 0, 0, 0, 0, 0, "Move texture channel down");
2567 uiBlockSetCol(block, TH_AUTO);
2568 uiBlockBeginAlign(block);
2569 uiDefButS(block, ROW, B_LAMPPRV, "Glob", 100,110,60,20, &(mtex->texco), 4.0, (float)TEXCO_GLOB, 0, 0, "Uses global coordinates for the texture coordinates");
2570 uiDefButS(block, ROW, B_LAMPPRV, "View", 160,110,70,20, &(mtex->texco), 4.0, (float)TEXCO_VIEW, 0, 0, "Uses view coordinates for the texture coordinates");
2571 uiDefButS(block, ROW, B_LAMPPRV, "Object", 230,110,70,20, &(mtex->texco), 4.0, (float)TEXCO_OBJECT, 0, 0, "Uses linked object's coordinates for texture coordinates");
2572 uiDefIDPoinBut(block, test_obpoin_but, ID_OB, B_LAMPPRV, "", 100,90,200,20, &(mtex->object), "");
2574 uiBlockBeginAlign(block);
2575 uiDefButF(block, NUM, B_LAMPPRV, "dX", 100,50,100,18, mtex->ofs, -20.0, 20.0, 10, 0, "Fine tunes texture mapping X coordinate");
2576 uiDefButF(block, NUM, B_LAMPPRV, "dY", 100,30,100,18, mtex->ofs+1, -20.0, 20.0, 10, 0, "Fine tunes texture mapping Y coordinate");
2577 uiDefButF(block, NUM, B_LAMPPRV, "dZ", 100,10,100,18, mtex->ofs+2, -20.0, 20.0, 10, 0, "Fine tunes texture mapping Z coordinate");
2578 uiBlockBeginAlign(block);
2579 uiDefButF(block, NUM, B_LAMPPRV, "sizeX", 200,50,100,18, mtex->size, -10.0, 10.0, 10, 0, "Sets scaling for the texture's X size");
2580 uiDefButF(block, NUM, B_LAMPPRV, "sizeY", 200,30,100,18, mtex->size+1, -10.0, 10.0, 10, 0, "Sets scaling for the texture's Y size");
2581 uiDefButF(block, NUM, B_LAMPPRV, "sizeZ", 200,10,100,18, mtex->size+2, -10.0, 10.0, 10, 0, "Sets scaling for the texture's Z size");
2582 uiBlockEndAlign(block);
2585 static void lamp_panel_spot(Object *ob, Lamp *la)
2590 block= uiNewBlock(&curarea->uiblocks, "lamp_panel_spot", UI_EMBOSS, UI_HELV, curarea->win);
2591 if(uiNewPanel(curarea, block, "Shadow and Spot", "Lamp", 640, 0, 318, 224)==0) return;
2593 /* hemis and ray shadow dont work at all... */
2594 /* yafray: ignore photonlight as well */
2595 if ((la->type==LA_HEMI) || (la->type==LA_YF_PHOTON)) return;
2597 if(G.vd) grid= G.vd->grid;
2598 if(grid<1.0) grid= 1.0;
2600 uiSetButLock(la->id.lib!=0, ERROR_LIBDATA_MESSAGE);
2602 uiBlockSetCol(block, TH_BUT_SETTING1);
2603 uiBlockBeginAlign(block);
2604 uiDefButBitS(block, TOG, LA_SHAD_RAY, B_SHADRAY,"Ray Shadow",10,180,80,19,&la->mode, 0, 0, 0, 0, "Use ray tracing for shadow");
2605 if(la->type==LA_SPOT) {
2606 uiDefButBitS(block, TOG, LA_SHAD_BUF, B_SHADBUF, "Buf.Shadow",10,160,80,19,&la->mode, 0, 0, 0, 0, "Lets spotlight produce shadows using shadow buffer");
2607 if(la->mode & LA_SHAD_BUF) {
2608 char *tip= "Regular buffer type";
2609 if(la->buftype==LA_SHADBUF_IRREGULAR)
2610 tip= "Irregular buffer produces sharp shadow always, but it doesn't show up for raytracing";
2611 else if(la->buftype==LA_SHADBUF_HALFWAY)
2612 tip= "Regular buffer, averaging the closest and 2nd closest Z value for reducing biasing";
2614 uiDefButC(block, MENU, B_REDR, "Classical %x0|Classic-Halfway %x2|Irregular %x1", 10,140,80,19,&la->buftype, 0, 0, 0, 0, tip);
2617 uiBlockEndAlign(block);
2619 uiDefButBitS(block, TOG, LA_ONLYSHADOW, B_LAMPPRV,"OnlyShadow", 10,110,80,19,&la->mode, 0, 0, 0, 0, "Causes light to cast shadows only without illuminating objects");
2621 if(la->type==LA_SPOT) {
2622 uiBlockBeginAlign(block);
2623 uiDefButBitS(block, TOG, LA_SQUARE, B_LAMPREDRAW,"Square", 10,60,80,19,&la->mode, 0, 0, 0, 0, "Sets square spotbundles");
2624 uiDefButBitS(block, TOG, LA_HALO, B_LAMPREDRAW,"Halo", 10,40,80,19,&la->mode, 0, 0, 0, 0, "Renders spotlight with a volumetric halo");
2626 uiBlockBeginAlign(block);
2627 uiDefButF(block, NUMSLI,B_LAMPREDRAW,"SpotSi ", 100,180,200,19,&la->spotsize, 1.0, 180.0, 0, 0, "Sets the angle of the spotlight beam in degrees");
2628 uiDefButF(block, NUMSLI,B_LAMPREDRAW,"SpotBl ", 100,160,200,19,&la->spotblend, 0.0, 1.0, 0, 0, "Sets the softness of the spotlight edge");
2629 uiBlockEndAlign(block);
2631 uiDefButF(block, NUMSLI,B_LAMPREDRAW,"HaloInt ", 100,135,200,19,&la->haint, 0.0, 5.0, 0, 0, "Sets the intensity of the spotlight halo");
2633 if(la->mode & LA_SHAD_BUF) {
2634 if(ELEM(la->buftype, LA_SHADBUF_REGULAR, LA_SHADBUF_HALFWAY)) {
2635 uiBlockBeginAlign(block);
2636 uiDefButS(block, NUM,B_SBUFF,"ShadowBufferSize:", 100,110,200,19, &la->bufsize,512,10240, 0, 0, "Sets the size of the shadow buffer to nearest multiple of 16");
2637 uiDefButS(block, ROW,B_NOP, "Box", 100,90,65,19, &la->filtertype, 0.0, LA_SHADBUF_BOX, 0, 0, "Apply Box filter for shadowbuffer samples");
2638 uiDefButS(block, ROW,B_NOP, "Tent", 165,90,65,19, &la->filtertype, 0.0, LA_SHADBUF_TENT, 0, 0, "Apply Tent filter for shadowbuffer samples");
2639 uiDefButS(block, ROW,B_NOP, "Gauss", 230,90,70,19, &la->filtertype, 0.0, LA_SHADBUF_GAUSS, 0, 0, "Apply Gauss filter for shadowbuffer samples");
2641 uiBlockBeginAlign(block);
2642 uiDefButS(block, ROW,B_NOP,"SampleBuffers: 1", 100,-15,140,19, &la->buffers, 1.0, 1.0, 0, 0, "Only one lampbuffer rendered");
2643 uiDefButS(block, ROW,B_NOP,"4", 240,-15,30,19, &la->buffers, 1.0, 4.0, 0, 0, "Renders 4 lampbuffers for better AA, this quadruples memory usage");
2644 uiDefButS(block, ROW,B_NOP,"9", 270,-15,30,19, &la->buffers, 1.0, 9.0, 0, 0, "Renders 9 lampbuffers for better AA, this uses nine times more memory");
2646 uiBlockBeginAlign(block);
2647 uiDefButS(block, NUM,B_LAMPREDRAW,"Samples:", 100,60,100,19, &la->samp,1.0,16.0, 0, 0, "Sets the number of shadow map samples");
2648 uiDefButS(block, NUM,B_NOP,"Halo step:", 200,60,100,19, &la->shadhalostep, 0.0, 12.0, 0, 0, "Sets the volumetric halo sampling frequency");
2649 uiDefButF(block, NUM,B_LAMPREDRAW,"Bias:", 100,40,100,19, &la->bias, 0.001, 5.0, 1, 0, "Sets the shadow map sampling bias");
2650 uiDefButF(block, NUM,B_LAMPREDRAW,"Soft:", 200,40,100,19, &la->soft,1.0,100.0, 100, 0, "Sets the size of the shadow sample area");
2652 else { /* LA_SHADBUF_IRREGULAR */
2653 uiDefButF(block, NUM,B_LAMPREDRAW,"Bias:", 100,40,100,19, &la->bias, 0.01, 5.0, 1, 0, "Sets the shadow map sampling bias");
2656 uiBlockBeginAlign(block);
2657 uiDefIconButBitC(block, TOG, LA_SHADBUF_AUTO_START, B_REDR, ICON_AUTO, 10, 10, 25, 19, &la->bufflag, 0.0, 0.0, 0, 0, "Automatic calculation of clipping-start, based on visible vertices");
2658 if(la->bufflag & LA_SHADBUF_AUTO_START)
2659 uiDefBut(block, LABEL, B_NOP, "ClipSta: Auto", 35,10,115,19, NULL, 0, 0, 0, 0, "");
2661 uiDefButF(block, NUM,REDRAWVIEW3D,"ClipSta:", 35,10,115,19, &la->clipsta, 0.1*grid,1000.0*grid, 10, 0, "Sets the shadow map clip start: objects closer will not generate shadows");
2662 uiDefIconButBitC(block, TOG, LA_SHADBUF_AUTO_END, B_REDR, ICON_AUTO, 160, 10, 25, 19, &la->bufflag, 0.0, 0.0, 0, 0, "Automatic calculation of clipping-end, based on visible vertices");
2663 if(la->bufflag & LA_SHADBUF_AUTO_END)
2664 uiDefBut(block, LABEL,B_NOP, "ClipEnd: Auto", 185,10,115,19, NULL, 0, 0, 0, 0, "");
2666 uiDefButF(block, NUM,REDRAWVIEW3D,"ClipEnd:", 185,10,115,19,&la->clipend, 1.0, 5000.0*grid, 100, 0, "Sets the shadow map clip end beyond which objects will not generate shadows");
2667 uiBlockEndAlign(block);
2671 if(ELEM4(la->type, LA_AREA, LA_SPOT, LA_SUN, LA_LOCAL) && (la->mode & LA_SHAD_RAY)) {
2673 if (ELEM3(la->type, LA_SPOT, LA_SUN, LA_LOCAL)) {
2674 if (la->ray_samp_method == LA_SAMP_CONSTANT) la->ray_samp_method = LA_SAMP_HALTON;
2676 uiDefButS(block, MENU, B_REDR, "Adaptive QMC %x1|Constant QMC %x2",
2677 100,110,200,19, &la->ray_samp_method, 0, 0, 0, 0, "Method for generating shadow samples: Adaptive QMC is fastest, Constant QMC is less noisy but slower");
2679 uiDefButF(block, NUM,B_LAMPREDRAW,"Soft Size", 100,80,200,19, &la->area_size, 0.01, 100.0, 10, 0, "Area light size, doesn't affect energy amount");
2681 uiDefButS(block, NUM,0,"Samples:", 100,60,200,19, &la->ray_samp, 1.0, 16.0, 100, 0, "Sets the amount of samples taken extra (samp x samp)");
2682 uiDefButF(block, NUM,0,"Threshold:", 100,40,200,19, &la->adapt_thresh, 0.0, 1.0, 100, 0, "Threshold for adaptive sampling, to control what level is considered already in shadow");
2684 else if (la->type == LA_AREA) {
2685 uiDefButS(block, MENU, B_REDR, "Adaptive QMC %x1|Constant QMC %x2|Constant Jittered %x0",
2686 100,180,200,19, &la->ray_samp_method, 0, 0, 0, 0, "Method for generating shadow samples: Adaptive QMC is fastest");
2688 if(la->area_shape==LA_AREA_SQUARE)
2689 uiDefButS(block, NUM,0,"Samples:", 100,150,200,19, &la->ray_samp, 1.0, 16.0, 100, 0, "Sets the amount of samples taken extra (samp x samp)");
2690 else if(la->area_shape==LA_AREA_CUBE)
2691 uiDefButS(block, NUM,0,"Samples:", 100,130,200,19, &la->ray_samp, 1.0, 16.0, 100, 0, "Sets the amount of samples taken extra (samp x samp x samp)");
2693 if (ELEM(la->area_shape, LA_AREA_RECT, LA_AREA_BOX)) {
2694 uiDefButS(block, NUM,0,"SamplesX:", 100,150,200,19, &la->ray_samp, 1.0, 16.0, 100, 0, "Sets the amount of X samples taken extra");
2695 uiDefButS(block, NUM,0,"SamplesY:", 100,130,200,19, &la->ray_sampy, 1.0, 16.0, 100, 0, "Sets the amount of Y samples taken extra");
2696 if(la->area_shape==LA_AREA_BOX)
2697 uiDefButS(block, NUM,0,"SamplesZ:", 100,110,200,19, &la->ray_sampz, 1.0, 8.0, 100, 0, "Sets the amount of Z samples taken extra");
2700 if (la->ray_samp_method == LA_SAMP_CONSTANT) {
2701 uiBlockBeginAlign(block);
2702 uiDefButBitS(block, TOG, LA_SAMP_UMBRA, 0,"Umbra", 100,90,200,19,&la->ray_samp_type, 0, 0, 0, 0, "Emphasis parts that are fully shadowed");
2703 uiDefButBitS(block, TOG, LA_SAMP_DITHER, 0,"Dither", 100,70,100,19,&la->ray_samp_type, 0, 0, 0, 0, "Use 2x2 dithering for sampling");
2704 uiDefButBitS(block, TOG, LA_SAMP_JITTER, 0,"Noise", 200,70,100,19,&la->ray_samp_type, 0, 0, 0, 0, "Use noise for sampling");
2705 } else if (la->ray_samp_method == LA_SAMP_HALTON) {
2706 uiDefButF(block, NUM,0,"Threshold:", 100,90,200,19, &la->adapt_thresh, 0.0, 1.0, 100, 0, "Threshold for adaptive sampling, to control what level is considered already in shadow");
2712 else uiDefBut(block, LABEL,0," ", 100,180,200,19,NULL, 0, 0, 0, 0, "");
2716 /* yafray: adaptation of lamp_panel_spot above with yafray specific parameters */
2717 static void lamp_panel_yafray(Object *ob, Lamp *la)
2721 block= uiNewBlock(&curarea->uiblocks, "lamp_panel_yafray", UI_EMBOSS, UI_HELV, curarea->win);
2722 if(uiNewPanel(curarea, block, "Yafray: Shadow and Photons", "Lamp", 640, 0, 318, 204)==0) return;
2724 /* hemis not used in yafray */
2725 if(la->type==LA_HEMI) return;
2727 uiSetButLock(la->id.lib!=0, ERROR_LIBDATA_MESSAGE);
2729 /* photonlight params */
2730 if (la->type==LA_YF_PHOTON) {
2731 uiBlockSetCol(block, TH_BUT_SETTING1);
2732 uiDefButBitS(block, TOG, 1, B_DIFF,"Use QMC",10,180,80,19,&la->YF_useqmc, 0, 0, 0, 0, "Use QMC sampling (sometimes visible patterns)");
2733 uiBlockSetCol(block, TH_AUTO);
2734 uiDefButF(block, NUMSLI,B_LAMPREDRAW,"Angle ", 100,180,200,19,&la->spotsize, 1.0, 180.0, 0, 0, "Sets the angle of the photonlight beam in degrees");
2735 uiDefButI(block, NUM,B_DIFF,"photons:", 10,150,290,19, &la->YF_numphotons, 10000, 100000000, 0, 0, "Maximum number of photons to shoot");
2736 uiDefButI(block, NUM,B_DIFF,"search:", 10,130,290,19, &la->YF_numsearch, 100, 1000, 0, 0, "Number of photons to mix (blur)");
2737 uiDefButS(block, NUM,B_DIFF,"depth:", 10,100,290,19, &la->YF_phdepth, 1, 100, 0, 0, "Maximum caustic bounce depth");
2738 uiDefButF(block, NUM,B_DIFF,"Blur:", 10,70,290,19, &la->YF_causticblur, 0.01, 1.0, 1, 0, "Amount of caustics blurring (also depends on search)");
2742 uiBlockSetCol(block, TH_BUT_SETTING1);
2744 /* in yafray arealights always cast shadows, so ray shadow flag not needed */
2745 /* ray shadow also not used when halo for spot enabled */
2746 if ((la->type!=LA_AREA) && (!((la->type==LA_SPOT) && (la->mode & LA_HALO))))
2747 uiDefButBitS(block, TOG, LA_SHAD_RAY, B_SHADRAY,"Ray Shadow",10,180,80,19,&la->mode, 0, 0, 0, 0, "Use ray tracing for shadow");
2749 /* in yafray the regular lamp can use shadowbuffers (softlight), used by spot with halo as well */
2750 /* to prevent clash with blender shadowbuf flag, a special flag is used for yafray */
2751 if (la->type==LA_LOCAL) {
2752 uiDefButBitS(block, TOG, LA_YF_SOFT, B_SHADBUF, "Buf.Shadow",10,160,80,19,&la->mode, 0, 0, 0, 0, "Lets light produce shadows using shadow buffer");
2753 uiDefButF(block, NUM, B_DIFF, "GloInt:", 100,155,200,19, &la->YF_glowint, 0.0, 1.0, 1, 0, "Sets light glow intensity, 0 is off");
2754 uiDefButF(block, NUM, B_DIFF, "GloOfs:", 100,135,100,19, &la->YF_glowofs, 0.0, 2.0, 1, 0, "Sets light glow offset, the higher, the less 'peaked' the glow");
2755 uiDefButS(block, NUM, B_DIFF, "GlowType:", 200,135,100,19, &la->YF_glowtype, 0, 1, 1, 0, "Sets light glow type");
2758 /* shadowbuffers used only for 'softlight' & spotlight with halo */
2759 if (((la->type==LA_LOCAL) && (la->mode & LA_YF_SOFT)) || ((la->type==LA_SPOT) && (la->mode & LA_HALO))) {
2760 /* Shadow buffer size can be anything in yafray, but reasonable minimum is 128 */
2761 /* Maximum is 1024, since zbuf in yafray is float, no multiple of 16 restriction */
2762 uiDefButS(block, NUM,B_DIFF,"ShadowBufferSize:", 100,110,200,19, &la->YF_bufsize, 128, 1024, 0, 0, "Sets the size of the shadow buffer");
2764 /* samples & halostep params only used for spotlight with halo */
2765 if ((la->type==LA_SPOT) && (la->mode & LA_HALO)) {
2766 uiDefButS(block, NUM,B_DIFF,"Samples:", 100,30,100,19, &la->samp,1.0,16.0, 0, 0, "Sets the number of shadow map samples");
2767 uiDefButS(block, NUM,B_DIFF,"Halo step:", 200,30,100,19, &la->shadhalostep, 0.0, 12.0, 0, 0, "Sets the volumetric halo sampling frequency");
2769 uiDefButF(block, NUM,B_DIFF,"Bias:", 100,10,100,19, &la->bias, 0.01, 5.0, 1, 0, "Sets the shadow map sampling bias");
2770 /* here can use the Blender soft param, since for yafray it has the same function as in Blender */
2771 uiDefButF(block, NUM,B_DIFF,"Soft:", 200,10,100,19, &la->soft,1.0,100.0, 100, 0, "Sets the size of the shadow sample area");
2773 else if ((la->type==LA_LOCAL) && (la->mode & LA_SHAD_RAY)) {
2774 /* for spherelight, light radius */
2775 uiDefButF(block, NUM,B_DIFF,"Radius:", 200,10,100,19, &la->YF_ltradius, 0.0,100.0, 100, 0, "Sets the radius of the lightsource, 0 is same as pointlight");
2778 if (la->type==LA_SPOT) {
2780 uiDefButBitS(block, TOG, LA_HALO, B_LAMPREDRAW,"Halo", 10,50,80,19,&la->mode, 0, 0, 0, 0, "Renders spotlight with a volumetric halo");
2782 uiBlockSetCol(block, TH_AUTO);
2783 uiBlockBeginAlign(block);
2784 uiDefButF(block, NUMSLI,B_LAMPREDRAW,"SpotSi ", 100,180,200,19,&la->spotsize, 1.0, 180.0, 0, 0, "Sets the angle of the spotlight beam in degrees");
2785 uiDefButF(block, NUMSLI,B_LAMPREDRAW,"SpotBl ", 100,160,200,19,&la->spotblend, 0.0, 1.0, 0, 0, "Sets the softness of the spotlight edge");
2786 uiBlockEndAlign(block);
2788 if (la->mode & LA_HALO) uiDefButF(block, NUMSLI,0,"HaloInt ", 100,135,200,19,&la->haint, 0.0, 5.0, 0, 0, "Sets the intensity of the spotlight halo");
2790 else if ((la->type==LA_AREA) || ((la->type==LA_LOCAL) && (la->mode & LA_SHAD_RAY))) {
2791 /* area samples param also used for 'spherelight' */
2792 uiBlockBeginAlign(block);
2793 uiBlockSetCol(block, TH_AUTO);
2795 uiDefButS(block, NUM,B_DIFF,"Samples:", 100,180,200,19, &la->ray_samp, 1.0, 16.0, 100, 0, "Sets the amount of samples taken extra (samp x samp)");
2797 /* shadow sampling types not used in yafray, removed */
2799 else uiDefBut(block, LABEL,0," ", 100,180,200,19,NULL, 0, 0, 0, 0, "");
2803 static void lamp_panel_falloff(Object *ob, Lamp *la)
2807 short yco=PANEL_YMAX;
2810 /* name "Preview" is abused to detect previewrender offset panel */
2811 block= uiNewBlock(&curarea->uiblocks, "lamp_panel_falloff", UI_EMBOSS, UI_HELV, curarea->win);
2812 uiNewPanelTabbed("Lamp", "Lamp");
2813 if(uiNewPanel(curarea, block, "Falloff Curve", "Lamp", PANELX, PANELY, PANELW, PANELH)==0) return;
2815 if(G.vd) grid= G.vd->grid;
2816 if(grid<1.0) grid= 1.0;
2818 uiSetButLock(la->id.lib!=0, ERROR_LIBDATA_MESSAGE);
2820 BLI_init_rctf(&butr, 10.0, 310.0, 10.0, (float)yco);
2821 curvemap_buttons(block, la->curfalloff, 's', B_LFALLOFFCHANGED, B_LAMPREDRAW, &butr);
2825 static void lamp_panel_lamp(Object *ob, Lamp *la)
2831 block= uiNewBlock(&curarea->uiblocks, "lamp_panel_lamp", UI_EMBOSS, UI_HELV, curarea->win);
2832 if(uiNewPanel(curarea, block, "Lamp", "Lamp", 320, 0, 318, 204)==0) return;
2834 if(G.vd) grid= G.vd->grid;
2835 if(grid<1.0) grid= 1.0;
2837 uiSetButLock(la->id.lib!=0, ERROR_LIBDATA_MESSAGE);
2839 uiBlockSetCol(block, TH_BUT_SETTING2);
2840 xco= std_libbuttons(block, 8, 180, 0, NULL, B_LAMPBROWSE, ID_LA, 0, (ID *)la, (ID *)ob, &(G.buts->menunr), B_LAMPALONE, B_LAMPLOCAL, 0, 0, 0);
2842 uiBlockSetCol(block, TH_AUTO);
2843 uiDefButF(block, NUM,B_LAMPREDRAW,"Dist:", xco,180,300-xco,20,&la->dist, 0.01, 5000.0*grid, 100, 0, "Sets the distance value at which light intensity is half");
2845 uiBlockBeginAlign(block);
2846 uiSetButLock(la->id.lib!=0, ERROR_LIBDATA_MESSAGE);
2847 if(la->type==LA_AREA) {
2848 //uiDefButS(block, MENU, B_LAMPREDRAW, "Shape %t|Square %x0|Rect %x1|Cube %x2|Box %x3",
2849 uiDefButS(block, MENU, B_LAMPREDRAW, "Shape %t|Square %x0|Rect %x1",
2850 10, 150, 100, 19, &la->area_shape, 0,0,0,0, "Sets area light shape");
2851 if (ELEM(la->area_shape, LA_AREA_RECT, LA_AREA_BOX)){
2852 uiDefButF(block, NUM,B_LAMPREDRAW,"SizeX ", 10,130,100,19, &la->area_size, 0.01, 100.0, 10, 0, "Area light size X, doesn't affect energy amount");
2853 uiDefButF(block, NUM,B_LAMPREDRAW,"SizeY ", 10,110,100,19, &la->area_sizey, 0.01, 100.0, 10, 0, "Area light size Y, doesn't affect energy amount");
2855 if(la->area_shape==LA_AREA_BOX)
2856 uiDefButF(block, NUM,B_LAMPREDRAW,"SizeZ ", 10,90,100,19, &la->area_sizez, 0.01, 100.0, 10, 0, "Area light size Z, doesn't affect energy amount");
2857 if (ELEM(la->area_shape, LA_AREA_SQUARE, LA_AREA_CUBE))
2858 uiDefButF(block, NUM,B_LAMPREDRAW,"Size ", 10,130,100,19, &la->area_size, 0.01, 100.0, 10, 0, "Area light size, doesn't affect energy amount");
2860 else if( ELEM(la->type, LA_LOCAL, LA_SPOT)) {
2861 uiBlockSetCol(block, TH_BUT_SETTING1);
2862 uiDefButS(block, MENU, B_LAMPREDRAW, "Falloff %t|Constant %x0|Inverse Linear %x1|Inverse Square %x2|Custom Curve %x3|Lin/Quad Weighted %x4|",
2863 10,150,100,19, &la->falloff_type, 0,0,0,0, "Lamp falloff - intensity decay with distance");
2864 uiDefButBitS(block, TOG, LA_SPHERE, REDRAWVIEW3D,"Sphere", 10,130,100,19,&la->mode, 0, 0, 0, 0, "Sets light intensity to zero for objects beyond the distance value");