|
Blender
V2.59
|
00001 /* 00002 * $Id: logic_window.c 37455 2011-06-13 17:08:33Z dfelinto $ 00003 * 00004 * ***** BEGIN GPL LICENSE BLOCK ***** 00005 * 00006 * This program is free software; you can redistribute it and/or 00007 * modify it under the terms of the GNU General Public License 00008 * as published by the Free Software Foundation; either version 2 00009 * of the License, or (at your option) any later version. 00010 * 00011 * This program is distributed in the hope that it will be useful, 00012 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00013 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00014 * GNU General Public License for more details. 00015 * 00016 * You should have received a copy of the GNU General Public License 00017 * along with this program; if not, write to the Free Software Foundation, 00018 * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 00019 * 00020 * The Original Code is Copyright (C) 2009 Blender Foundation. 00021 * All rights reserved. 00022 * 00023 * 00024 * Contributor(s): Blender Foundation 00025 * 00026 * ***** END GPL LICENSE BLOCK ***** 00027 */ 00028 00034 #include <string.h> 00035 #include <stdio.h> 00036 #include <stddef.h> 00037 #include <float.h> 00038 00039 #include "DNA_actuator_types.h" 00040 #include "DNA_controller_types.h" 00041 #include "DNA_property_types.h" 00042 #include "DNA_space_types.h" 00043 #include "DNA_scene_types.h" 00044 #include "DNA_screen_types.h" 00045 #include "DNA_sensor_types.h" 00046 #include "DNA_constraint_types.h" 00047 #include "DNA_windowmanager_types.h" 00048 #include "DNA_object_types.h" 00049 00050 #include "MEM_guardedalloc.h" 00051 00052 #include "BLI_blenlib.h" 00053 #include "BLI_utildefines.h" 00054 00055 #include "BKE_action.h" 00056 #include "BKE_context.h" 00057 #include "BKE_global.h" 00058 #include "BKE_library.h" 00059 #include "BKE_main.h" 00060 #include "BKE_sca.h" 00061 00062 #include "ED_util.h" 00063 00064 #include "WM_types.h" 00065 00066 #include "BIF_gl.h" 00067 00068 #include "UI_interface.h" 00069 00070 #include "RNA_access.h" 00071 00072 /* XXX BAD BAD */ 00073 #include "../interface/interface_intern.h" 00074 00075 #include "logic_intern.h" 00076 00077 00078 #define MAX_RENDER_PASS 100 00079 #define B_REDR 1 00080 #define B_IDNAME 2 00081 00082 #define B_ADD_SENS 2703 00083 #define B_CHANGE_SENS 2704 00084 #define B_DEL_SENS 2705 00085 00086 #define B_ADD_CONT 2706 00087 #define B_CHANGE_CONT 2707 00088 #define B_DEL_CONT 2708 00089 00090 #define B_ADD_ACT 2709 00091 #define B_CHANGE_ACT 2710 00092 #define B_DEL_ACT 2711 00093 00094 #define B_SOUNDACT_BROWSE 2712 00095 00096 #define B_SETSECTOR 2713 00097 #define B_SETPROP 2714 00098 #define B_SETACTOR 2715 00099 #define B_SETMAINACTOR 2716 00100 #define B_SETDYNA 2717 00101 #define B_SET_STATE_BIT 2718 00102 #define B_INIT_STATE_BIT 2719 00103 00104 /* proto */ 00105 static ID **get_selected_and_linked_obs(bContext *C, short *count, short scavisflag); 00106 00107 static int vergname(const void *v1, const void *v2) 00108 { 00109 char **x1, **x2; 00110 00111 x1= (char **)v1; 00112 x2= (char **)v2; 00113 00114 return strcmp(*x1, *x2); 00115 } 00116 00117 void make_unique_prop_names(bContext *C, char *str) 00118 { 00119 Object *ob; 00120 bProperty *prop; 00121 bSensor *sens; 00122 bController *cont; 00123 bActuator *act; 00124 ID **idar; 00125 short a, obcount, propcount=0, nr; 00126 char **names; 00127 00128 /* this function is called by a Button, and gives the current 00129 * stringpointer as an argument, this is the one that can change 00130 */ 00131 00132 idar= get_selected_and_linked_obs(C, &obcount, BUTS_SENS_SEL|BUTS_SENS_ACT|BUTS_ACT_SEL|BUTS_ACT_ACT|BUTS_CONT_SEL|BUTS_CONT_ACT); 00133 00134 /* for each object, make properties and sca names unique */ 00135 00136 /* count total names */ 00137 for(a=0; a<obcount; a++) { 00138 ob= (Object *)idar[a]; 00139 propcount+= BLI_countlist(&ob->prop); 00140 propcount+= BLI_countlist(&ob->sensors); 00141 propcount+= BLI_countlist(&ob->controllers); 00142 propcount+= BLI_countlist(&ob->actuators); 00143 } 00144 if(propcount==0) { 00145 if(idar) MEM_freeN(idar); 00146 return; 00147 } 00148 00149 /* make names array for sorting */ 00150 names= MEM_callocN(propcount*sizeof(void *), "names"); 00151 00152 /* count total names */ 00153 nr= 0; 00154 for(a=0; a<obcount; a++) { 00155 ob= (Object *)idar[a]; 00156 prop= ob->prop.first; 00157 while(prop) { 00158 names[nr++]= prop->name; 00159 prop= prop->next; 00160 } 00161 sens= ob->sensors.first; 00162 while(sens) { 00163 names[nr++]= sens->name; 00164 sens= sens->next; 00165 } 00166 cont= ob->controllers.first; 00167 while(cont) { 00168 names[nr++]= cont->name; 00169 cont= cont->next; 00170 } 00171 act= ob->actuators.first; 00172 while(act) { 00173 names[nr++]= act->name; 00174 act= act->next; 00175 } 00176 } 00177 00178 qsort(names, propcount, sizeof(void *), vergname); 00179 00180 /* now we check for double names, and change them */ 00181 00182 for(nr=0; nr<propcount; nr++) { 00183 if(names[nr]!=str && strcmp( names[nr], str )==0 ) { 00184 BLI_newname(str, +1); 00185 } 00186 } 00187 00188 MEM_freeN(idar); 00189 MEM_freeN(names); 00190 } 00191 00192 static void make_unique_prop_names_cb(bContext *C, void *strv, void *UNUSED(redraw_view3d_flagv)) 00193 { 00194 char *str= strv; 00195 // int redraw_view3d_flag= GET_INT_FROM_POINTER(redraw_view3d_flagv); 00196 00197 make_unique_prop_names(C, str); 00198 } 00199 00200 00201 static void old_sca_move_sensor(bContext *C, void *datav, void *move_up) 00202 { 00203 /* deprecated, no longer using it (moved to sca.c) */ 00204 Scene *scene= CTX_data_scene(C); 00205 bSensor *sens_to_delete= datav; 00206 int val; 00207 Base *base; 00208 bSensor *sens, *tmp; 00209 00210 // val= pupmenu("Move up%x1|Move down %x2"); 00211 val = move_up ? 1:2; 00212 00213 if(val>0) { 00214 /* now find out which object has this ... */ 00215 base= FIRSTBASE; 00216 while(base) { 00217 00218 sens= base->object->sensors.first; 00219 while(sens) { 00220 if(sens == sens_to_delete) break; 00221 sens= sens->next; 00222 } 00223 00224 if(sens) { 00225 if( val==1 && sens->prev) { 00226 for (tmp=sens->prev; tmp; tmp=tmp->prev) { 00227 if (tmp->flag & SENS_VISIBLE) 00228 break; 00229 } 00230 if (tmp) { 00231 BLI_remlink(&base->object->sensors, sens); 00232 BLI_insertlinkbefore(&base->object->sensors, tmp, sens); 00233 } 00234 } 00235 else if( val==2 && sens->next) { 00236 for (tmp=sens->next; tmp; tmp=tmp->next) { 00237 if (tmp->flag & SENS_VISIBLE) 00238 break; 00239 } 00240 if (tmp) { 00241 BLI_remlink(&base->object->sensors, sens); 00242 BLI_insertlink(&base->object->sensors, tmp, sens); 00243 } 00244 } 00245 ED_undo_push(C, "Move sensor"); 00246 break; 00247 } 00248 00249 base= base->next; 00250 } 00251 } 00252 } 00253 00254 static void old_sca_move_controller(bContext *C, void *datav, void *move_up) 00255 { 00256 /* deprecated, no longer using it (moved to sca.c) */ 00257 Scene *scene= CTX_data_scene(C); 00258 bController *controller_to_del= datav; 00259 int val; 00260 Base *base; 00261 bController *cont, *tmp; 00262 00263 //val= pupmenu("Move up%x1|Move down %x2"); 00264 val = move_up ? 1:2; 00265 00266 if(val>0) { 00267 /* now find out which object has this ... */ 00268 base= FIRSTBASE; 00269 while(base) { 00270 00271 cont= base->object->controllers.first; 00272 while(cont) { 00273 if(cont == controller_to_del) break; 00274 cont= cont->next; 00275 } 00276 00277 if(cont) { 00278 if( val==1 && cont->prev) { 00279 /* locate the controller that has the same state mask but is earlier in the list */ 00280 tmp = cont->prev; 00281 while(tmp) { 00282 if(tmp->state_mask & cont->state_mask) 00283 break; 00284 tmp = tmp->prev; 00285 } 00286 if (tmp) { 00287 BLI_remlink(&base->object->controllers, cont); 00288 BLI_insertlinkbefore(&base->object->controllers, tmp, cont); 00289 } 00290 } 00291 else if( val==2 && cont->next) { 00292 tmp = cont->next; 00293 while(tmp) { 00294 if(tmp->state_mask & cont->state_mask) 00295 break; 00296 tmp = tmp->next; 00297 } 00298 BLI_remlink(&base->object->controllers, cont); 00299 BLI_insertlink(&base->object->controllers, tmp, cont); 00300 } 00301 ED_undo_push(C, "Move controller"); 00302 break; 00303 } 00304 00305 base= base->next; 00306 } 00307 } 00308 } 00309 00310 static void old_sca_move_actuator(bContext *C, void *datav, void *move_up) 00311 { 00312 /* deprecated, no longer using it (moved to sca.c) */ 00313 Scene *scene= CTX_data_scene(C); 00314 bActuator *actuator_to_move= datav; 00315 int val; 00316 Base *base; 00317 bActuator *act, *tmp; 00318 00319 //val= pupmenu("Move up%x1|Move down %x2"); 00320 val = move_up ? 1:2; 00321 00322 if(val>0) { 00323 /* now find out which object has this ... */ 00324 base= FIRSTBASE; 00325 while(base) { 00326 00327 act= base->object->actuators.first; 00328 while(act) { 00329 if(act == actuator_to_move) break; 00330 act= act->next; 00331 } 00332 00333 if(act) { 00334 if( val==1 && act->prev) { 00335 /* locate the first visible actuators before this one */ 00336 for (tmp = act->prev; tmp; tmp=tmp->prev) { 00337 if (tmp->flag & ACT_VISIBLE) 00338 break; 00339 } 00340 if (tmp) { 00341 BLI_remlink(&base->object->actuators, act); 00342 BLI_insertlinkbefore(&base->object->actuators, tmp, act); 00343 } 00344 } 00345 else if( val==2 && act->next) { 00346 for (tmp=act->next; tmp; tmp=tmp->next) { 00347 if (tmp->flag & ACT_VISIBLE) 00348 break; 00349 } 00350 if (tmp) { 00351 BLI_remlink(&base->object->actuators, act); 00352 BLI_insertlink(&base->object->actuators, tmp, act); 00353 } 00354 } 00355 ED_undo_push(C, "Move actuator"); 00356 break; 00357 } 00358 00359 base= base->next; 00360 } 00361 } 00362 } 00363 00364 static void do_logic_buts(bContext *C, void *UNUSED(arg), int event) 00365 { 00366 Main *bmain= CTX_data_main(C); 00367 bSensor *sens; 00368 bController *cont; 00369 bActuator *act; 00370 Object *ob; 00371 int didit, bit; 00372 00373 ob= CTX_data_active_object(C); 00374 if(ob==NULL) return; 00375 00376 switch(event) { 00377 00378 case B_SETPROP: 00379 /* check for inconsistent types */ 00380 ob->gameflag &= ~(OB_SECTOR|OB_MAINACTOR|OB_DYNAMIC|OB_ACTOR); 00381 break; 00382 00383 case B_SETACTOR: 00384 case B_SETDYNA: 00385 case B_SETMAINACTOR: 00386 ob->gameflag &= ~(OB_SECTOR|OB_PROP); 00387 break; 00388 00389 case B_ADD_SENS: 00390 for(ob=bmain->object.first; ob; ob=ob->id.next) { 00391 if(ob->scaflag & OB_ADDSENS) { 00392 ob->scaflag &= ~OB_ADDSENS; 00393 sens= new_sensor(SENS_ALWAYS); 00394 BLI_addtail(&(ob->sensors), sens); 00395 make_unique_prop_names(C, sens->name); 00396 ob->scaflag |= OB_SHOWSENS; 00397 } 00398 } 00399 00400 ED_undo_push(C, "Add sensor"); 00401 break; 00402 00403 case B_CHANGE_SENS: 00404 for(ob=bmain->object.first; ob; ob=ob->id.next) { 00405 sens= ob->sensors.first; 00406 while(sens) { 00407 if(sens->type != sens->otype) { 00408 init_sensor(sens); 00409 sens->otype= sens->type; 00410 break; 00411 } 00412 sens= sens->next; 00413 } 00414 } 00415 break; 00416 00417 case B_DEL_SENS: 00418 for(ob=bmain->object.first; ob; ob=ob->id.next) { 00419 sens= ob->sensors.first; 00420 while(sens) { 00421 if(sens->flag & SENS_DEL) { 00422 BLI_remlink(&(ob->sensors), sens); 00423 free_sensor(sens); 00424 break; 00425 } 00426 sens= sens->next; 00427 } 00428 } 00429 ED_undo_push(C, "Delete sensor"); 00430 break; 00431 00432 case B_ADD_CONT: 00433 for(ob=bmain->object.first; ob; ob=ob->id.next) { 00434 if(ob->scaflag & OB_ADDCONT) { 00435 ob->scaflag &= ~OB_ADDCONT; 00436 cont= new_controller(CONT_LOGIC_AND); 00437 make_unique_prop_names(C, cont->name); 00438 ob->scaflag |= OB_SHOWCONT; 00439 BLI_addtail(&(ob->controllers), cont); 00440 /* set the controller state mask from the current object state. 00441 A controller is always in a single state, so select the lowest bit set 00442 from the object state */ 00443 for (bit=0; bit<32; bit++) { 00444 if (ob->state & (1<<bit)) 00445 break; 00446 } 00447 cont->state_mask = (1<<bit); 00448 if (cont->state_mask == 0) { 00449 /* shouldn't happen, object state is never 0 */ 00450 cont->state_mask = 1; 00451 } 00452 } 00453 } 00454 ED_undo_push(C, "Add controller"); 00455 break; 00456 00457 case B_SET_STATE_BIT: 00458 for(ob=bmain->object.first; ob; ob=ob->id.next) { 00459 if(ob->scaflag & OB_ALLSTATE) { 00460 ob->scaflag &= ~OB_ALLSTATE; 00461 ob->state = 0x3FFFFFFF; 00462 } 00463 } 00464 break; 00465 00466 case B_INIT_STATE_BIT: 00467 for(ob=bmain->object.first; ob; ob=ob->id.next) { 00468 if(ob->scaflag & OB_INITSTBIT) { 00469 ob->scaflag &= ~OB_INITSTBIT; 00470 ob->state = ob->init_state; 00471 if (!ob->state) 00472 ob->state = 1; 00473 } 00474 } 00475 break; 00476 00477 case B_CHANGE_CONT: 00478 for(ob=bmain->object.first; ob; ob=ob->id.next) { 00479 cont= ob->controllers.first; 00480 while(cont) { 00481 if(cont->type != cont->otype) { 00482 init_controller(cont); 00483 cont->otype= cont->type; 00484 break; 00485 } 00486 cont= cont->next; 00487 } 00488 } 00489 break; 00490 00491 00492 case B_DEL_CONT: 00493 for(ob=bmain->object.first; ob; ob=ob->id.next) { 00494 cont= ob->controllers.first; 00495 while(cont) { 00496 if(cont->flag & CONT_DEL) { 00497 BLI_remlink(&(ob->controllers), cont); 00498 unlink_controller(cont); 00499 free_controller(cont); 00500 break; 00501 } 00502 cont= cont->next; 00503 } 00504 } 00505 ED_undo_push(C, "Delete controller"); 00506 break; 00507 00508 case B_ADD_ACT: 00509 for(ob=bmain->object.first; ob; ob=ob->id.next) { 00510 if(ob->scaflag & OB_ADDACT) { 00511 ob->scaflag &= ~OB_ADDACT; 00512 act= new_actuator(ACT_OBJECT); 00513 make_unique_prop_names(C, act->name); 00514 BLI_addtail(&(ob->actuators), act); 00515 ob->scaflag |= OB_SHOWACT; 00516 } 00517 } 00518 ED_undo_push(C, "Add actuator"); 00519 break; 00520 00521 case B_CHANGE_ACT: 00522 for(ob=bmain->object.first; ob; ob=ob->id.next) { 00523 act= ob->actuators.first; 00524 while(act) { 00525 if(act->type != act->otype) { 00526 init_actuator(act); 00527 act->otype= act->type; 00528 break; 00529 } 00530 act= act->next; 00531 } 00532 } 00533 break; 00534 00535 case B_DEL_ACT: 00536 for(ob=bmain->object.first; ob; ob=ob->id.next) { 00537 act= ob->actuators.first; 00538 while(act) { 00539 if(act->flag & ACT_DEL) { 00540 BLI_remlink(&(ob->actuators), act); 00541 unlink_actuator(act); 00542 free_actuator(act); 00543 break; 00544 } 00545 act= act->next; 00546 } 00547 } 00548 ED_undo_push(C, "Delete actuator"); 00549 break; 00550 00551 case B_SOUNDACT_BROWSE: 00552 /* since we don't know which... */ 00553 didit= 0; 00554 for(ob=bmain->object.first; ob; ob=ob->id.next) { 00555 act= ob->actuators.first; 00556 while(act) 00557 { 00558 if(act->type==ACT_SOUND) 00559 { 00560 bSoundActuator *sa= act->data; 00561 if(sa->sndnr) 00562 { 00563 ID *sound= bmain->sound.first; 00564 int nr= 1; 00565 00566 if(sa->sndnr == -2) { 00567 // XXX activate_databrowse((ID *)bmain->sound.first, ID_SO, 0, B_SOUNDACT_BROWSE, 00568 // &sa->sndnr, do_logic_buts); 00569 break; 00570 } 00571 00572 while(sound) 00573 { 00574 if(nr==sa->sndnr) 00575 break; 00576 nr++; 00577 sound= sound->next; 00578 } 00579 00580 if(sa->sound) 00581 ((ID *)sa->sound)->us--; 00582 00583 sa->sound= (struct bSound *)sound; 00584 00585 if(sound) 00586 sound->us++; 00587 00588 sa->sndnr= 0; 00589 didit= 1; 00590 } 00591 } 00592 act= act->next; 00593 } 00594 if(didit) 00595 break; 00596 } 00597 00598 break; 00599 } 00600 } 00601 00602 00603 static const char *sensor_name(int type) 00604 { 00605 switch (type) { 00606 case SENS_ALWAYS: 00607 return "Always"; 00608 case SENS_TOUCH: 00609 return "Touch"; 00610 case SENS_NEAR: 00611 return "Near"; 00612 case SENS_KEYBOARD: 00613 return "Keyboard"; 00614 case SENS_PROPERTY: 00615 return "Property"; 00616 case SENS_ARMATURE: 00617 return "Armature"; 00618 case SENS_ACTUATOR: 00619 return "Actuator"; 00620 case SENS_DELAY: 00621 return "Delay"; 00622 case SENS_MOUSE: 00623 return "Mouse"; 00624 case SENS_COLLISION: 00625 return "Collision"; 00626 case SENS_RADAR: 00627 return "Radar"; 00628 case SENS_RANDOM: 00629 return "Random"; 00630 case SENS_RAY: 00631 return "Ray"; 00632 case SENS_MESSAGE: 00633 return "Message"; 00634 case SENS_JOYSTICK: 00635 return "Joystick"; 00636 } 00637 return "unknown"; 00638 } 00639 00640 static const char *sensor_pup(void) 00641 { 00642 /* the number needs to match defines in DNA_sensor_types.h */ 00643 return "Sensors %t|Always %x0|Delay %x13|Keyboard %x3|Mouse %x5|" 00644 "Touch %x1|Collision %x6|Near %x2|Radar %x7|" 00645 "Property %x4|Random %x8|Ray %x9|Message %x10|Joystick %x11|Actuator %x12|Armature %x14"; 00646 } 00647 00648 static const char *controller_name(int type) 00649 { 00650 switch (type) { 00651 case CONT_LOGIC_AND: 00652 return "And"; 00653 case CONT_LOGIC_OR: 00654 return "Or"; 00655 case CONT_LOGIC_NAND: 00656 return "Nand"; 00657 case CONT_LOGIC_NOR: 00658 return "Nor"; 00659 case CONT_LOGIC_XOR: 00660 return "Xor"; 00661 case CONT_LOGIC_XNOR: 00662 return "Xnor"; 00663 case CONT_EXPRESSION: 00664 return "Expression"; 00665 case CONT_PYTHON: 00666 return "Python"; 00667 } 00668 return "unknown"; 00669 } 00670 00671 static const char *controller_pup(void) 00672 { 00673 return "Controllers %t|AND %x0|OR %x1|XOR %x6|NAND %x4|NOR %x5|XNOR %x7|Expression %x2|Python %x3"; 00674 } 00675 00676 static const char *actuator_name(int type) 00677 { 00678 switch (type) { 00679 case ACT_SHAPEACTION: 00680 return "Shape Action"; 00681 case ACT_ACTION: 00682 return "Action"; 00683 case ACT_OBJECT: 00684 return "Motion"; 00685 case ACT_IPO: 00686 return "F-Curve"; 00687 case ACT_LAMP: 00688 return "Lamp"; 00689 case ACT_CAMERA: 00690 return "Camera"; 00691 case ACT_MATERIAL: 00692 return "Material"; 00693 case ACT_SOUND: 00694 return "Sound"; 00695 case ACT_PROPERTY: 00696 return "Property"; 00697 case ACT_EDIT_OBJECT: 00698 return "Edit Object"; 00699 case ACT_CONSTRAINT: 00700 return "Constraint"; 00701 case ACT_SCENE: 00702 return "Scene"; 00703 case ACT_GROUP: 00704 return "Group"; 00705 case ACT_RANDOM: 00706 return "Random"; 00707 case ACT_MESSAGE: 00708 return "Message"; 00709 case ACT_GAME: 00710 return "Game"; 00711 case ACT_VISIBILITY: 00712 return "Visibility"; 00713 case ACT_2DFILTER: 00714 return "Filter 2D"; 00715 case ACT_PARENT: 00716 return "Parent"; 00717 case ACT_STATE: 00718 return "State"; 00719 case ACT_ARMATURE: 00720 return "Armature"; 00721 } 00722 return "unknown"; 00723 } 00724 00725 00726 00727 00728 static const char *actuator_pup(Object *owner) 00729 { 00730 switch (owner->type) 00731 { 00732 case OB_ARMATURE: 00733 return "Actuators %t|Action %x15|Armature %x23|Motion %x0|Constraint %x9|Ipo %x1" 00734 "|Camera %x3|Sound %x5|Property %x6|Edit Object %x10" 00735 "|Scene %x11|Random %x13|Message %x14|Game %x17" 00736 "|Visibility %x18|2D Filter %x19|Parent %x20|State %x22"; 00737 break; 00738 00739 case OB_MESH: 00740 return "Actuators %t|Shape Action %x21|Motion %x0|Constraint %x9|Ipo %x1" 00741 "|Camera %x3|Sound %x5|Property %x6|Edit Object %x10" 00742 "|Scene %x11|Random %x13|Message %x14|Game %x17" 00743 "|Visibility %x18|2D Filter %x19|Parent %x20|State %x22"; 00744 break; 00745 00746 default: 00747 return "Actuators %t|Motion %x0|Constraint %x9|Ipo %x1" 00748 "|Camera %x3|Sound %x5|Property %x6|Edit Object %x10" 00749 "|Scene %x11|Random %x13|Message %x14|Game %x17" 00750 "|Visibility %x18|2D Filter %x19|Parent %x20|State %x22"; 00751 } 00752 } 00753 00754 00755 00756 static void set_sca_ob(Object *ob) 00757 { 00758 bController *cont; 00759 bActuator *act; 00760 00761 cont= ob->controllers.first; 00762 while(cont) { 00763 cont->mynew= (bController *)ob; 00764 cont= cont->next; 00765 } 00766 act= ob->actuators.first; 00767 while(act) { 00768 act->mynew= (bActuator *)ob; 00769 act= act->next; 00770 } 00771 } 00772 00773 static ID **get_selected_and_linked_obs(bContext *C, short *count, short scavisflag) 00774 { 00775 Base *base; 00776 Main *bmain= CTX_data_main(C); 00777 Scene *scene= CTX_data_scene(C); 00778 Object *ob, *obt, *obact= CTX_data_active_object(C); 00779 ID **idar; 00780 bSensor *sens; 00781 bController *cont; 00782 unsigned int lay; 00783 int a, nr, doit; 00784 00785 /* we need a sorted object list */ 00786 /* set scavisflags flags in Objects to indicate these should be evaluated */ 00787 /* also hide ob pointers in ->new entries of controllerss/actuators */ 00788 00789 *count= 0; 00790 00791 if(scene==NULL) return NULL; 00792 00793 ob= bmain->object.first; 00794 while(ob) { 00795 ob->scavisflag= 0; 00796 set_sca_ob(ob); 00797 ob= ob->id.next; 00798 } 00799 00800 /* XXX here it checked 3d lay */ 00801 lay= scene->lay; 00802 00803 base= FIRSTBASE; 00804 while(base) { 00805 if(base->lay & lay) { 00806 if(base->flag & SELECT) { 00807 if(scavisflag & BUTS_SENS_SEL) base->object->scavisflag |= OB_VIS_SENS; 00808 if(scavisflag & BUTS_CONT_SEL) base->object->scavisflag |= OB_VIS_CONT; 00809 if(scavisflag & BUTS_ACT_SEL) base->object->scavisflag |= OB_VIS_ACT; 00810 } 00811 } 00812 base= base->next; 00813 } 00814 00815 if(obact) { 00816 if(scavisflag & BUTS_SENS_ACT) obact->scavisflag |= OB_VIS_SENS; 00817 if(scavisflag & BUTS_CONT_ACT) obact->scavisflag |= OB_VIS_CONT; 00818 if(scavisflag & BUTS_ACT_ACT) obact->scavisflag |= OB_VIS_ACT; 00819 } 00820 00821 /* BUTS_XXX_STATE are similar to BUTS_XXX_LINK for selecting the object */ 00822 if(scavisflag & (BUTS_SENS_LINK|BUTS_CONT_LINK|BUTS_ACT_LINK|BUTS_SENS_STATE|BUTS_ACT_STATE)) { 00823 doit= 1; 00824 while(doit) { 00825 doit= 0; 00826 00827 ob= bmain->object.first; 00828 while(ob) { 00829 00830 /* 1st case: select sensor when controller selected */ 00831 if((scavisflag & (BUTS_SENS_LINK|BUTS_SENS_STATE)) && (ob->scavisflag & OB_VIS_SENS)==0) { 00832 sens= ob->sensors.first; 00833 while(sens) { 00834 for(a=0; a<sens->totlinks; a++) { 00835 if(sens->links[a]) { 00836 obt= (Object *)sens->links[a]->mynew; 00837 if(obt && (obt->scavisflag & OB_VIS_CONT)) { 00838 doit= 1; 00839 ob->scavisflag |= OB_VIS_SENS; 00840 break; 00841 } 00842 } 00843 } 00844 if(doit) break; 00845 sens= sens->next; 00846 } 00847 } 00848 00849 /* 2nd case: select cont when act selected */ 00850 if((scavisflag & BUTS_CONT_LINK) && (ob->scavisflag & OB_VIS_CONT)==0) { 00851 cont= ob->controllers.first; 00852 while(cont) { 00853 for(a=0; a<cont->totlinks; a++) { 00854 if(cont->links[a]) { 00855 obt= (Object *)cont->links[a]->mynew; 00856 if(obt && (obt->scavisflag & OB_VIS_ACT)) { 00857 doit= 1; 00858 ob->scavisflag |= OB_VIS_CONT; 00859 break; 00860 } 00861 } 00862 } 00863 if(doit) break; 00864 cont= cont->next; 00865 } 00866 } 00867 00868 /* 3rd case: select controller when sensor selected */ 00869 if((scavisflag & BUTS_CONT_LINK) && (ob->scavisflag & OB_VIS_SENS)) { 00870 sens= ob->sensors.first; 00871 while(sens) { 00872 for(a=0; a<sens->totlinks; a++) { 00873 if(sens->links[a]) { 00874 obt= (Object *)sens->links[a]->mynew; 00875 if(obt && (obt->scavisflag & OB_VIS_CONT)==0) { 00876 doit= 1; 00877 obt->scavisflag |= OB_VIS_CONT; 00878 } 00879 } 00880 } 00881 sens= sens->next; 00882 } 00883 } 00884 00885 /* 4th case: select actuator when controller selected */ 00886 if( (scavisflag & (BUTS_ACT_LINK|BUTS_ACT_STATE)) && (ob->scavisflag & OB_VIS_CONT)) { 00887 cont= ob->controllers.first; 00888 while(cont) { 00889 for(a=0; a<cont->totlinks; a++) { 00890 if(cont->links[a]) { 00891 obt= (Object *)cont->links[a]->mynew; 00892 if(obt && (obt->scavisflag & OB_VIS_ACT)==0) { 00893 doit= 1; 00894 obt->scavisflag |= OB_VIS_ACT; 00895 } 00896 } 00897 } 00898 cont= cont->next; 00899 } 00900 00901 } 00902 ob= ob->id.next; 00903 } 00904 } 00905 } 00906 00907 /* now we count */ 00908 ob= bmain->object.first; 00909 while(ob) { 00910 if( ob->scavisflag ) (*count)++; 00911 ob= ob->id.next; 00912 } 00913 00914 if(*count==0) return NULL; 00915 if(*count>24) *count= 24; /* temporal */ 00916 00917 idar= MEM_callocN( (*count)*sizeof(void *), "idar"); 00918 00919 ob= bmain->object.first; 00920 nr= 0; 00921 00922 /* make the active object always the first one of the list */ 00923 if (obact) { 00924 idar[0]= (ID *)obact; 00925 nr++; 00926 } 00927 00928 while(ob) { 00929 if( (ob->scavisflag) && (ob != obact)) { 00930 idar[nr]= (ID *)ob; 00931 nr++; 00932 } 00933 if(nr>=24) break; 00934 ob= ob->id.next; 00935 } 00936 00937 /* just to be sure... these were set in set_sca_done_ob() */ 00938 clear_sca_new_poins(); 00939 00940 return idar; 00941 } 00942 00943 00944 static int get_col_sensor(int type) 00945 { 00946 /* XXX themecolors not here */ 00947 00948 switch(type) { 00949 case SENS_ALWAYS: return TH_PANEL; 00950 case SENS_DELAY: return TH_PANEL; 00951 case SENS_TOUCH: return TH_PANEL; 00952 case SENS_COLLISION: return TH_PANEL; 00953 case SENS_NEAR: return TH_PANEL; 00954 case SENS_KEYBOARD: return TH_PANEL; 00955 case SENS_PROPERTY: return TH_PANEL; 00956 case SENS_ARMATURE: return TH_PANEL; 00957 case SENS_ACTUATOR: return TH_PANEL; 00958 case SENS_MOUSE: return TH_PANEL; 00959 case SENS_RADAR: return TH_PANEL; 00960 case SENS_RANDOM: return TH_PANEL; 00961 case SENS_RAY: return TH_PANEL; 00962 case SENS_MESSAGE: return TH_PANEL; 00963 case SENS_JOYSTICK: return TH_PANEL; 00964 default: return TH_PANEL; 00965 } 00966 } 00967 static void set_col_sensor(int type, int medium) 00968 { 00969 int col= get_col_sensor(type); 00970 UI_ThemeColorShade(col, medium?30:0); 00971 } 00972 00973 00974 static void verify_logicbutton_func(bContext *UNUSED(C), void *data1, void *data2) 00975 { 00976 bSensor *sens= (bSensor*)data1; 00977 00978 if(sens->level && sens->tap) { 00979 if(data2 == &(sens->level)) 00980 sens->tap= 0; 00981 else 00982 sens->level= 0; 00983 } 00984 } 00985 00986 static void test_scriptpoin_but(struct bContext *C, const char *name, ID **idpp) 00987 { 00988 *idpp= BLI_findstring(&CTX_data_main(C)->text, name, offsetof(ID, name) + 2); 00989 } 00990 00991 static void test_actionpoin_but(struct bContext *C, const char *name, ID **idpp) 00992 { 00993 *idpp= BLI_findstring(&CTX_data_main(C)->action, name, offsetof(ID, name) + 2); 00994 if(*idpp) 00995 id_us_plus(*idpp); 00996 } 00997 00998 00999 static void test_obpoin_but(struct bContext *C, const char *name, ID **idpp) 01000 { 01001 *idpp= BLI_findstring(&CTX_data_main(C)->object, name, offsetof(ID, name) + 2); 01002 if(*idpp) 01003 id_lib_extern(*idpp); /* checks lib data, sets correct flag for saving then */ 01004 } 01005 01006 static void test_meshpoin_but(struct bContext *C, const char *name, ID **idpp) 01007 { 01008 *idpp= BLI_findstring(&CTX_data_main(C)->mesh, name, offsetof(ID, name) + 2); 01009 if(*idpp) 01010 id_us_plus(*idpp); 01011 } 01012 01013 static void test_matpoin_but(struct bContext *C, const char *name, ID **idpp) 01014 { 01015 *idpp= BLI_findstring(&CTX_data_main(C)->mat, name, offsetof(ID, name) + 2); 01016 if(*idpp) 01017 id_us_plus(*idpp); 01018 } 01019 01020 static void test_scenepoin_but(struct bContext *C, const char *name, ID **idpp) 01021 { 01022 *idpp= BLI_findstring(&CTX_data_main(C)->scene, name, offsetof(ID, name) + 2); 01023 if(*idpp) 01024 id_us_plus(*idpp); 01025 } 01026 01027 static void test_keyboard_event(struct bContext *UNUSED(C), void *arg_ks, void *UNUSED(arg)) 01028 { 01029 bKeyboardSensor *ks= (bKeyboardSensor*)arg_ks; 01030 01031 if(!ISKEYBOARD(ks->key)) 01032 ks->key= 0; 01033 if(!ISKEYBOARD(ks->qual)) 01034 ks->qual= 0; 01035 if(!ISKEYBOARD(ks->qual2)) 01036 ks->qual2= 0; 01037 } 01038 01043 static void draw_default_sensor_header(bSensor *sens, 01044 uiBlock *block, 01045 short x, 01046 short y, 01047 short w) 01048 { 01049 uiBut *but; 01050 01051 /* Pulsing and frequency */ 01052 uiBlockBeginAlign(block); 01053 uiDefIconButBitS(block, TOG, SENS_PULSE_REPEAT, 1, ICON_DOTSUP, 01054 (short)(x + 10 + 0. * (w-20)), (short)(y - 21), (short)(0.1 * (w-20)), 19, 01055 &sens->pulse, 0.0, 0.0, 0, 0, 01056 "Activate TRUE level triggering (pulse mode)"); 01057 01058 uiDefIconButBitS(block, TOG, SENS_NEG_PULSE_MODE, 1, ICON_DOTSDOWN, 01059 (short)(x + 10 + 0.1 * (w-20)), (short)(y - 21), (short)(0.1 * (w-20)), 19, 01060 &sens->pulse, 0.0, 0.0, 0, 0, 01061 "Activate FALSE level triggering (pulse mode)"); 01062 uiDefButS(block, NUM, 1, "f:", 01063 (short)(x + 10 + 0.2 * (w-20)), (short)(y - 21), (short)(0.275 * (w-20)), 19, 01064 &sens->freq, 0.0, 10000.0, 0, 0, 01065 "Delay between repeated pulses (in logic tics, 0 = no delay)"); 01066 uiBlockEndAlign(block); 01067 01068 /* value or shift? */ 01069 uiBlockBeginAlign(block); 01070 but= uiDefButS(block, TOG, 1, "Level", 01071 (short)(x + 10 + 0.5 * (w-20)), (short)(y - 21), (short)(0.20 * (w-20)), 19, 01072 &sens->level, 0.0, 0.0, 0, 0, 01073 "Level detector, trigger controllers of new states (only applicable upon logic state transition)"); 01074 uiButSetFunc(but, verify_logicbutton_func, sens, &(sens->level)); 01075 but= uiDefButS(block, TOG, 1, "Tap", 01076 (short)(x + 10 + 0.702 * (w-20)), (short)(y - 21), (short)(0.12 * (w-20)), 19, 01077 &sens->tap, 0.0, 0.0, 0, 0, 01078 "Trigger controllers only for an instant, even while the sensor remains true"); 01079 uiButSetFunc(but, verify_logicbutton_func, sens, &(sens->tap)); 01080 uiBlockEndAlign(block); 01081 01082 uiDefButS(block, TOG, 1, "Inv", 01083 (short)(x + 10 + 0.85 * (w-20)), (short)(y - 21), (short)(0.15 * (w-20)), 19, 01084 &sens->invert, 0.0, 0.0, 0, 0, 01085 "Invert the level (output) of this sensor"); 01086 } 01087 01088 static void get_armature_bone_constraint(Object *ob, const char *posechannel, const char *constraint_name, bConstraint **constraint) 01089 { 01090 /* check that bone exist in the active object */ 01091 if (ob->type == OB_ARMATURE && ob->pose) { 01092 bPoseChannel *pchan= get_pose_channel(ob->pose, posechannel); 01093 if(pchan) { 01094 bConstraint *con= BLI_findstring(&pchan->constraints, constraint_name, offsetof(bConstraint, name)); 01095 if(con) { 01096 *constraint= con; 01097 } 01098 } 01099 } 01100 /* didn't find any */ 01101 } 01102 static void check_armature_bone_constraint(Object *ob, char *posechannel, char *constraint) 01103 { 01104 /* check that bone exist in the active object */ 01105 if (ob->type == OB_ARMATURE && ob->pose) { 01106 bPoseChannel *pchan; 01107 bPose *pose = ob->pose; 01108 for (pchan=pose->chanbase.first; pchan; pchan=pchan->next) { 01109 if (!strcmp(pchan->name, posechannel)) { 01110 /* found it, now look for constraint channel */ 01111 bConstraint *con; 01112 for (con=pchan->constraints.first; con; con=con->next) { 01113 if (!strcmp(con->name, constraint)) { 01114 /* found it, all ok */ 01115 return; 01116 } 01117 } 01118 /* didn't find constraint, make empty */ 01119 constraint[0] = 0; 01120 return; 01121 } 01122 } 01123 } 01124 /* didn't find any */ 01125 posechannel[0] = 0; 01126 constraint[0] = 0; 01127 } 01128 01129 static void check_armature_sensor(bContext *C, void *arg1_but, void *arg2_sens) 01130 { 01131 bArmatureSensor *sens = arg2_sens; 01132 uiBut *but = arg1_but; 01133 Object *ob= CTX_data_active_object(C); 01134 01135 /* check that bone exist in the active object */ 01136 but->retval = B_REDR; 01137 check_armature_bone_constraint(ob, sens->posechannel, sens->constraint); 01138 } 01139 01140 static short draw_sensorbuttons(Object *ob, bSensor *sens, uiBlock *block, short xco, short yco, short width) 01141 { 01142 bNearSensor *ns = NULL; 01143 bTouchSensor *ts = NULL; 01144 bKeyboardSensor *ks = NULL; 01145 bPropertySensor *ps = NULL; 01146 bArmatureSensor *arm = NULL; 01147 bMouseSensor *ms = NULL; 01148 bCollisionSensor *cs = NULL; 01149 bRadarSensor *rs = NULL; 01150 bRandomSensor *randomSensor = NULL; 01151 bRaySensor *raySens = NULL; 01152 bMessageSensor *mes = NULL; 01153 bJoystickSensor *joy = NULL; 01154 bActuatorSensor *as = NULL; 01155 bDelaySensor *ds = NULL; 01156 uiBut *but; 01157 short ysize; 01158 const char *str; 01159 01160 /* yco is at the top of the rect, draw downwards */ 01161 01162 set_col_sensor(sens->type, 0); 01163 01164 switch (sens->type) 01165 { 01166 case SENS_ALWAYS: 01167 { 01168 ysize= 24; 01169 01170 glRects(xco, yco-ysize, xco+width, yco); 01171 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 01172 01173 draw_default_sensor_header(sens, block, xco, yco, width); 01174 01175 yco-= ysize; 01176 01177 break; 01178 } 01179 case SENS_TOUCH: 01180 { 01181 ysize= 48; 01182 01183 glRects(xco, yco-ysize, xco+width, yco); 01184 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 01185 01186 draw_default_sensor_header(sens, block, xco, yco, width); 01187 01188 ts= sens->data; 01189 01190 /* uiDefBut(block, TEX, 1, "Property:", xco,yco-22,width, 19, &ts->name, 0, 31, 0, 0, "Only look for Objects with this property"); */ 01191 uiDefIDPoinBut(block, test_matpoin_but, ID_MA, 1, "MA:",(short)(xco + 10),(short)(yco-44), (short)(width - 20), 19, &ts->ma, "Only look for floors with this Material"); 01193 yco-= ysize; 01194 break; 01195 } 01196 case SENS_COLLISION: 01197 { 01198 ysize= 48; 01199 01200 glRects(xco, yco-ysize, xco+width, yco); 01201 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 01202 01203 draw_default_sensor_header(sens, block, xco, yco, width); 01204 cs= sens->data; 01205 01206 /* The collision sensor will become a generic collision (i.e. it */ 01207 /* absorb the old touch sensor). */ 01208 01209 uiDefButBitS(block, TOG, SENS_COLLISION_PULSE, B_REDR, "Pulse",(short)(xco + 10),(short)(yco - 44), 01210 (short)(0.20 * (width-20)), 19, &cs->mode, 0.0, 0.0, 0, 0, 01211 "Changes to the set of colliding objects generated pulses"); 01212 01213 uiDefButBitS(block, TOG, SENS_COLLISION_MATERIAL, B_REDR, "M/P",(short)(xco + 10 + (0.20 * (width-20))),(short)(yco - 44), 01214 (short)(0.20 * (width-20)), 19, &cs->mode, 0.0, 0.0, 0, 0, 01215 "Toggle collision on material or property"); 01216 01217 if (cs->mode & SENS_COLLISION_MATERIAL) { 01218 uiDefBut(block, TEX, 1, "Material:", (short)(xco + 10 + 0.40 * (width-20)), 01219 (short)(yco-44), (short)(0.6*(width-20)), 19, &cs->materialName, 0, 31, 0, 0, 01220 "Only look for Objects with this material"); 01221 } else { 01222 uiDefBut(block, TEX, 1, "Property:", (short)(xco + 10 + 0.40 * (width-20)), (short)(yco-44), 01223 (short)(0.6*(width-20)), 19, &cs->name, 0, 31, 0, 0, 01224 "Only look for Objects with this property"); 01225 } 01226 01227 /* uiDefButS(block, NUM, 1, "Damp:", xco+10+width-90,yco-24, 70, 19, &cs->damp, 0, 250, 0, 0, "For 'damp' time don't detect another collision"); */ 01228 01229 yco-= ysize; 01230 break; 01231 } 01232 case SENS_NEAR: 01233 { 01234 ysize= 72; 01235 01236 glRects(xco, yco-ysize, xco+width, yco); 01237 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 01238 01239 draw_default_sensor_header(sens, block, xco, yco, width); 01240 ns= sens->data; 01241 01242 uiDefBut(block, TEX, 1, "Property:",(short)(10+xco),(short)(yco-44), (short)(width-20), 19, 01243 &ns->name, 0, 31, 0, 0, "Only look for Objects with this property"); 01244 uiDefButF(block, NUM, 1, "Dist",(short)(10+xco),(short)(yco-68),(short)((width-22)/2), 19, 01245 &ns->dist, 0.0, 1000.0, 1000, 0, "Trigger distance"); 01246 uiDefButF(block, NUM, 1, "Reset",(short)(10+xco+(width-22)/2), (short)(yco-68), (short)((width-22)/2), 19, 01247 &ns->resetdist, 0.0, 1000.0, 1000, 0, "Reset distance"); 01248 yco-= ysize; 01249 break; 01250 } 01251 case SENS_RADAR: 01252 { 01253 ysize= 72; 01254 01255 glRects(xco, yco-ysize, xco+width, yco); 01256 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 01257 01258 draw_default_sensor_header(sens, block, xco, yco, width); 01259 01260 rs= sens->data; 01261 01262 uiDefBut(block, TEX, 1, "Prop:", 01263 (short)(10+xco),(short)(yco-44), (short)(0.7 * (width-20)), 19, 01264 &rs->name, 0, 31, 0, 0, 01265 "Only look for Objects with this property"); 01266 01267 str = "Type %t|+X axis %x0|+Y axis %x1|+Z axis %x2|-X axis %x3|-Y axis %x4|-Z axis %x5"; 01268 uiDefButS(block, MENU, B_REDR, str, 01269 (short)(10+xco+0.7 * (width-20)), (short)(yco-44), (short)(0.3 * (width-22)), 19, 01270 &rs->axis, 2.0, 31, 0, 0, 01271 "Specify along which axis the radar cone is cast"); 01272 01273 uiDefButF(block, NUM, 1, "Ang:", 01274 (short)(10+xco), (short)(yco-68), (short)((width-20)/2), 19, 01275 &rs->angle, 0.0, 179.9, 10, 0, 01276 "Opening angle of the radar cone"); 01277 uiDefButF(block, NUM, 1, "Dist:", 01278 (short)(xco+10 + (width-20)/2), (short)(yco-68), (short)((width-20)/2), 19, 01279 &rs->range, 0.01, 10000.0, 100, 0, 01280 "Depth of the radar cone"); 01281 yco-= ysize; 01282 break; 01283 } 01284 case SENS_KEYBOARD: 01285 { 01286 ks= sens->data; 01287 01288 /* 5 lines: 120 height */ 01289 ysize= (ks->type&1) ? 96:120; 01290 01291 glRects(xco, yco-ysize, xco+width, yco); 01292 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 01293 01294 /* header line */ 01295 draw_default_sensor_header(sens, block, xco, yco, width); 01296 01297 /* part of line 1 */ 01298 uiDefBut(block, LABEL, 0, "Key", xco, yco-44, 40, 19, NULL, 0, 0, 0, 0, ""); 01299 uiDefButBitS(block, TOG, 1, B_REDR, "All keys", xco+40+(width/2), yco-44, (width/2)-50, 19, 01300 &ks->type, 0, 0, 0, 0, ""); 01301 01302 01303 if ((ks->type&1)==0) { /* is All Keys option off? */ 01304 /* line 2: hotkey and allkeys toggle */ 01305 but= uiDefKeyevtButS(block, 0, "", xco+40, yco-44, (width)/2, 19, &ks->key, "Key code"); 01306 uiButSetFunc(but, test_keyboard_event, ks, NULL); 01307 01308 /* line 3: two key modifyers (qual1, qual2) */ 01309 uiDefBut(block, LABEL, 0, "Hold", xco, yco-68, 40, 19, NULL, 0, 0, 0, 0, ""); 01310 but= uiDefKeyevtButS(block, 0, "", xco+40, yco-68, (width-50)/2, 19, &ks->qual, "Modifier key code"); 01311 uiButSetFunc(but, test_keyboard_event, ks, NULL); 01312 but= uiDefKeyevtButS(block, 0, "", xco+40+(width-50)/2, yco-68, (width-50)/2, 19, &ks->qual2, "Second Modifier key code"); 01313 uiButSetFunc(but, test_keyboard_event, ks, NULL); 01314 } 01315 01316 /* line 4: toggle property for string logging mode */ 01317 uiDefBut(block, TEX, 1, "LogToggle: ", 01318 xco+10, yco-((ks->type&1) ? 68:92), (width-20), 19, 01319 ks->toggleName, 0, 31, 0, 0, 01320 "Property that indicates whether to log " 01321 "keystrokes as a string"); 01322 01323 /* line 5: target property for string logging mode */ 01324 uiDefBut(block, TEX, 1, "Target: ", 01325 xco+10, yco-((ks->type&1) ? 92:116), (width-20), 19, 01326 ks->targetName, 0, 31, 0, 0, 01327 "Property that receives the keystrokes in case " 01328 "a string is logged"); 01329 01330 yco-= ysize; 01331 break; 01332 } 01333 case SENS_PROPERTY: 01334 { 01335 ysize= 96; 01336 01337 glRects(xco, yco-ysize, xco+width, yco); 01338 uiEmboss((float)xco, (float)yco-ysize, 01339 (float)xco+width, (float)yco, 1); 01340 01341 draw_default_sensor_header(sens, block, xco, yco, width); 01342 ps= sens->data; 01343 01344 str= "Type %t|Equal %x0|Not Equal %x1|Interval %x2|Changed %x3"; 01345 /* str= "Type %t|Equal %x0|Not Equal %x1"; */ 01346 uiDefButI(block, MENU, B_REDR, str, xco+30,yco-44,width-60, 19, 01347 &ps->type, 0, 31, 0, 0, "Type"); 01348 01349 if (ps->type != SENS_PROP_EXPRESSION) 01350 { 01351 uiDefBut(block, TEX, 1, "Prop: ", xco+30,yco-68,width-60, 19, 01352 ps->name, 0, 31, 0, 0, "Property name"); 01353 } 01354 01355 if(ps->type == SENS_PROP_INTERVAL) 01356 { 01357 uiDefBut(block, TEX, 1, "Min: ", xco,yco-92,width/2, 19, 01358 ps->value, 0, 31, 0, 0, "check for min value"); 01359 uiDefBut(block, TEX, 1, "Max: ", xco+width/2,yco-92,width/2, 19, 01360 ps->maxvalue, 0, 31, 0, 0, "check for max value"); 01361 } 01362 else if(ps->type == SENS_PROP_CHANGED); 01363 else 01364 { 01365 uiDefBut(block, TEX, 1, "Value: ", xco+30,yco-92,width-60, 19, 01366 ps->value, 0, 31, 0, 0, "check for value"); 01367 } 01368 01369 yco-= ysize; 01370 break; 01371 } 01372 case SENS_ARMATURE: 01373 { 01374 ysize= 70; 01375 01376 glRects(xco, yco-ysize, xco+width, yco); 01377 uiEmboss((float)xco, (float)yco-ysize, 01378 (float)xco+width, (float)yco, 1); 01379 01380 draw_default_sensor_header(sens, block, xco, yco, width); 01381 arm= sens->data; 01382 01383 if (ob->type == OB_ARMATURE) { 01384 uiBlockBeginAlign(block); 01385 but = uiDefBut(block, TEX, 1, "Bone: ", 01386 (xco+10), (yco-44), (width-20)/2, 19, 01387 arm->posechannel, 0, 31, 0, 0, 01388 "Bone on which you want to check a constraint"); 01389 uiButSetFunc(but, check_armature_sensor, but, arm); 01390 but = uiDefBut(block, TEX, 1, "Cons: ", 01391 (xco+10)+(width-20)/2, (yco-44), (width-20)/2, 19, 01392 arm->constraint, 0, 31, 0, 0, 01393 "Name of the constraint you want to control"); 01394 uiButSetFunc(but, check_armature_sensor, but, arm); 01395 uiBlockEndAlign(block); 01396 01397 str= "Type %t|State changed %x0|Lin error below %x1|Lin error above %x2|Rot error below %x3|Rot error above %x4"; 01398 01399 uiDefButI(block, MENU, B_REDR, str, xco+10,yco-66,0.4*(width-20), 19, 01400 &arm->type, 0, 31, 0, 0, "Type"); 01401 01402 if (arm->type != SENS_ARM_STATE_CHANGED) 01403 { 01404 uiDefButF(block, NUM, 1, "Value: ", xco+10+0.4*(width-20),yco-66,0.6*(width-20), 19, 01405 &arm->value, -10000.0, 10000.0, 100, 0, "Test the error against this value"); 01406 } 01407 } 01408 yco-= ysize; 01409 break; 01410 } 01411 case SENS_ACTUATOR: 01412 { 01413 ysize= 48; 01414 01415 glRects(xco, yco-ysize, xco+width, yco); 01416 uiEmboss((float)xco, (float)yco-ysize, 01417 (float)xco+width, (float)yco, 1); 01418 01419 draw_default_sensor_header(sens, block, xco, yco, width); 01420 as= sens->data; 01421 01422 uiDefBut(block, TEX, 1, "Act: ", xco+30,yco-44,width-60, 19, 01423 as->name, 0, 31, 0, 0, "Actuator name, actuator active state modifications will be detected"); 01424 yco-= ysize; 01425 break; 01426 } 01427 case SENS_DELAY: 01428 { 01429 ysize= 48; 01430 01431 glRects(xco, yco-ysize, xco+width, yco); 01432 uiEmboss((float)xco, (float)yco-ysize, 01433 (float)xco+width, (float)yco, 1); 01434 01435 draw_default_sensor_header(sens, block, xco, yco, width); 01436 ds = sens->data; 01437 01438 uiDefButS(block, NUM, 0, "Delay",(short)(10+xco),(short)(yco-44),(short)((width-22)*0.4+10), 19, 01439 &ds->delay, 0.0, 5000.0, 0, 0, "Delay in number of logic tics before the positive trigger (default 60 per second)"); 01440 uiDefButS(block, NUM, 0, "Dur",(short)(10+xco+(width-22)*0.4+10),(short)(yco-44),(short)((width-22)*0.4-10), 19, 01441 &ds->duration, 0.0, 5000.0, 0, 0, "If >0, delay in number of logic tics before the negative trigger following the positive trigger"); 01442 uiDefButBitS(block, TOG, SENS_DELAY_REPEAT, 0, "REP",(short)(xco + 10 + (width-22)*0.8),(short)(yco - 44), 01443 (short)(0.20 * (width-22)), 19, &ds->flag, 0.0, 0.0, 0, 0, 01444 "Toggle repeat option. If selected, the sensor restarts after Delay+Dur logic tics"); 01445 yco-= ysize; 01446 break; 01447 } 01448 case SENS_MOUSE: 01449 { 01450 ms= sens->data; 01451 /* Two lines: 48 pixels high. */ 01452 ysize = 48; 01453 01454 glRects(xco, yco-ysize, xco+width, yco); 01455 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 01456 01457 /* line 1: header */ 01458 draw_default_sensor_header(sens, block, xco, yco, width); 01459 01460 /* Line 2: type selection. The number are a bit mangled to get 01461 * proper compatibility with older .blend files. */ 01462 /* Any sensor type default is 0 but the ms enum starts in 1. 01463 * Therefore the mosue sensor is initialized to 1 in sca.c */ 01464 str= "Type %t|Left button %x1|Middle button %x2|" 01465 "Right button %x4|Wheel Up %x5|Wheel Down %x6|Movement %x8|Mouse over %x16|Mouse over any%x32"; 01466 uiDefButS(block, MENU, B_REDR, str, xco+10, yco-44, (width*0.8f)-20, 19, 01467 &ms->type, 0, 31, 0, 0, 01468 "Specify the type of event this mouse sensor should trigger on"); 01469 01470 if(ms->type==32) { 01471 uiDefButBitS(block, TOG, SENS_MOUSE_FOCUS_PULSE, B_REDR, "Pulse",(short)(xco + 10) + (width*0.8f)-20,(short)(yco - 44), 01472 (short)(0.20 * (width-20)), 19, &ms->flag, 0.0, 0.0, 0, 0, 01473 "Moving the mouse over a different object generates a pulse"); 01474 } 01475 01476 yco-= ysize; 01477 break; 01478 } 01479 case SENS_RANDOM: 01480 { 01481 ysize = 48; 01482 01483 glRects(xco, yco-ysize, xco+width, yco); 01484 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 01485 01486 draw_default_sensor_header(sens, block, xco, yco, width); 01487 randomSensor = sens->data; 01488 /* some files were wrongly written, avoid crash now */ 01489 if (randomSensor) 01490 { 01491 uiDefButI(block, NUM, 1, "Seed: ", xco+10,yco-44,(width-20), 19, 01492 &randomSensor->seed, 0, 1000, 0, 0, 01493 "Initial seed of the generator. (Choose 0 for not random)"); 01494 } 01495 yco-= ysize; 01496 break; 01497 } 01498 case SENS_RAY: 01499 { 01500 ysize = 72; 01501 glRects(xco, yco-ysize, xco+width, yco); 01502 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 01503 01504 draw_default_sensor_header(sens, block, xco, yco, width); 01505 raySens = sens->data; 01506 01507 /* 1. property or material */ 01508 uiDefButBitS(block, TOG, SENS_COLLISION_MATERIAL, B_REDR, "M/P", 01509 xco + 10,yco - 44, 0.20 * (width-20), 19, 01510 &raySens->mode, 0.0, 0.0, 0, 0, 01511 "Toggle collision on material or property"); 01512 01513 if (raySens->mode & SENS_COLLISION_MATERIAL) 01514 { 01515 uiDefBut(block, TEX, 1, "Material:", xco + 10 + 0.20 * (width-20), yco-44, 0.8*(width-20), 19, 01516 &raySens->matname, 0, 31, 0, 0, 01517 "Only look for Objects with this material"); 01518 } 01519 else 01520 { 01521 uiDefBut(block, TEX, 1, "Property:", xco + 10 + 0.20 * (width-20), yco-44, 0.8*(width-20), 19, 01522 &raySens->propname, 0, 31, 0, 0, 01523 "Only look for Objects with this property"); 01524 } 01525 01526 /* X-Ray option */ 01527 uiDefButBitS(block, TOG, SENS_RAY_XRAY, 1, "X", 01528 xco + 10,yco - 68, 0.10 * (width-20), 19, 01529 &raySens->mode, 0.0, 0.0, 0, 0, 01530 "Toggle X-Ray option (see through objects that don't have the property)"); 01531 /* 2. sensing range */ 01532 uiDefButF(block, NUM, 1, "Range", xco+10 + 0.10 * (width-20), yco-68, 0.5 * (width-20), 19, 01533 &raySens->range, 0.01, 10000.0, 100, 0, 01534 "Sense objects no farther than this distance"); 01535 01536 /* 3. axis choice */ 01537 str = "Type %t|+ X axis %x1|+ Y axis %x0|+ Z axis %x2|- X axis %x3|- Y axis %x4|- Z axis %x5"; 01538 uiDefButI(block, MENU, B_REDR, str, xco+10 + 0.6 * (width-20), yco-68, 0.4 * (width-20), 19, 01539 &raySens->axisflag, 2.0, 31, 0, 0, 01540 "Specify along which axis the ray is cast"); 01541 01542 yco-= ysize; 01543 break; 01544 } 01545 case SENS_MESSAGE: 01546 { 01547 mes = sens->data; 01548 ysize = 2 * 24; /* total number of lines * 24 pixels/line */ 01549 01550 glRects(xco, yco-ysize, xco+width, yco); 01551 uiEmboss((float)xco, (float)yco-ysize, 01552 (float)xco+width, (float)yco, 1); 01553 01554 /* line 1: header line */ 01555 draw_default_sensor_header(sens, block, xco, yco, width); 01556 01557 /* line 2: Subject filter */ 01558 uiDefBut(block, TEX, 1, "Subject: ", 01559 (xco+10), (yco-44), (width-20), 19, 01560 mes->subject, 0, 31, 0, 0, 01561 "Optional subject filter: only accept messages with this subject" 01562 ", or empty for all"); 01563 01564 yco -= ysize; 01565 break; 01566 } 01567 case SENS_JOYSTICK: 01568 { 01569 01570 ysize = 72; 01571 01572 glRects(xco, yco-ysize, xco+width, yco); 01573 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 01574 01575 /* line 1: header */ 01576 draw_default_sensor_header(sens, block, xco, yco, width); 01577 01578 joy= sens->data; 01579 01580 uiDefButC(block, NUM, 1, "Index:", xco+10, yco-44, 0.33 * (width-20), 19, 01581 &joy->joyindex, 0, SENS_JOY_MAXINDEX-1, 100, 0, 01582 "Specify which joystick to use"); 01583 01584 str= "Type %t|Button %x0|Axis %x1|Single Axis %x3|Hat%x2"; 01585 uiDefButC(block, MENU, B_REDR, str, xco+87, yco-44, 0.26 * (width-20), 19, 01586 &joy->type, 0, 31, 0, 0, 01587 "The type of event this joystick sensor is triggered on"); 01588 01589 if (joy->type != SENS_JOY_AXIS_SINGLE) { 01590 if (joy->flag & SENS_JOY_ANY_EVENT) { 01591 switch (joy->type) { 01592 case SENS_JOY_AXIS: 01593 str = "All Axis Events"; 01594 break; 01595 case SENS_JOY_BUTTON: 01596 str = "All Button Events"; 01597 break; 01598 default: 01599 str = "All Hat Events"; 01600 break; 01601 } 01602 } else { 01603 str = "All"; 01604 } 01605 01606 uiDefButBitS(block, TOG, SENS_JOY_ANY_EVENT, B_REDR, str, 01607 xco+10 + 0.475 * (width-20), yco-68, ((joy->flag & SENS_JOY_ANY_EVENT) ? 0.525 : 0.12) * (width-20), 19, 01608 &joy->flag, 0, 0, 0, 0, 01609 "Triggered by all events on this joysticks current type (axis/button/hat)"); 01610 } 01611 if(joy->type == SENS_JOY_BUTTON) 01612 { 01613 if ((joy->flag & SENS_JOY_ANY_EVENT)==0) { 01614 uiDefButI(block, NUM, 1, "Number:", xco+10 + 0.6 * (width-20), yco-68, 0.4 * (width-20), 19, 01615 &joy->button, 0, 18, 100, 0, 01616 "Specify which button to use"); 01617 } 01618 } 01619 else if(joy->type == SENS_JOY_AXIS) 01620 { 01621 uiDefButS(block, NUM, 1, "Number:", xco+10, yco-68, 0.46 * (width-20), 19, 01622 &joy->axis, 1, 8.0, 100, 0, 01623 "Specify which axis pair to use, 1 is useually the main direction input"); 01624 01625 uiDefButI(block, NUM, 1, "Threshold:", xco+10 + 0.6 * (width-20),yco-44, 0.4 * (width-20), 19, 01626 &joy->precision, 0, 32768.0, 100, 0, 01627 "Specify the precision of the axis"); 01628 01629 if ((joy->flag & SENS_JOY_ANY_EVENT)==0) { 01630 str = "Type %t|Up Axis %x1 |Down Axis %x3|Left Axis %x2|Right Axis %x0"; 01631 uiDefButI(block, MENU, B_REDR, str, xco+10 + 0.6 * (width-20), yco-68, 0.4 * (width-20), 19, 01632 &joy->axisf, 2.0, 31, 0, 0, 01633 "The direction of the axis, use 'All Events' to receive events on any direction"); 01634 } 01635 } 01636 else if (joy->type == SENS_JOY_HAT) 01637 { 01638 uiDefButI(block, NUM, 1, "Number:", xco+10, yco-68, 0.46 * (width-20), 19, 01639 &joy->hat, 1, 4.0, 100, 0, 01640 "Specify which hat to use"); 01641 01642 if ((joy->flag & SENS_JOY_ANY_EVENT)==0) { 01643 str = "Direction%t|Up%x1|Down%x4|Left%x8|Right%x2|%l|Up/Right%x3|Down/Left%x12|Up/Left%x9|Down/Right%x6"; 01644 uiDefButI(block, MENU, 0, str, xco+10 + 0.6 * (width-20), yco-68, 0.4 * (width-20), 19, 01645 &joy->hatf, 2.0, 31, 0, 0, 01646 "The direction of the hat, use 'All Events' to receive events on any direction"); 01647 } 01648 } 01649 else { /* (joy->type == SENS_JOY_AXIS_SINGLE)*/ 01650 uiDefButS(block, NUM, 1, "Number:", xco+10, yco-68, 0.46 * (width-20), 19, 01651 &joy->axis_single, 1, 16.0, 100, 0, 01652 "Specify a single axis (verticle/horizontal/other) to detect"); 01653 01654 uiDefButI(block, NUM, 1, "Threshold:", xco+10 + 0.6 * (width-20),yco-44, 0.4 * (width-20), 19, 01655 &joy->precision, 0, 32768.0, 100, 0, 01656 "Specify the precision of the axis"); 01657 } 01658 yco-= ysize; 01659 break; 01660 } 01661 } 01662 01663 return yco-4; 01664 } 01665 01666 01667 01668 static short draw_controllerbuttons(bController *cont, uiBlock *block, short xco, short yco, short width) 01669 { 01670 bExpressionCont *ec; 01671 bPythonCont *pc; 01672 short ysize; 01673 01674 switch (cont->type) { 01675 case CONT_EXPRESSION: 01676 ysize= 28; 01677 01678 UI_ThemeColor(TH_PANEL); 01679 glRects(xco, yco-ysize, xco+width, yco); 01680 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 01681 01682 /* uiDefBut(block, LABEL, 1, "Not yet...", xco,yco-24,80, 19, NULL, 0, 0, 0, 0, ""); */ 01683 ec= cont->data; 01684 /* uiDefBut(block, BUT, 1, "Variables", xco,yco-24,80, 19, NULL, 0, 0, 0, 0, "Available variables for expression"); */ 01685 uiDefBut(block, TEX, 1, "Exp:", xco + 10 , yco-21, width-20, 19, 01686 ec->str, 0, 127, 0, 0, 01687 "Expression"); 01688 01689 yco-= ysize; 01690 break; 01691 case CONT_PYTHON: 01692 ysize= 28; 01693 01694 if(cont->data==NULL) init_controller(cont); 01695 pc= cont->data; 01696 01697 UI_ThemeColor(TH_PANEL); 01698 glRects(xco, yco-ysize, xco+width, yco); 01699 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 01700 01701 01702 uiBlockBeginAlign(block); 01703 uiDefButI(block, MENU, B_REDR, "Execution Method%t|Script%x0|Module%x1", xco+4,yco-23, 66, 19, &pc->mode, 0, 0, 0, 0, "Python script type (textblock or module - faster)"); 01704 if(pc->mode==0) 01705 uiDefIDPoinBut(block, test_scriptpoin_but, ID_TXT, 1, "", xco+70,yco-23,width-74, 19, &pc->text, "Blender textblock to run as a script"); 01706 else { 01707 uiDefBut(block, TEX, 1, "", xco+70,yco-23,(width-70)-25, 19, pc->module, 0, 63, 0, 0, "Module name and function to run e.g. \"someModule.main\". Internal texts and external python files can be used"); 01708 uiDefButBitI(block, TOG, CONT_PY_DEBUG, B_REDR, "D", (xco+width)-25, yco-23, 19, 19, &pc->flag, 0, 0, 0, 0, "Continuously reload the module from disk for editing external modules without restarting"); 01709 } 01710 uiBlockEndAlign(block); 01711 01712 yco-= ysize; 01713 break; 01714 01715 default: 01716 ysize= 4; 01717 01718 UI_ThemeColor(TH_PANEL); 01719 glRects(xco, yco-ysize, xco+width, yco); 01720 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 01721 01722 yco-= ysize; 01723 } 01724 01725 return yco; 01726 } 01727 01728 static int get_col_actuator(int type) 01729 { 01730 switch(type) { 01731 case ACT_ACTION: return TH_PANEL; 01732 case ACT_SHAPEACTION: return TH_PANEL; 01733 case ACT_OBJECT: return TH_PANEL; 01734 case ACT_IPO: return TH_PANEL; 01735 case ACT_PROPERTY: return TH_PANEL; 01736 case ACT_SOUND: return TH_PANEL; 01737 case ACT_CAMERA: return TH_PANEL; 01738 case ACT_EDIT_OBJECT: return TH_PANEL; 01739 case ACT_GROUP: return TH_PANEL; 01740 case ACT_RANDOM: return TH_PANEL; 01741 case ACT_SCENE: return TH_PANEL; 01742 case ACT_MESSAGE: return TH_PANEL; 01743 case ACT_GAME: return TH_PANEL; 01744 case ACT_VISIBILITY: return TH_PANEL; 01745 case ACT_CONSTRAINT: return TH_PANEL; 01746 case ACT_STATE: return TH_PANEL; 01747 case ACT_ARMATURE: return TH_PANEL; 01748 default: return TH_PANEL; 01749 } 01750 } 01751 static void set_col_actuator(int item, int medium) 01752 { 01753 int col= get_col_actuator(item); 01754 UI_ThemeColorShade(col, medium?30:10); 01755 01756 } 01757 01758 static void change_object_actuator(bContext *UNUSED(C), void *act, void *UNUSED(arg)) 01759 { 01760 bObjectActuator *oa = act; 01761 01762 if (oa->type != oa->otype) { 01763 switch (oa->type) { 01764 case ACT_OBJECT_NORMAL: 01765 memset(oa, 0, sizeof(bObjectActuator)); 01766 oa->flag = ACT_FORCE_LOCAL|ACT_TORQUE_LOCAL|ACT_DLOC_LOCAL|ACT_DROT_LOCAL; 01767 oa->type = ACT_OBJECT_NORMAL; 01768 break; 01769 01770 case ACT_OBJECT_SERVO: 01771 memset(oa, 0, sizeof(bObjectActuator)); 01772 oa->flag = ACT_LIN_VEL_LOCAL; 01773 oa->type = ACT_OBJECT_SERVO; 01774 oa->forcerot[0] = 30.0f; 01775 oa->forcerot[1] = 0.5f; 01776 oa->forcerot[2] = 0.0f; 01777 break; 01778 } 01779 } 01780 } 01781 01782 static void change_ipo_actuator(bContext *UNUSED(C), void *arg1_but, void *arg2_ia) 01783 { 01784 bIpoActuator *ia = arg2_ia; 01785 uiBut *but = arg1_but; 01786 01787 if (but->retval & ACT_IPOFORCE) 01788 ia->flag &= ~ACT_IPOADD; 01789 else if (but->retval & ACT_IPOADD) 01790 ia->flag &= ~ACT_IPOFORCE; 01791 but->retval = B_REDR; 01792 } 01793 01794 static void update_object_actuator_PID(bContext *UNUSED(C), void *act, void *UNUSED(arg)) 01795 { 01796 bObjectActuator *oa = act; 01797 oa->forcerot[0] = 60.0f*oa->forcerot[1]; 01798 } 01799 01800 static char *get_state_name(Object *ob, short bit) 01801 { 01802 bController *cont; 01803 unsigned int mask; 01804 01805 mask = (1<<bit); 01806 cont = ob->controllers.first; 01807 while (cont) { 01808 if (cont->state_mask & mask) { 01809 return cont->name; 01810 } 01811 cont = cont->next; 01812 } 01813 return (char*)""; 01814 } 01815 01816 static void check_state_mask(bContext *C, void *arg1_but, void *arg2_mask) 01817 { 01818 wmWindow *win= CTX_wm_window(C); 01819 int shift= win->eventstate->shift; 01820 unsigned int *cont_mask = arg2_mask; 01821 uiBut *but = arg1_but; 01822 01823 if (*cont_mask == 0 || !(shift)) 01824 *cont_mask = (1<<but->retval); 01825 but->retval = B_REDR; 01826 } 01827 01828 static void check_armature_actuator(bContext *C, void *arg1_but, void *arg2_act) 01829 { 01830 bArmatureActuator *act = arg2_act; 01831 uiBut *but = arg1_but; 01832 Object *ob= CTX_data_active_object(C); 01833 01834 /* check that bone exist in the active object */ 01835 but->retval = B_REDR; 01836 check_armature_bone_constraint(ob, act->posechannel, act->constraint); 01837 } 01838 01839 01840 static short draw_actuatorbuttons(Main *bmain, Object *ob, bActuator *act, uiBlock *block, short xco, short yco, short width) 01841 { 01842 bSoundActuator *sa = NULL; 01843 bObjectActuator *oa = NULL; 01844 bIpoActuator *ia = NULL; 01845 bPropertyActuator *pa = NULL; 01846 bCameraActuator *ca = NULL; 01847 bEditObjectActuator *eoa = NULL; 01848 bConstraintActuator *coa = NULL; 01849 bSceneActuator *sca = NULL; 01850 bGroupActuator *ga = NULL; 01851 bRandomActuator *randAct = NULL; 01852 bMessageActuator *ma = NULL; 01853 bActionActuator *aa = NULL; 01854 bGameActuator *gma = NULL; 01855 bVisibilityActuator *visAct = NULL; 01856 bTwoDFilterActuator *tdfa = NULL; 01857 bParentActuator *parAct = NULL; 01858 bStateActuator *staAct = NULL; 01859 bArmatureActuator *armAct = NULL; 01860 01861 float *fp; 01862 short ysize = 0, wval; 01863 const char *str; 01864 int myline, stbit; 01865 uiBut *but; 01866 01867 01868 /* yco is at the top of the rect, draw downwards */ 01869 set_col_actuator(act->type, 0); 01870 01871 switch (act->type) 01872 { 01873 case ACT_OBJECT: 01874 { 01875 oa = act->data; 01876 wval = (width-100)/3; 01877 if (oa->type == ACT_OBJECT_NORMAL) 01878 { 01879 if ( ob->gameflag & OB_DYNAMIC ) 01880 { 01881 ysize= 175; 01882 } 01883 else 01884 { 01885 ysize= 72; 01886 } 01887 01888 glRects(xco, yco-ysize, xco+width, yco); 01889 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 01890 01891 uiBlockBeginAlign(block); 01892 uiDefBut(block, LABEL, 0, "Loc", xco, yco-45, 45, 19, NULL, 0, 0, 0, 0, "Sets the location"); 01893 uiDefButF(block, NUM, 0, "", xco+45, yco-45, wval, 19, oa->dloc, -10000.0, 10000.0, 10, 0, ""); 01894 uiDefButF(block, NUM, 0, "", xco+45+wval, yco-45, wval, 19, oa->dloc+1, -10000.0, 10000.0, 10, 0, ""); 01895 uiDefButF(block, NUM, 0, "", xco+45+2*wval, yco-45, wval, 19, oa->dloc+2, -10000.0, 10000.0, 10, 0, ""); 01896 uiBlockEndAlign(block); 01897 01898 uiDefBut(block, LABEL, 0, "Rot", xco, yco-64, 45, 19, NULL, 0, 0, 0, 0, "Sets the rotation"); 01899 uiBlockBeginAlign(block); 01900 uiDefButF(block, NUM, 0, "", xco+45, yco-64, wval, 19, oa->drot, -10000.0, 10000.0, 10, 0, ""); 01901 uiDefButF(block, NUM, 0, "", xco+45+wval, yco-64, wval, 19, oa->drot+1, -10000.0, 10000.0, 10, 0, ""); 01902 uiDefButF(block, NUM, 0, "", xco+45+2*wval, yco-64, wval, 19, oa->drot+2, -10000.0, 10000.0, 10, 0, ""); 01903 uiBlockEndAlign(block); 01904 01905 uiDefButBitS(block, TOG, ACT_DLOC_LOCAL, 0, "L", xco+45+3*wval, yco-45, 15, 19, &oa->flag, 0.0, 0.0, 0, 0, "Local transformation"); 01906 uiDefButBitS(block, TOG, ACT_DROT_LOCAL, 0, "L", xco+45+3*wval, yco-64, 15, 19, &oa->flag, 0.0, 0.0, 0, 0, "Local transformation"); 01907 01908 if ( ob->gameflag & OB_DYNAMIC ) 01909 { 01910 uiDefBut(block, LABEL, 0, "Force", xco, yco-87, 55, 19, NULL, 0, 0, 0, 0, "Sets the force"); 01911 uiBlockBeginAlign(block); 01912 uiDefButF(block, NUM, 0, "", xco+45, yco-87, wval, 19, oa->forceloc, -10000.0, 10000.0, 10, 0, ""); 01913 uiDefButF(block, NUM, 0, "", xco+45+wval, yco-87, wval, 19, oa->forceloc+1, -10000.0, 10000.0, 10, 0, ""); 01914 uiDefButF(block, NUM, 0, "", xco+45+2*wval, yco-87, wval, 19, oa->forceloc+2, -10000.0, 10000.0, 10, 0, ""); 01915 uiBlockEndAlign(block); 01916 01917 uiDefBut(block, LABEL, 0, "Torque", xco, yco-106, 55, 19, NULL, 0, 0, 0, 0, "Sets the torque"); 01918 uiBlockBeginAlign(block); 01919 uiDefButF(block, NUM, 0, "", xco+45, yco-106, wval, 19, oa->forcerot, -10000.0, 10000.0, 10, 0, ""); 01920 uiDefButF(block, NUM, 0, "", xco+45+wval, yco-106, wval, 19, oa->forcerot+1, -10000.0, 10000.0, 10, 0, ""); 01921 uiDefButF(block, NUM, 0, "", xco+45+2*wval, yco-106, wval, 19, oa->forcerot+2, -10000.0, 10000.0, 10, 0, ""); 01922 uiBlockEndAlign(block); 01923 } 01924 01925 if ( ob->gameflag & OB_DYNAMIC ) 01926 { 01927 uiDefBut(block, LABEL, 0, "LinV", xco, yco-129, 45, 19, NULL, 0, 0, 0, 0, "Sets the linear velocity"); 01928 uiBlockBeginAlign(block); 01929 uiDefButF(block, NUM, 0, "", xco+45, yco-129, wval, 19, oa->linearvelocity, -10000.0, 10000.0, 10, 0, ""); 01930 uiDefButF(block, NUM, 0, "", xco+45+wval, yco-129, wval, 19, oa->linearvelocity+1, -10000.0, 10000.0, 10, 0, ""); 01931 uiDefButF(block, NUM, 0, "", xco+45+2*wval, yco-129, wval, 19, oa->linearvelocity+2, -10000.0, 10000.0, 10, 0, ""); 01932 uiBlockEndAlign(block); 01933 01934 uiDefBut(block, LABEL, 0, "AngV", xco, yco-148, 45, 19, NULL, 0, 0, 0, 0, "Sets the angular velocity"); 01935 uiBlockBeginAlign(block); 01936 uiDefButF(block, NUM, 0, "", xco+45, yco-148, wval, 19, oa->angularvelocity, -10000.0, 10000.0, 10, 0, ""); 01937 uiDefButF(block, NUM, 0, "", xco+45+wval, yco-148, wval, 19, oa->angularvelocity+1, -10000.0, 10000.0, 10, 0, ""); 01938 uiDefButF(block, NUM, 0, "", xco+45+2*wval, yco-148, wval, 19, oa->angularvelocity+2, -10000.0, 10000.0, 10, 0, ""); 01939 uiBlockEndAlign(block); 01940 01941 uiDefBut(block, LABEL, 0, "Damp", xco, yco-171, 45, 19, NULL, 0, 0, 0, 0, "Number of frames to reach the target velocity"); 01942 uiDefButS(block, NUM, 0, "", xco+45, yco-171, wval, 19, &oa->damping, 0.0, 1000.0, 100, 0, ""); 01943 01944 uiDefButBitS(block, TOG, ACT_FORCE_LOCAL, 0, "L", xco+45+3*wval, yco-87, 15, 19, &oa->flag, 0.0, 0.0, 0, 0, "Local transformation"); 01945 uiDefButBitS(block, TOG, ACT_TORQUE_LOCAL, 0, "L", xco+45+3*wval, yco-106, 15, 19, &oa->flag, 0.0, 0.0, 0, 0, "Local transformation"); 01946 uiDefButBitS(block, TOG, ACT_LIN_VEL_LOCAL, 0, "L", xco+45+3*wval, yco-129, 15, 19, &oa->flag, 0.0, 0.0, 0, 0, "Local transformation"); 01947 uiDefButBitS(block, TOG, ACT_ANG_VEL_LOCAL, 0, "L", xco+45+3*wval, yco-148, 15, 19, &oa->flag, 0.0, 0.0, 0, 0, "Local transformation"); 01948 01949 uiDefButBitS(block, TOG, ACT_ADD_LIN_VEL, 0, "use_additive",xco+45+3*wval+15, yco-129, 35, 19, &oa->flag, 0.0, 0.0, 0, 0, "Toggles between ADD and SET linV"); 01950 } 01951 } else if (oa->type == ACT_OBJECT_SERVO) 01952 { 01953 ysize= 195; 01954 01955 glRects(xco, yco-ysize, xco+width, yco); 01956 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 01957 01958 uiDefBut(block, LABEL, 0, "Ref", xco, yco-45, 45, 19, NULL, 0, 0, 0, 0, ""); 01959 uiDefIDPoinBut(block, test_obpoin_but, ID_OB, 1, "OB:", xco+45, yco-45, wval*3, 19, &(oa->reference), "Reference object for velocity calculation, leave empty for world reference"); 01960 uiDefBut(block, LABEL, 0, "linV", xco, yco-68, 45, 19, NULL, 0, 0, 0, 0, "Sets the target relative linear velocity, it will be achieved by automatic application of force. Null velocity is a valid target"); 01961 uiBlockBeginAlign(block); 01962 uiDefButF(block, NUM, 0, "", xco+45, yco-68, wval, 19, oa->linearvelocity, -10000.0, 10000.0, 10, 0, ""); 01963 uiDefButF(block, NUM, 0, "", xco+45+wval, yco-68, wval, 19, oa->linearvelocity+1, -10000.0, 10000.0, 10, 0, ""); 01964 uiDefButF(block, NUM, 0, "", xco+45+2*wval, yco-68, wval, 19, oa->linearvelocity+2, -10000.0, 10000.0, 10, 0, ""); 01965 uiBlockEndAlign(block); 01966 uiDefButBitS(block, TOG, ACT_LIN_VEL_LOCAL, 0, "L", xco+45+3*wval, yco-68, 15, 19, &oa->flag, 0.0, 0.0, 0, 0, "Velocity is defined in local coordinates"); 01967 01968 uiDefBut(block, LABEL, 0, "Limit", xco, yco-91, 45, 19, NULL, 0, 0, 0, 0, "Select if the force needs to be limited along certain axis (local or global depending on LinV Local flag)"); 01969 uiBlockBeginAlign(block); 01970 uiDefButBitS(block, TOG, ACT_SERVO_LIMIT_X, B_REDR, "X", xco+45, yco-91, wval, 19, &oa->flag, 0.0, 0.0, 0, 0, "Set limit to force along the X axis"); 01971 uiDefButBitS(block, TOG, ACT_SERVO_LIMIT_Y, B_REDR, "Y", xco+45+wval, yco-91, wval, 19, &oa->flag, 0.0, 0.0, 0, 0, "Set limit to force along the Y axis"); 01972 uiDefButBitS(block, TOG, ACT_SERVO_LIMIT_Z, B_REDR, "Z", xco+45+2*wval, yco-91, wval, 19, &oa->flag, 0.0, 0.0, 0, 0, "Set limit to force along the Z axis"); 01973 uiBlockEndAlign(block); 01974 uiDefBut(block, LABEL, 0, "Max", xco, yco-110, 45, 19, NULL, 0, 0, 0, 0, "Set the upper limit for force"); 01975 uiDefBut(block, LABEL, 0, "Min", xco, yco-129, 45, 19, NULL, 0, 0, 0, 0, "Set the lower limit for force"); 01976 if (oa->flag & ACT_SERVO_LIMIT_X) { 01977 uiDefButF(block, NUM, 0, "", xco+45, yco-110, wval, 19, oa->dloc, -10000.0, 10000.0, 10, 0, ""); 01978 uiDefButF(block, NUM, 0, "", xco+45, yco-129, wval, 19, oa->drot, -10000.0, 10000.0, 10, 0, ""); 01979 } 01980 if (oa->flag & ACT_SERVO_LIMIT_Y) { 01981 uiDefButF(block, NUM, 0, "", xco+45+wval, yco-110, wval, 19, oa->dloc+1, -10000.0, 10000.0, 10, 0, ""); 01982 uiDefButF(block, NUM, 0, "", xco+45+wval, yco-129, wval, 19, oa->drot+1, -10000.0, 10000.0, 10, 0, ""); 01983 } 01984 if (oa->flag & ACT_SERVO_LIMIT_Z) { 01985 uiDefButF(block, NUM, 0, "", xco+45+2*wval, yco-110, wval, 19, oa->dloc+2, -10000.0, 10000.0, 10, 0, ""); 01986 uiDefButF(block, NUM, 0, "", xco+45+2*wval, yco-129, wval, 19, oa->drot+2, -10000.0, 10000.0, 10, 0, ""); 01987 } 01988 uiDefBut(block, LABEL, 0, "Servo", xco, yco-152, 45, 19, NULL, 0, 0, 0, 0, "Coefficients of the PID servo controller"); 01989 uiDefButF(block, NUMSLI, B_REDR, "P: ", xco+45, yco-152, wval*3, 19, oa->forcerot, 0.00, 200.0, 100, 0, "Proportional coefficient, typical value is 60x Integral coefficient"); 01990 uiDefBut(block, LABEL, 0, "Slow", xco, yco-171, 45, 19, NULL, 0, 0, 0, 0, "Low value of I coefficient correspond to slow response"); 01991 but = uiDefButF(block, NUMSLI, B_REDR, " I : ", xco+45, yco-171, wval*3, 19, oa->forcerot+1, 0.0, 3.0, 1, 0, "Integral coefficient, low value (0.01) for slow response, high value (0.5) for fast response"); 01992 uiButSetFunc(but, update_object_actuator_PID, oa, NULL); 01993 uiDefBut(block, LABEL, 0, "Fast", xco+45+3*wval, yco-171, 45, 19, NULL, 0, 0, 0, 0, "High value of I coefficient correspond to fast response"); 01994 uiDefButF(block, NUMSLI, B_REDR, "D: ", xco+45, yco-190, wval*3, 19, oa->forcerot+2, -100.0, 100.0, 100, 0, "Derivate coefficient, not required, high values can cause instability"); 01995 } 01996 str= "Motion Type %t|Simple motion %x0|Servo Control %x1"; 01997 but = uiDefButS(block, MENU, B_REDR, str, xco+40, yco-23, (width-80), 19, &oa->type, 0.0, 0.0, 0, 0, ""); 01998 oa->otype = oa->type; 01999 uiButSetFunc(but, change_object_actuator, oa, NULL); 02000 yco-= ysize; 02001 break; 02002 } 02003 case ACT_ACTION: 02004 case ACT_SHAPEACTION: 02005 { 02006 /* DrawAct */ 02007 #ifdef __NLA_ACTION_BY_MOTION_ACTUATOR 02008 ysize = 112; 02009 #else 02010 ysize= 92; 02011 #endif 02012 02013 glRects(xco, yco-ysize, xco+width, yco); 02014 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02015 02016 aa = act->data; 02017 wval = (width-60)/3; 02018 02019 // str= "Action types %t|Play %x0|Ping Pong %x1|Flipper %x2|Loop Stop %x3|Loop End %x4|Property %x6"; 02020 #ifdef __NLA_ACTION_BY_MOTION_ACTUATOR 02021 str= "Action types %t|Play %x0|Flipper %x2|Loop Stop %x3|Loop End %x4|Property %x6|Displacement %x7"; 02022 #else 02023 str= "Action types %t|Play %x0|Flipper %x2|Loop Stop %x3|Loop End %x4|Property %x6"; 02024 #endif 02025 uiDefButS(block, MENU, B_REDR, str, xco+10, yco-24, width/3, 19, &aa->type, 0.0, 0.0, 0.0, 0.0, "Action playback type"); 02026 uiDefIDPoinBut(block, test_actionpoin_but, ID_AC, 1, "AC: ", xco+10+ (width/3), yco-24, ((width/3)*2) - (20 + 60), 19, &aa->act, "Action name"); 02027 02028 uiDefButBitS(block, TOGN, 1, 0, "Continue", xco+((width/3)*2)+20, yco-24, 60, 19, 02029 &aa->end_reset, 0.0, 0.0, 0, 0, "Restore last frame when switching on/off, otherwise play from the start each time"); 02030 02031 02032 if(aa->type == ACT_ACTION_FROM_PROP) 02033 { 02034 uiDefBut(block, TEX, 0, "Prop: ",xco+10, yco-44, width-20, 19, aa->name, 0.0, 31.0, 0, 0, "Use this property to define the Action position"); 02035 } 02036 else 02037 { 02038 uiDefButF(block, NUM, 0, "Sta: ",xco+10, yco-44, (width-20)/2, 19, &aa->sta, 1.0, MAXFRAMEF, 0, 0, "Start frame"); 02039 uiDefButF(block, NUM, 0, "End: ",xco+10+(width-20)/2, yco-44, (width-20)/2, 19, &aa->end, 1.0, MAXFRAMEF, 0, 0, "End frame"); 02040 } 02041 02042 uiDefButS(block, NUM, 0, "Blendin: ", xco+10, yco-64, (width-20)/2, 19, &aa->blendin, 0.0, 32767, 0.0, 0.0, "Number of frames of motion blending"); 02043 uiDefButS(block, NUM, 0, "Priority: ", xco+10+(width-20)/2, yco-64, (width-20)/2, 19, &aa->priority, 0.0, 100.0, 0.0, 0.0, "Execution priority - lower numbers will override actions with higher numbers, With 2 or more actions at once, the overriding channels must be lower in the stack"); 02044 02045 uiDefBut(block, TEX, 0, "FrameProp: ",xco+10, yco-84, width-20, 19, aa->frameProp, 0.0, 31.0, 0, 0, "Assign the action's current frame number to this property"); 02046 02047 02048 #ifdef __NLA_ACTION_BY_MOTION_ACTUATOR 02049 if(aa->type == ACT_ACTION_MOTION) 02050 { 02051 uiDefButF(block, NUM, 0, "Cycle: ",xco+30, yco-84, (width-60)/2, 19, &aa->stridelength, 0.0, 2500.0, 0, 0, "Distance covered by a single cycle of the action"); 02052 } 02053 #endif 02054 02055 02056 02057 yco-=ysize; 02058 break; 02059 } 02060 case ACT_IPO: 02061 { 02062 ia= act->data; 02063 02064 ysize= 72; 02065 02066 glRects(xco, yco-ysize, xco+width, yco); 02067 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02068 02069 str = "Ipo types %t|Play %x0|Ping Pong %x1|Flipper %x2|Loop Stop %x3|Loop End %x4|Property %x6"; 02070 02071 uiDefButS(block, MENU, B_REDR, str, xco+10, yco-24, (width-20)/2, 19, &ia->type, 0, 0, 0, 0, ""); 02072 02073 but = uiDefButBitS(block, TOG, ACT_IPOFORCE, ACT_IPOFORCE, 02074 "Force", xco+10+(width-20)/2, yco-24, (width-20)/4-10, 19, 02075 &ia->flag, 0, 0, 0, 0, 02076 "Apply Ipo as a global or local force depending on the local option (dynamic objects only)"); 02077 uiButSetFunc(but, change_ipo_actuator, but, ia); 02078 02079 but = uiDefButBitS(block, TOG, ACT_IPOADD, ACT_IPOADD, 02080 "Add", xco+3*(width-20)/4, yco-24, (width-20)/4-10, 19, 02081 &ia->flag, 0, 0, 0, 0, 02082 "Ipo is added to the current loc/rot/scale in global or local coordinate according to Local flag"); 02083 uiButSetFunc(but, change_ipo_actuator, but, ia); 02084 02085 /* Only show the do-force-local toggle if force is requested */ 02086 if (ia->flag & (ACT_IPOFORCE|ACT_IPOADD)) { 02087 uiDefButBitS(block, TOG, ACT_IPOLOCAL, 0, 02088 "L", xco+width-30, yco-24, 20, 19, 02089 &ia->flag, 0, 0, 0, 0, 02090 "Let the ipo acts in local coordinates, used in Force and Add mode"); 02091 } 02092 02093 if(ia->type==ACT_IPO_FROM_PROP) { 02094 uiDefBut(block, TEX, 0, 02095 "Prop: ", xco+10, yco-44, width-80, 19, 02096 ia->name, 0.0, 31.0, 0, 0, 02097 "Use this property to define the Ipo position"); 02098 } 02099 else { 02100 uiDefButF(block, NUM, 0, 02101 "Sta", xco+10, yco-44, (width-80)/2, 19, 02102 &ia->sta, 1.0, MAXFRAMEF, 0, 0, 02103 "Start frame"); 02104 uiDefButF(block, NUM, 0, 02105 "End", xco+10+(width-80)/2, yco-44, (width-80)/2, 19, 02106 &ia->end, 1.0, MAXFRAMEF, 0, 0, 02107 "End frame"); 02108 } 02109 uiDefButBitS(block, TOG, ACT_IPOCHILD, B_REDR, 02110 "Child", xco+10+(width-80), yco-44, 60, 19, 02111 &ia->flag, 0, 0, 0, 0, 02112 "Update IPO on all children Objects as well"); 02113 uiDefBut(block, TEX, 0, 02114 "FrameProp: ", xco+10, yco-64, width-20, 19, 02115 ia->frameProp, 0.0, 31.0, 0, 0, 02116 "Assign the action's current frame number to this property"); 02117 02118 yco-= ysize; 02119 break; 02120 } 02121 case ACT_PROPERTY: 02122 { 02123 ysize= 68; 02124 02125 glRects(xco, yco-ysize, xco+width, yco); 02126 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02127 02128 pa= act->data; 02129 02130 str= "Type%t|Assign%x0|Add %x1|Copy %x2|Toggle (bool/int/float/timer)%x3"; 02131 uiDefButI(block, MENU, B_REDR, str, xco+30,yco-24,width-60, 19, &pa->type, 0, 31, 0, 0, "Type"); 02132 02133 uiDefBut(block, TEX, 1, "Prop: ", xco+30,yco-44,width-60, 19, pa->name, 0, 31, 0, 0, "Property name"); 02134 02135 02136 if(pa->type==ACT_PROP_TOGGLE) { 02137 /* no ui */ 02138 ysize -= 22; 02139 } 02140 else if(pa->type==ACT_PROP_COPY) { 02141 uiDefIDPoinBut(block, test_obpoin_but, ID_OB, 1, "OB:", xco+10, yco-64, (width-20)/2, 19, &(pa->ob), "Copy from this Object"); 02142 uiDefBut(block, TEX, 1, "Prop: ", xco+10+(width-20)/2, yco-64, (width-20)/2, 19, pa->value, 0, 31, 0, 0, "Copy this property"); 02143 } 02144 else { 02145 uiDefBut(block, TEX, 1, "Value: ", xco+30,yco-64,width-60, 19, pa->value, 0, 31, 0, 0, "change with this value, use \"\" around strings"); 02146 } 02147 yco-= ysize; 02148 02149 break; 02150 } 02151 case ACT_SOUND: 02152 { 02153 sa = act->data; 02154 sa->sndnr = 0; 02155 02156 if(sa->flag & ACT_SND_3D_SOUND) 02157 ysize = 180; 02158 else 02159 ysize = 92; 02160 02161 wval = (width-20)/2; 02162 glRects(xco, yco-ysize, xco+width, yco); 02163 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02164 02165 if(bmain->sound.first) { 02166 IDnames_to_pupstring(&str, "Sound files", NULL, &(bmain->sound), (ID *)sa->sound, &(sa->sndnr)); 02167 /* reset this value, it is for handling the event */ 02168 sa->sndnr = 0; 02169 uiDefButS(block, MENU, B_SOUNDACT_BROWSE, str, xco+10,yco-22,20,19, &(sa->sndnr), 0, 0, 0, 0, ""); 02170 uiDefButO(block, BUT, "sound.open", 0, "Load Sound", xco+wval+10, yco-22, wval, 19, "Load a sound file. Remember to set caching on for small sounds that are played often."); 02171 02172 if(sa->sound) { 02173 char dummy_str[] = "Sound mode %t|Play Stop %x0|Play End %x1|Loop Stop %x2|Loop End %x3|Loop Ping Pong Stop %x5|Loop Ping Pong %x4"; 02174 uiDefBut(block, TEX, B_IDNAME, "SO:",xco+30,yco-22,wval-20,19, ((ID *)sa->sound)->name+2, 0.0, 21.0, 0, 0, ""); 02175 uiDefButS(block, MENU, 1, dummy_str,xco+10,yco-44,width-20, 19, &sa->type, 0.0, 0.0, 0, 0, ""); 02176 uiDefButF(block, NUM, 0, "Volume:", xco+10,yco-66,wval, 19, &sa->volume, 0.0, 1.0, 0, 0, "Sets the volume of this sound"); 02177 uiDefButF(block, NUM, 0, "Pitch:",xco+wval+10,yco-66,wval, 19, &sa->pitch,-12.0, 12.0, 0, 0, "Sets the pitch of this sound"); 02178 uiDefButS(block, TOG | BIT, 0, "3D Sound", xco+10, yco-88, width-20, 19, &sa->flag, 0.0, 1.0, 0.0, 0.0, "Plays the sound positioned in 3D space."); 02179 if(sa->flag & ACT_SND_3D_SOUND) 02180 { 02181 uiDefButF(block, NUM, 0, "Minimum Gain: ", xco+10, yco-110, wval, 19, &sa->sound3D.min_gain, 0.0, 1.0, 0.0, 0.0, "The minimum gain of the sound, no matter how far it is away."); 02182 uiDefButF(block, NUM, 0, "Maximum Gain: ", xco+10, yco-132, wval, 19, &sa->sound3D.max_gain, 0.0, 1.0, 0.0, 0.0, "The maximum gain of the sound, no matter how near it is."); 02183 uiDefButF(block, NUM, 0, "Reference Distance: ", xco+10, yco-154, wval, 19, &sa->sound3D.reference_distance, 0.0, FLT_MAX, 0.0, 0.0, "The reference distance is the distance where the sound has a gain of 1.0."); 02184 uiDefButF(block, NUM, 0, "Maximum Distance: ", xco+10, yco-176, wval, 19, &sa->sound3D.max_distance, 0.0, FLT_MAX, 0.0, 0.0, "The maximum distance at which you can hear the sound."); 02185 uiDefButF(block, NUM, 0, "Rolloff: ", xco+wval+10, yco-110, wval, 19, &sa->sound3D.rolloff_factor, 0.0, 5.0, 0.0, 0.0, "The rolloff factor defines the influence factor on volume depending on distance."); 02186 uiDefButF(block, NUM, 0, "Cone Outer Gain: ", xco+wval+10, yco-132, wval, 19, &sa->sound3D.cone_outer_gain, 0.0, 1.0, 0.0, 0.0, "The gain outside the outer cone. The gain in the outer cone will be interpolated between this value and the normal gain in the inner cone."); 02187 uiDefButF(block, NUM, 0, "Cone Outer Angle: ", xco+wval+10, yco-154, wval, 19, &sa->sound3D.cone_outer_angle, 0.0, 360.0, 0.0, 0.0, "The angle of the outer cone."); 02188 uiDefButF(block, NUM, 0, "Cone Inner Angle: ", xco+wval+10, yco-176, wval, 19, &sa->sound3D.cone_inner_angle, 0.0, 360.0, 0.0, 0.0, "The angle of the inner cone."); 02189 } 02190 } 02191 MEM_freeN((void *)str); 02192 } 02193 else { 02194 uiDefButO(block, BUT, "sound.open", 0, "Load Sound", xco+10, yco-22, width-20, 19, "Load a sound file."); 02195 } 02196 02197 yco-= ysize; 02198 02199 break; 02200 } 02201 case ACT_CAMERA: 02202 02203 ysize= 48; 02204 02205 glRects(xco, yco-ysize, xco+width, yco); 02206 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02207 02208 ca= act->data; 02209 02210 uiDefIDPoinBut(block, test_obpoin_but, ID_OB, 1, "OB:", xco+10, yco-24, (width-20)/2, 19, &(ca->ob), "Look at this Object"); 02211 uiDefButF(block, NUM, 0, "Height:", xco+10+(width-20)/2, yco-24, (width-20)/2, 19, &ca->height, 0.0, 20.0, 0, 0, ""); 02212 02213 uiDefButF(block, NUM, 0, "Min:", xco+10, yco-44, (width-60)/2, 19, &ca->min, 0.0, 20.0, 0, 0, ""); 02214 02215 if(ca->axis==0) ca->axis= 'x'; 02216 uiDefButS(block, ROW, 0, "X", xco+10+(width-60)/2, yco-44, 20, 19, &ca->axis, 4.0, (float)'x', 0, 0, "Camera tries to get behind the X axis"); 02217 uiDefButS(block, ROW, 0, "Y", xco+30+(width-60)/2, yco-44, 20, 19, &ca->axis, 4.0, (float)'y', 0, 0, "Camera tries to get behind the Y axis"); 02218 02219 uiDefButF(block, NUM, 0, "Max:", xco+20+(width)/2, yco-44, (width-60)/2, 19, &ca->max, 0.0, 20.0, 0, 0, ""); 02220 02221 yco-= ysize; 02222 02223 break; 02224 02225 case ACT_EDIT_OBJECT: 02226 02227 eoa= act->data; 02228 02229 if(eoa->type==ACT_EDOB_ADD_OBJECT) { 02230 ysize = 92; 02231 glRects(xco, yco-ysize, xco+width, yco); 02232 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02233 02234 uiDefIDPoinBut(block, test_obpoin_but, ID_OB, 1, "OB:", xco+10, yco-44, (width-20)/2, 19, &(eoa->ob), "Add this Object and all its children (cant be on an visible layer)"); 02235 uiDefButI(block, NUM, 0, "Time:", xco+10+(width-20)/2, yco-44, (width-20)/2, 19, &eoa->time, 0.0, 2000.0, 0, 0, "Duration the new Object lives"); 02236 02237 wval= (width-60)/3; 02238 uiDefBut(block, LABEL, 0, "linV", xco, yco-68, 45, 19, 02239 NULL, 0, 0, 0, 0, 02240 "Velocity upon creation"); 02241 uiDefButF(block, NUM, 0, "", xco+45, yco-68, wval, 19, 02242 eoa->linVelocity, -100.0, 100.0, 10, 0, 02243 "Velocity upon creation, x component"); 02244 uiDefButF(block, NUM, 0, "", xco+45+wval, yco-68, wval, 19, 02245 eoa->linVelocity+1, -100.0, 100.0, 10, 0, 02246 "Velocity upon creation, y component"); 02247 uiDefButF(block, NUM, 0, "", xco+45+2*wval, yco-68, wval, 19, 02248 eoa->linVelocity+2, -100.0, 100.0, 10, 0, 02249 "Velocity upon creation, z component"); 02250 uiDefButBitS(block, TOG, ACT_EDOB_LOCAL_LINV, 0, "L", xco+45+3*wval, yco-68, 15, 19, 02251 &eoa->localflag, 0.0, 0.0, 0, 0, 02252 "Apply the transformation locally"); 02253 02254 02255 uiDefBut(block, LABEL, 0, "AngV", xco, yco-90, 45, 19, 02256 NULL, 0, 0, 0, 0, 02257 "Angular velocity upon creation"); 02258 uiDefButF(block, NUM, 0, "", xco+45, yco-90, wval, 19, 02259 eoa->angVelocity, -10000.0, 10000.0, 10, 0, 02260 "Angular velocity upon creation, x component"); 02261 uiDefButF(block, NUM, 0, "", xco+45+wval, yco-90, wval, 19, 02262 eoa->angVelocity+1, -10000.0, 10000.0, 10, 0, 02263 "Angular velocity upon creation, y component"); 02264 uiDefButF(block, NUM, 0, "", xco+45+2*wval, yco-90, wval, 19, 02265 eoa->angVelocity+2, -10000.0, 10000.0, 10, 0, 02266 "Angular velocity upon creation, z component"); 02267 uiDefButBitS(block, TOG, ACT_EDOB_LOCAL_ANGV, 0, "L", xco+45+3*wval, yco-90, 15, 19, 02268 &eoa->localflag, 0.0, 0.0, 0, 0, 02269 "Apply the rotation locally"); 02270 02271 02272 } 02273 else if(eoa->type==ACT_EDOB_END_OBJECT) { 02274 ysize= 28; 02275 glRects(xco, yco-ysize, xco+width, yco); 02276 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02277 } 02278 else if(eoa->type==ACT_EDOB_REPLACE_MESH) { 02279 ysize= 48; 02280 glRects(xco, yco-ysize, xco+width, yco); 02281 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02282 02283 uiDefIDPoinBut(block, test_meshpoin_but, ID_ME, 1, "ME:", xco+40, yco-44, (width-80)/2, 19, &(eoa->me), "replace the existing, when left blank 'Phys' will remake the existing physics mesh"); 02284 02285 uiDefButBitS(block, TOGN, ACT_EDOB_REPLACE_MESH_NOGFX, 0, "Gfx", xco+40 + (width-80)/2, yco-44, (width-80)/4, 19, &eoa->flag, 0, 0, 0, 0, "Replace the display mesh"); 02286 uiDefButBitS(block, TOG, ACT_EDOB_REPLACE_MESH_PHYS, 0, "Phys", xco+40 + (width-80)/2 +(width-80)/4, yco-44, (width-80)/4, 19, &eoa->flag, 0, 0, 0, 0, "Replace the physics mesh (triangle bounds only. compound shapes not supported)"); 02287 } 02288 else if(eoa->type==ACT_EDOB_TRACK_TO) { 02289 ysize= 48; 02290 glRects(xco, yco-ysize, xco+width, yco); 02291 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02292 02293 uiDefIDPoinBut(block, test_obpoin_but, ID_OB, 1, "OB:", xco+10, yco-44, (width-20)/2, 19, &(eoa->ob), "Track to this Object"); 02294 uiDefButI(block, NUM, 0, "Time:", xco+10+(width-20)/2, yco-44, (width-20)/2-40, 19, &eoa->time, 0.0, 2000.0, 0, 0, "Duration the tracking takes"); 02295 uiDefButS(block, TOG, 0, "3D", xco+width-50, yco-44, 40, 19, &eoa->flag, 0.0, 0.0, 0, 0, "Enable 3D tracking"); 02296 } 02297 else if(eoa->type==ACT_EDOB_DYNAMICS) { 02298 ysize= 69; 02299 glRects(xco, yco-ysize, xco+width, yco); 02300 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02301 02302 str= "Dynamic Operation %t|Restore Dynamics %x0|Suspend Dynamics %x1|Enable Rigid Body %x2|Disable Rigid Body %x3|Set Mass %x4"; 02303 uiDefButS(block, MENU, B_REDR, str, xco+40, yco-44, (width-80), 19, &(eoa->dyn_operation), 0.0, 0.0, 0, 0, ""); 02304 if(eoa->dyn_operation==4) { 02305 uiDefButF(block, NUM, 0, "", xco+40, yco-63, width-80, 19, 02306 &eoa->mass, 0.0, 10000.0, 10, 0, 02307 "Mass for object"); 02308 } 02309 } 02310 str= "Edit Object %t|Add Object %x0|End Object %x1|Replace Mesh %x2|Track to %x3|Dynamics %x4"; 02311 uiDefButS(block, MENU, B_REDR, str, xco+40, yco-24, (width-80), 19, &eoa->type, 0.0, 0.0, 0, 0, ""); 02312 02313 yco-= ysize; 02314 02315 break; 02316 02317 case ACT_CONSTRAINT: 02318 coa= act->data; 02319 02320 if (coa->type == ACT_CONST_TYPE_LOC) { 02321 ysize= 69; 02322 02323 glRects(xco, yco-ysize, xco+width, yco); 02324 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02325 02326 /* str= "Limit %t|None %x0|Loc X %x1|Loc Y %x2|Loc Z %x4|Rot X %x8|Rot Y %x16|Rot Z %x32"; */ 02327 /* coa->flag &= ~(63); */ 02328 str= "Limit %t|None %x0|Loc X %x1|Loc Y %x2|Loc Z %x4"; 02329 coa->flag &= 7; 02330 coa->time = 0; 02331 uiDefButS(block, MENU, 1, str, xco+10, yco-65, 70, 19, &coa->flag, 0.0, 0.0, 0, 0, ""); 02332 02333 uiDefButS(block, NUM, 0, "damp", xco+10, yco-45, 70, 19, &coa->damp, 0.0, 100.0, 0, 0, "Damping factor: time constant (in frame) of low pass filter"); 02334 uiDefBut(block, LABEL, 0, "Min", xco+80, yco-45, (width-90)/2, 19, NULL, 0.0, 0.0, 0, 0, ""); 02335 uiDefBut(block, LABEL, 0, "Max", xco+80+(width-90)/2, yco-45, (width-90)/2, 19, NULL, 0.0, 0.0, 0, 0, ""); 02336 02337 if(coa->flag & ACT_CONST_LOCX) fp= coa->minloc; 02338 else if(coa->flag & ACT_CONST_LOCY) fp= coa->minloc+1; 02339 else if(coa->flag & ACT_CONST_LOCZ) fp= coa->minloc+2; 02340 else if(coa->flag & ACT_CONST_ROTX) fp= coa->minrot; 02341 else if(coa->flag & ACT_CONST_ROTY) fp= coa->minrot+1; 02342 else fp= coa->minrot+2; 02343 02344 uiDefButF(block, NUM, 0, "", xco+80, yco-65, (width-90)/2, 19, fp, -2000.0, 2000.0, 10, 0, ""); 02345 uiDefButF(block, NUM, 0, "", xco+80+(width-90)/2, yco-65, (width-90)/2, 19, fp+3, -2000.0, 2000.0, 10, 0, ""); 02346 } else if (coa->type == ACT_CONST_TYPE_DIST) { 02347 ysize= 106; 02348 02349 glRects(xco, yco-ysize, xco+width, yco); 02350 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02351 02352 str= "Direction %t|None %x0|X axis %x1|Y axis %x2|Z axis %x4|-X axis %x8|-Y axis %x16|-Z axis %x32"; 02353 uiDefButS(block, MENU, B_REDR, str, xco+10, yco-65, 70, 19, &coa->mode, 0.0, 0.0, 0, 0, "Set the direction of the ray"); 02354 02355 uiDefButS(block, NUM, 0, "damp", xco+10, yco-45, 70, 19, &coa->damp, 0.0, 100.0, 0, 0, "Damping factor: time constant (in frame) of low pass filter"); 02356 uiDefBut(block, LABEL, 0, "Range", xco+80, yco-45, (width-115)/2, 19, NULL, 0.0, 0.0, 0, 0, "Set the maximum length of ray"); 02357 uiDefButBitS(block, TOG, ACT_CONST_DISTANCE, B_REDR, "Dist", xco+80+(width-115)/2, yco-45, (width-115)/2, 19, &coa->flag, 0.0, 0.0, 0, 0, "Force distance of object to point of impact of ray"); 02358 uiDefButBitS(block, TOG, ACT_CONST_LOCAL, 0, "L", xco+80+(width-115), yco-45, 25, 19, 02359 &coa->flag, 0.0, 0.0, 0, 0, "Set ray along object's axis or global axis"); 02360 02361 if(coa->mode & (ACT_CONST_DIRPX|ACT_CONST_DIRNX)) fp= coa->minloc; 02362 else if(coa->mode & (ACT_CONST_DIRPY|ACT_CONST_DIRNY)) fp= coa->minloc+1; 02363 else fp= coa->minloc+2; 02364 02365 uiDefButF(block, NUM, 0, "", xco+80, yco-65, (width-115)/2, 19, fp+3, 0.0, 2000.0, 10, 0, "Maximum length of ray"); 02366 if (coa->flag & ACT_CONST_DISTANCE) 02367 uiDefButF(block, NUM, 0, "", xco+80+(width-115)/2, yco-65, (width-115)/2, 19, fp, -2000.0, 2000.0, 10, 0, "Keep this distance to target"); 02368 uiDefButBitS(block, TOG, ACT_CONST_NORMAL, 0, "N", xco+80+(width-115), yco-65, 25, 19, 02369 &coa->flag, 0.0, 0.0, 0, 0, "Set object axis along (local axis) or parallel (global axis) to the normal at hit position"); 02370 uiDefButBitS(block, TOG, ACT_CONST_MATERIAL, B_REDR, "M/P", xco+10, yco-84, 40, 19, 02371 &coa->flag, 0.0, 0.0, 0, 0, "Detect material instead of property"); 02372 if (coa->flag & ACT_CONST_MATERIAL) 02373 { 02374 uiDefBut(block, TEX, 1, "Material:", xco + 50, yco-84, (width-60), 19, 02375 coa->matprop, 0, 31, 0, 0, 02376 "Ray detects only Objects with this material"); 02377 } 02378 else 02379 { 02380 uiDefBut(block, TEX, 1, "Property:", xco + 50, yco-84, (width-60), 19, 02381 coa->matprop, 0, 31, 0, 0, 02382 "Ray detect only Objects with this property"); 02383 } 02384 uiDefButBitS(block, TOG, ACT_CONST_PERMANENT, 0, "PER", xco+10, yco-103, 40, 19, 02385 &coa->flag, 0.0, 0.0, 0, 0, "Persistent actuator: stays active even if ray does not reach target"); 02386 uiDefButS(block, NUM, 0, "time", xco+50, yco-103, (width-60)/2, 19, &(coa->time), 0.0, 1000.0, 0, 0, "Maximum activation time in frame, 0 for unlimited"); 02387 uiDefButS(block, NUM, 0, "rotDamp", xco+50+(width-60)/2, yco-103, (width-60)/2, 19, &(coa->rotdamp), 0.0, 100.0, 0, 0, "Use a different damping for orientation"); 02388 } else if (coa->type == ACT_CONST_TYPE_ORI) { 02389 ysize= 87; 02390 02391 glRects(xco, yco-ysize, xco+width, yco); 02392 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02393 02394 str= "Direction %t|None %x0|X axis %x1|Y axis %x2|Z axis %x4"; 02395 uiDefButS(block, MENU, B_REDR, str, xco+10, yco-65, 70, 19, &coa->mode, 0.0, 0.0, 0, 0, "Select the axis to be aligned along the reference direction"); 02396 02397 uiDefButS(block, NUM, 0, "damp", xco+10, yco-45, 70, 19, &coa->damp, 0.0, 100.0, 0, 0, "Damping factor: time constant (in frame) of low pass filter"); 02398 uiDefBut(block, LABEL, 0, "X", xco+80, yco-45, (width-115)/3, 19, NULL, 0.0, 0.0, 0, 0, ""); 02399 uiDefBut(block, LABEL, 0, "Y", xco+80+(width-115)/3, yco-45, (width-115)/3, 19, NULL, 0.0, 0.0, 0, 0, ""); 02400 uiDefBut(block, LABEL, 0, "Z", xco+80+2*(width-115)/3, yco-45, (width-115)/3, 19, NULL, 0.0, 0.0, 0, 0, ""); 02401 02402 uiDefButF(block, NUM, 0, "", xco+80, yco-65, (width-115)/3, 19, &coa->maxrot[0], -2000.0, 2000.0, 10, 0, "X component of reference direction"); 02403 uiDefButF(block, NUM, 0, "", xco+80+(width-115)/3, yco-65, (width-115)/3, 19, &coa->maxrot[1], -2000.0, 2000.0, 10, 0, "Y component of reference direction"); 02404 uiDefButF(block, NUM, 0, "", xco+80+2*(width-115)/3, yco-65, (width-115)/3, 19, &coa->maxrot[2], -2000.0, 2000.0, 10, 0, "Z component of reference direction"); 02405 02406 uiDefButS(block, NUM, 0, "time", xco+10, yco-84, 70, 19, &(coa->time), 0.0, 1000.0, 0, 0, "Maximum activation time in frame, 0 for unlimited"); 02407 uiDefButF(block, NUM, 0, "min", xco+80, yco-84, (width-115)/2, 19, &(coa->minloc[0]), 0.0, 180.0, 10, 1, "Minimum angle (in degree) to maintain with target direction. No correction is done if angle with target direction is between min and max"); 02408 uiDefButF(block, NUM, 0, "max", xco+80+(width-115)/2, yco-84, (width-115)/2, 19, &(coa->maxloc[0]), 0.0, 180.0, 10, 1, "Maximum angle (in degree) allowed with target direction. No correction is done if angle with target direction is between min and max"); 02409 } else if (coa->type == ACT_CONST_TYPE_FH) { 02410 ysize= 106; 02411 02412 glRects(xco, yco-ysize, xco+width, yco); 02413 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02414 02415 str= "Direction %t|None %x0|X axis %x1|Y axis %x2|Z axis %x4|-X axis %x8|-Y axis %x16|-Z axis %x32"; 02416 uiDefButS(block, MENU, B_REDR, str, xco+10, yco-65, 70, 19, &coa->mode, 0.0, 0.0, 0, 0, "Set the direction of the ray (in world coordinate)"); 02417 02418 if(coa->mode & (ACT_CONST_DIRPX|ACT_CONST_DIRNX)) fp= coa->minloc; 02419 else if(coa->mode & (ACT_CONST_DIRPY|ACT_CONST_DIRNY)) fp= coa->minloc+1; 02420 else fp= coa->minloc+2; 02421 02422 uiDefButF(block, NUM, 0, "damp", xco+10, yco-45, (width-70)/2, 19, &coa->maxrot[0], 0.0, 1.0, 1, 0, "Damping factor of the Fh spring force"); 02423 uiDefButF(block, NUM, 0, "dist", xco+10+(width-70)/2, yco-45, (width-70)/2, 19, fp, 0.010, 2000.0, 10, 0, "Height of the Fh area"); 02424 uiDefButBitS(block, TOG, ACT_CONST_DOROTFH, 0, "Rot Fh", xco+10+(width-70), yco-45, 50, 19, &coa->flag, 0.0, 0.0, 0, 0, "Keep object axis parallel to normal"); 02425 02426 uiDefButF(block, NUMSLI, 0, "Fh ", xco+80, yco-65, (width-115), 19, fp+3, 0.0, 1.0, 0, 0, "Spring force within the Fh area"); 02427 uiDefButBitS(block, TOG, ACT_CONST_NORMAL, 0, "N", xco+80+(width-115), yco-65, 25, 19, 02428 &coa->flag, 0.0, 0.0, 0, 0, "Add a horizontal spring force on slopes"); 02429 uiDefButBitS(block, TOG, ACT_CONST_MATERIAL, B_REDR, "M/P", xco+10, yco-84, 40, 19, 02430 &coa->flag, 0.0, 0.0, 0, 0, "Detect material instead of property"); 02431 if (coa->flag & ACT_CONST_MATERIAL) 02432 { 02433 uiDefBut(block, TEX, 1, "Material:", xco + 50, yco-84, (width-60), 19, 02434 coa->matprop, 0, 31, 0, 0, 02435 "Ray detects only Objects with this material"); 02436 } 02437 else 02438 { 02439 uiDefBut(block, TEX, 1, "Property:", xco + 50, yco-84, (width-60), 19, 02440 coa->matprop, 0, 31, 0, 0, 02441 "Ray detect only Objects with this property"); 02442 } 02443 uiDefButBitS(block, TOG, ACT_CONST_PERMANENT, 0, "PER", xco+10, yco-103, 40, 19, 02444 &coa->flag, 0.0, 0.0, 0, 0, "Persistent actuator: stays active even if ray does not reach target"); 02445 uiDefButS(block, NUM, 0, "time", xco+50, yco-103, 90, 19, &(coa->time), 0.0, 1000.0, 0, 0, "Maximum activation time in frame, 0 for unlimited"); 02446 uiDefButF(block, NUM, 0, "rotDamp", xco+140, yco-103, (width-150), 19, &coa->maxrot[1], 0.0, 1.0, 1, 0, "Use a different damping for rotation"); 02447 } 02448 str= "Constraint Type %t|Location %x0|Distance %x1|Orientation %x2|Force field %x3"; 02449 but = uiDefButS(block, MENU, B_REDR, str, xco+40, yco-23, (width-80), 19, &coa->type, 0.0, 0.0, 0, 0, ""); 02450 yco-= ysize; 02451 break; 02452 02453 case ACT_SCENE: 02454 sca= act->data; 02455 02456 if(sca->type==ACT_SCENE_RESTART) { 02457 ysize= 28; 02458 glRects(xco, yco-ysize, xco+width, yco); 02459 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02460 } 02461 else if(sca->type==ACT_SCENE_CAMERA) { 02462 02463 ysize= 48; 02464 glRects(xco, yco-ysize, xco+width, yco); 02465 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02466 02467 uiDefIDPoinBut(block, test_obpoin_but, ID_OB, 1, "OB:", xco+40, yco-44, (width-80), 19, &(sca->camera), "Set this Camera. Leave empty to refer to self object"); 02468 } 02469 else if(sca->type==ACT_SCENE_SET) { 02470 02471 ysize= 48; 02472 glRects(xco, yco-ysize, xco+width, yco); 02473 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02474 02475 uiDefIDPoinBut(block, test_scenepoin_but, ID_SCE, 1, "SCE:", xco+40, yco-44, (width-80), 19, &(sca->scene), "Set this Scene"); 02476 } 02477 else if(sca->type==ACT_SCENE_ADD_FRONT) { 02478 02479 ysize= 48; 02480 glRects(xco, yco-ysize, xco+width, yco); 02481 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02482 02483 uiDefIDPoinBut(block, test_scenepoin_but, ID_SCE, 1, "SCE:", xco+40, yco-44, (width-80), 19, &(sca->scene), "Add an Overlay Scene"); 02484 } 02485 else if(sca->type==ACT_SCENE_ADD_BACK) { 02486 02487 ysize= 48; 02488 glRects(xco, yco-ysize, xco+width, yco); 02489 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02490 02491 uiDefIDPoinBut(block, test_scenepoin_but, ID_SCE, 1, "SCE:", xco+40, yco-44, (width-80), 19, &(sca->scene), "Add a Background Scene"); 02492 } 02493 else if(sca->type==ACT_SCENE_REMOVE) { 02494 02495 ysize= 48; 02496 glRects(xco, yco-ysize, xco+width, yco); 02497 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02498 02499 uiDefIDPoinBut(block, test_scenepoin_but, ID_SCE, 1, "SCE:", xco+40, yco-44, (width-80), 19, &(sca->scene), "Remove a Scene"); 02500 } 02501 else if(sca->type==ACT_SCENE_SUSPEND) { 02502 02503 ysize= 48; 02504 glRects(xco, yco-ysize, xco+width, yco); 02505 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02506 02507 uiDefIDPoinBut(block, test_scenepoin_but, ID_SCE, 1, "SCE:", xco+40, yco-44, (width-80), 19, &(sca->scene), "Pause a Scene"); 02508 } 02509 else if(sca->type==ACT_SCENE_RESUME) { 02510 02511 ysize= 48; 02512 glRects(xco, yco-ysize, xco+width, yco); 02513 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02514 02515 uiDefIDPoinBut(block, test_scenepoin_but, ID_SCE, 1, "SCE:", xco+40, yco-44, (width-80), 19, &(sca->scene), "Unpause a Scene"); 02516 } 02517 02518 str= "Scene %t|Restart %x0|Set Scene %x1|Set Camera %x2|Add OverlayScene %x3|Add BackgroundScene %x4|Remove Scene %x5|Suspend Scene %x6|Resume Scene %x7"; 02519 uiDefButS(block, MENU, B_REDR, str, xco+40, yco-24, (width-80), 19, &sca->type, 0.0, 0.0, 0, 0, ""); 02520 02521 yco-= ysize; 02522 break; 02523 case ACT_GAME: 02524 { 02525 gma = act->data; 02526 if (gma->type == ACT_GAME_LOAD) 02527 { 02528 //ysize = 68; 02529 ysize = 48; 02530 glRects(xco, yco-ysize, xco+width, yco); 02531 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02532 uiDefBut(block, TEX, 1, "File: ", xco+10, yco-44,width-20,19, &(gma->filename), 0, 63, 0, 0, "Load this blend file, use the \"//\" prefix for a path relative to the current blend file"); 02533 // uiDefBut(block, TEX, 1, "Anim: ", xco+10, yco-64,width-20,19, &(gma->loadaniname), 0, 63, 0, 0, "Use this loadinganimation"); 02534 } 02535 /* else if (gma->type == ACT_GAME_START) 02536 { 02537 ysize = 68; 02538 glRects(xco, yco-ysize, xco+width, yco); 02539 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02540 02541 uiDefBut(block, TEX, 1, "File: ", xco+10, yco-44,width-20,19, &(gma->filename), 0, 63, 0, 0, "Load this file"); 02542 uiDefBut(block, TEX, 1, "Anim: ", xco+10, yco-64,width-20,19, &(gma->loadaniname), 0, 63, 0, 0, "Use this loadinganimation"); 02543 } 02544 */ else if (ELEM4(gma->type, ACT_GAME_RESTART, ACT_GAME_QUIT, ACT_GAME_SAVECFG, ACT_GAME_LOADCFG)) 02545 { 02546 ysize = 28; 02547 glRects(xco, yco-ysize, xco+width, yco); 02548 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02549 } 02550 02551 //str = "Scene %t|Load game%x0|Start loaded game%x1|Restart this game%x2|Quit this game %x3"; 02552 str = "Scene %t|Start new game%x0|Restart this game%x2|Quit this game %x3|Save bge.logic.globalDict %x4|Load bge.logic.globalDict %x5"; 02553 uiDefButS(block, MENU, B_REDR, str, xco+40, yco-24, (width-80), 19, &gma->type, 0.0, 0.0, 0, 0, ""); 02554 02555 yco -= ysize; 02556 break; 02557 } 02558 case ACT_GROUP: 02559 ga= act->data; 02560 02561 ysize= 52; 02562 02563 glRects(xco, yco-ysize, xco+width, yco); 02564 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02565 02566 str= "GroupKey types %t|Set Key %x6|Play %x0|Ping Pong %x1|Flipper %x2|Loop Stop %x3|Loop End %x4|Property %x5"; 02567 02568 uiDefButS(block, MENU, 1, str, xco+20, yco-24, width-40, 19, &ga->type, 0, 0, 0, 0, ""); 02569 if(ga->type==ACT_GROUP_SET) { 02570 uiDefBut(block, TEX, 0, "Key: ", xco+20, yco-44, (width-10)/2, 19, ga->name, 0.0, 31.0, 0, 0, "This name defines groupkey to be set"); 02571 uiDefButI(block, NUM, 0, "Frame:", xco+20+(width-10)/2, yco-44, (width-70)/2, 19, &ga->sta, 0.0, 2500.0, 0, 0, "Set this frame"); 02572 } 02573 else if(ga->type==ACT_GROUP_FROM_PROP) { 02574 uiDefBut(block, TEX, 0, "Prop: ", xco+20, yco-44, width-40, 19, ga->name, 0.0, 31.0, 0, 0, "Use this property to define the Group position"); 02575 } 02576 else { 02577 uiDefButI(block, NUM, 0, "State", xco+20, yco-44, (width-40)/2, 19, &ga->sta, 0.0, 2500.0, 0, 0, "Start frame"); 02578 uiDefButI(block, NUM, 0, "End", xco+20+(width-40)/2, yco-44, (width-40)/2, 19, &ga->end, 0.0, 2500.0, 0, 0, "End frame"); 02579 } 02580 yco-= ysize; 02581 break; 02582 02583 case ACT_VISIBILITY: 02584 ysize = 24; 02585 02586 glRects(xco, yco-ysize, xco+width, yco); 02587 uiEmboss((float)xco, 02588 (float)yco-ysize, (float)xco+width, (float)yco, 1); 02589 02590 visAct = act->data; 02591 02592 uiBlockBeginAlign(block); 02593 uiDefButBitI(block, TOGN, ACT_VISIBILITY_INVISIBLE, B_REDR, 02594 "Visible", 02595 xco + 10, yco - 20, (width - 20)/3, 19, &visAct->flag, 02596 0.0, 0.0, 0, 0, 02597 "Set the objects visible. Initialized from the objects render restriction toggle (access in the outliner)"); 02598 uiDefButBitI(block, TOG, ACT_VISIBILITY_OCCLUSION, B_REDR, 02599 "Occlusion", 02600 xco + 10 + ((width - 20)/3), yco - 20, (width - 20)/3, 19, &visAct->flag, 02601 0.0, 0.0, 0, 0, 02602 "Set the object to occlude objects behind it. Initialized from the object type in physics button"); 02603 uiBlockEndAlign(block); 02604 02605 uiDefButBitI(block, TOG, ACT_VISIBILITY_RECURSIVE, 0, 02606 "Children", 02607 xco + 10 + (((width - 20)/3)*2)+10, yco - 20, ((width - 20)/3)-10, 19, &visAct->flag, 02608 0.0, 0.0, 0, 0, 02609 "Sets all the children of this object to the same visibility/occlusion recursively"); 02610 02611 yco-= ysize; 02612 02613 break; 02614 02615 case ACT_STATE: 02616 ysize = 34; 02617 02618 glRects(xco, yco-ysize, xco+width, yco); 02619 uiEmboss((float)xco, 02620 (float)yco-ysize, (float)xco+width, (float)yco, 1); 02621 02622 staAct = act->data; 02623 02624 str= "Operation %t|Cpy %x0|Add %x1|Sub %x2|Inv %x3"; 02625 02626 uiDefButI(block, MENU, B_REDR, str, 02627 xco + 10, yco - 24, 65, 19, &staAct->type, 02628 0.0, 0.0, 0, 0, 02629 "Select the bit operation on object state mask"); 02630 02631 for (wval=0; wval<15; wval+=5) { 02632 uiBlockBeginAlign(block); 02633 for (stbit=0; stbit<5; stbit++) { 02634 but = uiDefButBitI(block, TOG, 1<<(stbit+wval), stbit+wval, "", (short)(xco+85+12*stbit+13*wval), yco-17, 12, 12, (int *)&(staAct->mask), 0, 0, 0, 0, get_state_name(ob, (short)(stbit+wval))); 02635 uiButSetFunc(but, check_state_mask, but, &(staAct->mask)); 02636 } 02637 for (stbit=0; stbit<5; stbit++) { 02638 but = uiDefButBitI(block, TOG, 1<<(stbit+wval+15), stbit+wval+15, "", (short)(xco+85+12*stbit+13*wval), yco-29, 12, 12, (int *)&(staAct->mask), 0, 0, 0, 0, get_state_name(ob, (short)(stbit+wval+15))); 02639 uiButSetFunc(but, check_state_mask, but, &(staAct->mask)); 02640 } 02641 } 02642 uiBlockEndAlign(block); 02643 02644 yco-= ysize; 02645 02646 break; 02647 02648 case ACT_RANDOM: 02649 ysize = 69; 02650 02651 glRects(xco, yco-ysize, xco+width, yco); 02652 uiEmboss((float)xco, 02653 (float)yco-ysize, (float)xco+width, (float)yco, 1); 02654 02655 randAct = act->data; 02656 02657 /* 1. seed */ 02658 uiDefButI(block, NUM, 1, "Seed: ", (xco+10),yco-24, 0.4 *(width-20), 19, 02659 &randAct->seed, 0, 1000, 0, 0, 02660 "Initial seed of the random generator. Use Python for more freedom. " 02661 " (Choose 0 for not random)"); 02662 02663 /* 2. distribution type */ 02664 /* One pick per distribution. These numbers MUST match the #defines */ 02665 /* in game.h !!! */ 02666 str= "Distribution %t|Bool Constant %x0|Bool Uniform %x1" 02667 "|Bool Bernoulli %x2|Int Constant %x3|Int Uniform %x4" 02668 "|Int Poisson %x5|Float Constant %x6|Float Uniform %x7" 02669 "|Float Normal %x8|Float Neg. Exp. %x9"; 02670 uiDefButI(block, MENU, B_REDR, str, (xco+10) + 0.4 * (width-20), yco-24, 0.6 * (width-20), 19, 02671 &randAct->distribution, 0.0, 0.0, 0, 0, 02672 "Choose the type of distribution"); 02673 02674 /* 3. property */ 02675 uiDefBut(block, TEX, 1, "Property:", (xco+10), yco-44, (width-20), 19, 02676 &randAct->propname, 0, 31, 0, 0, 02677 "Assign the random value to this property"); 02678 02679 /*4. and 5. arguments for the distribution*/ 02680 switch (randAct->distribution) { 02681 case ACT_RANDOM_BOOL_CONST: 02682 uiDefButBitI(block, TOG, 1, 1, "Always true", (xco+10), yco-64, (width-20), 19, 02683 &randAct->int_arg_1, 2.0, 1, 0, 0, 02684 "Always false or always true"); 02685 break; 02686 case ACT_RANDOM_BOOL_UNIFORM: 02687 uiDefBut(block, LABEL, 0, " Do a 50-50 pick", (xco+10), yco-64, (width-20), 19, 02688 NULL, 0, 0, 0, 0, 02689 "Choose between true and false, 50% chance each"); 02690 break; 02691 case ACT_RANDOM_BOOL_BERNOUILLI: 02692 uiDefButF(block, NUM, 1, "Chance", (xco+10), yco-64, (width-20), 19, 02693 &randAct->float_arg_1, 0.0, 1.0, 0, 0, 02694 "Pick a number between 0 and 1. Success if you stay " 02695 "below this value"); 02696 break; 02697 case ACT_RANDOM_INT_CONST: 02698 uiDefButI(block, NUM, 1, "Value: ", (xco+10), yco-64, (width-20), 19, 02699 &randAct->int_arg_1, -1000, 1000, 0, 0, 02700 "Always return this number"); 02701 break; 02702 case ACT_RANDOM_INT_UNIFORM: 02703 uiDefButI(block, NUM, 1, "Min: ", (xco+10), yco-64, (width-20)/2, 19, 02704 &randAct->int_arg_1, -1000, 1000, 0, 0, 02705 "Choose a number from a range. " 02706 "Lower boundary of the range"); 02707 uiDefButI(block, NUM, 1, "Max: ", (xco+10) + (width-20)/2, yco-64, (width-20)/2, 19, 02708 &randAct->int_arg_2, -1000, 1000, 0, 0, 02709 "Choose a number from a range. " 02710 "Upper boundary of the range"); 02711 break; 02712 case ACT_RANDOM_INT_POISSON: 02713 uiDefButF(block, NUM, 1, "Mean: ", (xco+10), yco-64, (width-20), 19, 02714 &randAct->float_arg_1, 0.01, 100.0, 0, 0, 02715 "Expected mean value of the distribution"); 02716 break; 02717 case ACT_RANDOM_FLOAT_CONST: 02718 uiDefButF(block, NUM, 1, "Value: ", (xco+10), yco-64, (width-20), 19, 02719 &randAct->float_arg_1, 0.0, 1.0, 0, 0, 02720 "Always return this number"); 02721 break; 02722 case ACT_RANDOM_FLOAT_UNIFORM: 02723 uiDefButF(block, NUM, 1, "Min: ", (xco+10), yco-64, (width-20)/2, 19, 02724 &randAct->float_arg_1, -10000.0, 10000.0, 0, 0, 02725 "Choose a number from a range" 02726 "Lower boundary of the range"); 02727 uiDefButF(block, NUM, 1, "Max: ", (xco+10) + (width-20)/2, yco-64, (width-20)/2, 19, 02728 &randAct->float_arg_2, -10000.0, 10000.0, 0, 0, 02729 "Choose a number from a range" 02730 "Upper boundary of the range"); 02731 break; 02732 case ACT_RANDOM_FLOAT_NORMAL: 02733 uiDefButF(block, NUM, 1, "Mean: ", (xco+10), yco-64, (width-20)/2, 19, 02734 &randAct->float_arg_1, -10000.0, 10000.0, 0, 0, 02735 "A normal distribution. Mean of the distribution"); 02736 uiDefButF(block, NUM, 1, "SD: ", (xco+10) + (width-20)/2, yco-64, (width-20)/2, 19, 02737 &randAct->float_arg_2, 0.0, 10000.0, 0, 0, 02738 "A normal distribution. Standard deviation of the " 02739 "distribution"); 02740 break; 02741 case ACT_RANDOM_FLOAT_NEGATIVE_EXPONENTIAL: 02742 uiDefButF(block, NUM, 1, "Half-life time: ", (xco+10), yco-64, (width-20), 19, 02743 &randAct->float_arg_1, 0.001, 10000.0, 0, 0, 02744 "Negative exponential dropoff"); 02745 break; 02746 default: 02747 ; /* don't know what this distro is... can be useful for testing */ 02748 /* though :) */ 02749 } 02750 02751 yco-= ysize; 02752 break; 02753 case ACT_MESSAGE: 02754 ma = act->data; 02755 02756 ysize = 4 + (3 * 24); /* footer + number of lines * 24 pixels/line */ 02757 02758 glRects(xco, yco-ysize, xco+width, yco); 02759 uiEmboss((float)xco, (float)yco-ysize, 02760 (float)xco+width, (float)yco, 1); 02761 02762 myline=1; 02763 02764 /* line 1: To */ 02765 uiDefBut(block, TEX, 1, "To: ", 02766 (xco+10), (yco-(myline++*24)), (width-20), 19, 02767 &ma->toPropName, 0, 31, 0, 0, 02768 "Optional send message to objects with this name only, or empty to broadcast"); 02769 02770 /* line 2: Message Subject */ 02771 uiDefBut(block, TEX, 1, "Subject: ", 02772 (xco+10), (yco-(myline++*24)), (width-20), 19, 02773 &ma->subject, 0, 31, 0, 0, 02774 "Optional message subject. This is what can be filtered on"); 02775 02776 /* line 3: Text/Property */ 02777 uiDefButBitS(block, TOG, 1, B_REDR, "T/P", 02778 (xco+10),(yco-(myline*24)), (0.20 * (width-20)), 19, 02779 &ma->bodyType, 0.0, 0.0, 0, 0, 02780 "Toggle message type: either Text or a PropertyName"); 02781 02782 if (ma->bodyType == ACT_MESG_MESG) 02783 { 02784 /* line 3: Message Body */ 02785 uiDefBut(block, TEX, 1, "Body: ", 02786 (xco+10+(0.20*(width-20))),(yco-(myline++*24)),(0.8*(width-20)),19, 02787 &ma->body, 0, 31, 0, 0, 02788 "Optional message body Text"); 02789 } else 02790 { 02791 /* line 3: Property body (set by property) */ 02792 uiDefBut(block, TEX, 1, "Propname: ", 02793 (xco+10+(0.20*(width-20))),(yco-(myline++*24)),(0.8*(width-20)),19, 02794 &ma->body, 0, 31, 0, 0, 02795 "The message body will be set by the Property Value"); 02796 } 02797 02798 yco -= ysize; 02799 break; 02800 case ACT_2DFILTER: 02801 tdfa = act->data; 02802 02803 ysize = 50; 02804 if(tdfa->type == ACT_2DFILTER_CUSTOMFILTER) 02805 { 02806 ysize +=20; 02807 } 02808 glRects( xco, yco-ysize, xco+width, yco ); 02809 uiEmboss( (float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1 ); 02810 02811 switch(tdfa->type) 02812 { 02813 case ACT_2DFILTER_MOTIONBLUR: 02814 if(!tdfa->flag) 02815 { 02816 uiDefButS(block, TOG, B_REDR, "D", xco+30,yco-44,19, 19, &tdfa->flag, 0.0, 0.0, 0.0, 0.0, "Disable Motion Blur"); 02817 uiDefButF(block, NUM, B_REDR, "Value:", xco+52,yco-44,width-82,19,&tdfa->float_arg,0.0,1.0,0.0,0.0,"Set motion blur value"); 02818 } 02819 else 02820 { 02821 uiDefButS(block, TOG, B_REDR, "Disabled", xco+30,yco-44,width-60, 19, &tdfa->flag, 0.0, 0.0, 0.0, 0.0, "Enable Motion Blur"); 02822 } 02823 break; 02824 case ACT_2DFILTER_BLUR: 02825 case ACT_2DFILTER_SHARPEN: 02826 case ACT_2DFILTER_DILATION: 02827 case ACT_2DFILTER_EROSION: 02828 case ACT_2DFILTER_LAPLACIAN: 02829 case ACT_2DFILTER_SOBEL: 02830 case ACT_2DFILTER_PREWITT: 02831 case ACT_2DFILTER_GRAYSCALE: 02832 case ACT_2DFILTER_SEPIA: 02833 case ACT_2DFILTER_INVERT: 02834 case ACT_2DFILTER_NOFILTER: 02835 case ACT_2DFILTER_DISABLED: 02836 case ACT_2DFILTER_ENABLED: 02837 uiDefButI(block, NUM, B_REDR, "Pass Number:", xco+30,yco-44,width-60,19,&tdfa->int_arg,0.0,MAX_RENDER_PASS-1,0.0,0.0,"Set filter order"); 02838 break; 02839 case ACT_2DFILTER_CUSTOMFILTER: 02840 uiDefButI(block, NUM, B_REDR, "Pass Number:", xco+30,yco-44,width-60,19,&tdfa->int_arg,0.0,MAX_RENDER_PASS-1,0.0,0.0,"Set filter order"); 02841 uiDefIDPoinBut(block, test_scriptpoin_but, ID_SCRIPT, 1, "Script: ", xco+30,yco-64,width-60, 19, &tdfa->text, ""); 02842 break; 02843 } 02844 02845 str= "2D Filter %t|Motion Blur %x1|Blur %x2|Sharpen %x3|Dilation %x4|Erosion %x5|" 02846 "Laplacian %x6|Sobel %x7|Prewitt %x8|Gray Scale %x9|Sepia %x10|Invert %x11|Custom Filter %x12|" 02847 "Enable Filter %x-2|Disable Filter %x-1|Remove Filter %x0|"; 02848 uiDefButS(block, MENU, B_REDR, str, xco+30,yco-24,width-60, 19, &tdfa->type, 0.0, 0.0, 0.0, 0.0, "2D filter type"); 02849 02850 yco -= ysize; 02851 break; 02852 case ACT_PARENT: 02853 parAct = act->data; 02854 02855 if(parAct->type==ACT_PARENT_SET) { 02856 02857 ysize= 48; 02858 glRects(xco, yco-ysize, xco+width, yco); 02859 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02860 uiDefIDPoinBut(block, test_obpoin_but, ID_OB, 1, "OB:", xco+95, yco-24, (width-100), 19, &(parAct->ob), "Set this object as parent"); 02861 uiBlockBeginAlign(block); 02862 uiDefButBitS(block, TOGN, ACT_PARENT_COMPOUND, B_REDR, 02863 "Compound", 02864 xco + 5, yco - 44, (width - 10)/2, 19, &parAct->flag, 02865 0.0, 0.0, 0, 0, 02866 "Add this object shape to the parent shape (only if the parent shape is already compound)"); 02867 uiDefButBitS(block, TOGN, ACT_PARENT_GHOST, B_REDR, 02868 "Ghost", 02869 xco + 5 + ((width - 10)/2), yco - 44, (width - 10)/2, 19, &parAct->flag, 02870 0.0, 0.0, 0, 0, 02871 "Make this object ghost while parented (only if not compound)"); 02872 uiBlockEndAlign(block); 02873 } 02874 else if(parAct->type==ACT_PARENT_REMOVE) { 02875 02876 ysize= 28; 02877 glRects(xco, yco-ysize, xco+width, yco); 02878 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02879 } 02880 02881 str= "Parent %t|Set Parent %x0|Remove Parent %x1"; 02882 uiDefButI(block, MENU, B_REDR, str, xco+5, yco-24, parAct->type==1?(width-80):90, 19, &parAct->type, 0.0, 0.0, 0, 0, ""); 02883 02884 yco-= ysize; 02885 break; 02886 case ACT_ARMATURE: 02887 armAct = act->data; 02888 02889 if (ob->type == OB_ARMATURE) { 02890 str= "Constraint %t|Run armature %x0|Enable %x1|Disable %x2|Set target %x3|Set weight %x4"; 02891 uiDefButI(block, MENU, B_REDR, str, xco+5, yco-24, (width-10)*0.35, 19, &armAct->type, 0.0, 0.0, 0, 0, ""); 02892 02893 switch (armAct->type) { 02894 case ACT_ARM_RUN: 02895 ysize = 28; 02896 break; 02897 default: 02898 uiBlockBeginAlign(block); 02899 but = uiDefBut(block, TEX, 1, "Bone: ", 02900 (xco+5), (yco-44), (width-10)/2, 19, 02901 armAct->posechannel, 0, 31, 0, 0, 02902 "Bone on which the constraint is defined"); 02903 uiButSetFunc(but, check_armature_actuator, but, armAct); 02904 but = uiDefBut(block, TEX, 1, "Cons: ", 02905 (xco+5)+(width-10)/2, (yco-44), (width-10)/2, 19, 02906 armAct->constraint, 0, 31, 0, 0, 02907 "Name of the constraint you want to control"); 02908 uiButSetFunc(but, check_armature_actuator, but, armAct); 02909 uiBlockEndAlign(block); 02910 ysize = 48; 02911 switch (armAct->type) { 02912 case ACT_ARM_SETTARGET: 02913 uiDefIDPoinBut(block, test_obpoin_but, ID_OB, 1, "Target: ", xco+5, yco-64, (width-10), 19, &(armAct->target), "Set this object as the target of the constraint"); 02914 uiDefIDPoinBut(block, test_obpoin_but, ID_OB, 1, "Secondary Target: ", xco+5, yco-84, (width-10), 19, &(armAct->subtarget), "Set this object as the secondary target of the constraint (only IK polar target at the moment)"); 02915 ysize += 40; 02916 break; 02917 case ACT_ARM_SETWEIGHT: 02918 uiDefButF(block, NUM, B_REDR, "Weight:", xco+5+(width-10)*0.35,yco-24,(width-10)*0.65,19,&armAct->weight,0.0,1.0,0.0,0.0,"Set weight of this constraint"); 02919 break; 02920 } 02921 } 02922 } 02923 glRects(xco, yco-ysize, xco+width, yco); 02924 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02925 yco-= ysize; 02926 break; 02927 02928 default: 02929 ysize= 4; 02930 02931 glRects(xco, yco-ysize, xco+width, yco); 02932 uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); 02933 02934 yco-= ysize; 02935 break; 02936 } 02937 02938 uiBlockSetEmboss(block, UI_EMBOSS); 02939 02940 return yco-4; 02941 } 02942 02943 static void do_sensor_menu(bContext *C, void *UNUSED(arg), int event) 02944 { 02945 SpaceLogic *slogic= CTX_wm_space_logic(C); 02946 ID **idar; 02947 Object *ob; 02948 bSensor *sens; 02949 short count, a; 02950 02951 idar= get_selected_and_linked_obs(C, &count, slogic->scaflag); 02952 02953 for(a=0; a<count; a++) { 02954 ob= (Object *)idar[a]; 02955 if(event==0 || event==2) ob->scaflag |= OB_SHOWSENS; 02956 else if(event==1) ob->scaflag &= ~OB_SHOWSENS; 02957 } 02958 02959 for(a=0; a<count; a++) { 02960 ob= (Object *)idar[a]; 02961 sens= ob->sensors.first; 02962 while(sens) { 02963 if(event==2) sens->flag |= SENS_SHOW; 02964 else if(event==3) sens->flag &= ~SENS_SHOW; 02965 sens= sens->next; 02966 } 02967 } 02968 02969 if(idar) MEM_freeN(idar); 02970 } 02971 02972 static uiBlock *sensor_menu(bContext *C, ARegion *ar, void *UNUSED(arg)) 02973 { 02974 uiBlock *block; 02975 int yco=0; 02976 02977 block= uiBeginBlock(C, ar, "filemenu", UI_EMBOSSP); 02978 uiBlockSetButmFunc(block, do_sensor_menu, NULL); 02979 02980 uiDefBut(block, BUTM, 1, "Show Objects", 0, (short)(yco-=20), 160, 19, NULL, 0.0, 0.0, 1, 0, ""); 02981 uiDefBut(block, BUTM, 1, "Hide Objects", 0, (short)(yco-=20), 160, 19, NULL, 0.0, 0.0, 1, 1, ""); 02982 uiDefBut(block, SEPR, 0, "", 0, (short)(yco-=6), 160, 6, NULL, 0.0, 0.0, 0, 0, ""); 02983 uiDefBut(block, BUTM, 1, "Show Sensors", 0, (short)(yco-=20), 160, 19, NULL, 0.0, 0.0, 1, 2, ""); 02984 uiDefBut(block, BUTM, 1, "Hide Sensors", 0, (short)(yco-=20), 160, 19, NULL, 0.0, 0.0, 1, 3, ""); 02985 02986 uiBlockSetDirection(block, UI_TOP); 02987 uiEndBlock(C, block); 02988 02989 return block; 02990 } 02991 02992 static void do_controller_menu(bContext *C, void *UNUSED(arg), int event) 02993 { 02994 SpaceLogic *slogic= CTX_wm_space_logic(C); 02995 ID **idar; 02996 Object *ob; 02997 bController *cont; 02998 short count, a; 02999 03000 idar= get_selected_and_linked_obs(C, &count, slogic->scaflag); 03001 03002 for(a=0; a<count; a++) { 03003 ob= (Object *)idar[a]; 03004 if(event==0 || event==2) ob->scaflag |= OB_SHOWCONT; 03005 else if(event==1) ob->scaflag &= ~OB_SHOWCONT; 03006 } 03007 03008 for(a=0; a<count; a++) { 03009 ob= (Object *)idar[a]; 03010 cont= ob->controllers.first; 03011 while(cont) { 03012 if(event==2) cont->flag |= CONT_SHOW; 03013 else if(event==3) cont->flag &= ~CONT_SHOW; 03014 cont= cont->next; 03015 } 03016 } 03017 03018 if(idar) MEM_freeN(idar); 03019 } 03020 03021 static uiBlock *controller_menu(bContext *C, ARegion *ar, void *UNUSED(arg)) 03022 { 03023 uiBlock *block; 03024 int yco=0; 03025 03026 block= uiBeginBlock(C, ar, "filemenu", UI_EMBOSSP); 03027 uiBlockSetButmFunc(block, do_controller_menu, NULL); 03028 03029 uiDefBut(block, BUTM, 1, "Show Objects", 0, (short)(yco-=20), 160, 19, NULL, 0.0, 0.0, 1, 0, ""); 03030 uiDefBut(block, BUTM, 1, "Hide Objects", 0,(short)(yco-=20), 160, 19, NULL, 0.0, 0.0, 1, 1, ""); 03031 uiDefBut(block, SEPR, 0, "", 0, (short)(yco-=6), 160, 6, NULL, 0.0, 0.0, 0, 0, ""); 03032 uiDefBut(block, BUTM, 1, "Show Controllers", 0, (short)(yco-=20), 160, 19, NULL, 0.0, 0.0, 2, 2, ""); 03033 uiDefBut(block, BUTM, 1, "Hide Controllers", 0, (short)(yco-=20), 160, 19, NULL, 0.0, 0.0, 3, 3, ""); 03034 03035 uiBlockSetDirection(block, UI_TOP); 03036 uiEndBlock(C, block); 03037 03038 return block; 03039 } 03040 03041 static void do_actuator_menu(bContext *C, void *UNUSED(arg), int event) 03042 { 03043 SpaceLogic *slogic= CTX_wm_space_logic(C); 03044 ID **idar; 03045 Object *ob; 03046 bActuator *act; 03047 short count, a; 03048 03049 idar= get_selected_and_linked_obs(C, &count, slogic->scaflag); 03050 03051 for(a=0; a<count; a++) { 03052 ob= (Object *)idar[a]; 03053 if(event==0 || event==2) ob->scaflag |= OB_SHOWACT; 03054 else if(event==1) ob->scaflag &= ~OB_SHOWACT; 03055 } 03056 03057 for(a=0; a<count; a++) { 03058 ob= (Object *)idar[a]; 03059 act= ob->actuators.first; 03060 while(act) { 03061 if(event==2) act->flag |= ACT_SHOW; 03062 else if(event==3) act->flag &= ~ACT_SHOW; 03063 act= act->next; 03064 } 03065 } 03066 03067 if(idar) MEM_freeN(idar); 03068 } 03069 03070 static uiBlock *actuator_menu(bContext *C, ARegion *ar, void *UNUSED(arg)) 03071 { 03072 uiBlock *block; 03073 int xco=0; 03074 03075 block= uiBeginBlock(C, ar, "filemenu", UI_EMBOSSP); 03076 uiBlockSetButmFunc(block, do_actuator_menu, NULL); 03077 03078 uiDefBut(block, BUTM, 1, "Show Objects", 0, (short)(xco-=20), 160, 19, NULL, 0.0, 0.0, 1, 0, ""); 03079 uiDefBut(block, BUTM, 1, "Hide Objects", 0, (short)(xco-=20), 160, 19, NULL, 0.0, 0.0, 1, 1, ""); 03080 uiDefBut(block, SEPR, 0, "", 0, (short)(xco-=6), 160, 6, NULL, 0.0, 0.0, 0, 0, ""); 03081 uiDefBut(block, BUTM, 1, "Show Actuators", 0, (short)(xco-=20), 160, 19, NULL, 0.0, 0.0, 1, 2, ""); 03082 uiDefBut(block, BUTM, 1, "Hide Actuators", 0, (short)(xco-=20), 160, 19, NULL, 0.0, 0.0, 1, 3, ""); 03083 03084 uiBlockSetDirection(block, UI_TOP); 03085 uiEndBlock(C, block); 03086 03087 return block; 03088 } 03089 03090 03091 03092 static void check_controller_state_mask(bContext *UNUSED(C), void *arg1_but, void *arg2_mask) 03093 { 03094 unsigned int *cont_mask = arg2_mask; 03095 uiBut *but = arg1_but; 03096 03097 /* a controller is always in a single state */ 03098 *cont_mask = (1<<but->retval); 03099 but->retval = B_REDR; 03100 } 03101 03102 static int first_bit(unsigned int mask) 03103 { 03104 int bit; 03105 03106 for (bit=0; bit<32; bit++) { 03107 if (mask & (1<<bit)) 03108 return bit; 03109 } 03110 return -1; 03111 } 03112 03113 static uiBlock *controller_state_mask_menu(bContext *C, ARegion *ar, void *arg_cont) 03114 { 03115 uiBlock *block; 03116 uiBut *but; 03117 bController *cont = arg_cont; 03118 03119 short yco = 12, xco = 0, stbit, offset; 03120 03121 block= uiBeginBlock(C, ar, "Controller state mask", UI_EMBOSS); 03122 03123 /* use this for a fake extra empy space around the buttons */ 03124 uiDefBut(block, LABEL, 0, "", -5, -5, 200, 34, NULL, 0, 0, 0, 0, ""); 03125 03126 for (offset=0; offset<15; offset+=5) { 03127 uiBlockBeginAlign(block); 03128 for (stbit=0; stbit<5; stbit++) { 03129 but = uiDefButBitI(block, TOG, (1<<(stbit+offset)), (stbit+offset), "", (short)(xco+12*stbit+13*offset), yco, 12, 12, (int *)&(cont->state_mask), 0, 0, 0, 0, ""); 03130 uiButSetFunc(but, check_controller_state_mask, but, &(cont->state_mask)); 03131 } 03132 for (stbit=0; stbit<5; stbit++) { 03133 but = uiDefButBitI(block, TOG, (1<<(stbit+offset+15)), (stbit+offset+15), "", (short)(xco+12*stbit+13*offset), yco-12, 12, 12, (int *)&(cont->state_mask), 0, 0, 0, 0, ""); 03134 uiButSetFunc(but, check_controller_state_mask, but, &(cont->state_mask)); 03135 } 03136 } 03137 uiBlockEndAlign(block); 03138 03139 uiBlockSetDirection(block, UI_TOP); 03140 uiEndBlock(C, block); 03141 03142 return block; 03143 } 03144 03145 static void do_object_state_menu(bContext *UNUSED(C), void *arg, int event) 03146 { 03147 Object *ob = arg; 03148 03149 switch (event) { 03150 case 0: 03151 ob->state = 0x3FFFFFFF; 03152 break; 03153 case 1: 03154 ob->state = ob->init_state; 03155 if (!ob->state) 03156 ob->state = 1; 03157 break; 03158 case 2: 03159 ob->init_state = ob->state; 03160 break; 03161 } 03162 } 03163 03164 static uiBlock *object_state_mask_menu(bContext *C, ARegion *ar, void *arg_obj) 03165 { 03166 uiBlock *block; 03167 short xco = 0; 03168 03169 block= uiBeginBlock(C, ar, "obstatemenu", UI_EMBOSSP); 03170 uiBlockSetButmFunc(block, do_object_state_menu, arg_obj); 03171 03172 uiDefBut(block, BUTM, 1, "Set all bits", 0, (short)(xco-=20), 160, 19, NULL, 0.0, 0.0, 1, 0, ""); 03173 uiDefBut(block, BUTM, 1, "Recall init state", 0, (short)(xco-=20), 160, 19, NULL, 0.0, 0.0, 1, 1, ""); 03174 uiDefBut(block, SEPR, 0, "", 0, (short)(xco-=6), 160, 6, NULL, 0.0, 0.0, 0, 0, ""); 03175 uiDefBut(block, BUTM, 1, "Store init state", 0, (short)(xco-=20), 160, 19, NULL, 0.0, 0.0, 1, 2, ""); 03176 03177 uiBlockSetDirection(block, UI_TOP); 03178 uiEndBlock(C, block); 03179 03180 return block; 03181 } 03182 03183 static int is_sensor_linked(uiBlock *block, bSensor *sens) 03184 { 03185 bController *cont; 03186 int i; 03187 03188 for (i=0; i<sens->totlinks; i++) { 03189 cont = sens->links[i]; 03190 if (uiFindInlink(block, cont) != NULL) 03191 return 1; 03192 } 03193 return 0; 03194 } 03195 03196 /* Sensors code */ 03197 03198 static void draw_sensor_header(uiLayout *layout, PointerRNA *ptr, PointerRNA *logic_ptr) 03199 { 03200 uiLayout *box, *row, *subrow; 03201 bSensor *sens= (bSensor *)ptr->data; 03202 03203 box= uiLayoutBox(layout); 03204 row= uiLayoutRow(box, 0); 03205 03206 uiItemR(row, ptr, "show_expanded", UI_ITEM_R_NO_BG, "", ICON_NONE); 03207 if(RNA_boolean_get(ptr, "show_expanded")) { 03208 uiItemR(row, ptr, "type", 0, "", ICON_NONE); 03209 uiItemR(row, ptr, "name", 0, "", ICON_NONE); 03210 } else { 03211 uiItemL(row, sensor_name(sens->type), ICON_NONE); 03212 uiItemL(row, sens->name, ICON_NONE); 03213 } 03214 03215 subrow= uiLayoutRow(row, 0); 03216 uiLayoutSetActive(subrow, ((RNA_boolean_get(logic_ptr, "show_sensors_active_states") 03217 && RNA_boolean_get(ptr, "show_expanded")) || RNA_boolean_get(ptr, "pin"))); 03218 uiItemR(subrow, ptr, "pin", UI_ITEM_R_NO_BG, "", ICON_NONE); 03219 03220 if(RNA_boolean_get(ptr, "show_expanded")==0) { 03221 subrow= uiLayoutRow(row, 1); 03222 uiItemEnumO(subrow, "LOGIC_OT_sensor_move", "", ICON_TRIA_UP, "direction", 1); // up 03223 uiItemEnumO(subrow, "LOGIC_OT_sensor_move", "", ICON_TRIA_DOWN, "direction", 2); // down 03224 } 03225 03226 uiItemO(row, "", ICON_X, "LOGIC_OT_sensor_remove"); 03227 } 03228 03229 static void draw_sensor_internal_header(uiLayout *layout, PointerRNA *ptr) 03230 { 03231 uiLayout *box, *split, *subrow, *row; 03232 03233 box= uiLayoutBox(layout); 03234 split = uiLayoutSplit(box, 0.45, 0); 03235 03236 row= uiLayoutRow(split, 1); 03237 uiItemR(row, ptr, "use_pulse_true_level", 0, "", ICON_DOTSUP); 03238 uiItemR(row, ptr, "use_pulse_false_level", 0, "", ICON_DOTSDOWN); 03239 03240 subrow=uiLayoutRow(row, 0); 03241 uiLayoutSetActive(subrow, (RNA_boolean_get(ptr, "use_pulse_true_level") 03242 || RNA_boolean_get(ptr, "use_pulse_false_level"))); 03243 uiItemR(subrow, ptr, "frequency", 0, "Freq", ICON_NONE); 03244 03245 row= uiLayoutRow(split, 1); 03246 uiItemR(row, ptr, "use_level", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03247 uiItemR(row, ptr, "use_tap", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03248 03249 row= uiLayoutRow(split, 1); 03250 uiItemR(row, ptr, "invert", UI_ITEM_R_TOGGLE, "Invert", ICON_NONE); 03251 } 03252 /* sensors in alphabetical order */ 03253 03254 static void draw_sensor_actuator(uiLayout *layout, PointerRNA *ptr) 03255 { 03256 Object *ob = (Object *)ptr->id.data; 03257 PointerRNA settings_ptr; 03258 03259 RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); 03260 uiItemPointerR(layout, ptr, "actuator", &settings_ptr, "actuators", NULL, ICON_LOGIC); 03261 } 03262 03263 static void draw_sensor_armature(uiLayout *layout, PointerRNA *ptr) 03264 { 03265 bSensor *sens = (bSensor*)ptr->data; 03266 bArmatureSensor *as = (bArmatureSensor *) sens->data; 03267 Object *ob = (Object *)ptr->id.data; 03268 PointerRNA pose_ptr, pchan_ptr; 03269 PropertyRNA *bones_prop= NULL; 03270 uiLayout *row; 03271 03272 if(ob->type != OB_ARMATURE){ 03273 uiItemL(layout, "Sensor only available for armatures", ICON_NONE); 03274 return; 03275 } 03276 03277 if (ob->pose) { 03278 RNA_pointer_create((ID *)ob, &RNA_Pose, ob->pose, &pose_ptr); 03279 bones_prop = RNA_struct_find_property(&pose_ptr, "bones"); 03280 } 03281 03282 if (&pose_ptr.data) { 03283 uiItemPointerR(layout, ptr, "bone", &pose_ptr, "bones", NULL, ICON_BONE_DATA); 03284 03285 if (RNA_property_collection_lookup_string(&pose_ptr, bones_prop, as->posechannel, &pchan_ptr)) 03286 uiItemPointerR(layout, ptr, "constraint", &pchan_ptr, "constraints", NULL, ICON_CONSTRAINT_BONE); 03287 } 03288 row = uiLayoutRow(layout, 1); 03289 uiItemR(row, ptr, "test_type", 0, NULL, ICON_NONE); 03290 if (RNA_enum_get(ptr, "test_type") != SENS_ARM_STATE_CHANGED) 03291 uiItemR(row, ptr, "value", 0, NULL, ICON_NONE); 03292 } 03293 03294 static void draw_sensor_collision(uiLayout *layout, PointerRNA *ptr, bContext *C) 03295 { 03296 uiLayout *row, *split; 03297 PointerRNA main_ptr; 03298 03299 RNA_main_pointer_create(CTX_data_main(C), &main_ptr); 03300 03301 split = uiLayoutSplit(layout, 0.3, 0); 03302 row = uiLayoutRow(split, 1); 03303 uiItemR(row, ptr, "use_pulse", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03304 uiItemR(row, ptr, "use_material", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03305 03306 switch (RNA_boolean_get(ptr, "use_material")) { 03307 case SENS_COLLISION_PROPERTY: 03308 uiItemR(split, ptr, "property", 0, NULL, ICON_NONE); 03309 break; 03310 case SENS_COLLISION_MATERIAL: 03311 uiItemPointerR(split, ptr, "material", &main_ptr, "materials", NULL, ICON_MATERIAL_DATA); 03312 break; 03313 } 03314 } 03315 03316 static void draw_sensor_delay(uiLayout *layout, PointerRNA *ptr) 03317 { 03318 uiLayout *row; 03319 03320 row= uiLayoutRow(layout, 0); 03321 03322 uiItemR(row, ptr, "delay", 0, NULL, ICON_NONE); 03323 uiItemR(row, ptr, "duration", 0, NULL, ICON_NONE); 03324 uiItemR(row, ptr, "use_repeat", 0, NULL, ICON_NONE); 03325 } 03326 03327 static void draw_sensor_joystick(uiLayout *layout, PointerRNA *ptr) 03328 { 03329 uiLayout *col, *row; 03330 03331 uiItemR(layout, ptr, "joystick_index", 0, NULL, ICON_NONE); 03332 uiItemR(layout, ptr, "event_type", 0, NULL, ICON_NONE); 03333 03334 switch (RNA_enum_get(ptr, "event_type")) { 03335 case SENS_JOY_BUTTON: 03336 uiItemR(layout, ptr, "use_all_events", 0, NULL, ICON_NONE); 03337 03338 col = uiLayoutColumn(layout, 0); 03339 uiLayoutSetActive(col, RNA_boolean_get(ptr, "use_all_events")==0); 03340 uiItemR(col, ptr, "button_number", 0, NULL, ICON_NONE); 03341 break; 03342 case SENS_JOY_AXIS: 03343 row = uiLayoutRow(layout, 0); 03344 uiItemR(row, ptr, "axis_number", 0, NULL, ICON_NONE); 03345 uiItemR(row, ptr, "axis_threshold", 0, NULL, ICON_NONE); 03346 03347 uiItemR(layout, ptr, "use_all_events", 0, NULL, ICON_NONE); 03348 col = uiLayoutColumn(layout, 0); 03349 uiLayoutSetActive(col, RNA_boolean_get(ptr, "use_all_events")==0); 03350 uiItemR(col, ptr, "axis_direction", 0, NULL, ICON_NONE); 03351 break; 03352 case SENS_JOY_HAT: 03353 uiItemR(layout, ptr, "hat_number", 0, NULL, ICON_NONE); 03354 uiItemR(layout, ptr, "use_all_events", 0, NULL, ICON_NONE); 03355 03356 col = uiLayoutColumn(layout, 0); 03357 uiLayoutSetActive(col, RNA_boolean_get(ptr, "use_all_events")==0); 03358 uiItemR(col, ptr, "hat_direction", 0, NULL, ICON_NONE); 03359 break; 03360 case SENS_JOY_AXIS_SINGLE: 03361 row = uiLayoutRow(layout, 0); 03362 uiItemR(row, ptr, "single_axis_number", 0, NULL, ICON_NONE); 03363 uiItemR(row, ptr, "axis_threshold", 0, NULL, ICON_NONE); 03364 break; 03365 } 03366 } 03367 03368 static void draw_sensor_keyboard(uiLayout *layout, PointerRNA *ptr) 03369 { 03370 Object *ob = (Object *)ptr->id.data; 03371 PointerRNA settings_ptr; 03372 uiLayout *row, *col; 03373 03374 row = uiLayoutRow(layout, 0); 03375 uiItemL(row, "Key:", ICON_NONE); 03376 col = uiLayoutColumn(row, 0); 03377 uiLayoutSetActive(col, RNA_boolean_get(ptr, "use_all_keys")==0); 03378 uiItemR(col, ptr, "key", UI_ITEM_R_EVENT, "", ICON_NONE); 03379 col = uiLayoutColumn(row, 0); 03380 uiItemR(col, ptr, "use_all_keys", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03381 03382 col = uiLayoutColumn(layout, 0); 03383 uiLayoutSetActive(col, RNA_boolean_get(ptr, "use_all_keys")==0); 03384 row = uiLayoutRow(col, 0); 03385 uiItemL(row, "First Modifier:", ICON_NONE); 03386 uiItemR(row, ptr, "modifier_key_1", UI_ITEM_R_EVENT, "", ICON_NONE); 03387 03388 row = uiLayoutRow(col, 0); 03389 uiItemL(row, "Second Modifier:", ICON_NONE); 03390 uiItemR(row, ptr, "modifier_key_2", UI_ITEM_R_EVENT, "", ICON_NONE); 03391 03392 RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); 03393 uiItemPointerR(layout, ptr, "log", &settings_ptr, "properties", NULL, ICON_NONE); 03394 uiItemPointerR(layout, ptr, "target", &settings_ptr, "properties", NULL, ICON_NONE); 03395 } 03396 03397 static void draw_sensor_message(uiLayout *layout, PointerRNA *ptr) 03398 { 03399 uiItemR(layout, ptr, "subject", 0, NULL, ICON_NONE); 03400 } 03401 03402 static void draw_sensor_mouse(uiLayout *layout, PointerRNA *ptr) 03403 { 03404 uiItemR(layout, ptr, "mouse_event", 0, NULL, ICON_NONE); 03405 } 03406 03407 static void draw_sensor_near(uiLayout *layout, PointerRNA *ptr) 03408 { 03409 uiLayout *row; 03410 03411 uiItemR(layout, ptr, "property", 0, NULL, ICON_NONE); 03412 03413 row= uiLayoutRow(layout, 1); 03414 uiItemR(row, ptr, "distance", 0, NULL, ICON_NONE); 03415 uiItemR(row, ptr, "reset_distance", 0, NULL, ICON_NONE); 03416 } 03417 03418 static void draw_sensor_property(uiLayout *layout, PointerRNA *ptr) 03419 { 03420 Object *ob = (Object *)ptr->id.data; 03421 PointerRNA settings_ptr; 03422 03423 uiLayout *row; 03424 uiItemR(layout, ptr, "evaluation_type", 0, NULL, ICON_NONE); 03425 03426 RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); 03427 uiItemPointerR(layout, ptr, "property", &settings_ptr, "properties", NULL, ICON_NONE); 03428 03429 switch (RNA_enum_get(ptr, "evaluation_type")) { 03430 case SENS_PROP_INTERVAL: 03431 row = uiLayoutRow(layout, 0); 03432 uiItemR(row, ptr, "value_min", 0, NULL, ICON_NONE); 03433 uiItemR(row, ptr, "value_max", 0, NULL, ICON_NONE); 03434 break; 03435 case SENS_PROP_EQUAL: 03436 uiItemR(layout, ptr, "value", 0, NULL, ICON_NONE); 03437 break; 03438 case SENS_PROP_NEQUAL: 03439 uiItemR(layout, ptr, "value", 0, NULL, ICON_NONE); 03440 break; 03441 case SENS_PROP_CHANGED: 03442 break; 03443 } 03444 } 03445 03446 static void draw_sensor_radar(uiLayout *layout, PointerRNA *ptr) 03447 { 03448 uiLayout *row; 03449 03450 uiItemR(layout, ptr, "property", 0, NULL, ICON_NONE); 03451 uiItemR(layout, ptr, "axis", 0, NULL, ICON_NONE); 03452 03453 row= uiLayoutRow(layout, 0); 03454 uiItemR(row, ptr, "angle", 0, NULL, ICON_NONE); 03455 uiItemR(row, ptr, "distance", 0, NULL, ICON_NONE); 03456 } 03457 03458 static void draw_sensor_random(uiLayout *layout, PointerRNA *ptr) 03459 { 03460 uiItemR(layout, ptr, "seed", 0, NULL, ICON_NONE); 03461 } 03462 03463 static void draw_sensor_ray(uiLayout *layout, PointerRNA *ptr, bContext *C) 03464 { 03465 uiLayout *split, *row; 03466 PointerRNA main_ptr; 03467 03468 RNA_main_pointer_create(CTX_data_main(C), &main_ptr); 03469 split= uiLayoutSplit(layout, 0.3, 0); 03470 uiItemR(split, ptr, "ray_type", 0, "", ICON_NONE); 03471 switch (RNA_enum_get(ptr, "ray_type")) { 03472 case SENS_RAY_PROPERTY: 03473 uiItemR(split, ptr, "property", 0, "", ICON_NONE); 03474 break; 03475 case SENS_RAY_MATERIAL: 03476 uiItemPointerR(split, ptr, "material", &main_ptr, "materials", "", ICON_MATERIAL_DATA); 03477 break; 03478 } 03479 03480 split= uiLayoutSplit(layout, 0.3, 0); 03481 uiItemR(split, ptr, "axis", 0, "", ICON_NONE); 03482 row= uiLayoutRow(split, 0); 03483 uiItemR(row, ptr, "range", 0, NULL, ICON_NONE); 03484 uiItemR(row, ptr, "use_x_ray", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03485 } 03486 03487 static void draw_sensor_touch(uiLayout *layout, PointerRNA *ptr) 03488 { 03489 uiItemR(layout, ptr, "material", 0, NULL, ICON_NONE); 03490 } 03491 03492 static void draw_brick_sensor(uiLayout *layout, PointerRNA *ptr, bContext *C) 03493 { 03494 uiLayout *box; 03495 03496 if (!RNA_boolean_get(ptr, "show_expanded")) 03497 return; 03498 03499 draw_sensor_internal_header(layout, ptr); 03500 03501 box = uiLayoutBox(layout); 03502 03503 switch (RNA_enum_get(ptr, "type")) { 03504 03505 case SENS_ACTUATOR: 03506 draw_sensor_actuator(box, ptr); 03507 break; 03508 case SENS_ALWAYS: 03509 break; 03510 case SENS_ARMATURE: 03511 draw_sensor_armature(box, ptr); 03512 break; 03513 case SENS_COLLISION: 03514 draw_sensor_collision(box, ptr, C); 03515 break; 03516 case SENS_DELAY: 03517 draw_sensor_delay(box, ptr); 03518 break; 03519 case SENS_JOYSTICK: 03520 draw_sensor_joystick(box, ptr); 03521 break; 03522 case SENS_KEYBOARD: 03523 draw_sensor_keyboard(box, ptr); 03524 break; 03525 case SENS_MESSAGE: 03526 draw_sensor_message(box, ptr); 03527 break; 03528 case SENS_MOUSE: 03529 draw_sensor_mouse(box, ptr); 03530 break; 03531 case SENS_NEAR: 03532 draw_sensor_near(box, ptr); 03533 break; 03534 case SENS_PROPERTY: 03535 draw_sensor_property(box, ptr); 03536 break; 03537 case SENS_RADAR: 03538 draw_sensor_radar(box, ptr); 03539 break; 03540 case SENS_RANDOM: 03541 draw_sensor_random(box, ptr); 03542 break; 03543 case SENS_RAY: 03544 draw_sensor_ray(box, ptr, C); 03545 break; 03546 case SENS_TOUCH: 03547 draw_sensor_touch(box, ptr); 03548 break; 03549 } 03550 } 03551 03552 /* Controller code */ 03553 static void draw_controller_header(uiLayout *layout, PointerRNA *ptr, int xco, int width, int yco) 03554 { 03555 uiLayout *box, *row, *subrow; 03556 bController *cont= (bController *)ptr->data; 03557 03558 char state[3]; 03559 sprintf(state, "%d", RNA_int_get(ptr, "states")); 03560 03561 box= uiLayoutBox(layout); 03562 row= uiLayoutRow(box, 0); 03563 03564 uiItemR(row, ptr, "show_expanded", UI_ITEM_R_NO_BG, "", ICON_NONE); 03565 if(RNA_boolean_get(ptr, "show_expanded")) { 03566 uiItemR(row, ptr, "type", 0, "", ICON_NONE); 03567 uiItemR(row, ptr, "name", 0, "", ICON_NONE); 03568 /* XXX provisory for Blender 2.50Beta */ 03569 uiDefBlockBut(uiLayoutGetBlock(layout), controller_state_mask_menu, cont, state, (short)(xco+width-44), yco, 22+22, UI_UNIT_Y, "Set controller state index (from 1 to 30)"); 03570 } else { 03571 uiItemL(row, controller_name(cont->type), ICON_NONE); 03572 uiItemL(row, cont->name, ICON_NONE); 03573 uiItemL(row, state, ICON_NONE); 03574 } 03575 03576 uiItemR(row, ptr, "use_priority", 0, "", ICON_NONE); 03577 03578 if(RNA_boolean_get(ptr, "show_expanded")==0) { 03579 subrow= uiLayoutRow(row, 1); 03580 uiItemEnumO(subrow, "LOGIC_OT_controller_move", "", ICON_TRIA_UP, "direction", 1); // up 03581 uiItemEnumO(subrow, "LOGIC_OT_controller_move", "", ICON_TRIA_DOWN, "direction", 2); // down 03582 } 03583 uiItemO(row, "", ICON_X, "LOGIC_OT_controller_remove"); 03584 } 03585 03586 static void draw_controller_expression(uiLayout *layout, PointerRNA *ptr) 03587 { 03588 uiItemR(layout, ptr, "expression", 0, "", ICON_NONE); 03589 } 03590 03591 static void draw_controller_python(uiLayout *layout, PointerRNA *ptr) 03592 { 03593 uiLayout *split, *subsplit; 03594 03595 split = uiLayoutSplit(layout, 0.3, 1); 03596 uiItemR(split, ptr, "mode", 0, "", ICON_NONE); 03597 if (RNA_enum_get(ptr, "mode") == CONT_PY_SCRIPT) { 03598 uiItemR(split, ptr, "text", 0, "", ICON_NONE); 03599 } 03600 else { 03601 subsplit = uiLayoutSplit(split, 0.8, 0); 03602 uiItemR(subsplit, ptr, "module", 0, "", ICON_NONE); 03603 uiItemR(subsplit, ptr, "use_debug", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03604 } 03605 } 03606 03607 static void draw_controller_state(uiLayout *UNUSED(layout), PointerRNA *UNUSED(ptr)) 03608 { 03609 03610 } 03611 03612 static void draw_brick_controller(uiLayout *layout, PointerRNA *ptr) 03613 { 03614 uiLayout *box; 03615 03616 if (!RNA_boolean_get(ptr, "show_expanded")) 03617 return; 03618 03619 box = uiLayoutBox(layout); 03620 03621 draw_controller_state(box, ptr); 03622 03623 switch (RNA_enum_get(ptr, "type")) { 03624 case CONT_LOGIC_AND: 03625 break; 03626 case CONT_LOGIC_OR: 03627 break; 03628 case CONT_EXPRESSION: 03629 draw_controller_expression(box, ptr); 03630 break; 03631 case CONT_PYTHON: 03632 draw_controller_python(box, ptr); 03633 break; 03634 case CONT_LOGIC_NAND: 03635 break; 03636 case CONT_LOGIC_NOR: 03637 break; 03638 case CONT_LOGIC_XOR: 03639 break; 03640 case CONT_LOGIC_XNOR: 03641 break; 03642 } 03643 } 03644 03645 /* Actuator code */ 03646 static void draw_actuator_header(uiLayout *layout, PointerRNA *ptr, PointerRNA *logic_ptr) 03647 { 03648 uiLayout *box, *row, *subrow; 03649 bActuator *act= (bActuator *)ptr->data; 03650 03651 box= uiLayoutBox(layout); 03652 row= uiLayoutRow(box, 0); 03653 03654 uiItemR(row, ptr, "show_expanded", UI_ITEM_R_NO_BG, "", ICON_NONE); 03655 if(RNA_boolean_get(ptr, "show_expanded")) { 03656 uiItemR(row, ptr, "type", 0, "", ICON_NONE); 03657 uiItemR(row, ptr, "name", 0, "", ICON_NONE); 03658 } else { 03659 uiItemL(row, actuator_name(act->type), ICON_NONE); 03660 uiItemL(row, act->name, ICON_NONE); 03661 } 03662 03663 subrow= uiLayoutRow(row, 0); 03664 uiLayoutSetActive(subrow, ((RNA_boolean_get(logic_ptr, "show_actuators_active_states") 03665 && RNA_boolean_get(ptr, "show_expanded")) || RNA_boolean_get(ptr, "pin"))); 03666 uiItemR(subrow, ptr, "pin", UI_ITEM_R_NO_BG, "", ICON_NONE); 03667 03668 if(RNA_boolean_get(ptr, "show_expanded")==0) { 03669 subrow= uiLayoutRow(row, 1); 03670 uiItemEnumO(subrow, "LOGIC_OT_actuator_move", "", ICON_TRIA_UP, "direction", 1); // up 03671 uiItemEnumO(subrow, "LOGIC_OT_actuator_move", "", ICON_TRIA_DOWN, "direction", 2); // down 03672 } 03673 uiItemO(row, "", ICON_X, "LOGIC_OT_actuator_remove"); 03674 } 03675 03676 static void draw_actuator_action(uiLayout *layout, PointerRNA *ptr) 03677 { 03678 Object *ob = (Object *)ptr->id.data; 03679 PointerRNA settings_ptr; 03680 uiLayout *row; 03681 03682 if(ob->type != OB_ARMATURE){ 03683 uiItemL(layout, "Actuator only available for armatures", ICON_NONE); 03684 return; 03685 } 03686 RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); 03687 03688 row= uiLayoutRow(layout, 0); 03689 uiItemR(row, ptr, "play_mode", 0, "", ICON_NONE); 03690 uiItemR(row, ptr, "action", 0, "", ICON_NONE); 03691 uiItemR(row, ptr, "use_continue_last_frame", 0, NULL, ICON_NONE); 03692 03693 row= uiLayoutRow(layout, 0); 03694 if((RNA_enum_get(ptr, "play_mode") == ACT_ACTION_FROM_PROP)) 03695 uiItemPointerR(row, ptr, "property", &settings_ptr, "properties", NULL, ICON_NONE); 03696 03697 else { 03698 uiItemR(row, ptr, "frame_start", 0, NULL, ICON_NONE); 03699 uiItemR(row, ptr, "frame_end", 0, NULL, ICON_NONE); 03700 } 03701 03702 row= uiLayoutRow(layout, 0); 03703 uiItemR(row, ptr, "frame_blend_in", 0, NULL, ICON_NONE); 03704 uiItemR(row, ptr, "priority", 0, NULL, ICON_NONE); 03705 03706 row= uiLayoutRow(layout, 0); 03707 uiItemPointerR(layout, ptr, "frame_property", &settings_ptr, "properties", NULL, ICON_NONE); 03708 03709 #ifdef __NLA_ACTION_BY_MOTION_ACTUATOR 03710 uiItemR(row, "stride_length", 0, NULL, ICON_NONE); 03711 #endif 03712 } 03713 03714 static void draw_actuator_armature(uiLayout *layout, PointerRNA *ptr) 03715 { 03716 bActuator *act = (bActuator*)ptr->data; 03717 bArmatureActuator *aa = (bArmatureActuator *) act->data; 03718 Object *ob = (Object *)ptr->id.data; 03719 bConstraint *constraint = NULL; 03720 PointerRNA pose_ptr, pchan_ptr; 03721 PropertyRNA *bones_prop = NULL; 03722 03723 if(ob->type != OB_ARMATURE){ 03724 uiItemL(layout, "Actuator only available for armatures", ICON_NONE); 03725 return; 03726 } 03727 03728 if (ob->pose) { 03729 RNA_pointer_create((ID *)ob, &RNA_Pose, ob->pose, &pose_ptr); 03730 bones_prop = RNA_struct_find_property(&pose_ptr, "bones"); 03731 } 03732 03733 uiItemR(layout, ptr, "mode", 0, NULL, ICON_NONE); 03734 03735 switch (RNA_enum_get(ptr, "mode")) 03736 { 03737 case ACT_ARM_RUN: 03738 break; 03739 case ACT_ARM_ENABLE: 03740 case ACT_ARM_DISABLE: 03741 if (ob->pose) { 03742 uiItemPointerR(layout, ptr, "bone", &pose_ptr, "bones", NULL, ICON_BONE_DATA); 03743 03744 if (RNA_property_collection_lookup_string(&pose_ptr, bones_prop, aa->posechannel, &pchan_ptr)) 03745 uiItemPointerR(layout, ptr, "constraint", &pchan_ptr, "constraints", NULL, ICON_CONSTRAINT_BONE); 03746 } 03747 break; 03748 case ACT_ARM_SETTARGET: 03749 if (ob->pose) { 03750 uiItemPointerR(layout, ptr, "bone", &pose_ptr, "bones", NULL, ICON_BONE_DATA); 03751 03752 if (RNA_property_collection_lookup_string(&pose_ptr, bones_prop, aa->posechannel, &pchan_ptr)) 03753 uiItemPointerR(layout, ptr, "constraint", &pchan_ptr, "constraints", NULL, ICON_CONSTRAINT_BONE); 03754 } 03755 03756 uiItemR(layout, ptr, "target", 0, NULL, ICON_NONE); 03757 03758 /* show second target only if the constraint supports it */ 03759 get_armature_bone_constraint(ob, aa->posechannel, aa->constraint, &constraint); 03760 if (constraint && constraint->type == CONSTRAINT_TYPE_KINEMATIC) { 03761 uiItemR(layout, ptr, "secondary_target", 0, NULL, ICON_NONE); 03762 } 03763 break; 03764 case ACT_ARM_SETWEIGHT: 03765 if (ob->pose) { 03766 uiItemPointerR(layout, ptr, "bone", &pose_ptr, "bones", NULL, ICON_BONE_DATA); 03767 03768 if (RNA_property_collection_lookup_string(&pose_ptr, bones_prop, aa->posechannel, &pchan_ptr)) 03769 uiItemPointerR(layout, ptr, "constraint", &pchan_ptr, "constraints", NULL, ICON_CONSTRAINT_BONE); 03770 } 03771 03772 uiItemR(layout, ptr, "weight", 0, NULL, ICON_NONE); 03773 break; 03774 } 03775 } 03776 03777 static void draw_actuator_camera(uiLayout *layout, PointerRNA *ptr) 03778 { 03779 uiLayout *row; 03780 uiItemR(layout, ptr, "object", 0, NULL, ICON_NONE); 03781 03782 row = uiLayoutRow(layout, 0); 03783 uiItemR(row, ptr, "height", 0, NULL, ICON_NONE); 03784 uiItemR(row, ptr, "axis", 0, NULL, ICON_NONE); 03785 03786 row = uiLayoutRow(layout, 1); 03787 uiItemR(row, ptr, "min", 0, NULL, ICON_NONE); 03788 uiItemR(row, ptr, "max", 0, NULL, ICON_NONE); 03789 03790 uiItemR(layout, ptr, "damping", 0, NULL, ICON_NONE); 03791 } 03792 03793 static void draw_actuator_constraint(uiLayout *layout, PointerRNA *ptr, bContext *C) 03794 { 03795 uiLayout *row, *col, *subcol, *split; 03796 PointerRNA main_ptr; 03797 03798 RNA_main_pointer_create(CTX_data_main(C), &main_ptr); 03799 03800 uiItemR(layout, ptr, "mode", 0, NULL, ICON_NONE); 03801 switch (RNA_enum_get(ptr, "mode")) 03802 { 03803 case ACT_CONST_TYPE_LOC: 03804 uiItemR(layout, ptr, "limit", 0, NULL, ICON_NONE); 03805 03806 row = uiLayoutRow(layout, 1); 03807 uiItemR(row, ptr, "limit_min", 0, NULL, ICON_NONE); 03808 uiItemR(row, ptr, "limit_max", 0, NULL, ICON_NONE); 03809 03810 uiItemR(layout, ptr, "damping", UI_ITEM_R_SLIDER, NULL, ICON_NONE); 03811 break; 03812 03813 case ACT_CONST_TYPE_DIST: 03814 split = uiLayoutSplit(layout, 0.8, 0); 03815 uiItemR(split, ptr, "direction", 0, NULL, ICON_NONE); 03816 row = uiLayoutRow(split, 1); 03817 uiItemR(row, ptr, "use_local", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03818 uiItemR(row, ptr, "use_normal", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03819 03820 row = uiLayoutRow(layout, 0); 03821 col = uiLayoutColumn(row, 0); 03822 uiItemL(col, "Range:", ICON_NONE); 03823 uiItemR(col, ptr, "range", 0, "", ICON_NONE); 03824 03825 col = uiLayoutColumn(row, 1); 03826 uiItemR(col, ptr, "use_force_distance", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03827 subcol = uiLayoutColumn(col, 0); 03828 uiLayoutSetActive(subcol, RNA_boolean_get(ptr, "use_force_distance")==1); 03829 uiItemR(subcol, ptr, "distance", 0, "", ICON_NONE); 03830 03831 uiItemR(layout, ptr, "damping", UI_ITEM_R_SLIDER , NULL, ICON_NONE); 03832 03833 split = uiLayoutSplit(layout, 0.15, 0); 03834 uiItemR(split, ptr, "use_material_detect", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03835 if (RNA_boolean_get(ptr, "use_material_detect")) 03836 uiItemPointerR(split, ptr, "material", &main_ptr, "materials", NULL, ICON_MATERIAL_DATA); 03837 else 03838 uiItemR(split, ptr, "property", 0, NULL, ICON_NONE); 03839 03840 split = uiLayoutSplit(layout, 0.15, 0); 03841 uiItemR(split, ptr, "use_persistent", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03842 03843 row = uiLayoutRow(split, 1); 03844 uiItemR(row, ptr, "time", 0, NULL, ICON_NONE); 03845 uiItemR(row, ptr, "damping_rotation", UI_ITEM_R_SLIDER, NULL, ICON_NONE); 03846 break; 03847 03848 case ACT_CONST_TYPE_ORI: 03849 uiItemR(layout, ptr, "direction_axis_pos", 0, NULL, ICON_NONE); 03850 03851 row=uiLayoutRow(layout, 1); 03852 uiItemR(row, ptr, "damping", UI_ITEM_R_SLIDER , NULL, ICON_NONE); 03853 uiItemR(row, ptr, "time", 0, NULL, ICON_NONE); 03854 03855 row=uiLayoutRow(layout, 0); 03856 uiItemR(row, ptr, "rotation_max", 0, NULL, ICON_NONE); 03857 03858 row=uiLayoutRow(layout, 1); 03859 uiItemR(row, ptr, "angle_min", 0, NULL, ICON_NONE); 03860 uiItemR(row, ptr, "angle_max", 0, NULL, ICON_NONE); 03861 break; 03862 03863 case ACT_CONST_TYPE_FH: 03864 split=uiLayoutSplit(layout, 0.75, 0); 03865 row= uiLayoutRow(split, 0); 03866 uiItemR(row, ptr, "fh_damping", UI_ITEM_R_SLIDER , NULL, ICON_NONE); 03867 03868 uiItemR(row, ptr, "fh_height", 0, NULL, ICON_NONE); 03869 uiItemR(split, ptr, "use_fh_paralel_axis", UI_ITEM_R_TOGGLE , NULL, ICON_NONE); 03870 03871 row = uiLayoutRow(layout, 0); 03872 uiItemR(row, ptr, "direction_axis", 0, NULL, ICON_NONE); 03873 split = uiLayoutSplit(row, 0.9, 0); 03874 uiItemR(split, ptr, "fh_force", 0, NULL, ICON_NONE); 03875 uiItemR(split, ptr, "use_fh_normal", UI_ITEM_R_TOGGLE , NULL, ICON_NONE); 03876 03877 split = uiLayoutSplit(layout, 0.15, 0); 03878 uiItemR(split, ptr, "use_material_detect", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03879 if (RNA_boolean_get(ptr, "use_material_detect")) 03880 uiItemPointerR(split, ptr, "material", &main_ptr, "materials", NULL, ICON_MATERIAL_DATA); 03881 else 03882 uiItemR(split, ptr, "property", 0, NULL, ICON_NONE); 03883 03884 split = uiLayoutSplit(layout, 0.15, 0); 03885 uiItemR(split, ptr, "use_persistent", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03886 03887 row = uiLayoutRow(split, 0); 03888 uiItemR(row, ptr, "time", 0, NULL, ICON_NONE); 03889 uiItemR(row, ptr, "damping_rotation", UI_ITEM_R_SLIDER, NULL, ICON_NONE); 03890 break; 03891 } 03892 } 03893 03894 static void draw_actuator_edit_object(uiLayout *layout, PointerRNA *ptr) 03895 { 03896 Object *ob = (Object *)ptr->id.data; 03897 uiLayout *row, *split, *subsplit; 03898 uiItemR(layout, ptr, "mode", 0, NULL, ICON_NONE); 03899 03900 switch (RNA_enum_get(ptr, "mode")) 03901 { 03902 case ACT_EDOB_ADD_OBJECT: 03903 row = uiLayoutRow(layout, 0); 03904 uiItemR(row, ptr, "object", 0, NULL, ICON_NONE); 03905 uiItemR(row, ptr, "time", 0, NULL, ICON_NONE); 03906 03907 split = uiLayoutSplit(layout, 0.9, 0); 03908 row = uiLayoutRow(split, 0); 03909 uiItemR(row, ptr, "linear_velocity", 0, NULL, ICON_NONE); 03910 uiItemR(split, ptr, "use_local_linear_velocity", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03911 03912 split = uiLayoutSplit(layout, 0.9, 0); 03913 row = uiLayoutRow(split, 0); 03914 uiItemR(row, ptr, "angular_velocity", 0, NULL, ICON_NONE); 03915 uiItemR(split, ptr, "use_local_angular_velocity", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03916 break; 03917 case ACT_EDOB_END_OBJECT: 03918 break; 03919 case ACT_EDOB_REPLACE_MESH: 03920 if(ob->type != OB_MESH) { 03921 uiItemL(layout, "Mode only available for mesh objects", ICON_NONE); 03922 break; 03923 } 03924 split = uiLayoutSplit(layout, 0.6, 0); 03925 uiItemR(split, ptr, "mesh", 0, NULL, ICON_NONE); 03926 row = uiLayoutRow(split, 0); 03927 uiItemR(row, ptr, "use_replace_display_mesh", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03928 uiItemR(row, ptr, "use_replace_physics_mesh", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03929 break; 03930 case ACT_EDOB_TRACK_TO: 03931 split = uiLayoutSplit(layout, 0.5, 0); 03932 uiItemR(split, ptr, "track_object", 0, NULL, ICON_NONE); 03933 subsplit = uiLayoutSplit(split, 0.7, 0); 03934 uiItemR(subsplit, ptr, "time", 0, NULL, ICON_NONE); 03935 uiItemR(subsplit, ptr, "use_3d_tracking", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03936 break; 03937 case ACT_EDOB_DYNAMICS: 03938 if(ob->type != OB_MESH) { 03939 uiItemL(layout, "Mode only available for mesh objects", ICON_NONE); 03940 break; 03941 } 03942 uiItemR(layout, ptr, "dynamic_operation", 0, NULL, ICON_NONE); 03943 if (RNA_enum_get(ptr, "dynamic_operation") == ACT_EDOB_SET_MASS) 03944 uiItemR(layout, ptr, "mass", 0, NULL, ICON_NONE); 03945 break; 03946 } 03947 } 03948 03949 static void draw_actuator_filter_2d(uiLayout *layout, PointerRNA *ptr) 03950 { 03951 uiLayout *row, *split; 03952 03953 uiItemR(layout, ptr, "mode", 0, NULL, ICON_NONE); 03954 switch (RNA_enum_get(ptr, "mode")) 03955 { 03956 case ACT_2DFILTER_CUSTOMFILTER: 03957 uiItemR(layout, ptr, "filter_pass", 0, NULL, ICON_NONE); 03958 uiItemR(layout, ptr, "glsl_shader", 0, NULL, ICON_NONE); 03959 break; 03960 case ACT_2DFILTER_MOTIONBLUR: 03961 split=uiLayoutSplit(layout, 0.75, 1); 03962 row= uiLayoutRow(split, 0); 03963 uiLayoutSetActive(row, RNA_boolean_get(ptr, "use_motion_blur")==1); 03964 uiItemR(row, ptr, "motion_blur_factor", 0, NULL, ICON_NONE); 03965 uiItemR(split, ptr, "use_motion_blur", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03966 break; 03967 default: // all other 2D Filters 03968 uiItemR(layout, ptr, "filter_pass", 0, NULL, ICON_NONE); 03969 break; 03970 } 03971 } 03972 03973 static void draw_actuator_game(uiLayout *layout, PointerRNA *ptr) 03974 { 03975 uiItemR(layout, ptr, "mode", 0, NULL, ICON_NONE); 03976 if (RNA_enum_get(ptr, "mode") == ACT_GAME_LOAD) 03977 uiItemR(layout, ptr, "filename", 0, NULL, ICON_NONE); 03978 } 03979 03980 static void draw_actuator_ipo(uiLayout *layout, PointerRNA *ptr) 03981 { 03982 Object *ob; 03983 PointerRNA settings_ptr; 03984 uiLayout *row, *subrow, *col; 03985 03986 ob = (Object *)ptr->id.data; 03987 RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); 03988 03989 row= uiLayoutRow(layout, 0); 03990 uiItemR(row, ptr, "play_type", 0, "", ICON_NONE); 03991 subrow= uiLayoutRow(row, 1); 03992 uiItemR(subrow, ptr, "use_force", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03993 uiItemR(subrow, ptr, "use_additive", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03994 03995 col = uiLayoutColumn(subrow, 0); 03996 uiLayoutSetActive(col, (RNA_boolean_get(ptr, "use_additive") || RNA_boolean_get(ptr, "use_force"))); 03997 uiItemR(col, ptr, "use_local", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 03998 03999 row= uiLayoutRow(layout, 0); 04000 if((RNA_enum_get(ptr, "play_type") == ACT_IPO_FROM_PROP)) 04001 uiItemPointerR(row, ptr, "property", &settings_ptr, "properties", NULL, ICON_NONE); 04002 04003 else { 04004 uiItemR(row, ptr, "frame_start", 0, NULL, ICON_NONE); 04005 uiItemR(row, ptr, "frame_end", 0, NULL, ICON_NONE); 04006 } 04007 uiItemR(row, ptr, "apply_to_children", 0, NULL, ICON_NONE); 04008 04009 row= uiLayoutRow(layout, 0); 04010 uiItemPointerR(row, ptr, "frame_property", &settings_ptr, "properties", NULL, ICON_NONE); 04011 } 04012 04013 static void draw_actuator_message(uiLayout *layout, PointerRNA *ptr, bContext *C) 04014 { 04015 Object *ob; 04016 PointerRNA main_ptr, settings_ptr; 04017 uiLayout *row; 04018 04019 RNA_main_pointer_create(CTX_data_main(C), &main_ptr); 04020 04021 ob = (Object *)ptr->id.data; 04022 RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); 04023 04024 uiItemPointerR(layout, ptr, "to_property", &main_ptr, "objects", NULL, ICON_OBJECT_DATA); 04025 uiItemR(layout, ptr, "subject", 0, NULL, ICON_NONE); 04026 04027 row= uiLayoutRow(layout, 1); 04028 uiItemR(row, ptr, "body_type", 0, NULL, ICON_NONE); 04029 04030 if(RNA_enum_get(ptr, "body_type") == ACT_MESG_MESG) 04031 uiItemR(row, ptr, "body_message", 0, "", ICON_NONE); 04032 else // mode == ACT_MESG_PROP 04033 uiItemPointerR(row, ptr, "body_property", &settings_ptr, "properties", "", ICON_NONE); 04034 } 04035 04036 static void draw_actuator_motion(uiLayout *layout, PointerRNA *ptr) 04037 { 04038 Object *ob; 04039 PointerRNA settings_ptr; 04040 uiLayout *split, *row, *col, *subcol; 04041 int physics_type; 04042 04043 ob = (Object *)ptr->id.data; 04044 RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); 04045 physics_type = RNA_enum_get(&settings_ptr, "physics_type"); 04046 04047 uiItemR(layout, ptr, "mode", 0, NULL, ICON_NONE); 04048 04049 switch (RNA_enum_get(ptr, "mode")) { 04050 case ACT_OBJECT_NORMAL: 04051 split = uiLayoutSplit(layout, 0.9, 0); 04052 row = uiLayoutRow(split, 0); 04053 uiItemR(row, ptr, "offset_location", 0, NULL, ICON_NONE); 04054 uiItemR(split, ptr, "use_local_location", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 04055 04056 split = uiLayoutSplit(layout, 0.9, 0); 04057 row = uiLayoutRow(split, 0); 04058 uiItemR(row, ptr, "offset_rotation", 0, NULL, ICON_NONE); 04059 uiItemR(split, ptr, "use_local_rotation", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 04060 04061 if (ELEM3(physics_type, OB_BODY_TYPE_DYNAMIC, OB_BODY_TYPE_RIGID, OB_BODY_TYPE_SOFT)) { 04062 uiItemL(layout, "Dynamic Object Settings:", ICON_NONE); 04063 split = uiLayoutSplit(layout, 0.9, 0); 04064 row = uiLayoutRow(split, 0); 04065 uiItemR(row, ptr, "force", 0, NULL, ICON_NONE); 04066 uiItemR(split, ptr, "use_local_force", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 04067 04068 split = uiLayoutSplit(layout, 0.9, 0); 04069 row = uiLayoutRow(split, 0); 04070 uiItemR(row, ptr, "torque", 0, NULL, ICON_NONE); 04071 uiItemR(split, ptr, "use_local_torque", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 04072 04073 split = uiLayoutSplit(layout, 0.9, 0); 04074 row = uiLayoutRow(split, 0); 04075 uiItemR(row, ptr, "linear_velocity", 0, NULL, ICON_NONE); 04076 row = uiLayoutRow(split, 1); 04077 uiItemR(row, ptr, "use_local_linear_velocity", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 04078 uiItemR(row, ptr, "use_add_linear_velocity", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 04079 04080 split = uiLayoutSplit(layout, 0.9, 0); 04081 row = uiLayoutRow(split, 0); 04082 uiItemR(row, ptr, "angular_velocity", 0, NULL, ICON_NONE); 04083 uiItemR(split, ptr, "use_local_angular_velocity", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 04084 04085 uiItemR(layout, ptr, "damping", 0, NULL, ICON_NONE); 04086 } 04087 break; 04088 case ACT_OBJECT_SERVO: 04089 uiItemR(layout, ptr, "reference_object", 0, NULL, ICON_NONE); 04090 04091 split = uiLayoutSplit(layout, 0.9, 0); 04092 row = uiLayoutRow(split, 0); 04093 uiItemR(row, ptr, "linear_velocity", 0, NULL, ICON_NONE); 04094 uiItemR(split, ptr, "use_local_linear_velocity", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 04095 04096 row = uiLayoutRow(layout, 0); 04097 col = uiLayoutColumn(row, 0); 04098 uiItemR(col, ptr, "use_servo_limit_x", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 04099 subcol = uiLayoutColumn(col, 1); 04100 uiLayoutSetActive(subcol, RNA_boolean_get(ptr, "use_servo_limit_x")==1); 04101 uiItemR(subcol, ptr, "force_max_x", 0, NULL, ICON_NONE); 04102 uiItemR(subcol, ptr, "force_min_x", 0, NULL, ICON_NONE); 04103 04104 col = uiLayoutColumn(row, 0); 04105 uiItemR(col, ptr, "use_servo_limit_y", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 04106 subcol = uiLayoutColumn(col, 1); 04107 uiLayoutSetActive(subcol, RNA_boolean_get(ptr, "use_servo_limit_y")==1); 04108 uiItemR(subcol, ptr, "force_max_y", 0, NULL, ICON_NONE); 04109 uiItemR(subcol, ptr, "force_min_y", 0, NULL, ICON_NONE); 04110 04111 col = uiLayoutColumn(row, 0); 04112 uiItemR(col, ptr, "use_servo_limit_z", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 04113 subcol = uiLayoutColumn(col, 1); 04114 uiLayoutSetActive(subcol, RNA_boolean_get(ptr, "use_servo_limit_z")==1); 04115 uiItemR(subcol, ptr, "force_max_z", 0, NULL, ICON_NONE); 04116 uiItemR(subcol, ptr, "force_min_z", 0, NULL, ICON_NONE); 04117 04118 //XXXACTUATOR missing labels from original 2.49 ui (e.g. Servo, Min, Max, Fast) 04119 //Layout designers willing to help on that, please compare with 2.49 ui 04120 // (since the old code is going to be deleted ... soon) 04121 04122 col = uiLayoutColumn(layout, 1); 04123 uiItemR(col, ptr, "proportional_coefficient", UI_ITEM_R_SLIDER, NULL, ICON_NONE); 04124 uiItemR(col, ptr, "integral_coefficient", UI_ITEM_R_SLIDER, NULL, ICON_NONE); 04125 uiItemR(col, ptr, "derivate_coefficient", UI_ITEM_R_SLIDER, NULL, ICON_NONE); 04126 break; 04127 } 04128 } 04129 04130 static void draw_actuator_parent(uiLayout *layout, PointerRNA *ptr) 04131 { 04132 uiLayout *row, *subrow; 04133 04134 uiItemR(layout, ptr, "mode", 0, NULL, ICON_NONE); 04135 04136 if (RNA_enum_get(ptr, "mode") == ACT_PARENT_SET) { 04137 uiItemR(layout, ptr, "object", 0, NULL, ICON_NONE); 04138 04139 row = uiLayoutRow(layout, 0); 04140 uiItemR(row, ptr, "use_compound", 0, NULL, ICON_NONE); 04141 subrow= uiLayoutRow(row, 0); 04142 uiLayoutSetActive(subrow, RNA_boolean_get(ptr, "use_compound")==1); 04143 uiItemR(subrow, ptr, "use_ghost", 0, NULL, ICON_NONE); 04144 } 04145 } 04146 04147 static void draw_actuator_property(uiLayout *layout, PointerRNA *ptr) 04148 { 04149 Object *ob = (Object *)ptr->id.data; 04150 bActuator *act = (bActuator *)ptr->data; 04151 bPropertyActuator *pa = (bPropertyActuator *) act->data; 04152 Object *ob_from= pa->ob; 04153 PointerRNA settings_ptr, obj_settings_ptr; 04154 04155 uiLayout *row, *subrow; 04156 04157 RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); 04158 04159 uiItemR(layout, ptr, "mode", 0, NULL, ICON_NONE); 04160 uiItemPointerR(layout, ptr, "property", &settings_ptr, "properties", NULL, ICON_NONE); 04161 04162 switch(RNA_enum_get(ptr, "mode")) 04163 { 04164 case ACT_PROP_TOGGLE: 04165 break; 04166 case ACT_PROP_ADD: 04167 uiItemR(layout, ptr, "value", 0, NULL, ICON_NONE); 04168 break; 04169 case ACT_PROP_ASSIGN: 04170 uiItemR(layout, ptr, "value", 0, NULL, ICON_NONE); 04171 break; 04172 case ACT_PROP_COPY: 04173 row = uiLayoutRow(layout, 0); 04174 uiItemR(row, ptr, "object", 0, NULL, ICON_NONE); 04175 if(ob_from){ 04176 RNA_pointer_create((ID *)ob_from, &RNA_GameObjectSettings, ob_from, &obj_settings_ptr); 04177 uiItemPointerR(row, ptr, "object_property", &obj_settings_ptr, "properties", NULL, ICON_NONE); 04178 }else 04179 { 04180 subrow= uiLayoutRow(row, 0); 04181 uiLayoutSetActive(subrow, 0); 04182 uiItemR(subrow, ptr, "object_property", 0, NULL, ICON_NONE); 04183 } 04184 break; 04185 } 04186 } 04187 04188 static void draw_actuator_random(uiLayout *layout, PointerRNA *ptr) 04189 { 04190 Object *ob; 04191 PointerRNA settings_ptr; 04192 uiLayout *row; 04193 04194 ob = (Object *)ptr->id.data; 04195 RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); 04196 04197 row = uiLayoutRow(layout, 0); 04198 04199 uiItemR(row, ptr, "seed", 0, NULL, ICON_NONE); 04200 uiItemR(row, ptr, "distribution", 0, NULL, ICON_NONE); 04201 04202 row = uiLayoutRow(layout, 0); 04203 uiItemPointerR(row, ptr, "property", &settings_ptr, "properties", NULL, ICON_NONE); 04204 04205 row = uiLayoutRow(layout, 0); 04206 04207 switch (RNA_enum_get(ptr, "distribution")){ 04208 case ACT_RANDOM_BOOL_CONST: 04209 uiItemR(row, ptr, "use_always_true", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 04210 break; 04211 04212 case ACT_RANDOM_BOOL_UNIFORM: 04213 uiItemL(row, "Choose between true and false, 50% chance each", ICON_NONE); 04214 break; 04215 04216 case ACT_RANDOM_BOOL_BERNOUILLI: 04217 uiItemR(row, ptr, "chance", 0, NULL, ICON_NONE); 04218 break; 04219 04220 case ACT_RANDOM_INT_CONST: 04221 uiItemR(row, ptr, "int_value", 0, NULL, ICON_NONE); 04222 break; 04223 04224 case ACT_RANDOM_INT_UNIFORM: 04225 uiItemR(row, ptr, "int_min", 0, NULL, ICON_NONE); 04226 uiItemR(row, ptr, "int_max", 0, NULL, ICON_NONE); 04227 break; 04228 04229 case ACT_RANDOM_INT_POISSON: 04230 uiItemR(row, ptr, "int_mean", 0, NULL, ICON_NONE); 04231 break; 04232 04233 case ACT_RANDOM_FLOAT_CONST: 04234 uiItemR(row, ptr, "float_value", 0, NULL, ICON_NONE); 04235 break; 04236 04237 case ACT_RANDOM_FLOAT_UNIFORM: 04238 uiItemR(row, ptr, "float_min", 0, NULL, ICON_NONE); 04239 uiItemR(row, ptr, "float_max", 0, NULL, ICON_NONE); 04240 break; 04241 04242 case ACT_RANDOM_FLOAT_NORMAL: 04243 uiItemR(row, ptr, "float_mean", 0, NULL, ICON_NONE); 04244 uiItemR(row, ptr, "standard_derivation", 0, NULL, ICON_NONE); 04245 break; 04246 04247 case ACT_RANDOM_FLOAT_NEGATIVE_EXPONENTIAL: 04248 uiItemR(row, ptr, "half_life_time", 0, NULL, ICON_NONE); 04249 break; 04250 } 04251 } 04252 04253 static void draw_actuator_scene(uiLayout *layout, PointerRNA *ptr) 04254 { 04255 uiItemR(layout, ptr, "mode", 0, NULL, ICON_NONE); 04256 04257 switch (RNA_enum_get(ptr, "mode")) { 04258 case ACT_SCENE_CAMERA: 04259 uiItemR(layout, ptr, "camera", 0, NULL, ICON_NONE); 04260 break; 04261 case ACT_SCENE_RESTART: 04262 break; 04263 default: // ACT_SCENE_SET|ACT_SCENE_ADD_FRONT|ACT_SCENE_ADD_BACK|ACT_SCENE_REMOVE|ACT_SCENE_SUSPEND|ACT_SCENE_RESUME 04264 uiItemR(layout, ptr, "scene", 0, NULL, ICON_NONE); 04265 break; 04266 } 04267 } 04268 04269 static void draw_actuator_shape_action(uiLayout *layout, PointerRNA *ptr) 04270 { 04271 Object *ob = (Object *)ptr->id.data; 04272 PointerRNA settings_ptr; 04273 uiLayout *row; 04274 04275 if(ob->type != OB_MESH){ 04276 uiItemL(layout, "Actuator only available for mesh objects", ICON_NONE); 04277 return; 04278 } 04279 04280 RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); 04281 04282 row= uiLayoutRow(layout, 0); 04283 uiItemR(row, ptr, "mode", 0, "", ICON_NONE); 04284 uiItemR(row, ptr, "action", 0, "", ICON_NONE); 04285 uiItemR(row, ptr, "use_continue_last_frame", 0, NULL, ICON_NONE); 04286 04287 row= uiLayoutRow(layout, 0); 04288 if((RNA_enum_get(ptr, "mode") == ACT_ACTION_FROM_PROP)) 04289 uiItemPointerR(row, ptr, "property", &settings_ptr, "properties", NULL, ICON_NONE); 04290 04291 else { 04292 uiItemR(row, ptr, "frame_start", 0, NULL, ICON_NONE); 04293 uiItemR(row, ptr, "frame_end", 0, NULL, ICON_NONE); 04294 } 04295 04296 row= uiLayoutRow(layout, 0); 04297 uiItemR(row, ptr, "frame_blend_in", 0, NULL, ICON_NONE); 04298 uiItemR(row, ptr, "priority", 0, NULL, ICON_NONE); 04299 04300 row= uiLayoutRow(layout, 0); 04301 uiItemPointerR(row, ptr, "frame_property", &settings_ptr, "properties", NULL, ICON_NONE); 04302 04303 #ifdef __NLA_ACTION_BY_MOTION_ACTUATOR 04304 uiItemR(row, "stride_length", 0, NULL, ICON_NONE); 04305 #endif 04306 } 04307 04308 static void draw_actuator_sound(uiLayout *layout, PointerRNA *ptr, bContext *C) 04309 { 04310 uiLayout *row, *col; 04311 04312 uiTemplateID(layout, C, ptr, "sound", NULL, "SOUND_OT_open", NULL); 04313 if (!RNA_pointer_get(ptr, "sound").data) 04314 { 04315 uiItemL(layout, "Select a sound from the list or load a new one", ICON_NONE); 04316 return; 04317 } 04318 uiItemR(layout, ptr, "mode", 0, NULL, ICON_NONE); 04319 04320 row = uiLayoutRow(layout, 0); 04321 uiItemR(row, ptr, "volume", 0, NULL, ICON_NONE); 04322 uiItemR(row, ptr, "pitch", 0, NULL, ICON_NONE); 04323 04324 uiItemR(layout, ptr, "use_sound_3d", 0, NULL, ICON_NONE); 04325 04326 col = uiLayoutColumn(layout, 0); 04327 uiLayoutSetActive(col, RNA_boolean_get(ptr, "use_sound_3d")==1); 04328 04329 row = uiLayoutRow(col, 0); 04330 uiItemR(row, ptr, "gain_3d_min", 0, NULL, ICON_NONE); 04331 uiItemR(row, ptr, "gain_3d_max", 0, NULL, ICON_NONE); 04332 04333 row = uiLayoutRow(col, 0); 04334 uiItemR(row, ptr, "distance_3d_reference", 0, NULL, ICON_NONE); 04335 uiItemR(row, ptr, "distance_3d_max", 0, NULL, ICON_NONE); 04336 04337 row = uiLayoutRow(col, 0); 04338 uiItemR(row, ptr, "rolloff_factor_3d", 0, NULL, ICON_NONE); 04339 uiItemR(row, ptr, "cone_outer_gain_3d", 0, NULL, ICON_NONE); 04340 04341 row = uiLayoutRow(col, 0); 04342 uiItemR(row, ptr, "cone_outer_angle_3d", 0, NULL, ICON_NONE); 04343 uiItemR(row, ptr, "cone_inner_angle_3d", 0, NULL, ICON_NONE); 04344 } 04345 04346 static void draw_actuator_state(uiLayout *layout, PointerRNA *ptr) 04347 { 04348 uiLayout *split; 04349 Object *ob = (Object *)ptr->id.data; 04350 PointerRNA settings_ptr; 04351 RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); 04352 04353 split = uiLayoutSplit(layout, 0.35, 0); 04354 uiItemR(split, ptr, "operation", 0, NULL, ICON_NONE); 04355 04356 uiTemplateLayers(split, ptr, "states", &settings_ptr, "used_states", 0); 04357 } 04358 04359 static void draw_actuator_visibility(uiLayout *layout, PointerRNA *ptr) 04360 { 04361 uiLayout *row; 04362 row = uiLayoutRow(layout, 0); 04363 04364 uiItemR(row, ptr, "use_visible", 0, NULL, ICON_NONE); 04365 uiItemR(row, ptr, "use_occlusion", 0, NULL, ICON_NONE); 04366 uiItemR(row, ptr, "apply_to_children", 0, NULL, ICON_NONE); 04367 } 04368 04369 static void draw_brick_actuator(uiLayout *layout, PointerRNA *ptr, bContext *C) 04370 { 04371 uiLayout *box; 04372 04373 if (!RNA_boolean_get(ptr, "show_expanded")) 04374 return; 04375 04376 box = uiLayoutBox(layout); 04377 04378 switch (RNA_enum_get(ptr, "type")) { 04379 case ACT_ACTION: 04380 draw_actuator_action(box, ptr); 04381 break; 04382 case ACT_ARMATURE: 04383 draw_actuator_armature(box, ptr); 04384 break; 04385 case ACT_CAMERA: 04386 draw_actuator_camera(box, ptr); 04387 break; 04388 case ACT_CONSTRAINT: 04389 draw_actuator_constraint(box, ptr, C); 04390 break; 04391 case ACT_EDIT_OBJECT: 04392 draw_actuator_edit_object(box, ptr); 04393 break; 04394 case ACT_2DFILTER: 04395 draw_actuator_filter_2d(box, ptr); 04396 break; 04397 case ACT_GAME: 04398 draw_actuator_game(box, ptr); 04399 break; 04400 case ACT_IPO: 04401 draw_actuator_ipo(box, ptr); 04402 break; 04403 case ACT_MESSAGE: 04404 draw_actuator_message(box, ptr, C); 04405 break; 04406 case ACT_OBJECT: 04407 draw_actuator_motion(box, ptr); 04408 break; 04409 case ACT_PARENT: 04410 draw_actuator_parent(box, ptr); 04411 break; 04412 case ACT_PROPERTY: 04413 draw_actuator_property(box, ptr); 04414 break; 04415 case ACT_RANDOM: 04416 draw_actuator_random(box, ptr); 04417 break; 04418 case ACT_SCENE: 04419 draw_actuator_scene(box, ptr); 04420 break; 04421 case ACT_SHAPEACTION: 04422 draw_actuator_shape_action(box, ptr); 04423 break; 04424 case ACT_SOUND: 04425 draw_actuator_sound(box, ptr, C); 04426 break; 04427 case ACT_STATE: 04428 draw_actuator_state(box, ptr); 04429 break; 04430 case ACT_VISIBILITY: 04431 draw_actuator_visibility(box, ptr); 04432 break; 04433 } 04434 } 04435 04436 static void logic_buttons_new(bContext *C, ARegion *ar) 04437 { 04438 SpaceLogic *slogic= CTX_wm_space_logic(C); 04439 Object *ob= CTX_data_active_object(C); 04440 Object *act_ob= ob; 04441 ID **idar; 04442 04443 PointerRNA logic_ptr, settings_ptr; 04444 04445 uiLayout *layout, *row, *box; 04446 uiBlock *block; 04447 uiBut *but; 04448 char name[32]; 04449 short a, count; 04450 int xco, yco, width; 04451 04452 if(ob==NULL) return; 04453 04454 RNA_pointer_create(NULL, &RNA_SpaceLogicEditor, slogic, &logic_ptr); 04455 idar= get_selected_and_linked_obs(C, &count, slogic->scaflag); 04456 04457 sprintf(name, "buttonswin %p", (void *)ar); 04458 block= uiBeginBlock(C, ar, name, UI_EMBOSS); 04459 uiBlockSetHandleFunc(block, do_logic_buts, NULL); 04460 04461 /* loop over all objects and set visible/linked flags for the logic bricks */ 04462 for(a=0; a<count; a++) { 04463 bActuator *act; 04464 bSensor *sens; 04465 bController *cont; 04466 int iact; 04467 short flag; 04468 04469 ob= (Object *)idar[a]; 04470 04471 /* clean ACT_LINKED and ACT_VISIBLE of all potentially visible actuators so that we can determine which is actually linked/visible */ 04472 act = ob->actuators.first; 04473 while(act) { 04474 act->flag &= ~(ACT_LINKED|ACT_VISIBLE); 04475 act = act->next; 04476 } 04477 /* same for sensors */ 04478 sens= ob->sensors.first; 04479 while(sens) { 04480 sens->flag &= ~(SENS_VISIBLE); 04481 sens = sens->next; 04482 } 04483 04484 /* mark the linked and visible actuators */ 04485 cont= ob->controllers.first; 04486 while(cont) { 04487 flag = ACT_LINKED; 04488 04489 /* this controller is visible, mark all its actuator */ 04490 if ((ob->scaflag & OB_ALLSTATE) || (ob->state & cont->state_mask)) 04491 flag |= ACT_VISIBLE; 04492 04493 for (iact=0; iact<cont->totlinks; iact++) { 04494 act = cont->links[iact]; 04495 if (act) 04496 act->flag |= flag; 04497 } 04498 cont = cont->next; 04499 } 04500 } 04501 04502 /* ****************** Controllers ****************** */ 04503 04504 xco= 420; yco= 170; width= 300; 04505 layout= uiBlockLayout(block, UI_LAYOUT_VERTICAL, UI_LAYOUT_PANEL, xco, yco, width, 20, U.uistyles.first); 04506 row = uiLayoutRow(layout, 1); 04507 04508 uiDefBlockBut(block, controller_menu, NULL, "Controllers", xco-10, yco, 300, UI_UNIT_Y, ""); /* replace this with uiLayout stuff later */ 04509 04510 uiItemR(row, &logic_ptr, "show_controllers_selected_objects", 0, "Sel", ICON_NONE); 04511 uiItemR(row, &logic_ptr, "show_controllers_active_object", 0, "Act", ICON_NONE); 04512 uiItemR(row, &logic_ptr, "show_controllers_linked_controller", 0, "Link", ICON_NONE); 04513 04514 for(a=0; a<count; a++) { 04515 bController *cont; 04516 PointerRNA ptr; 04517 uiLayout *split, *subsplit, *col; 04518 04519 04520 ob= (Object *)idar[a]; 04521 04522 /* only draw the controller common header if "use_visible" */ 04523 if( (ob->scavisflag & OB_VIS_CONT) == 0) continue; 04524 04525 /* Drawing the Controller Header common to all Selected Objects */ 04526 04527 RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); 04528 04529 split= uiLayoutSplit(layout, 0.05, 0); 04530 uiItemR(split, &settings_ptr, "show_state_panel", UI_ITEM_R_NO_BG, "", ICON_DISCLOSURE_TRI_RIGHT); 04531 04532 row = uiLayoutRow(split, 1); 04533 uiDefButBitS(block, TOG, OB_SHOWCONT, B_REDR, ob->id.name+2,(short)(xco-10), yco, (short)(width-30), UI_UNIT_Y, &ob->scaflag, 0, 31, 0, 0, "Object name, click to show/hide controllers"); 04534 if (ob == act_ob) 04535 uiItemMenuEnumO(row, "LOGIC_OT_controller_add", "type", "Add Controller", ICON_NONE); 04536 04537 if (RNA_boolean_get(&settings_ptr, "show_state_panel")) { 04538 04539 box= uiLayoutBox(layout); 04540 split= uiLayoutSplit(box, 0.2, 0); 04541 04542 col= uiLayoutColumn(split, 0); 04543 uiItemL(col, "Visible", ICON_NONE); 04544 uiItemL(col, "Initial", ICON_NONE); 04545 04546 subsplit= uiLayoutSplit(split, 0.85, 0); 04547 col= uiLayoutColumn(subsplit, 0); 04548 row= uiLayoutRow(col, 0); 04549 uiLayoutSetActive(row, RNA_boolean_get(&settings_ptr, "use_all_states")==0); 04550 uiTemplateLayers(row, &settings_ptr, "states_visible", &settings_ptr, "used_states", 0); 04551 row= uiLayoutRow(col, 0); 04552 uiTemplateLayers(row, &settings_ptr, "states_initial", &settings_ptr, "used_states", 0); 04553 04554 col= uiLayoutColumn(subsplit, 0); 04555 uiItemR(col, &settings_ptr, "use_all_states", UI_ITEM_R_TOGGLE, NULL, ICON_NONE); 04556 uiItemR(col, &settings_ptr, "show_debug_state", 0, "", ICON_NONE); 04557 } 04558 04559 /* End of Drawing the Controller Header common to all Selected Objects */ 04560 04561 if ((ob->scaflag & OB_SHOWCONT) == 0) continue; 04562 04563 04564 uiItemS(layout); 04565 04566 for(cont= ob->controllers.first; cont; cont=cont->next) { 04567 RNA_pointer_create((ID *)ob, &RNA_Controller, cont, &ptr); 04568 04569 if (!(ob->scaflag & OB_ALLSTATE) && !(ob->state & cont->state_mask)) 04570 continue; 04571 04572 /* use two nested splits to align inlinks/links properly */ 04573 split = uiLayoutSplit(layout, 0.05, 0); 04574 04575 /* put inlink button to the left */ 04576 col = uiLayoutColumn(split, 0); 04577 uiLayoutSetAlignment(col, UI_LAYOUT_ALIGN_LEFT); 04578 uiDefIconBut(block, INLINK, 0, ICON_INLINK, 0, 0, UI_UNIT_X, UI_UNIT_Y, cont, LINK_CONTROLLER, 0, 0, 0, ""); 04579 04580 //col = uiLayoutColumn(split, 1); 04581 /* nested split for middle and right columns */ 04582 subsplit = uiLayoutSplit(split, 0.95, 0); 04583 04584 col = uiLayoutColumn(subsplit, 1); 04585 uiLayoutSetContextPointer(col, "controller", &ptr); 04586 04587 /* should make UI template for controller header.. function will do for now */ 04588 // draw_controller_header(col, &ptr); 04589 draw_controller_header(col, &ptr, xco, width, yco); //provisory for 2.50 beta 04590 04591 /* draw the brick contents */ 04592 draw_brick_controller(col, &ptr); 04593 04594 04595 /* put link button to the right */ 04596 col = uiLayoutColumn(subsplit, 0); 04597 uiLayoutSetAlignment(col, UI_LAYOUT_ALIGN_LEFT); 04598 but= uiDefIconBut(block, LINK, 0, ICON_LINK, 0, 0, UI_UNIT_X, UI_UNIT_Y, NULL, 0, 0, 0, 0, ""); 04599 uiSetButLink(but, NULL, (void ***)&(cont->links), &cont->totlinks, LINK_CONTROLLER, LINK_ACTUATOR); 04600 } 04601 } 04602 uiBlockLayoutResolve(block, NULL, &yco); /* stores final height in yco */ 04603 04604 04605 /* ****************** Sensors ****************** */ 04606 04607 xco= 10; yco= 170; width= 340; 04608 layout= uiBlockLayout(block, UI_LAYOUT_VERTICAL, UI_LAYOUT_PANEL, xco, yco, width, 20, U.uistyles.first); 04609 row = uiLayoutRow(layout, 1); 04610 04611 uiDefBlockBut(block, sensor_menu, NULL, "Sensors", xco-10, yco, 300, UI_UNIT_Y, ""); /* replace this with uiLayout stuff later */ 04612 04613 uiItemR(row, &logic_ptr, "show_sensors_selected_objects", 0, "Sel", ICON_NONE); 04614 uiItemR(row, &logic_ptr, "show_sensors_active_object", 0, "Act", ICON_NONE); 04615 uiItemR(row, &logic_ptr, "show_sensors_linked_controller", 0, "Link", ICON_NONE); 04616 uiItemR(row, &logic_ptr, "show_sensors_active_states", 0, "State", ICON_NONE); 04617 04618 for(a=0; a<count; a++) { 04619 bSensor *sens; 04620 PointerRNA ptr; 04621 04622 ob= (Object *)idar[a]; 04623 04624 /* only draw the sensor common header if "use_visible" */ 04625 if((ob->scavisflag & OB_VIS_SENS) == 0) continue; 04626 04627 row = uiLayoutRow(layout, 1); 04628 uiDefButBitS(block, TOG, OB_SHOWSENS, B_REDR, ob->id.name+2,(short)(xco-10), yco, (short)(width-30), UI_UNIT_Y, &ob->scaflag, 0, 31, 0, 0, "Object name, click to show/hide sensors"); 04629 if (ob == act_ob) 04630 uiItemMenuEnumO(row, "LOGIC_OT_sensor_add", "type", "Add Sensor", ICON_NONE); 04631 04632 if ((ob->scaflag & OB_SHOWSENS) == 0) continue; 04633 04634 uiItemS(layout); 04635 04636 for(sens= ob->sensors.first; sens; sens=sens->next) { 04637 RNA_pointer_create((ID *)ob, &RNA_Sensor, sens, &ptr); 04638 04639 if ((ob->scaflag & OB_ALLSTATE) || 04640 !(slogic->scaflag & BUTS_SENS_STATE) || 04641 (sens->totlinks == 0) || /* always display sensor without links so that is can be edited */ 04642 (sens->flag & SENS_PIN && slogic->scaflag & BUTS_SENS_STATE) || /* states can hide some sensors, pinned sensors ignore the visible state */ 04643 (is_sensor_linked(block, sens)) 04644 ) 04645 { // gotta check if the current state is visible or not 04646 uiLayout *split, *col; 04647 04648 /* make as visible, for move operator */ 04649 sens->flag |= SENS_VISIBLE; 04650 04651 split = uiLayoutSplit(layout, 0.95, 0); 04652 col = uiLayoutColumn(split, 1); 04653 uiLayoutSetContextPointer(col, "sensor", &ptr); 04654 04655 /* should make UI template for sensor header.. function will do for now */ 04656 draw_sensor_header(col, &ptr, &logic_ptr); 04657 04658 /* draw the brick contents */ 04659 draw_brick_sensor(col, &ptr, C); 04660 04661 /* put link button to the right */ 04662 col = uiLayoutColumn(split, 0); 04663 /* use oldskool uiButtons for links for now */ 04664 but= uiDefIconBut(block, LINK, 0, ICON_LINK, 0, 0, UI_UNIT_X, UI_UNIT_Y, NULL, 0, 0, 0, 0, ""); 04665 uiSetButLink(but, NULL, (void ***)&(sens->links), &sens->totlinks, LINK_SENSOR, LINK_CONTROLLER); 04666 } 04667 } 04668 } 04669 uiBlockLayoutResolve(block, NULL, &yco); /* stores final height in yco */ 04670 04671 /* ****************** Actuators ****************** */ 04672 04673 xco= 800; yco= 170; width= 340; 04674 layout= uiBlockLayout(block, UI_LAYOUT_VERTICAL, UI_LAYOUT_PANEL, xco, yco, width, 20, U.uistyles.first); 04675 row = uiLayoutRow(layout, 1); 04676 04677 uiDefBlockBut(block, actuator_menu, NULL, "Actuators", xco-10, yco, 300, UI_UNIT_Y, ""); /* replace this with uiLayout stuff later */ 04678 04679 uiItemR(row, &logic_ptr, "show_actuators_selected_objects", 0, "Sel", ICON_NONE); 04680 uiItemR(row, &logic_ptr, "show_actuators_active_object", 0, "Act", ICON_NONE); 04681 uiItemR(row, &logic_ptr, "show_actuators_linked_controller", 0, "Link", ICON_NONE); 04682 uiItemR(row, &logic_ptr, "show_actuators_active_states", 0, "State", ICON_NONE); 04683 04684 for(a=0; a<count; a++) { 04685 bActuator *act; 04686 PointerRNA ptr; 04687 04688 ob= (Object *)idar[a]; 04689 04690 /* only draw the actuator common header if "use_visible" */ 04691 if( (ob->scavisflag & OB_VIS_ACT) == 0) continue; 04692 04693 row = uiLayoutRow(layout, 1); 04694 uiDefButBitS(block, TOG, OB_SHOWACT, B_REDR, ob->id.name+2,(short)(xco-10), yco, (short)(width-30), UI_UNIT_Y, &ob->scaflag, 0, 31, 0, 0, "Object name, click to show/hide actuators"); 04695 if (ob == act_ob) 04696 uiItemMenuEnumO(row, "LOGIC_OT_actuator_add", "type", "Add Actuator", ICON_NONE); 04697 04698 if ((ob->scaflag & OB_SHOWACT) == 0) continue; 04699 04700 uiItemS(layout); 04701 04702 for(act= ob->actuators.first; act; act=act->next) { 04703 04704 RNA_pointer_create((ID *)ob, &RNA_Actuator, act, &ptr); 04705 04706 if ((ob->scaflag & OB_ALLSTATE) || 04707 !(slogic->scaflag & BUTS_ACT_STATE) || 04708 !(act->flag & ACT_LINKED) || /* always display actuators without links so that is can be edited */ 04709 (act->flag & ACT_VISIBLE) || /* this actuator has visible connection, display it */ 04710 (act->flag & ACT_PIN && slogic->scaflag & BUTS_ACT_STATE) /* states can hide some sensors, pinned sensors ignore the visible state */ 04711 ) 04712 { // gotta check if the current state is visible or not 04713 uiLayout *split, *col; 04714 04715 /* make as visible, for move operator */ 04716 act->flag |= ACT_VISIBLE; 04717 04718 split = uiLayoutSplit(layout, 0.05, 0); 04719 04720 /* put inlink button to the left */ 04721 col = uiLayoutColumn(split, 0); 04722 uiDefIconBut(block, INLINK, 0, ICON_INLINK, 0, 0, UI_UNIT_X, UI_UNIT_Y, act, LINK_ACTUATOR, 0, 0, 0, ""); 04723 04724 col = uiLayoutColumn(split, 1); 04725 uiLayoutSetContextPointer(col, "actuator", &ptr); 04726 04727 /* should make UI template for actuator header.. function will do for now */ 04728 draw_actuator_header(col, &ptr, &logic_ptr); 04729 04730 /* draw the brick contents */ 04731 draw_brick_actuator(col, &ptr, C); 04732 04733 } 04734 } 04735 } 04736 uiBlockLayoutResolve(block, NULL, &yco); /* stores final height in yco */ 04737 04738 04739 uiComposeLinks(block); 04740 04741 uiEndBlock(C, block); 04742 uiDrawBlock(C, block); 04743 04744 if(idar) MEM_freeN(idar); 04745 } 04746 04747 void logic_buttons(bContext *C, ARegion *ar) 04748 { 04749 Main *bmain= CTX_data_main(C); 04750 SpaceLogic *slogic= CTX_wm_space_logic(C); 04751 Object *ob= CTX_data_active_object(C); 04752 ID **idar; 04753 bSensor *sens; 04754 bController *cont; 04755 bActuator *act; 04756 uiBlock *block; 04757 uiBut *but; 04758 PointerRNA logic_ptr; 04759 int a, iact, stbit, offset; 04760 int xco, yco, width, ycoo; 04761 short count; 04762 char name[32]; 04763 /* pin is a bool used for actuator and sensor drawing with states 04764 * pin so changing states dosnt hide the logic brick */ 04765 char pin; 04766 04767 if (G.rt == 0) { 04768 logic_buttons_new(C, ar); 04769 return; 04770 } 04771 04772 if(ob==NULL) return; 04773 // uiSetButLock(object_is_libdata(ob), ERROR_LIBDATA_MESSAGE); 04774 04775 sprintf(name, "buttonswin %p", (void *)ar); 04776 block= uiBeginBlock(C, ar, name, UI_EMBOSS); 04777 uiBlockSetHandleFunc(block, do_logic_buts, NULL); 04778 04779 RNA_pointer_create(NULL, &RNA_SpaceLogicEditor, slogic, &logic_ptr); 04780 04781 idar= get_selected_and_linked_obs(C, &count, slogic->scaflag); 04782 04783 /* clean ACT_LINKED and ACT_VISIBLE of all potentially visible actuators so that 04784 we can determine which is actually linked/visible */ 04785 for(a=0; a<count; a++) { 04786 ob= (Object *)idar[a]; 04787 act= ob->actuators.first; 04788 while(act) { 04789 act->flag &= ~(ACT_LINKED|ACT_VISIBLE); 04790 act = act->next; 04791 } 04792 /* same for sensors */ 04793 sens= ob->sensors.first; 04794 while(sens) { 04795 sens->flag &= ~(SENS_VISIBLE); 04796 sens = sens->next; 04797 } 04798 } 04799 04800 /* start with the controller because we need to know which one is visible */ 04801 /* ******************************* */ 04802 xco= 400; yco= 170; width= 300; 04803 04804 uiDefBlockBut(block, controller_menu, NULL, "Controllers", xco-10, yco+35, 100, UI_UNIT_Y, ""); 04805 04806 uiBlockBeginAlign(block); 04807 uiDefButBitS(block, TOG, BUTS_CONT_SEL, B_REDR, "Sel", xco+110, yco+35, (width-100)/3, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show all selected Objects"); 04808 uiDefButBitS(block, TOG, BUTS_CONT_ACT, B_REDR, "Act", xco+110+(width-100)/3, yco+35, (width-100)/3, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show active Object"); 04809 uiDefButBitS(block, TOG, BUTS_CONT_LINK, B_REDR, "Link", xco+110+2*(width-100)/3, yco+35, (width-100)/3, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show linked Objects to Sensor/Actuator"); 04810 uiBlockEndAlign(block); 04811 04812 for(a=0; a<count; a++) { 04813 unsigned int controller_state_mask = 0; /* store a bitmask for states that are used */ 04814 04815 ob= (Object *)idar[a]; 04816 // uiClearButLock(); 04817 // uiSetButLock(object_is_libdata(ob), ERROR_LIBDATA_MESSAGE); 04818 if( (ob->scavisflag & OB_VIS_CONT) == 0) continue; 04819 04820 /* presume it is only objects for now */ 04821 uiBlockBeginAlign(block); 04822 // if(ob->controllers.first) uiSetCurFont(block, UI_HELVB); 04823 uiDefButBitS(block, TOG, OB_SHOWCONT, B_REDR, ob->id.name+2,(short)(xco-10), yco, (short)(width-30), UI_UNIT_Y, &ob->scaflag, 0, 0, 0, 0, "Active Object name"); 04824 // if(ob->controllers.first) uiSetCurFont(block, UI_HELV); 04825 uiDefButBitS(block, TOG, OB_ADDCONT, B_ADD_CONT, "Add",(short)(xco+width-40), yco, 50, UI_UNIT_Y, &ob->scaflag, 0, 0, 0, 0, "Add a new Controller"); 04826 uiBlockEndAlign(block); 04827 yco-=20; 04828 04829 /* mark all actuators linked to these controllers */ 04830 /* note that some of these actuators could be from objects that are not in the display list. 04831 It's ok because those actuators will not be displayed here */ 04832 cont= ob->controllers.first; 04833 while(cont) { 04834 for (iact=0; iact<cont->totlinks; iact++) { 04835 act = cont->links[iact]; 04836 if (act) 04837 act->flag |= ACT_LINKED; 04838 } 04839 controller_state_mask |= cont->state_mask; 04840 cont = cont->next; 04841 } 04842 04843 if(ob->scaflag & OB_SHOWCONT) { 04844 04845 /* first show the state */ 04846 uiDefBlockBut(block, object_state_mask_menu, ob, "State", (short)(xco-10), (short)(yco-10), 36, UI_UNIT_Y, "Object state menu: store and retrieve initial state"); 04847 04848 if (!ob->state) 04849 ob->state = 1; 04850 for (offset=0; offset<15; offset+=5) { 04851 uiBlockBeginAlign(block); 04852 for (stbit=0; stbit<5; stbit++) { 04853 but = uiDefButBitI(block, controller_state_mask&(1<<(stbit+offset)) ? BUT_TOGDUAL:TOG, 1<<(stbit+offset), stbit+offset, "", (short)(xco+31+12*stbit+13*offset), yco, 12, 12, (int *)&(ob->state), 0, 0, 0, 0, get_state_name(ob, (short)(stbit+offset))); 04854 uiButSetFunc(but, check_state_mask, but, &(ob->state)); 04855 } 04856 for (stbit=0; stbit<5; stbit++) { 04857 but = uiDefButBitI(block, controller_state_mask&(1<<(stbit+offset+15)) ? BUT_TOGDUAL:TOG, 1<<(stbit+offset+15), stbit+offset+15, "", (short)(xco+31+12*stbit+13*offset), yco-12, 12, 12, (int *)&(ob->state), 0, 0, 0, 0, get_state_name(ob, (short)(stbit+offset+15))); 04858 uiButSetFunc(but, check_state_mask, but, &(ob->state)); 04859 } 04860 } 04861 uiBlockBeginAlign(block); 04862 uiDefButBitS(block, TOG, OB_ALLSTATE, B_SET_STATE_BIT, "All",(short)(xco+226), yco-10, 22, UI_UNIT_Y, &ob->scaflag, 0, 0, 0, 0, "Set all state bits"); 04863 uiDefButBitS(block, TOG, OB_INITSTBIT, B_INIT_STATE_BIT, "Ini",(short)(xco+248), yco-10, 22, UI_UNIT_Y, &ob->scaflag, 0, 0, 0, 0, "Set the initial state"); 04864 uiDefButBitS(block, TOG, OB_DEBUGSTATE, 0, "D",(short)(xco+270), yco-10, 15, UI_UNIT_Y, &ob->scaflag, 0, 0, 0, 0, "Print state debug info"); 04865 uiBlockEndAlign(block); 04866 04867 yco-=35; 04868 04869 /* display only the controllers that match the current state */ 04870 offset = 0; 04871 for (stbit=0; stbit<32; stbit++) { 04872 if (!(ob->state & (1<<stbit))) 04873 continue; 04874 /* add a separation between controllers of different states */ 04875 if (offset) { 04876 offset = 0; 04877 yco -= 6; 04878 } 04879 cont= ob->controllers.first; 04880 while(cont) { 04881 if (cont->state_mask & (1<<stbit)) { 04882 /* this controller is visible, mark all its actuator */ 04883 for (iact=0; iact<cont->totlinks; iact++) { 04884 act = cont->links[iact]; 04885 if (act) 04886 act->flag |= ACT_VISIBLE; 04887 } 04888 uiDefIconButBitS(block, TOG, CONT_DEL, B_DEL_CONT, ICON_X, xco, yco, 22, UI_UNIT_Y, &cont->flag, 0, 0, 0, 0, "Delete Controller"); 04889 uiDefIconButBitS(block, ICONTOG, CONT_SHOW, B_REDR, ICON_RIGHTARROW, (short)(xco+width-22), yco, 22, UI_UNIT_Y, &cont->flag, 0, 0, 0, 0, "Controller settings"); 04890 uiDefIconButBitS(block, TOG, CONT_PRIO, B_REDR, ICON_BOOKMARKS, (short)(xco+width-66), yco, 22, UI_UNIT_Y, &cont->flag, 0, 0, 0, 0, "Mark controller for execution before all non-marked controllers (good for startup scripts)"); 04891 04892 sprintf(name, "%d", first_bit(cont->state_mask)+1); 04893 uiDefBlockBut(block, controller_state_mask_menu, cont, name, (short)(xco+width-44), yco, 22, UI_UNIT_Y, "Set controller state index (from 1 to 30)"); 04894 04895 if(cont->flag & CONT_SHOW) { 04896 cont->otype= cont->type; 04897 uiDefButS(block, MENU, B_CHANGE_CONT, controller_pup(),(short)(xco+22), yco, 70, UI_UNIT_Y, &cont->type, 0, 0, 0, 0, "Controller type"); 04898 but= uiDefBut(block, TEX, 1, "", (short)(xco+92), yco, (short)(width-158), UI_UNIT_Y, cont->name, 0, 31, 0, 0, "Controller name"); 04899 uiButSetFunc(but, make_unique_prop_names_cb, cont->name, (void*) 0); 04900 04901 ycoo= yco; 04902 yco= draw_controllerbuttons(cont, block, xco, yco, width); 04903 if(yco-6 < ycoo) ycoo= (yco+ycoo-20)/2; 04904 } 04905 else { 04906 cpack(0x999999); 04907 glRecti(xco+22, yco, xco+width-22,yco+19); 04908 but= uiDefBut(block, LABEL, 0, controller_name(cont->type), (short)(xco+22), yco, 70, UI_UNIT_Y, cont, 0, 0, 0, 0, "Controller type"); 04909 //uiButSetFunc(but, old_sca_move_controller, cont, NULL); 04910 but= uiDefBut(block, LABEL, 0, cont->name,(short)(xco+92), yco,(short)(width-158), UI_UNIT_Y, cont, 0, 0, 0, 0, "Controller name"); 04911 //uiButSetFunc(but, old_sca_move_controller, cont, NULL); 04912 04913 uiBlockBeginAlign(block); 04914 but= uiDefIconBut(block, BUT, B_REDR, ICON_TRIA_UP, (short)(xco+width-(110+5)), yco, 22, UI_UNIT_Y, NULL, 0, 0, 0, 0, "Move this logic brick up"); 04915 uiButSetFunc(but, old_sca_move_controller, cont, (void *)TRUE); 04916 but= uiDefIconBut(block, BUT, B_REDR, ICON_TRIA_DOWN, (short)(xco+width-(88+5)), yco, 22, UI_UNIT_Y, NULL, 0, 0, 0, 0, "Move this logic brick down"); 04917 uiButSetFunc(but, old_sca_move_controller, cont, (void *)FALSE); 04918 uiBlockEndAlign(block); 04919 04920 ycoo= yco; 04921 } 04922 04923 but= uiDefIconBut(block, LINK, 0, ICON_LINK, (short)(xco+width), ycoo, UI_UNIT_X, UI_UNIT_Y, NULL, 0, 0, 0, 0, ""); 04924 uiSetButLink(but, NULL, (void ***)&(cont->links), &cont->totlinks, LINK_CONTROLLER, LINK_ACTUATOR); 04925 04926 uiDefIconBut(block, INLINK, 0, ICON_INLINK,(short)(xco-19), ycoo, UI_UNIT_X, UI_UNIT_Y, cont, LINK_CONTROLLER, 0, 0, 0, ""); 04927 /* offset is >0 if at least one controller was displayed */ 04928 offset++; 04929 yco-=20; 04930 } 04931 cont= cont->next; 04932 } 04933 04934 } 04935 yco-= 6; 04936 } 04937 } 04938 04939 /* ******************************* */ 04940 xco= 10; yco= 170; width= 300; 04941 04942 uiDefBlockBut(block, sensor_menu, NULL, "Sensors", xco-10, yco+35, 70, UI_UNIT_Y, ""); 04943 04944 uiBlockBeginAlign(block); 04945 uiDefButBitS(block, TOG, BUTS_SENS_SEL, B_REDR, "Sel", xco+80, yco+35, (width-70)/4, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show all selected Objects"); 04946 uiDefButBitS(block, TOG, BUTS_SENS_ACT, B_REDR, "Act", xco+80+(width-70)/4, yco+35, (width-70)/4, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show active Object"); 04947 uiDefButBitS(block, TOG, BUTS_SENS_LINK, B_REDR, "Link", xco+80+2*(width-70)/4, yco+35, (width-70)/4, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show linked Objects to Controller"); 04948 uiDefButBitS(block, TOG, BUTS_SENS_STATE, B_REDR, "State", xco+80+3*(width-70)/4, yco+35, (width-70)/4, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show only sensors connected to active states"); 04949 uiBlockEndAlign(block); 04950 04951 for(a=0; a<count; a++) { 04952 ob= (Object *)idar[a]; 04953 // uiClearButLock(); 04954 // uiSetButLock(object_is_libdata(ob), ERROR_LIBDATA_MESSAGE); 04955 04956 if( (ob->scavisflag & OB_VIS_SENS) == 0) continue; 04957 04958 /* presume it is only objects for now */ 04959 uiBlockBeginAlign(block); 04960 // if(ob->sensors.first) uiSetCurFont(block, UI_HELVB); 04961 uiDefButBitS(block, TOG, OB_SHOWSENS, B_REDR, ob->id.name+2,(short)(xco-10), yco, (short)(width-30), UI_UNIT_Y, &ob->scaflag, 0, 31, 0, 0, "Object name, click to show/hide sensors"); 04962 // if(ob->sensors.first) uiSetCurFont(block, UI_HELV); 04963 uiDefButBitS(block, TOG, OB_ADDSENS, B_ADD_SENS, "Add",(short)(xco+width-40), yco, 50, UI_UNIT_Y, &ob->scaflag, 0, 0, 0, 0, "Add a new Sensor"); 04964 uiBlockEndAlign(block); 04965 yco-=20; 04966 04967 if(ob->scaflag & OB_SHOWSENS) { 04968 04969 sens= ob->sensors.first; 04970 while(sens) { 04971 if (!(slogic->scaflag & BUTS_SENS_STATE) || 04972 (sens->totlinks == 0) || /* always display sensor without links so that is can be edited */ 04973 (sens->flag & SENS_PIN && slogic->scaflag & BUTS_SENS_STATE) || /* states can hide some sensors, pinned sensors ignore the visible state */ 04974 (is_sensor_linked(block, sens)) 04975 ) { 04976 /* should we draw the pin? - for now always draw when there is a state */ 04977 pin = (slogic->scaflag & BUTS_SENS_STATE && (sens->flag & SENS_SHOW || sens->flag & SENS_PIN)) ? 1:0 ; 04978 04979 sens->flag |= SENS_VISIBLE; 04980 uiDefIconButBitS(block, TOG, SENS_DEL, B_DEL_SENS, ICON_X, xco, yco, 22, UI_UNIT_Y, &sens->flag, 0, 0, 0, 0, "Delete Sensor"); 04981 if (pin) 04982 uiDefIconButBitS(block, ICONTOG, SENS_PIN, B_REDR, ICON_PINNED, (short)(xco+width-44), yco, 22, UI_UNIT_Y, &sens->flag, 0, 0, 0, 0, "Display when not linked to a visible states controller"); 04983 04984 uiDefIconButBitS(block, ICONTOG, SENS_SHOW, B_REDR, ICON_RIGHTARROW, (short)(xco+width-22), yco, 22, UI_UNIT_Y, &sens->flag, 0, 0, 0, 0, "Sensor settings"); 04985 04986 ycoo= yco; 04987 if(sens->flag & SENS_SHOW) 04988 { 04989 uiDefButS(block, MENU, B_CHANGE_SENS, sensor_pup(), (short)(xco+22), yco, 80, UI_UNIT_Y, &sens->type, 0, 0, 0, 0, "Sensor type"); 04990 but= uiDefBut(block, TEX, 1, "", (short)(xco+102), yco, (short)(width-(pin?146:124)), UI_UNIT_Y, sens->name, 0, 31, 0, 0, "Sensor name"); 04991 uiButSetFunc(but, make_unique_prop_names_cb, sens->name, (void*) 0); 04992 04993 sens->otype= sens->type; 04994 yco= draw_sensorbuttons(ob, sens, block, xco, yco, width); 04995 if(yco-6 < ycoo) ycoo= (yco+ycoo-20)/2; 04996 } 04997 else { 04998 set_col_sensor(sens->type, 1); 04999 glRecti(xco+22, yco, xco+width-22,yco+19); 05000 but= uiDefBut(block, LABEL, 0, sensor_name(sens->type), (short)(xco+22), yco, 80, UI_UNIT_Y, sens, 0, 0, 0, 0, ""); 05001 //uiButSetFunc(but, old_sca_move_sensor, sens, NULL); 05002 but= uiDefBut(block, LABEL, 0, sens->name, (short)(xco+102), yco, (short)(width-(pin?146:124)), UI_UNIT_Y, sens, 0, 31, 0, 0, ""); 05003 //uiButSetFunc(but, old_sca_move_sensor, sens, NULL); 05004 05005 uiBlockBeginAlign(block); 05006 but= uiDefIconBut(block, BUT, B_REDR, ICON_TRIA_UP, (short)(xco+width-(66+5)), yco, 22, UI_UNIT_Y, NULL, 0, 0, 0, 0, "Move this logic brick up"); 05007 uiButSetFunc(but, old_sca_move_sensor, sens, (void *)TRUE); 05008 but= uiDefIconBut(block, BUT, B_REDR, ICON_TRIA_DOWN, (short)(xco+width-(44+5)), yco, 22, UI_UNIT_Y, NULL, 0, 0, 0, 0, "Move this logic brick down"); 05009 uiButSetFunc(but, old_sca_move_sensor, sens, (void *)FALSE); 05010 uiBlockEndAlign(block); 05011 } 05012 05013 but= uiDefIconBut(block, LINK, 0, ICON_LINK, (short)(xco+width), ycoo, UI_UNIT_X, UI_UNIT_Y, NULL, 0, 0, 0, 0, ""); 05014 uiSetButLink(but, NULL, (void ***)&(sens->links), &sens->totlinks, LINK_SENSOR, LINK_CONTROLLER); 05015 05016 yco-=20; 05017 } 05018 sens= sens->next; 05019 } 05020 yco-= 6; 05021 } 05022 } 05023 /* ******************************* */ 05024 xco= 800; yco= 170; width= 300; 05025 uiDefBlockBut(block, actuator_menu, NULL, "Actuators", xco-10, yco+35, 90, UI_UNIT_Y, ""); 05026 05027 uiBlockBeginAlign(block); 05028 uiDefButBitS(block, TOG, BUTS_ACT_SEL, B_REDR, "Sel", xco+110, yco+35, (width-100)/4, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show all selected Objects"); 05029 uiDefButBitS(block, TOG, BUTS_ACT_ACT, B_REDR, "Act", xco+110+(width-100)/4, yco+35, (width-100)/4, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show active Object"); 05030 uiDefButBitS(block, TOG, BUTS_ACT_LINK, B_REDR, "Link", xco+110+2*(width-100)/4, yco+35, (width-100)/4, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show linked Objects to Controller"); 05031 uiDefButBitS(block, TOG, BUTS_ACT_STATE, B_REDR, "State", xco+110+3*(width-100)/4, yco+35, (width-100)/4, UI_UNIT_Y, &slogic->scaflag, 0, 0, 0, 0, "Show only actuators connected to active states"); 05032 uiBlockEndAlign(block); 05033 for(a=0; a<count; a++) { 05034 ob= (Object *)idar[a]; 05035 // uiClearButLock(); 05036 // uiSetButLock(object_is_libdata(ob), ERROR_LIBDATA_MESSAGE); 05037 if( (ob->scavisflag & OB_VIS_ACT) == 0) continue; 05038 05039 /* presume it is only objects for now */ 05040 uiBlockBeginAlign(block); 05041 // if(ob->actuators.first) uiSetCurFont(block, UI_HELVB); 05042 uiDefButBitS(block, TOG, OB_SHOWACT, B_REDR, ob->id.name+2,(short)(xco-10), yco,(short)(width-30), UI_UNIT_Y, &ob->scaflag, 0, 31, 0, 0, "Object name, click to show/hide actuators"); 05043 // if(ob->actuators.first) uiSetCurFont(block, UI_HELV); 05044 uiDefButBitS(block, TOG, OB_ADDACT, B_ADD_ACT, "Add",(short)(xco+width-40), yco, 50, UI_UNIT_Y, &ob->scaflag, 0, 0, 0, 0, "Add a new Actuator"); 05045 uiBlockEndAlign(block); 05046 yco-=20; 05047 05048 if(ob->scaflag & OB_SHOWACT) { 05049 05050 act= ob->actuators.first; 05051 while(act) { 05052 if (!(slogic->scaflag & BUTS_ACT_STATE) || 05053 !(act->flag & ACT_LINKED) || /* always display actuators without links so that is can be edited */ 05054 (act->flag & ACT_VISIBLE) || /* this actuator has visible connection, display it */ 05055 (act->flag & ACT_PIN && slogic->scaflag & BUTS_ACT_STATE)) { 05056 05057 pin = (slogic->scaflag & BUTS_ACT_STATE && (act->flag & SENS_SHOW || act->flag & SENS_PIN)) ? 1:0 ; 05058 05059 act->flag |= ACT_VISIBLE; /* mark the actuator as visible to help implementing the up/down action */ 05060 uiDefIconButBitS(block, TOG, ACT_DEL, B_DEL_ACT, ICON_X, xco, yco, 22, UI_UNIT_Y, &act->flag, 0, 0, 0, 0, "Delete Actuator"); 05061 if (pin) 05062 uiDefIconButBitS(block, ICONTOG, ACT_PIN, B_REDR, ICON_PINNED, (short)(xco+width-44), yco, 22, UI_UNIT_Y, &act->flag, 0, 0, 0, 0, "Display when not linked to a visible states controller"); 05063 uiDefIconButBitS(block, ICONTOG, ACT_SHOW, B_REDR, ICON_RIGHTARROW, (short)(xco+width-22), yco, 22, UI_UNIT_Y, &act->flag, 0, 0, 0, 0, "Display the actuator"); 05064 05065 if(act->flag & ACT_SHOW) { 05066 act->otype= act->type; 05067 uiDefButS(block, MENU, B_CHANGE_ACT, actuator_pup(ob), (short)(xco+22), yco, 90, UI_UNIT_Y, &act->type, 0, 0, 0, 0, "Actuator type"); 05068 but= uiDefBut(block, TEX, 1, "", (short)(xco+112), yco, (short)(width-(pin?156:134)), UI_UNIT_Y, act->name, 0, 31, 0, 0, "Actuator name"); 05069 uiButSetFunc(but, make_unique_prop_names_cb, act->name, (void*) 0); 05070 05071 ycoo= yco; 05072 yco= draw_actuatorbuttons(bmain, ob, act, block, xco, yco, width); 05073 if(yco-6 < ycoo) ycoo= (yco+ycoo-20)/2; 05074 } 05075 else { 05076 set_col_actuator(act->type, 1); 05077 glRecti((short)(xco+22), yco, (short)(xco+width-22),(short)(yco+19)); 05078 /* but= */ uiDefBut(block, LABEL, 0, actuator_name(act->type), (short)(xco+22), yco, 90, UI_UNIT_Y, act, 0, 0, 0, 0, "Actuator type"); 05079 // uiButSetFunc(but, old_sca_move_actuator, act, NULL); 05080 /* but= */ uiDefBut(block, LABEL, 0, act->name, (short)(xco+112), yco, (short)(width-(pin?156:134)), UI_UNIT_Y, act, 0, 0, 0, 0, "Actuator name"); 05081 // uiButSetFunc(but, old_sca_move_actuator, act, NULL); 05082 05083 uiBlockBeginAlign(block); 05084 but= uiDefIconBut(block, BUT, B_REDR, ICON_TRIA_UP, (short)(xco+width-(66+5)), yco, 22, UI_UNIT_Y, NULL, 0, 0, 0, 0, "Move this logic brick up"); 05085 uiButSetFunc(but, old_sca_move_actuator, act, (void *)TRUE); 05086 but= uiDefIconBut(block, BUT, B_REDR, ICON_TRIA_DOWN, (short)(xco+width-(44+5)), yco, 22, UI_UNIT_Y, NULL, 0, 0, 0, 0, "Move this logic brick down"); 05087 uiButSetFunc(but, old_sca_move_actuator, act, (void *)FALSE); 05088 uiBlockEndAlign(block); 05089 05090 ycoo= yco; 05091 } 05092 05093 uiDefIconBut(block, INLINK, 0, ICON_INLINK,(short)(xco-19), ycoo, UI_UNIT_X, UI_UNIT_Y, act, LINK_ACTUATOR, 0, 0, 0, ""); 05094 05095 yco-=20; 05096 } 05097 act= act->next; 05098 } 05099 yco-= 6; 05100 } 05101 } 05102 05103 uiComposeLinks(block); 05104 05105 uiEndBlock(C, block); 05106 uiDrawBlock(C, block); 05107 05108 if(idar) MEM_freeN(idar); 05109 } 05110 05111 05112 05113 05114 05115