diff options
Diffstat (limited to 'source/blender/editors/space_logic')
-rw-r--r-- | source/blender/editors/space_logic/CMakeLists.txt | 39 | ||||
-rw-r--r-- | source/blender/editors/space_logic/Makefile | 2 | ||||
-rw-r--r-- | source/blender/editors/space_logic/logic_buttons.c | 10 | ||||
-rw-r--r-- | source/blender/editors/space_logic/logic_header.c | 120 | ||||
-rw-r--r-- | source/blender/editors/space_logic/logic_intern.h | 4 | ||||
-rw-r--r-- | source/blender/editors/space_logic/logic_ops.c | 696 | ||||
-rw-r--r-- | source/blender/editors/space_logic/logic_window.c | 1685 | ||||
-rw-r--r-- | source/blender/editors/space_logic/space_logic.c | 29 |
8 files changed, 2358 insertions, 227 deletions
diff --git a/source/blender/editors/space_logic/CMakeLists.txt b/source/blender/editors/space_logic/CMakeLists.txt new file mode 100644 index 00000000000..91087d57f11 --- /dev/null +++ b/source/blender/editors/space_logic/CMakeLists.txt @@ -0,0 +1,39 @@ +# $Id: CMakeLists.txt 12931 2007-12-17 18:20:48Z theeth $ +# ***** BEGIN GPL LICENSE BLOCK ***** +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License +# as published by the Free Software Foundation; either version 2 +# of the License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software Foundation, +# Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +# +# Contributor(s): Jacques Beaurain. +# +# ***** END GPL LICENSE BLOCK ***** + +FILE(GLOB SRC *.c) + +SET(INC + ../../blenkernel + ../../blenlib + ../include + ../../../../intern/guardedalloc + ../../makesdna + ../../makesrna + ../../windowmanager + ../../editors/interface +) + +IF(WITH_GAMEENGINE) + ADD_DEFINITIONS(-DGAMEBLENDER) +ENDIF(WITH_GAMEENGINE) + +BLENDERLIB(bf_editor_space_logic "${SRC}" "${INC}") diff --git a/source/blender/editors/space_logic/Makefile b/source/blender/editors/space_logic/Makefile index 90cd73bd62a..9b72e132be8 100644 --- a/source/blender/editors/space_logic/Makefile +++ b/source/blender/editors/space_logic/Makefile @@ -15,7 +15,7 @@ # # You should have received a copy of the GNU General Public License # along with this program; if not, write to the Free Software Foundation, -# Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +# Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. # # The Original Code is Copyright (C) 2007 Blender Foundation # All rights reserved. diff --git a/source/blender/editors/space_logic/logic_buttons.c b/source/blender/editors/space_logic/logic_buttons.c index fc0955bf9d1..d8dfd8cb52d 100644 --- a/source/blender/editors/space_logic/logic_buttons.c +++ b/source/blender/editors/space_logic/logic_buttons.c @@ -27,26 +27,16 @@ #include <string.h> #include <stdio.h> -#include "DNA_object_types.h" -#include "MEM_guardedalloc.h" #include "BLI_blenlib.h" #include "BLI_math.h" #include "BKE_context.h" -#include "BKE_global.h" -#include "BKE_library.h" -#include "BKE_main.h" -#include "BKE_mesh.h" -#include "BKE_node.h" #include "BKE_screen.h" -#include "BKE_utildefines.h" #include "ED_screen.h" -#include "BIF_gl.h" -#include "BIF_glutil.h" #include "RNA_access.h" #include "RNA_define.h" diff --git a/source/blender/editors/space_logic/logic_header.c b/source/blender/editors/space_logic/logic_header.c deleted file mode 100644 index 3e38eb815fb..00000000000 --- a/source/blender/editors/space_logic/logic_header.c +++ /dev/null @@ -1,120 +0,0 @@ -/** - * $Id$ - * - * ***** BEGIN GPL LICENSE BLOCK ***** - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License - * as published by the Free Software Foundation; either version 2 - * of the License, or (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software Foundation, - * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. - * - * The Original Code is Copyright (C) 2009 Blender Foundation. - * All rights reserved. - * - * - * Contributor(s): Blender Foundation - * - * ***** END GPL LICENSE BLOCK ***** - */ - -#include <string.h> -#include <stdio.h> - - -#include "MEM_guardedalloc.h" - -#include "BLI_blenlib.h" - -#include "BKE_context.h" -#include "BKE_screen.h" -#include "BKE_main.h" - -#include "ED_screen.h" -#include "ED_types.h" -#include "ED_util.h" - - -#include "BIF_gl.h" -#include "BIF_glutil.h" - -#include "UI_interface.h" -#include "UI_resources.h" -#include "UI_view2d.h" - -#include "logic_intern.h" - -/* ************************ header area region *********************** */ - - -static void do_logic_buttons(bContext *C, void *arg, int event) -{ -// SpaceLogic *slogic= CTX_wm_space_logic(C); -} - -static uiBlock *logic_addmenu(bContext *C, ARegion *ar, void *arg_unused) -{ -// SpaceLogic *slogic= CTX_wm_space_logic(C); - uiBlock *block; - short yco= 0, menuwidth=120; - - block= uiBeginBlock(C, ar, "logic_addmenu", UI_EMBOSSP); -// uiBlockSetButmFunc(block, do_logic_addmenu, NULL); - - uiDefIconTextBut(block, BUTM, 1, ICON_BLANK1, "Nothing yet", 0, yco-=20, menuwidth, 19, NULL, 0.0, 0.0, 1, 2, ""); - - uiTextBoundsBlock(block, 50); - uiBlockSetDirection(block, UI_TOP); - uiEndBlock(C, block); - - return block; -} - -void logic_header_buttons(const bContext *C, ARegion *ar) -{ - ScrArea *sa= CTX_wm_area(C); -// SpaceLogic *slogic= CTX_wm_space_logic(C); - uiBlock *block; - short xco, yco= 3; - - block= uiBeginBlock(C, ar, "header logic", UI_EMBOSS); - uiBlockSetHandleFunc(block, do_logic_buttons, NULL); - - xco= ED_area_header_standardbuttons(C, block, yco); - - if((sa->flag & HEADER_NO_PULLDOWN)==0) { - int xmax; - - xmax= GetButStringLength("View"); - uiDefPulldownBut(block, logic_addmenu, NULL, - "View", xco, yco, xmax-3, 20, ""); - xco+= xmax; - - xmax= GetButStringLength("Select"); - uiDefPulldownBut(block, logic_addmenu, NULL, - "Select", xco, yco, xmax-3, 20, ""); - xco+= xmax; - - xmax= GetButStringLength("Add"); - uiDefPulldownBut(block, logic_addmenu, NULL, - "Add", xco, yco, xmax-3, 20, ""); - xco+= xmax; - } - - uiBlockSetEmboss(block, UI_EMBOSS); - - UI_view2d_totRect_set(&ar->v2d, xco+XIC+100, (int)(ar->v2d.tot.ymax-ar->v2d.tot.ymin)); - - uiEndBlock(C, block); - uiDrawBlock(C, block); -} - - diff --git a/source/blender/editors/space_logic/logic_intern.h b/source/blender/editors/space_logic/logic_intern.h index 4d19a16ee9c..0c30aa711f1 100644 --- a/source/blender/editors/space_logic/logic_intern.h +++ b/source/blender/editors/space_logic/logic_intern.h @@ -42,9 +42,6 @@ struct Scene; /* space_logic.c */ struct ARegion *logic_has_buttons_region(struct ScrArea *sa); -/* logic_header.c */ -void logic_header_buttons(const struct bContext *C, struct ARegion *ar); - /* logic_ops.c */ /* logic_buttons.c */ @@ -54,6 +51,7 @@ void LOGIC_OT_links_cut(struct wmOperatorType *ot); /* logic_window.c */ void logic_buttons(struct bContext *C, struct ARegion *ar); +void make_unique_prop_names(struct bContext *C, char *str); #endif /* ED_LOGIC_INTERN_H */ diff --git a/source/blender/editors/space_logic/logic_ops.c b/source/blender/editors/space_logic/logic_ops.c new file mode 100644 index 00000000000..4641fd2ce61 --- /dev/null +++ b/source/blender/editors/space_logic/logic_ops.c @@ -0,0 +1,696 @@ +/** + * $Id$ + * + * ***** BEGIN GPL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + * The Original Code is Copyright (C) 2009 Blender Foundation. + * All rights reserved. + * + * + * Contributor(s): Blender Foundation + * + * ***** END GPL LICENSE BLOCK ***** + */ +#include <stddef.h> + +#include "DNA_object_types.h" +#include "DNA_sensor_types.h" +#include "DNA_controller_types.h" +#include "DNA_actuator_types.h" + +#include "BLI_blenlib.h" + +#include "BKE_context.h" +#include "BKE_main.h" +#include "BKE_sca.h" + +#include "ED_object.h" +#include "ED_screen.h" + +#include "RNA_access.h" +#include "RNA_define.h" +#include "RNA_enum_types.h" + +#include "WM_api.h" +#include "WM_types.h" + +#include "logic_intern.h" + +/* ************* Generic Operator Helpers ************* */ + +static int edit_sensor_poll(bContext *C) +{ + PointerRNA ptr= CTX_data_pointer_get_type(C, "sensor", &RNA_Sensor); + + if (ptr.data && ((ID*)ptr.id.data)->lib) return 0; + return 1; +} + +static int edit_controller_poll(bContext *C) +{ + PointerRNA ptr= CTX_data_pointer_get_type(C, "controller", &RNA_Controller); + + if (ptr.data && ((ID*)ptr.id.data)->lib) return 0; + return 1; +} + +static int edit_actuator_poll(bContext *C) +{ + PointerRNA ptr= CTX_data_pointer_get_type(C, "actuator", &RNA_Actuator); + + if (ptr.data && ((ID*)ptr.id.data)->lib) return 0; + return 1; +} + +static void edit_sensor_properties(wmOperatorType *ot) +{ + RNA_def_string(ot->srna, "sensor", "", 32, "Sensor", "Name of the sensor to edit"); + RNA_def_string(ot->srna, "object", "", 32, "Object", "Name of the object the sensor belongs to"); +} + +static int edit_sensor_invoke_properties(bContext *C, wmOperator *op) +{ + PointerRNA ptr= CTX_data_pointer_get_type(C, "sensor", &RNA_Sensor); + + if (RNA_property_is_set(op->ptr, "sensor") && RNA_property_is_set(op->ptr, "object") ) + return 1; + + if (ptr.data) { + bSensor *sens = ptr.data; + Object *ob = ptr.id.data; + + RNA_string_set(op->ptr, "sensor", sens->name); + RNA_string_set(op->ptr, "object", ob->id.name+2); + return 1; + } + + return 0; +} + +static Object *edit_object_property_get(bContext *C, wmOperator *op) +{ + char ob_name[32]; + Object *ob; + + RNA_string_get(op->ptr, "object", ob_name); + + /* if ob_name is valid try to find the object with this name + otherwise gets the active object */ + if (BLI_strnlen(ob_name, 32) > 0) + ob = BLI_findstring(&(CTX_data_main(C)->object), ob_name, offsetof(ID, name) + 2); + else + ob= ED_object_active_context(C); + + return ob; +} + +static bSensor *edit_sensor_property_get(bContext *C, wmOperator *op, Object **ob) +{ + char sensor_name[32]; + bSensor *sens; + + RNA_string_get(op->ptr, "sensor", sensor_name); + + *ob= edit_object_property_get(C, op); + if (!*ob) return NULL; + + sens = BLI_findstring(&((*ob)->sensors), sensor_name, offsetof(bSensor, name)); + return sens; +} + +static void edit_controller_properties(wmOperatorType *ot) +{ + RNA_def_string(ot->srna, "controller", "", 32, "Controller", "Name of the controller to edit"); + RNA_def_string(ot->srna, "object", "", 32, "Object", "Name of the object the controller belongs to"); +} + +static int edit_controller_invoke_properties(bContext *C, wmOperator *op) +{ + PointerRNA ptr= CTX_data_pointer_get_type(C, "controller", &RNA_Controller); + + if (RNA_property_is_set(op->ptr, "controller") && RNA_property_is_set(op->ptr, "object") ) + return 1; + + if (ptr.data) { + bController *cont = ptr.data; + Object *ob = ptr.id.data; + + RNA_string_set(op->ptr, "controller", cont->name); + RNA_string_set(op->ptr, "object", ob->id.name+2); + return 1; + } + + return 0; +} + +static bController *edit_controller_property_get(bContext *C, wmOperator *op, Object **ob) +{ + char controller_name[32]; + bController *cont; + + RNA_string_get(op->ptr, "controller", controller_name); + + *ob= edit_object_property_get(C, op); + if (!*ob) return NULL; + + cont = BLI_findstring(&((*ob)->controllers), controller_name, offsetof(bController, name)); + return cont; +} + +static void edit_actuator_properties(wmOperatorType *ot) +{ + RNA_def_string(ot->srna, "actuator", "", 32, "Actuator", "Name of the actuator to edit"); + RNA_def_string(ot->srna, "object", "", 32, "Object", "Name of the object the actuator belongs to"); +} + +static int edit_actuator_invoke_properties(bContext *C, wmOperator *op) +{ + PointerRNA ptr= CTX_data_pointer_get_type(C, "actuator", &RNA_Actuator); + + if (RNA_property_is_set(op->ptr, "actuator") && RNA_property_is_set(op->ptr, "object") ) + return 1; + + if (ptr.data) { + bActuator *act = ptr.data; + Object *ob = ptr.id.data; + + RNA_string_set(op->ptr, "actuator",act->name); + RNA_string_set(op->ptr, "object", ob->id.name+2); + return 1; + } + + return 0; +} + +static bActuator *edit_actuator_property_get(bContext *C, wmOperator *op, Object **ob) +{ + char actuator_name[32]; + bActuator *act; + + RNA_string_get(op->ptr, "actuator", actuator_name); + + *ob= edit_object_property_get(C, op); + if (!*ob) return NULL; + + act = BLI_findstring(&((*ob)->actuators), actuator_name, offsetof(bActuator, name)); + return act; +} + +static int logicbricks_move_property_get(wmOperator *op) +{ + int type = RNA_enum_get(op->ptr, "direction"); + + if (type == 1) + return TRUE; + else + return FALSE; +} + +/* ************* Add/Remove Sensor Operator ************* */ + +static int sensor_remove_exec(bContext *C, wmOperator *op) +{ + Object *ob=NULL; + bSensor *sens = edit_sensor_property_get(C, op, &ob); + + if (!sens) + return OPERATOR_CANCELLED; + + BLI_remlink(&(ob->sensors), sens); + free_sensor(sens); + + WM_event_add_notifier(C, NC_LOGIC, NULL); + + return OPERATOR_FINISHED; +} + + static int sensor_remove_invoke(bContext *C, wmOperator *op, wmEvent *event) +{ + if (edit_sensor_invoke_properties(C, op)) + return sensor_remove_exec(C, op); + else + return OPERATOR_CANCELLED; +} + +void LOGIC_OT_sensor_remove(wmOperatorType *ot) +{ + ot->name= "Remove Sensor"; + ot->description= "Remove a sensor from the active object"; + ot->idname= "LOGIC_OT_sensor_remove"; + + ot->invoke= sensor_remove_invoke; + ot->exec= sensor_remove_exec; + ot->poll= edit_sensor_poll; + + /* flags */ + ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; + edit_sensor_properties(ot); +} + +static int sensor_add_exec(bContext *C, wmOperator *op) +{ + Object *ob; + bSensor *sens; + PointerRNA sens_ptr; + PropertyRNA *prop; + const char *sens_name; + char name[32]; + int type= RNA_enum_get(op->ptr, "type"); + + ob= edit_object_property_get(C, op); + if (!ob) + return OPERATOR_CANCELLED; + + sens= new_sensor(type); + BLI_addtail(&(ob->sensors), sens); + + /* set the sensor name based on rna type enum */ + RNA_pointer_create((ID *)ob, &RNA_Sensor, sens, &sens_ptr); + prop = RNA_struct_find_property(&sens_ptr, "type"); + + RNA_string_get(op->ptr, "name", name); + if(BLI_strnlen(name, 32) < 1){ + RNA_property_enum_name(C, &sens_ptr, prop, RNA_property_enum_get(&sens_ptr, prop), &sens_name); + BLI_strncpy(sens->name, sens_name, sizeof(sens->name)); + } + else + BLI_strncpy(sens->name, name, sizeof(sens->name)); + + make_unique_prop_names(C, sens->name); + ob->scaflag |= OB_SHOWSENS; + + WM_event_add_notifier(C, NC_LOGIC, NULL); + + return OPERATOR_FINISHED; +} + +void LOGIC_OT_sensor_add(wmOperatorType *ot) +{ + PropertyRNA *prop; + + /* identifiers */ + ot->name= "Add Sensor"; + ot->description = "Add a sensor to the active object"; + ot->idname= "LOGIC_OT_sensor_add"; + + /* api callbacks */ + ot->invoke= WM_menu_invoke; + ot->exec= sensor_add_exec; + ot->poll= ED_operator_object_active_editable; + + /* flags */ + ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; + + /* properties */ + prop= RNA_def_enum(ot->srna, "type", DummyRNA_NULL_items, SENS_ALWAYS, "Type", "Type of sensor to add"); + RNA_def_enum_funcs(prop, rna_Sensor_type_itemf); + RNA_def_string(ot->srna, "name", "", 32, "Name", "Name of the Sensor to add"); + RNA_def_string(ot->srna, "object", "", 32, "Object", "Name of the Object to add the Sensor to"); +} + +/* ************* Add/Remove Controller Operator ************* */ + +static int controller_remove_exec(bContext *C, wmOperator *op) +{ + Object *ob = NULL; + bController *cont = edit_controller_property_get(C, op, &ob); + + if (!cont) + return OPERATOR_CANCELLED; + + BLI_remlink(&(ob->controllers), cont); + unlink_controller(cont); + free_controller(cont); + + WM_event_add_notifier(C, NC_LOGIC, NULL); + + return OPERATOR_FINISHED; +} + + static int controller_remove_invoke(bContext *C, wmOperator *op, wmEvent *event) +{ + if (edit_controller_invoke_properties(C, op)) + return controller_remove_exec(C, op); + else + return OPERATOR_CANCELLED; +} + +void LOGIC_OT_controller_remove(wmOperatorType *ot) +{ + ot->name= "Remove Controller"; + ot->description= "Remove a controller from the active object"; + ot->idname= "LOGIC_OT_controller_remove"; + + ot->invoke= controller_remove_invoke; + ot->exec= controller_remove_exec; + ot->poll= edit_controller_poll; + + /* flags */ + ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; + edit_controller_properties(ot); +} + +static int controller_add_exec(bContext *C, wmOperator *op) +{ + Object *ob; + bController *cont; + PointerRNA cont_ptr; + PropertyRNA *prop; + const char *cont_name; + int bit; + char name[32]; + int type= RNA_enum_get(op->ptr, "type"); + + ob= edit_object_property_get(C, op); + if(!ob) + return OPERATOR_CANCELLED; + + cont= new_controller(type); + BLI_addtail(&(ob->controllers), cont); + + /* set the controller name based on rna type enum */ + RNA_pointer_create((ID *)ob, &RNA_Controller, cont, &cont_ptr); + prop = RNA_struct_find_property(&cont_ptr, "type"); + + RNA_string_get(op->ptr, "name", name); + if(BLI_strnlen(name, 32) < 1){ + RNA_property_enum_name(C, &cont_ptr, prop, RNA_property_enum_get(&cont_ptr, prop), &cont_name); + BLI_strncpy(cont->name, cont_name, sizeof(cont->name)); + } + else + BLI_strncpy(cont->name, name, sizeof(cont->name)); + + make_unique_prop_names(C, cont->name); + /* set the controller state mask from the current object state. + A controller is always in a single state, so select the lowest bit set + from the object state */ + for (bit=0; bit<OB_MAX_STATES; bit++) { + if (ob->state & (1<<bit)) + break; + } + cont->state_mask = (1<<bit); + if (cont->state_mask == 0) { + /* shouldn't happen, object state is never 0 */ + cont->state_mask = 1; + } + + ob->scaflag |= OB_SHOWCONT; + + WM_event_add_notifier(C, NC_LOGIC, NULL); + + return OPERATOR_FINISHED; +} + +void LOGIC_OT_controller_add(wmOperatorType *ot) +{ + /* identifiers */ + ot->name= "Add Controller"; + ot->description = "Add a controller to the active object"; + ot->idname= "LOGIC_OT_controller_add"; + + /* api callbacks */ + ot->invoke= WM_menu_invoke; + ot->exec= controller_add_exec; + ot->poll= ED_operator_object_active_editable; + + /* flags */ + ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; + + /* properties */ + RNA_def_enum(ot->srna, "type", controller_type_items, CONT_LOGIC_AND, "Type", "Type of controller to add"); + RNA_def_string(ot->srna, "name", "", 32, "Name", "Name of the Controller to add"); + RNA_def_string(ot->srna, "object", "", 32, "Object", "Name of the Object to add the Controller to"); +} + +/* ************* Add/Remove Actuator Operator ************* */ + +static int actuator_remove_exec(bContext *C, wmOperator *op) +{ + Object *ob=NULL; + bActuator *act = edit_actuator_property_get(C, op, &ob); + + if (!act) + return OPERATOR_CANCELLED; + + BLI_remlink(&(ob->actuators), act); + unlink_actuator(act); + free_actuator(act); + + WM_event_add_notifier(C, NC_LOGIC, NULL); + + return OPERATOR_FINISHED; +} + +static int actuator_remove_invoke(bContext *C, wmOperator *op, wmEvent *event) +{ + if (edit_actuator_invoke_properties(C, op)) + return actuator_remove_exec(C, op); + else + return OPERATOR_CANCELLED; +} + +void LOGIC_OT_actuator_remove(wmOperatorType *ot) +{ + ot->name= "Remove Actuator"; + ot->description= "Remove a actuator from the active object"; + ot->idname= "LOGIC_OT_actuator_remove"; + + ot->invoke= actuator_remove_invoke; + ot->exec= actuator_remove_exec; + ot->poll= edit_actuator_poll; + + /* flags */ + ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; + edit_actuator_properties(ot); +} + +static int actuator_add_exec(bContext *C, wmOperator *op) +{ + Object *ob; + bActuator *act; + PointerRNA act_ptr; + PropertyRNA *prop; + const char *act_name; + char name[32]; + int type= RNA_enum_get(op->ptr, "type"); + + ob= edit_object_property_get(C, op); + if(!ob) + return OPERATOR_CANCELLED; + + act= new_actuator(type); + BLI_addtail(&(ob->actuators), act); + + /* set the actuator name based on rna type enum */ + RNA_pointer_create((ID *)ob, &RNA_Actuator, act, &act_ptr); + prop = RNA_struct_find_property(&act_ptr, "type"); + + RNA_string_get(op->ptr, "name", name); + if (BLI_strnlen(name, 32) < 1){ + RNA_property_enum_name(C, &act_ptr, prop, RNA_property_enum_get(&act_ptr, prop), &act_name); + BLI_strncpy(act->name, act_name, sizeof(act->name)); + } + else + BLI_strncpy(act->name, name, sizeof(act->name)); + + make_unique_prop_names(C, act->name); + ob->scaflag |= OB_SHOWACT; + + WM_event_add_notifier(C, NC_LOGIC, NULL); + + return OPERATOR_FINISHED; +} + +void LOGIC_OT_actuator_add(wmOperatorType *ot) +{ + PropertyRNA *prop; + + /* identifiers */ + ot->name= "Add Actuator"; + ot->description = "Add a actuator to the active object"; + ot->idname= "LOGIC_OT_actuator_add"; + + /* api callbacks */ + ot->invoke= WM_menu_invoke; + ot->exec= actuator_add_exec; + ot->poll= ED_operator_object_active_editable; + + /* flags */ + ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; + + /* properties */ + prop= RNA_def_enum(ot->srna, "type", DummyRNA_NULL_items, CONT_LOGIC_AND, "Type", "Type of actuator to add"); + RNA_def_enum_funcs(prop, rna_Actuator_type_itemf); + RNA_def_string(ot->srna, "name", "", 32, "Name", "Name of the Actuator to add"); + RNA_def_string(ot->srna, "object", "", 32, "Object", "Name of the Object to add the Actuator to"); +} + +/* ************* Move Logic Bricks Operator ************* */ +static EnumPropertyItem logicbricks_move_direction[] ={ + {1, "UP", 0, "Move Up", ""}, + {2, "DOWN", 0, "Move Down", ""}, + {0, NULL, 0, NULL, NULL}}; + + +static int sensor_move_exec(bContext *C, wmOperator *op) +{ + Object *ob=NULL; + bSensor *sens= edit_sensor_property_get(C, op, &ob); + int move_up= logicbricks_move_property_get(op); + + if (!sens) + return OPERATOR_CANCELLED; + + sca_move_sensor(sens, ob, move_up); + + WM_event_add_notifier(C, NC_LOGIC, NULL); + + return OPERATOR_FINISHED; +} + +static int sensor_move_invoke(bContext *C, wmOperator *op, wmEvent *event) +{ + if (edit_sensor_invoke_properties(C, op)) { + return sensor_move_exec(C, op); + } + else + return OPERATOR_CANCELLED; +} + +void LOGIC_OT_sensor_move(wmOperatorType *ot) +{ + /* identifiers */ + ot->name= "Move Sensor"; + ot->description = "Move Densor"; + ot->idname= "LOGIC_OT_sensor_move"; + + /* api callbacks */ + ot->invoke= sensor_move_invoke; + ot->exec= sensor_move_exec; + ot->poll= edit_sensor_poll; + + /* flags */ + ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; + + /* properties */ + edit_sensor_properties(ot); + RNA_def_enum(ot->srna, "direction", logicbricks_move_direction, 1, "Direction", "Move Up or Down"); +} + +static int controller_move_exec(bContext *C, wmOperator *op) +{ + Object *ob=NULL; + bController *cont= edit_controller_property_get(C, op, &ob); + int move_up= logicbricks_move_property_get(op); + + if (!cont) + return OPERATOR_CANCELLED; + + sca_move_controller(cont, ob, move_up); + + WM_event_add_notifier(C, NC_LOGIC, NULL); + + return OPERATOR_FINISHED; +} + +static int controller_move_invoke(bContext *C, wmOperator *op, wmEvent *event) +{ + if (edit_controller_invoke_properties(C, op)) { + return controller_move_exec(C, op); + } + else + return OPERATOR_CANCELLED; +} + +void LOGIC_OT_controller_move(wmOperatorType *ot) +{ + /* identifiers */ + ot->name= "Move Controller"; + ot->description = "Move Controller"; + ot->idname= "LOGIC_OT_controller_move"; + + /* api callbacks */ + ot->invoke= controller_move_invoke; + ot->exec= controller_move_exec; + ot->poll= edit_controller_poll; + + /* flags */ + ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; + + /* properties */ + edit_controller_properties(ot); + RNA_def_enum(ot->srna, "direction", logicbricks_move_direction, 1, "Direction", "Move Up or Down"); +} + +static int actuator_move_exec(bContext *C, wmOperator *op) +{ + Object *ob=NULL; + bActuator *act = edit_actuator_property_get(C, op, &ob); + int move_up= logicbricks_move_property_get(op); + + if (!act) + return OPERATOR_CANCELLED; + + sca_move_actuator(act, ob, move_up); + + WM_event_add_notifier(C, NC_LOGIC, NULL); + + return OPERATOR_FINISHED; +} + +static int actuator_move_invoke(bContext *C, wmOperator *op, wmEvent *event) +{ + if (edit_actuator_invoke_properties(C, op)) { + return actuator_move_exec(C, op); + } + else + return OPERATOR_CANCELLED; +} + +void LOGIC_OT_actuator_move(wmOperatorType *ot) +{ + /* identifiers */ + ot->name= "Move Actuator"; + ot->description = "Move Actuator"; + ot->idname= "LOGIC_OT_actuator_move"; + + /* api callbacks */ + ot->invoke= actuator_move_invoke; + ot->exec= actuator_move_exec; + ot->poll= edit_actuator_poll; + + /* flags */ + ot->flag= OPTYPE_REGISTER|OPTYPE_UNDO; + + /* properties */ + edit_actuator_properties(ot); + RNA_def_enum(ot->srna, "direction", logicbricks_move_direction, 1, "Direction", "Move Up or Down"); +} + + +void ED_operatortypes_logic(void) +{ + WM_operatortype_append(LOGIC_OT_sensor_remove); + WM_operatortype_append(LOGIC_OT_sensor_add); + WM_operatortype_append(LOGIC_OT_sensor_move); + WM_operatortype_append(LOGIC_OT_controller_remove); + WM_operatortype_append(LOGIC_OT_controller_add); + WM_operatortype_append(LOGIC_OT_controller_move); + WM_operatortype_append(LOGIC_OT_actuator_remove); + WM_operatortype_append(LOGIC_OT_actuator_add); + WM_operatortype_append(LOGIC_OT_actuator_move); +} diff --git a/source/blender/editors/space_logic/logic_window.c b/source/blender/editors/space_logic/logic_window.c index 39d3feafc19..8a703c510c4 100644 --- a/source/blender/editors/space_logic/logic_window.c +++ b/source/blender/editors/space_logic/logic_window.c @@ -40,6 +40,7 @@ #include "DNA_sensor_types.h" #include "DNA_constraint_types.h" #include "DNA_windowmanager_types.h" +#include "DNA_object_types.h" #include "MEM_guardedalloc.h" @@ -49,20 +50,18 @@ #include "BKE_global.h" #include "BKE_library.h" #include "BKE_main.h" -#include "BKE_property.h" -#include "BKE_screen.h" #include "BKE_sca.h" -#include "BKE_utildefines.h" #include "ED_util.h" #include "WM_types.h" #include "BIF_gl.h" -#include "BIF_glutil.h" #include "UI_interface.h" +#include "RNA_access.h" + /* XXX BAD BAD */ #include "../interface/interface_intern.h" @@ -192,8 +191,9 @@ static void make_unique_prop_names_cb(bContext *C, void *strv, void *redraw_view } -static void sca_move_sensor(bContext *C, void *datav, void *move_up) +static void old_sca_move_sensor(bContext *C, void *datav, void *move_up) { + /* deprecated, no longer using it (moved to sca.c) */ Scene *scene= CTX_data_scene(C); bSensor *sens_to_delete= datav; int val; @@ -244,8 +244,9 @@ static void sca_move_sensor(bContext *C, void *datav, void *move_up) } } -static void sca_move_controller(bContext *C, void *datav, void *move_up) +static void old_sca_move_controller(bContext *C, void *datav, void *move_up) { + /* deprecated, no longer using it (moved to sca.c) */ Scene *scene= CTX_data_scene(C); bController *controller_to_del= datav; int val; @@ -299,8 +300,9 @@ static void sca_move_controller(bContext *C, void *datav, void *move_up) } } -static void sca_move_actuator(bContext *C, void *datav, void *move_up) +static void old_sca_move_actuator(bContext *C, void *datav, void *move_up) { + /* deprecated, no longer using it (moved to sca.c) */ Scene *scene= CTX_data_scene(C); bActuator *actuator_to_move= datav; int val; @@ -354,6 +356,7 @@ static void sca_move_actuator(bContext *C, void *datav, void *move_up) void do_logic_buts(bContext *C, void *arg, int event) { + Main *bmain= CTX_data_main(C); bSensor *sens; bController *cont; bActuator *act; @@ -377,7 +380,7 @@ void do_logic_buts(bContext *C, void *arg, int event) break; case B_ADD_SENS: - for(ob=G.main->object.first; ob; ob=ob->id.next) { + for(ob=bmain->object.first; ob; ob=ob->id.next) { if(ob->scaflag & OB_ADDSENS) { ob->scaflag &= ~OB_ADDSENS; sens= new_sensor(SENS_ALWAYS); @@ -391,7 +394,7 @@ void do_logic_buts(bContext *C, void *arg, int event) break; case B_CHANGE_SENS: - for(ob=G.main->object.first; ob; ob=ob->id.next) { + for(ob=bmain->object.first; ob; ob=ob->id.next) { sens= ob->sensors.first; while(sens) { if(sens->type != sens->otype) { @@ -405,7 +408,7 @@ void do_logic_buts(bContext *C, void *arg, int event) break; case B_DEL_SENS: - for(ob=G.main->object.first; ob; ob=ob->id.next) { + for(ob=bmain->object.first; ob; ob=ob->id.next) { sens= ob->sensors.first; while(sens) { if(sens->flag & SENS_DEL) { @@ -420,7 +423,7 @@ void do_logic_buts(bContext *C, void *arg, int event) break; case B_ADD_CONT: - for(ob=G.main->object.first; ob; ob=ob->id.next) { + for(ob=bmain->object.first; ob; ob=ob->id.next) { if(ob->scaflag & OB_ADDCONT) { ob->scaflag &= ~OB_ADDCONT; cont= new_controller(CONT_LOGIC_AND); @@ -445,16 +448,16 @@ void do_logic_buts(bContext *C, void *arg, int event) break; case B_SET_STATE_BIT: - for(ob=G.main->object.first; ob; ob=ob->id.next) { - if(ob->scaflag & OB_SETSTBIT) { - ob->scaflag &= ~OB_SETSTBIT; + for(ob=bmain->object.first; ob; ob=ob->id.next) { + if(ob->scaflag & OB_ALLSTATE) { + ob->scaflag &= ~OB_ALLSTATE; ob->state = 0x3FFFFFFF; } } break; case B_INIT_STATE_BIT: - for(ob=G.main->object.first; ob; ob=ob->id.next) { + for(ob=bmain->object.first; ob; ob=ob->id.next) { if(ob->scaflag & OB_INITSTBIT) { ob->scaflag &= ~OB_INITSTBIT; ob->state = ob->init_state; @@ -465,7 +468,7 @@ void do_logic_buts(bContext *C, void *arg, int event) break; case B_CHANGE_CONT: - for(ob=G.main->object.first; ob; ob=ob->id.next) { + for(ob=bmain->object.first; ob; ob=ob->id.next) { cont= ob->controllers.first; while(cont) { if(cont->type != cont->otype) { @@ -480,7 +483,7 @@ void do_logic_buts(bContext *C, void *arg, int event) case B_DEL_CONT: - for(ob=G.main->object.first; ob; ob=ob->id.next) { + for(ob=bmain->object.first; ob; ob=ob->id.next) { cont= ob->controllers.first; while(cont) { if(cont->flag & CONT_DEL) { @@ -496,7 +499,7 @@ void do_logic_buts(bContext *C, void *arg, int event) break; case B_ADD_ACT: - for(ob=G.main->object.first; ob; ob=ob->id.next) { + for(ob=bmain->object.first; ob; ob=ob->id.next) { if(ob->scaflag & OB_ADDACT) { ob->scaflag &= ~OB_ADDACT; act= new_actuator(ACT_OBJECT); @@ -509,7 +512,7 @@ void do_logic_buts(bContext *C, void *arg, int event) break; case B_CHANGE_ACT: - for(ob=G.main->object.first; ob; ob=ob->id.next) { + for(ob=bmain->object.first; ob; ob=ob->id.next) { act= ob->actuators.first; while(act) { if(act->type != act->otype) { @@ -523,7 +526,7 @@ void do_logic_buts(bContext *C, void *arg, int event) break; case B_DEL_ACT: - for(ob=G.main->object.first; ob; ob=ob->id.next) { + for(ob=bmain->object.first; ob; ob=ob->id.next) { act= ob->actuators.first; while(act) { if(act->flag & ACT_DEL) { @@ -541,7 +544,7 @@ void do_logic_buts(bContext *C, void *arg, int event) case B_SOUNDACT_BROWSE: /* since we don't know which... */ didit= 0; - for(ob=G.main->object.first; ob; ob=ob->id.next) { + for(ob=bmain->object.first; ob; ob=ob->id.next) { act= ob->actuators.first; while(act) { @@ -550,11 +553,11 @@ void do_logic_buts(bContext *C, void *arg, int event) bSoundActuator *sa= act->data; if(sa->sndnr) { - bSound *sound= G.main->sound.first; + ID *sound= bmain->sound.first; int nr= 1; if(sa->sndnr == -2) { -// XXX activate_databrowse((ID *)G.main->sound.first, ID_SO, 0, B_SOUNDACT_BROWSE, +// XXX activate_databrowse((ID *)bmain->sound.first, ID_SO, 0, B_SOUNDACT_BROWSE, // &sa->sndnr, do_logic_buts); break; } @@ -564,16 +567,16 @@ void do_logic_buts(bContext *C, void *arg, int event) if(nr==sa->sndnr) break; nr++; - sound= sound->id.next; + sound= sound->next; } if(sa->sound) - sa->sound->id.us--; + ((ID *)sa->sound)->us--; - sa->sound= sound; + sa->sound= (struct bSound *)sound; if(sound) - sound->id.us++; + sound->us++; sa->sndnr= 0; didit= 1; @@ -639,17 +642,17 @@ static char *controller_name(int type) { switch (type) { case CONT_LOGIC_AND: - return "AND"; + return "And"; case CONT_LOGIC_OR: - return "OR"; + return "Or"; case CONT_LOGIC_NAND: - return "NAND"; + return "Nand"; case CONT_LOGIC_NOR: - return "NOR"; + return "Nor"; case CONT_LOGIC_XOR: - return "XOR"; + return "Xor"; case CONT_LOGIC_XNOR: - return "XNOR"; + return "Xnor"; case CONT_EXPRESSION: return "Expression"; case CONT_PYTHON: @@ -673,7 +676,7 @@ static char *actuator_name(int type) case ACT_OBJECT: return "Motion"; case ACT_IPO: - return "Ipo"; + return "F-Curve"; case ACT_LAMP: return "Lamp"; case ACT_CAMERA: @@ -701,7 +704,7 @@ static char *actuator_name(int type) case ACT_VISIBILITY: return "Visibility"; case ACT_2DFILTER: - return "2D Filter"; + return "Filter 2D"; case ACT_PARENT: return "Parent"; case ACT_STATE: @@ -763,6 +766,7 @@ static void set_sca_ob(Object *ob) static ID **get_selected_and_linked_obs(bContext *C, short *count, short scavisflag) { Base *base; + Main *bmain= CTX_data_main(C); Scene *scene= CTX_data_scene(C); Object *ob, *obt, *obact= CTX_data_active_object(C); ID **idar; @@ -779,7 +783,7 @@ static ID **get_selected_and_linked_obs(bContext *C, short *count, short scavisf if(scene==NULL) return NULL; - ob= G.main->object.first; + ob= bmain->object.first; while(ob) { ob->scavisflag= 0; set_sca_ob(ob); @@ -813,7 +817,7 @@ static ID **get_selected_and_linked_obs(bContext *C, short *count, short scavisf while(doit) { doit= 0; - ob= G.main->object.first; + ob= bmain->object.first; while(ob) { /* 1st case: select sensor when controller selected */ @@ -894,7 +898,7 @@ static ID **get_selected_and_linked_obs(bContext *C, short *count, short scavisf } /* now we count */ - ob= G.main->object.first; + ob= bmain->object.first; while(ob) { if( ob->scavisflag ) (*count)++; ob= ob->id.next; @@ -905,10 +909,17 @@ static ID **get_selected_and_linked_obs(bContext *C, short *count, short scavisf idar= MEM_callocN( (*count)*sizeof(void *), "idar"); - ob= G.main->object.first; + ob= bmain->object.first; nr= 0; + + /* make the active object always the first one of the list */ + if (obact) { + idar[0]= (ID *)obact; + nr++; + } + while(ob) { - if( ob->scavisflag ) { + if( (ob->scavisflag) && (ob != obact)) { idar[nr]= (ID *)ob; nr++; } @@ -1598,7 +1609,7 @@ static short draw_sensorbuttons(Object *ob, bSensor *sens, uiBlock *block, short str = "Type %t|Up Axis %x1 |Down Axis %x3|Left Axis %x2|Right Axis %x0"; uiDefButI(block, MENU, B_REDR, str, xco+10 + 0.6 * (width-20), yco-68, 0.4 * (width-20), 19, &joy->axisf, 2.0, 31, 0, 0, - "The direction of the axis, use 'All Events' to recieve events on any direction"); + "The direction of the axis, use 'All Events' to receive events on any direction"); } } else if (joy->type == SENS_JOY_HAT) @@ -1611,7 +1622,7 @@ static short draw_sensorbuttons(Object *ob, bSensor *sens, uiBlock *block, short str = "Direction%t|Up%x1|Down%x4|Left%x8|Right%x2|%l|Up/Right%x3|Down/Left%x12|Up/Left%x9|Down/Right%x6"; uiDefButI(block, MENU, 0, str, xco+10 + 0.6 * (width-20), yco-68, 0.4 * (width-20), 19, &joy->hatf, 2.0, 31, 0, 0, - "The direction of the hat, use 'All Events' to recieve events on any direction"); + "The direction of the hat, use 'All Events' to receive events on any direction"); } } else { /* (joy->type == SENS_JOY_AXIS_SINGLE)*/ @@ -1805,7 +1816,7 @@ static void check_armature_actuator(bContext *C, void *arg1_but, void *arg2_act) } -static short draw_actuatorbuttons(Object *ob, bActuator *act, uiBlock *block, short xco, short yco, short width) +static short draw_actuatorbuttons(Main *bmain, Object *ob, bActuator *act, uiBlock *block, short xco, short yco, short width) { bSoundActuator *sa = NULL; bObjectActuator *oa = NULL; @@ -1914,7 +1925,7 @@ static short draw_actuatorbuttons(Object *ob, bActuator *act, uiBlock *block, sh 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"); 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"); - uiDefButBitS(block, TOG, ACT_ADD_LIN_VEL, 0, "add",xco+45+3*wval+15, yco-129, 35, 19, &oa->flag, 0.0, 0.0, 0, 0, "Toggles between ADD and SET linV"); + 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"); } } else if (oa->type == ACT_OBJECT_SERVO) { @@ -2130,8 +2141,8 @@ static short draw_actuatorbuttons(Object *ob, bActuator *act, uiBlock *block, sh glRects(xco, yco-ysize, xco+width, yco); uiEmboss((float)xco, (float)yco-ysize, (float)xco+width, (float)yco, 1); - if(G.main->sound.first) { - IDnames_to_pupstring(&str, "Sound files", NULL, &(G.main->sound), (ID *)sa->sound, &(sa->sndnr)); + if(bmain->sound.first) { + IDnames_to_pupstring(&str, "Sound files", NULL, &(bmain->sound), (ID *)sa->sound, &(sa->sndnr)); /* reset this value, it is for handling the event */ sa->sndnr = 0; uiDefButS(block, MENU, B_SOUNDACT_BROWSE, str, xco+10,yco-22,20,19, &(sa->sndnr), 0, 0, 0, 0, ""); @@ -2139,7 +2150,7 @@ static short draw_actuatorbuttons(Object *ob, bActuator *act, uiBlock *block, sh if(sa->sound) { 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"; - uiDefBut(block, TEX, B_IDNAME, "SO:",xco+30,yco-22,wval-20,19, sa->sound->id.name+2, 0.0, 21.0, 0, 0, ""); + uiDefBut(block, TEX, B_IDNAME, "SO:",xco+30,yco-22,wval-20,19, ((ID *)sa->sound)->name+2, 0.0, 21.0, 0, 0, ""); uiDefButS(block, MENU, 1, dummy_str,xco+10,yco-44,width-20, 19, &sa->type, 0.0, 0.0, 0, 0, ""); 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"); 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"); @@ -2518,7 +2529,7 @@ static short draw_actuatorbuttons(Object *ob, bActuator *act, uiBlock *block, sh } //str = "Scene %t|Load game%x0|Start loaded game%x1|Restart this game%x2|Quit this game %x3"; - str = "Scene %t|Start new game%x0|Restart this game%x2|Quit this game %x3|Save GameLogic.globalDict %x4|Load GameLogic.globalDict %x5"; + 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"; uiDefButS(block, MENU, B_REDR, str, xco+40, yco-24, (width-80), 19, &gma->type, 0.0, 0.0, 0, 0, ""); yco -= ysize; @@ -3162,15 +3173,1542 @@ static int is_sensor_linked(uiBlock *block, bSensor *sens) return 0; } -/* never used, see CVS 1.134 for the code */ -/* static FreeCamera *new_freecamera(void) */ +/* Sensors code */ + +static void draw_sensor_header(uiLayout *layout, PointerRNA *ptr, PointerRNA *logic_ptr) +{ + uiLayout *box, *row, *subrow; + bSensor *sens= (bSensor *)ptr->data; + + box= uiLayoutBox(layout); + row= uiLayoutRow(box, 0); + + uiItemR(row, ptr, "show_expanded", UI_ITEM_R_NO_BG, "", 0); + if(RNA_boolean_get(ptr, "show_expanded")) { + uiItemR(row, ptr, "type", 0, "", 0); + uiItemR(row, ptr, "name", 0, "", 0); + } else { + uiItemL(row, sensor_name(sens->type), 0); + uiItemL(row, sens->name, 0); + } + + subrow= uiLayoutRow(row, 0); + uiLayoutSetActive(subrow, ((RNA_boolean_get(logic_ptr, "show_sensors_active_states") + && RNA_boolean_get(ptr, "show_expanded")) || RNA_boolean_get(ptr, "pin"))); + uiItemR(subrow, ptr, "pin", UI_ITEM_R_NO_BG, "", 0); + + if(RNA_boolean_get(ptr, "show_expanded")==0) { + subrow= uiLayoutRow(row, 1); + uiItemEnumO(subrow, "LOGIC_OT_sensor_move", "", ICON_TRIA_UP, "direction", 1); // up + uiItemEnumO(subrow, "LOGIC_OT_sensor_move", "", ICON_TRIA_DOWN, "direction", 2); // down + } + + uiItemO(row, "", ICON_X, "LOGIC_OT_sensor_remove"); +} + +static void draw_sensor_internal_header(uiLayout *layout, PointerRNA *ptr) +{ + uiLayout *box, *split, *row; + + box= uiLayoutBox(layout); + split = uiLayoutSplit(box, 0.45, 0); + + row= uiLayoutRow(split, 1); + uiItemR(row, ptr, "use_pulse_true_level", 0, "", ICON_DOTSUP); + uiItemR(row, ptr, "use_pulse_false_level", 0, "", ICON_DOTSDOWN); + uiItemR(row, ptr, "frequency", 0, "Freq", 0); + + row= uiLayoutRow(split, 1); + uiItemR(row, ptr, "use_level", UI_ITEM_R_TOGGLE, NULL, 0); + uiItemR(row, ptr, "use_tap", UI_ITEM_R_TOGGLE, NULL, 0); + + row= uiLayoutRow(split, 1); + uiItemR(row, ptr, "invert", UI_ITEM_R_TOGGLE, "Invert", 0); +} +/* sensors in alphabetical order */ + +static void draw_sensor_actuator(uiLayout *layout, PointerRNA *ptr) +{ + Object *ob = (Object *)ptr->id.data; + PointerRNA settings_ptr; + + RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); + uiItemPointerR(layout, ptr, "actuator", &settings_ptr, "actuators", NULL, ICON_LOGIC); +} + +static void draw_sensor_armature(uiLayout *layout, PointerRNA *ptr) +{ + bSensor *sens = (bSensor*)ptr->data; + bArmatureSensor *as = (bArmatureSensor *) sens->data; + Object *ob = (Object *)ptr->id.data; + PointerRNA pose_ptr, pchan_ptr; + PropertyRNA *bones_prop= NULL; + uiLayout *row; + + if(ob->type != OB_ARMATURE){ + uiItemL(layout, "Sensor only available for armatures", 0); + return; + } + + if (ob->pose) { + RNA_pointer_create((ID *)ob, &RNA_Pose, ob->pose, &pose_ptr); + bones_prop = RNA_struct_find_property(&pose_ptr, "bones"); + } + + if (&pose_ptr.data) { + uiItemPointerR(layout, ptr, "bone", &pose_ptr, "bones", NULL, ICON_BONE_DATA); + + if (RNA_property_collection_lookup_string(&pose_ptr, bones_prop, as->posechannel, &pchan_ptr)) + uiItemPointerR(layout, ptr, "constraint", &pchan_ptr, "constraints", NULL, ICON_CONSTRAINT_BONE); + } + row = uiLayoutRow(layout, 1); + uiItemR(row, ptr, "test_type", 0, NULL, 0); + uiItemR(row, ptr, "value", 0, NULL, 0); +} + +static void draw_sensor_collision(uiLayout *layout, PointerRNA *ptr, bContext *C) +{ + uiLayout *row, *split; + PointerRNA main_ptr; + + RNA_main_pointer_create(CTX_data_main(C), &main_ptr); + + split = uiLayoutSplit(layout, 0.3, 0); + row = uiLayoutRow(split, 1); + uiItemR(row, ptr, "use_pulse", UI_ITEM_R_TOGGLE, NULL, 0); + uiItemR(row, ptr, "use_material", UI_ITEM_R_TOGGLE, NULL, 0); + + switch (RNA_enum_get(ptr, "use_material")) { + case SENS_COLLISION_PROPERTY: + uiItemR(split, ptr, "property", 0, NULL, 0); + break; + case SENS_COLLISION_MATERIAL: + uiItemPointerR(split, ptr, "material", &main_ptr, "materials", NULL, ICON_MATERIAL_DATA); + break; + } +} + +static void draw_sensor_delay(uiLayout *layout, PointerRNA *ptr) +{ + uiLayout *row; + + row= uiLayoutRow(layout, 0); + + uiItemR(row, ptr, "delay", 0, NULL, 0); + uiItemR(row, ptr, "duration", 0, NULL, 0); + uiItemR(row, ptr, "use_repeat", 0, NULL, 0); +} + +static void draw_sensor_joystick(uiLayout *layout, PointerRNA *ptr) +{ + uiLayout *col, *row; + + uiItemR(layout, ptr, "joystick_index", 0, NULL, 0); + uiItemR(layout, ptr, "event_type", 0, NULL, 0); + + switch (RNA_enum_get(ptr, "event_type")) { + case SENS_JOY_BUTTON: + uiItemR(layout, ptr, "use_all_events", 0, NULL, 0); + + col = uiLayoutColumn(layout, 0); + uiLayoutSetActive(col, RNA_boolean_get(ptr, "use_all_events")==0); + uiItemR(col, ptr, "button_number", 0, NULL, 0); + break; + case SENS_JOY_AXIS: + row = uiLayoutRow(layout, 0); + uiItemR(row, ptr, "axis_number", 0, NULL, 0); + uiItemR(row, ptr, "axis_threshold", 0, NULL, 0); + + uiItemR(layout, ptr, "use_all_events", 0, NULL, 0); + col = uiLayoutColumn(layout, 0); + uiLayoutSetActive(col, RNA_boolean_get(ptr, "use_all_events")==0); + uiItemR(col, ptr, "axis_direction", 0, NULL, 0); + break; + case SENS_JOY_HAT: + uiItemR(layout, ptr, "hat_number", 0, NULL, 0); + uiItemR(layout, ptr, "use_all_events", 0, NULL, 0); + + col = uiLayoutColumn(layout, 0); + uiLayoutSetActive(col, RNA_boolean_get(ptr, "use_all_events")==0); + uiItemR(col, ptr, "hat_direction", 0, NULL, 0); + break; + case SENS_JOY_AXIS_SINGLE: + row = uiLayoutRow(layout, 0); + uiItemR(row, ptr, "single_axis_number", 0, NULL, 0); + uiItemR(row, ptr, "axis_threshold", 0, NULL, 0); + break; + } +} + +static void draw_sensor_keyboard(uiLayout *layout, PointerRNA *ptr) +{ + Object *ob = (Object *)ptr->id.data; + PointerRNA settings_ptr; + uiLayout *row, *col; + + row = uiLayoutRow(layout, 0); + uiItemL(row, "Key:", 0); + col = uiLayoutColumn(row, 0); + uiLayoutSetActive(col, RNA_boolean_get(ptr, "use_all_keys")==0); + uiItemR(col, ptr, "key", UI_ITEM_R_EVENT, "", 0); + col = uiLayoutColumn(row, 0); + uiItemR(col, ptr, "use_all_keys", UI_ITEM_R_TOGGLE, NULL, 0); + + col = uiLayoutColumn(layout, 0); + uiLayoutSetActive(col, RNA_boolean_get(ptr, "use_all_keys")==0); + row = uiLayoutRow(col, 0); + uiItemL(row, "First Modifier:", 0); + uiItemR(row, ptr, "modifier_key_1", UI_ITEM_R_EVENT, "", 0); + + row = uiLayoutRow(col, 0); + uiItemL(row, "Second Modifier:", 0); + uiItemR(row, ptr, "modifier_key_2", UI_ITEM_R_EVENT, "", 0); + + RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); + uiItemPointerR(layout, ptr, "target", &settings_ptr, "properties", NULL, 0); + uiItemPointerR(layout, ptr, "log", &settings_ptr, "properties", NULL, 0); +} + +static void draw_sensor_message(uiLayout *layout, PointerRNA *ptr) +{ + uiItemR(layout, ptr, "subject", 0, NULL, 0); +} + +static void draw_sensor_mouse(uiLayout *layout, PointerRNA *ptr) +{ + uiItemR(layout, ptr, "mouse_event", 0, NULL, 0); +} + +static void draw_sensor_near(uiLayout *layout, PointerRNA *ptr) +{ + uiLayout *row; + + uiItemR(layout, ptr, "property", 0, NULL, 0); + + row= uiLayoutRow(layout, 1); + uiItemR(row, ptr, "distance", 0, NULL, 0); + uiItemR(row, ptr, "reset_distance", 0, NULL, 0); +} + +static void draw_sensor_property(uiLayout *layout, PointerRNA *ptr) +{ + Object *ob = (Object *)ptr->id.data; + PointerRNA settings_ptr; + + uiLayout *row; + uiItemR(layout, ptr, "evaluation_type", 0, NULL, 0); + + RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); + uiItemPointerR(layout, ptr, "property", &settings_ptr, "properties", NULL, 0); + + switch (RNA_enum_get(ptr, "evaluation_type")) { + case SENS_PROP_INTERVAL: + row = uiLayoutRow(layout, 0); + uiItemR(row, ptr, "value_min", 0, NULL, 0); + uiItemR(row, ptr, "value_max", 0, NULL, 0); + break; + case SENS_PROP_EQUAL: + uiItemR(layout, ptr, "value", 0, NULL, 0); + break; + case SENS_PROP_NEQUAL: + uiItemR(layout, ptr, "value", 0, NULL, 0); + break; + case SENS_PROP_CHANGED: + break; + } +} + +static void draw_sensor_radar(uiLayout *layout, PointerRNA *ptr) +{ + uiLayout *row; + + uiItemR(layout, ptr, "property", 0, NULL, 0); + uiItemR(layout, ptr, "axis", 0, NULL, 0); + + row= uiLayoutRow(layout, 0); + uiItemR(row, ptr, "angle", 0, NULL, 0); + uiItemR(row, ptr, "distance", 0, NULL, 0); +} + +static void draw_sensor_random(uiLayout *layout, PointerRNA *ptr) +{ + uiItemR(layout, ptr, "seed", 0, NULL, 0); +} + +static void draw_sensor_ray(uiLayout *layout, PointerRNA *ptr, bContext *C) +{ + uiLayout *split, *row; + PointerRNA main_ptr; + + RNA_main_pointer_create(CTX_data_main(C), &main_ptr); + split= uiLayoutSplit(layout, 0.3, 0); + uiItemR(split, ptr, "ray_type", 0, "", 0); + switch (RNA_enum_get(ptr, "ray_type")) { + case SENS_RAY_PROPERTY: + uiItemR(split, ptr, "property", 0, "", 0); + break; + case SENS_RAY_MATERIAL: + uiItemPointerR(split, ptr, "material", &main_ptr, "materials", "", ICON_MATERIAL_DATA); + break; + } + + split= uiLayoutSplit(layout, 0.3, 0); + uiItemR(split, ptr, "axis", 0, "", 0); + row= uiLayoutRow(split, 0); + uiItemR(row, ptr, "range", 0, NULL, 0); + uiItemR(row, ptr, "use_x_ray", UI_ITEM_R_TOGGLE, NULL, 0); +} + +static void draw_sensor_touch(uiLayout *layout, PointerRNA *ptr) +{ + uiItemR(layout, ptr, "material", 0, NULL, 0); +} + +void draw_brick_sensor(uiLayout *layout, PointerRNA *ptr, bContext *C) +{ + uiLayout *box; + + if (!RNA_boolean_get(ptr, "show_expanded")) + return; + + draw_sensor_internal_header(layout, ptr); + + box = uiLayoutBox(layout); + + switch (RNA_enum_get(ptr, "type")) { + + case SENS_ACTUATOR: + draw_sensor_actuator(box, ptr); + break; + case SENS_ALWAYS: + break; + case SENS_ARMATURE: + draw_sensor_armature(box, ptr); + break; + case SENS_COLLISION: + draw_sensor_collision(box, ptr, C); + break; + case SENS_DELAY: + draw_sensor_delay(box, ptr); + break; + case SENS_JOYSTICK: + draw_sensor_joystick(box, ptr); + break; + case SENS_KEYBOARD: + draw_sensor_keyboard(box, ptr); + break; + case SENS_MESSAGE: + draw_sensor_message(box, ptr); + break; + case SENS_MOUSE: + draw_sensor_mouse(box, ptr); + break; + case SENS_NEAR: + draw_sensor_near(box, ptr); + break; + case SENS_PROPERTY: + draw_sensor_property(box, ptr); + break; + case SENS_RADAR: + draw_sensor_radar(box, ptr); + break; + case SENS_RANDOM: + draw_sensor_random(box, ptr); + break; + case SENS_RAY: + draw_sensor_ray(box, ptr, C); + break; + case SENS_TOUCH: + draw_sensor_touch(box, ptr); + break; + } +} + +/* Controller code */ +static void draw_controller_header(uiLayout *layout, PointerRNA *ptr, int xco, int width, int yco) +{ + uiLayout *box, *row, *subrow; + bController *cont= (bController *)ptr->data; + + char state[3]; + sprintf(state, "%d", RNA_int_get(ptr, "states")); + + box= uiLayoutBox(layout); + row= uiLayoutRow(box, 0); + + uiItemR(row, ptr, "show_expanded", UI_ITEM_R_NO_BG, "", 0); + if(RNA_boolean_get(ptr, "show_expanded")) { + uiItemR(row, ptr, "type", 0, "", 0); + uiItemR(row, ptr, "name", 0, "", 0); + /* XXX provisory for Blender 2.50Beta */ + 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)"); + } else { + uiItemL(row, controller_name(cont->type), 0); + uiItemL(row, cont->name, 0); + uiItemL(row, state, 0); + } + + uiItemR(row, ptr, "use_priority", 0, "", 0); + + if(RNA_boolean_get(ptr, "show_expanded")==0) { + subrow= uiLayoutRow(row, 1); + uiItemEnumO(subrow, "LOGIC_OT_controller_move", "", ICON_TRIA_UP, "direction", 1); // up + uiItemEnumO(subrow, "LOGIC_OT_controller_move", "", ICON_TRIA_DOWN, "direction", 2); // down + } + uiItemO(row, "", ICON_X, "LOGIC_OT_controller_remove"); +} + +static void draw_controller_expression(uiLayout *layout, PointerRNA *ptr) +{ + uiItemR(layout, ptr, "expression", 0, "", 0); +} + +static void draw_controller_python(uiLayout *layout, PointerRNA *ptr) +{ + uiLayout *split, *subsplit; + + split = uiLayoutSplit(layout, 0.3, 1); + uiItemR(split, ptr, "mode", 0, "", 0); + if (RNA_enum_get(ptr, "mode") == CONT_PY_SCRIPT) { + uiItemR(split, ptr, "text", 0, "", 0); + } + else { + subsplit = uiLayoutSplit(split, 0.8, 0); + uiItemR(subsplit, ptr, "module", 0, "", 0); + uiItemR(subsplit, ptr, "use_debug", UI_ITEM_R_TOGGLE, NULL, 0); + } +} + +static void draw_controller_state(uiLayout *layout, PointerRNA *ptr) +{ + +} + +void draw_brick_controller(uiLayout *layout, PointerRNA *ptr) +{ + uiLayout *box; + + if (!RNA_boolean_get(ptr, "show_expanded")) + return; + + box = uiLayoutBox(layout); + + draw_controller_state(box, ptr); + + switch (RNA_enum_get(ptr, "type")) { + case CONT_LOGIC_AND: + break; + case CONT_LOGIC_OR: + break; + case CONT_EXPRESSION: + draw_controller_expression(box, ptr); + break; + case CONT_PYTHON: + draw_controller_python(box, ptr); + break; + case CONT_LOGIC_NAND: + break; + case CONT_LOGIC_NOR: + break; + case CONT_LOGIC_XOR: + break; + case CONT_LOGIC_XNOR: + break; + } +} + +/* Actuator code */ +static void draw_actuator_header(uiLayout *layout, PointerRNA *ptr, PointerRNA *logic_ptr) +{ + uiLayout *box, *row, *subrow; + bActuator *act= (bActuator *)ptr->data; + + box= uiLayoutBox(layout); + row= uiLayoutRow(box, 0); + + uiItemR(row, ptr, "show_expanded", UI_ITEM_R_NO_BG, "", 0); + if(RNA_boolean_get(ptr, "show_expanded")) { + uiItemR(row, ptr, "type", 0, "", 0); + uiItemR(row, ptr, "name", 0, "", 0); + } else { + uiItemL(row, actuator_name(act->type), 0); + uiItemL(row, act->name, 0); + } + + subrow= uiLayoutRow(row, 0); + uiLayoutSetActive(subrow, ((RNA_boolean_get(logic_ptr, "show_actuators_active_states") + && RNA_boolean_get(ptr, "show_expanded")) || RNA_boolean_get(ptr, "pin"))); + uiItemR(subrow, ptr, "pin", UI_ITEM_R_NO_BG, "", 0); + + if(RNA_boolean_get(ptr, "show_expanded")==0) { + subrow= uiLayoutRow(row, 1); + uiItemEnumO(subrow, "LOGIC_OT_actuator_move", "", ICON_TRIA_UP, "direction", 1); // up + uiItemEnumO(subrow, "LOGIC_OT_actuator_move", "", ICON_TRIA_DOWN, "direction", 2); // down + } + uiItemO(row, "", ICON_X, "LOGIC_OT_actuator_remove"); +} + +static void draw_actuator_action(uiLayout *layout, PointerRNA *ptr) +{ + Object *ob = (Object *)ptr->id.data; + PointerRNA settings_ptr; + uiLayout *row; + + if(ob->type != OB_ARMATURE){ + uiItemL(layout, "Actuator only available for armatures", 0); + return; + } + RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); + + row= uiLayoutRow(layout, 0); + uiItemR(row, ptr, "play_mode", 0, "", 0); + uiItemR(row, ptr, "action", 0, NULL, 0); + uiItemR(row, ptr, "use_continue_last_frame", 0, NULL, 0); + + row= uiLayoutRow(layout, 0); + if((RNA_enum_get(ptr, "mode") == ACT_ACTION_FROM_PROP)) + uiItemPointerR(row, ptr, "property", &settings_ptr, "properties", NULL, 0); + + else { + uiItemR(row, ptr, "frame_start", 0, NULL, 0); + uiItemR(row, ptr, "frame_end", 0, NULL, 0); + } + + row= uiLayoutRow(layout, 0); + uiItemR(row, ptr, "frame_blend_in", 0, NULL, 0); + uiItemR(row, ptr, "priority", 0, NULL, 0); + + row= uiLayoutRow(layout, 0); + uiItemPointerR(layout, ptr, "frame_property", &settings_ptr, "properties", NULL, 0); + +#ifdef __NLA_ACTION_BY_MOTION_ACTUATOR + uiItemR(row, "stride_length", 0, NULL, 0); +#endif +} + +static void draw_actuator_armature(uiLayout *layout, PointerRNA *ptr) +{ + bActuator *act = (bActuator*)ptr->data; + bArmatureActuator *aa = (bArmatureActuator *) act->data; + Object *ob = (Object *)ptr->id.data; + PointerRNA pose_ptr, pchan_ptr; + PropertyRNA *bones_prop; + + if(ob->type != OB_ARMATURE){ + uiItemL(layout, "Actuator only available for armatures", 0); + return; + } + + if (ob->pose) { + RNA_pointer_create((ID *)ob, &RNA_Pose, ob->pose, &pose_ptr); + bones_prop = RNA_struct_find_property(&pose_ptr, "bones"); + } + + uiItemR(layout, ptr, "mode", 0, NULL, 0); + + switch (RNA_enum_get(ptr, "mode")) + { + case ACT_ARM_RUN: + break; + case ACT_ARM_ENABLE: + case ACT_ARM_DISABLE: + if (&pose_ptr.data) { + uiItemPointerR(layout, ptr, "bone", &pose_ptr, "bones", NULL, ICON_BONE_DATA); + + if (RNA_property_collection_lookup_string(&pose_ptr, bones_prop, aa->posechannel, &pchan_ptr)) + uiItemPointerR(layout, ptr, "constraint", &pchan_ptr, "constraints", NULL, ICON_CONSTRAINT_BONE); + } + break; + case ACT_ARM_SETTARGET: + if (&pose_ptr.data) { + uiItemPointerR(layout, ptr, "bone", &pose_ptr, "bones", NULL, ICON_BONE_DATA); + + if (RNA_property_collection_lookup_string(&pose_ptr, bones_prop, aa->posechannel, &pchan_ptr)) + uiItemPointerR(layout, ptr, "constraint", &pchan_ptr, "constraints", NULL, ICON_CONSTRAINT_BONE); + } + + uiItemR(layout, ptr, "target", 0, NULL, 0); + uiItemR(layout, ptr, "secondary_target", 0, NULL, 0); + break; + case ACT_ARM_SETWEIGHT: + if (&pose_ptr.data) { + uiItemPointerR(layout, ptr, "bone", &pose_ptr, "bones", NULL, ICON_BONE_DATA); + + if (RNA_property_collection_lookup_string(&pose_ptr, bones_prop, aa->posechannel, &pchan_ptr)) + uiItemPointerR(layout, ptr, "constraint", &pchan_ptr, "constraints", NULL, ICON_CONSTRAINT_BONE); + } + + uiItemR(layout, ptr, "weight", 0, NULL, 0); + break; + } +} + +static void draw_actuator_camera(uiLayout *layout, PointerRNA *ptr) +{ + uiLayout *row; + uiItemR(layout, ptr, "object", 0, NULL, 0); + + row = uiLayoutRow(layout, 0); + uiItemR(row, ptr, "height", 0, NULL, 0); + uiItemR(row, ptr, "axis", 0, NULL, 0); + + row = uiLayoutRow(layout, 0); + uiItemR(row, ptr, "min", 0, NULL, 0); + uiItemR(row, ptr, "max", 0, NULL, 0); +} + +static void draw_actuator_constraint(uiLayout *layout, PointerRNA *ptr, bContext *C) +{ + uiLayout *row, *col, *subcol, *split; + PointerRNA main_ptr; + + RNA_main_pointer_create(CTX_data_main(C), &main_ptr); + + uiItemR(layout, ptr, "mode", 0, NULL, 0); + switch (RNA_enum_get(ptr, "mode")) + { + case ACT_CONST_TYPE_LOC: + uiItemR(layout, ptr, "limit", 0, NULL, 0); + + row = uiLayoutRow(layout, 1); + uiItemR(row, ptr, "limit_min", 0, NULL, 0); + uiItemR(row, ptr, "limit_max", 0, NULL, 0); + + uiItemR(layout, ptr, "damping", UI_ITEM_R_SLIDER, NULL, 0); + break; + + case ACT_CONST_TYPE_DIST: + split = uiLayoutSplit(layout, 0.8, 0); + uiItemR(split, ptr, "direction", 0, NULL, 0); + row = uiLayoutRow(split, 1); + uiItemR(row, ptr, "use_local", UI_ITEM_R_TOGGLE, NULL, 0); + uiItemR(row, ptr, "use_normal", UI_ITEM_R_TOGGLE, NULL, 0); + + row = uiLayoutRow(layout, 0); + col = uiLayoutColumn(row, 0); + uiItemL(col, "Range:", 0); + uiItemR(col, ptr, "range", 0, "", 0); + + col = uiLayoutColumn(row, 1); + uiItemR(col, ptr, "use_force_distance", UI_ITEM_R_TOGGLE, NULL, 0); + subcol = uiLayoutColumn(col, 0); + uiLayoutSetActive(subcol, RNA_boolean_get(ptr, "use_force_distance")==1); + uiItemR(subcol, ptr, "distance", 0, "", 0); + + uiItemR(layout, ptr, "damping", UI_ITEM_R_SLIDER , NULL, 0); + + split = uiLayoutSplit(layout, 0.15, 0); + uiItemR(split, ptr, "use_material_detect", UI_ITEM_R_TOGGLE, NULL, 0); + if (RNA_boolean_get(ptr, "use_material_detect")) + uiItemPointerR(split, ptr, "material", &main_ptr, "materials", NULL, ICON_MATERIAL_DATA); + else + uiItemR(split, ptr, "property", 0, NULL, 0); + + split = uiLayoutSplit(layout, 0.15, 0); + uiItemR(split, ptr, "use_persistent", UI_ITEM_R_TOGGLE, NULL, 0); + + row = uiLayoutRow(split, 1); + uiItemR(row, ptr, "time", 0, NULL, 0); + uiItemR(row, ptr, "damping_rotation", UI_ITEM_R_SLIDER, NULL, 0); + break; + + case ACT_CONST_TYPE_ORI: + uiItemR(layout, ptr, "direction_axis", 0, NULL, 0); + + row=uiLayoutRow(layout, 1); + uiItemR(row, ptr, "damping", UI_ITEM_R_SLIDER , NULL, 0); + uiItemR(row, ptr, "time", 0, NULL, 0); + + row=uiLayoutRow(layout, 0); + uiItemR(row, ptr, "rotation_max", 0, NULL, 0); + + row=uiLayoutRow(layout, 1); + uiItemR(row, ptr, "angle_min", 0, NULL, 0); + uiItemR(row, ptr, "angle_max", 0, NULL, 0); + break; + + case ACT_CONST_TYPE_FH: + split=uiLayoutSplit(layout, 0.75, 0); + row= uiLayoutRow(split, 0); + uiItemR(row, ptr, "fh_damping", UI_ITEM_R_SLIDER , NULL, 0); + + uiItemR(row, ptr, "fh_height", 0, NULL, 0); + uiItemR(split, ptr, "use_fh_paralel_axis", UI_ITEM_R_TOGGLE , NULL, 0); + + row = uiLayoutRow(layout, 0); + uiItemR(row, ptr, "direction_axis", 0, NULL, 0); + split = uiLayoutSplit(row, 0.9, 0); + uiItemR(split, ptr, "spring", 0, NULL, 0); + uiItemR(split, ptr, "use_fh_normal", UI_ITEM_R_TOGGLE , NULL, 0); + + split = uiLayoutSplit(layout, 0.15, 0); + uiItemR(split, ptr, "use_material_detect", UI_ITEM_R_TOGGLE, NULL, 0); + if (RNA_boolean_get(ptr, "use_material_detect")) + uiItemPointerR(split, ptr, "material", &main_ptr, "materials", NULL, ICON_MATERIAL_DATA); + else + uiItemR(split, ptr, "property", 0, NULL, 0); + + split = uiLayoutSplit(layout, 0.15, 0); + uiItemR(split, ptr, "use_persistent", UI_ITEM_R_TOGGLE, NULL, 0); + + row = uiLayoutRow(split, 0); + uiItemR(row, ptr, "time", 0, NULL, 0); + uiItemR(row, ptr, "damping_rotation", UI_ITEM_R_SLIDER, NULL, 0); + break; + } +} + +static void draw_actuator_edit_object(uiLayout *layout, PointerRNA *ptr) +{ + Object *ob = (Object *)ptr->id.data; + uiLayout *row, *split, *subsplit; + uiItemR(layout, ptr, "mode", 0, NULL, 0); + + switch (RNA_enum_get(ptr, "mode")) + { + case ACT_EDOB_ADD_OBJECT: + row = uiLayoutRow(layout, 0); + uiItemR(row, ptr, "object", 0, NULL, 0); + uiItemR(row, ptr, "time", 0, NULL, 0); + + split = uiLayoutSplit(layout, 0.9, 0); + row = uiLayoutRow(split, 0); + uiItemR(row, ptr, "linear_velocity", 0, NULL, 0); + uiItemR(split, ptr, "use_local_linear_velocity", UI_ITEM_R_TOGGLE, NULL, 0); + + split = uiLayoutSplit(layout, 0.9, 0); + row = uiLayoutRow(split, 0); + uiItemR(row, ptr, "angular_velocity", 0, NULL, 0); + uiItemR(split, ptr, "use_local_angular_velocity", UI_ITEM_R_TOGGLE, NULL, 0); + break; + case ACT_EDOB_END_OBJECT: + break; + case ACT_EDOB_REPLACE_MESH: + if(ob->type != OB_MESH) { + uiItemL(layout, "Mode only available for mesh objects", 0); + break; + } + split = uiLayoutSplit(layout, 0.6, 0); + uiItemR(split, ptr, "mesh", 0, NULL, 0); + row = uiLayoutRow(split, 0); + uiItemR(row, ptr, "use_replace_display_mesh", UI_ITEM_R_TOGGLE, NULL, 0); + uiItemR(row, ptr, "use_replace_physics_mesh", UI_ITEM_R_TOGGLE, NULL, 0); + break; + case ACT_EDOB_TRACK_TO: + split = uiLayoutSplit(layout, 0.5, 0); + uiItemR(split, ptr, "track_object", 0, NULL, 0); + subsplit = uiLayoutSplit(split, 0.7, 0); + uiItemR(subsplit, ptr, "time", 0, NULL, 0); + uiItemR(subsplit, ptr, "use_3d_tracking", UI_ITEM_R_TOGGLE, NULL, 0); + break; + case ACT_EDOB_DYNAMICS: + if(ob->type != OB_MESH) { + uiItemL(layout, "Mode only available for mesh objects", 0); + break; + } + uiItemR(layout, ptr, "dynamic_operation", 0, NULL, 0); + if (RNA_enum_get(ptr, "dynamic_operation") == ACT_EDOB_SET_MASS) + uiItemR(layout, ptr, "mass", 0, NULL, 0); + break; + } +} + +static void draw_actuator_filter_2d(uiLayout *layout, PointerRNA *ptr) +{ + uiLayout *row, *split; + + uiItemR(layout, ptr, "mode", 0, NULL, 0); + switch (RNA_enum_get(ptr, "mode")) + { + case ACT_2DFILTER_CUSTOMFILTER: + uiItemR(layout, ptr, "filter_pass", 0, NULL, 0); + uiItemR(layout, ptr, "glsl_shader", 0, NULL, 0); + break; + case ACT_2DFILTER_MOTIONBLUR: + split=uiLayoutSplit(layout, 0.75, 1); + row= uiLayoutRow(split, 0); + uiLayoutSetActive(row, RNA_boolean_get(ptr, "use_motion_blur")==1); + uiItemR(row, ptr, "motion_blur_factor", 0, NULL, 0); + uiItemR(split, ptr, "use_motion_blur", UI_ITEM_R_TOGGLE, NULL, 0); + break; + default: // all other 2D Filters + uiItemR(layout, ptr, "filter_pass", 0, NULL, 0); + break; + } +} + +static void draw_actuator_game(uiLayout *layout, PointerRNA *ptr) +{ + uiItemR(layout, ptr, "mode", 0, NULL, 0); + if (RNA_enum_get(ptr, "mode") == ACT_GAME_LOAD) + uiItemR(layout, ptr, "filename", 0, NULL, 0); +} + +static void draw_actuator_ipo(uiLayout *layout, PointerRNA *ptr) +{ + Object *ob; + PointerRNA settings_ptr; + uiLayout *row, *subrow, *col; + + ob = (Object *)ptr->id.data; + RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); + + row= uiLayoutRow(layout, 0); + uiItemR(row, ptr, "play_type", 0, "", 0); + subrow= uiLayoutRow(row, 1); + uiItemR(subrow, ptr, "use_force", UI_ITEM_R_TOGGLE, NULL, 0); + uiItemR(subrow, ptr, "use_additive", UI_ITEM_R_TOGGLE, NULL, 0); + + col = uiLayoutColumn(subrow, 0); + uiLayoutSetActive(col, (RNA_boolean_get(ptr, "use_additive") || RNA_boolean_get(ptr, "use_force"))); + uiItemR(col, ptr, "use_local", UI_ITEM_R_TOGGLE, NULL, 0); + + row= uiLayoutRow(layout, 0); + if((RNA_enum_get(ptr, "play_type") == ACT_IPO_FROM_PROP)) + uiItemPointerR(row, ptr, "property", &settings_ptr, "properties", NULL, 0); + + else { + uiItemR(row, ptr, "frame_start", 0, NULL, 0); + uiItemR(row, ptr, "frame_end", 0, NULL, 0); + } + uiItemR(row, ptr, "apply_to_children", 0, NULL, 0); + + row= uiLayoutRow(layout, 0); + uiItemPointerR(row, ptr, "frame_property", &settings_ptr, "properties", NULL, 0); +} + +static void draw_actuator_message(uiLayout *layout, PointerRNA *ptr, bContext *C) +{ + Object *ob; + PointerRNA main_ptr, settings_ptr; + uiLayout *row; + + RNA_main_pointer_create(CTX_data_main(C), &main_ptr); + + ob = (Object *)ptr->id.data; + RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); + + uiItemPointerR(layout, ptr, "to_property", &main_ptr, "objects", NULL, ICON_OBJECT_DATA); + uiItemR(layout, ptr, "subject", 0, NULL, 0); + + row= uiLayoutRow(layout, 1); + uiItemR(row, ptr, "body_type", 0, NULL, 0); + + if(RNA_enum_get(ptr, "body_type") == ACT_MESG_MESG) + uiItemR(row, ptr, "body_message", 0, "", 0); + else // mode == ACT_MESG_PROP + uiItemPointerR(row, ptr, "body_property", &settings_ptr, "properties", "", 0); +} + +static void draw_actuator_motion(uiLayout *layout, PointerRNA *ptr) +{ + Object *ob; + PointerRNA settings_ptr; + uiLayout *split, *row, *col, *subcol; + int physics_type; + + ob = (Object *)ptr->id.data; + RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); + physics_type = RNA_enum_get(&settings_ptr, "physics_type"); + + uiItemR(layout, ptr, "mode", 0, NULL, 0); + + switch (RNA_enum_get(ptr, "mode")) { + case ACT_OBJECT_NORMAL: + split = uiLayoutSplit(layout, 0.9, 0); + row = uiLayoutRow(split, 0); + uiItemR(row, ptr, "offset_location", 0, NULL, 0); + uiItemR(split, ptr, "use_local_location", UI_ITEM_R_TOGGLE, NULL, 0); + + split = uiLayoutSplit(layout, 0.9, 0); + row = uiLayoutRow(split, 0); + uiItemR(row, ptr, "offset_rotation", 0, NULL, 0); + uiItemR(split, ptr, "use_local_rotation", UI_ITEM_R_TOGGLE, NULL, 0); + + if (ELEM3(physics_type, OB_BODY_TYPE_DYNAMIC, OB_BODY_TYPE_RIGID, OB_BODY_TYPE_SOFT)) { + uiItemL(layout, "Dynamic Object Settings:", 0); + split = uiLayoutSplit(layout, 0.9, 0); + row = uiLayoutRow(split, 0); + uiItemR(row, ptr, "force", 0, NULL, 0); + uiItemR(split, ptr, "use_local_force", UI_ITEM_R_TOGGLE, NULL, 0); + + split = uiLayoutSplit(layout, 0.9, 0); + row = uiLayoutRow(split, 0); + uiItemR(row, ptr, "torque", 0, NULL, 0); + uiItemR(split, ptr, "use_local_torque", UI_ITEM_R_TOGGLE, NULL, 0); + + split = uiLayoutSplit(layout, 0.9, 0); + row = uiLayoutRow(split, 0); + uiItemR(row, ptr, "linear_velocity", 0, NULL, 0); + row = uiLayoutRow(split, 1); + uiItemR(row, ptr, "use_local_linear_velocity", UI_ITEM_R_TOGGLE, NULL, 0); + uiItemR(row, ptr, "use_add_linear_velocity", UI_ITEM_R_TOGGLE, NULL, 0); + + split = uiLayoutSplit(layout, 0.9, 0); + row = uiLayoutRow(split, 0); + uiItemR(row, ptr, "angular_velocity", 0, NULL, 0); + uiItemR(split, ptr, "use_local_angular_velocity", UI_ITEM_R_TOGGLE, NULL, 0); + + uiItemR(layout, ptr, "damping", 0, NULL, 0); + } + break; + case ACT_OBJECT_SERVO: + uiItemR(layout, ptr, "reference_object", 0, NULL, 0); + + split = uiLayoutSplit(layout, 0.9, 0); + row = uiLayoutRow(split, 0); + uiItemR(row, ptr, "linear_velocity", 0, NULL, 0); + uiItemR(split, ptr, "use_local_linear_velocity", UI_ITEM_R_TOGGLE, NULL, 0); + + row = uiLayoutRow(layout, 0); + col = uiLayoutColumn(row, 0); + uiItemR(col, ptr, "use_servo_limit_x", UI_ITEM_R_TOGGLE, NULL, 0); + subcol = uiLayoutColumn(col, 1); + uiLayoutSetActive(subcol, RNA_boolean_get(ptr, "use_servo_limit_x")==1); + uiItemR(subcol, ptr, "force_max_x", 0, NULL, 0); + uiItemR(subcol, ptr, "force_min_x", 0, NULL, 0); + + col = uiLayoutColumn(row, 0); + uiItemR(col, ptr, "use_servo_limit_y", UI_ITEM_R_TOGGLE, NULL, 0); + subcol = uiLayoutColumn(col, 1); + uiLayoutSetActive(subcol, RNA_boolean_get(ptr, "use_servo_limit_y")==1); + uiItemR(subcol, ptr, "force_max_y", 0, NULL, 0); + uiItemR(subcol, ptr, "force_min_y", 0, NULL, 0); + + col = uiLayoutColumn(row, 0); + uiItemR(col, ptr, "use_servo_limit_z", UI_ITEM_R_TOGGLE, NULL, 0); + subcol = uiLayoutColumn(col, 1); + uiLayoutSetActive(subcol, RNA_boolean_get(ptr, "use_servo_limit_z")==1); + uiItemR(subcol, ptr, "force_max_z", 0, NULL, 0); + uiItemR(subcol, ptr, "force_min_z", 0, NULL, 0); + + //XXXACTUATOR missing labels from original 2.49 ui (e.g. Servo, Min, Max, Fast) + //Layout designers willing to help on that, please compare with 2.49 ui + // (since the old code is going to be deleted ... soon) + + col = uiLayoutColumn(layout, 1); + uiItemR(col, ptr, "proportional_coefficient", UI_ITEM_R_SLIDER, NULL, 0); + uiItemR(col, ptr, "integral_coefficient", UI_ITEM_R_SLIDER, NULL, 0); + uiItemR(col, ptr, "derivate_coefficient", UI_ITEM_R_SLIDER, NULL, 0); + break; + } +} + +static void draw_actuator_parent(uiLayout *layout, PointerRNA *ptr) +{ + uiLayout *row; + + uiItemR(layout, ptr, "mode", 0, NULL, 0); + uiItemR(layout, ptr, "object", 0, NULL, 0); + + row = uiLayoutRow(layout, 0); + uiItemR(row, ptr, "use_compound", 0, NULL, 0); + uiItemR(row, ptr, "use_ghost", 0, NULL, 0); +} + +static void draw_actuator_property(uiLayout *layout, PointerRNA *ptr) +{ + Object *ob = (Object *)ptr->id.data; + bActuator *act = (bActuator *)ptr->data; + bPropertyActuator *pa = (bPropertyActuator *) act->data; + Object *ob_from= pa->ob; + PointerRNA settings_ptr, obj_settings_ptr; + + uiLayout *row, *subrow; + + RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); -/* never used, see CVS 1.120 for the code */ -/* static uiBlock *freecamera_menu(void) */ + uiItemR(layout, ptr, "mode", 0, NULL, 0); + uiItemPointerR(layout, ptr, "property", &settings_ptr, "properties", NULL, 0); + switch(RNA_enum_get(ptr, "mode")) + { + case ACT_PROP_TOGGLE: + break; + case ACT_PROP_ADD: + uiItemR(layout, ptr, "value", 0, NULL, 0); + break; + case ACT_PROP_ASSIGN: + uiItemR(layout, ptr, "value", 0, NULL, 0); + break; + case ACT_PROP_COPY: + row = uiLayoutRow(layout, 0); + uiItemR(row, ptr, "object", 0, NULL, 0); + if(ob_from){ + RNA_pointer_create((ID *)ob_from, &RNA_GameObjectSettings, ob_from, &obj_settings_ptr); + uiItemPointerR(row, ptr, "object_property", &obj_settings_ptr, "properties", NULL, 0); + }else + { + subrow= uiLayoutRow(row, 0); + uiLayoutSetActive(subrow, 0); + uiItemR(subrow, ptr, "object_property", 0, NULL, 0); + } + break; + } +} + +static void draw_actuator_random(uiLayout *layout, PointerRNA *ptr) +{ + Object *ob; + PointerRNA settings_ptr; + uiLayout *row; + + ob = (Object *)ptr->id.data; + RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); + + row = uiLayoutRow(layout, 0); + + uiItemR(row, ptr, "seed", 0, NULL, 0); + uiItemR(row, ptr, "distribution", 0, NULL, 0); + + row = uiLayoutRow(layout, 0); + uiItemPointerR(row, ptr, "property", &settings_ptr, "properties", NULL, 0); + + row = uiLayoutRow(layout, 0); + + switch (RNA_enum_get(ptr, "distribution")){ + case ACT_RANDOM_BOOL_CONST: + uiItemR(row, ptr, "use_always_true", UI_ITEM_R_TOGGLE, NULL, 0); + break; + + case ACT_RANDOM_BOOL_UNIFORM: + uiItemL(row, "Choose between true and false, 50% chance each", 0); + break; + + case ACT_RANDOM_BOOL_BERNOUILLI: + uiItemR(row, ptr, "chance", 0, NULL, 0); + break; + + case ACT_RANDOM_INT_CONST: + uiItemR(row, ptr, "int_value", 0, NULL, 0); + break; + + case ACT_RANDOM_INT_UNIFORM: + uiItemR(row, ptr, "int_min", 0, NULL, 0); + uiItemR(row, ptr, "int_max", 0, NULL, 0); + break; + + case ACT_RANDOM_INT_POISSON: + uiItemR(row, ptr, "int_mean", 0, NULL, 0); + break; + + case ACT_RANDOM_FLOAT_CONST: + uiItemR(row, ptr, "float_value", 0, NULL, 0); + break; + + case ACT_RANDOM_FLOAT_UNIFORM: + uiItemR(row, ptr, "float_min", 0, NULL, 0); + uiItemR(row, ptr, "float_max", 0, NULL, 0); + break; + + case ACT_RANDOM_FLOAT_NORMAL: + uiItemR(row, ptr, "float_mean", 0, NULL, 0); + uiItemR(row, ptr, "standard_derivation", 0, NULL, 0); + break; + + case ACT_RANDOM_FLOAT_NEGATIVE_EXPONENTIAL: + uiItemR(row, ptr, "half_life_time", 0, NULL, 0); + break; + } +} + +static void draw_actuator_scene(uiLayout *layout, PointerRNA *ptr) +{ + uiItemR(layout, ptr, "mode", 0, NULL, 0); + + switch (RNA_enum_get(ptr, "mode")) { + case ACT_SCENE_CAMERA: + uiItemR(layout, ptr, "camera", 0, NULL, 0); + break; + case ACT_SCENE_RESTART: + break; + default: // ACT_SCENE_SET|ACT_SCENE_ADD_FRONT|ACT_SCENE_ADD_BACK|ACT_SCENE_REMOVE|ACT_SCENE_SUSPEND|ACT_SCENE_RESUME + uiItemR(layout, ptr, "scene", 0, NULL, 0); + break; + } +} + +static void draw_actuator_shape_action(uiLayout *layout, PointerRNA *ptr) +{ + Object *ob = (Object *)ptr->id.data; + PointerRNA settings_ptr; + uiLayout *row; + + if(ob->type != OB_MESH){ + uiItemL(layout, "Actuator only available for mesh objects", 0); + return; + } + + RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); + + row= uiLayoutRow(layout, 0); + uiItemR(row, ptr, "mode", 0, "", 0); + uiItemR(row, ptr, "action", 0, NULL, 0); + uiItemR(row, ptr, "use_continue_last_frame", 0, NULL, 0); + + row= uiLayoutRow(layout, 0); + if((RNA_enum_get(ptr, "mode") == ACT_ACTION_FROM_PROP)) + uiItemPointerR(row, ptr, "property", &settings_ptr, "properties", NULL, 0); + + else { + uiItemR(row, ptr, "frame_start", 0, NULL, 0); + uiItemR(row, ptr, "frame_end", 0, NULL, 0); + } + + row= uiLayoutRow(layout, 0); + uiItemR(row, ptr, "frame_blend_in", 0, NULL, 0); + uiItemR(row, ptr, "priority", 0, NULL, 0); + + row= uiLayoutRow(layout, 0); + uiItemPointerR(row, ptr, "frame_property", &settings_ptr, "properties", NULL, 0); + +#ifdef __NLA_ACTION_BY_MOTION_ACTUATOR + uiItemR(row, "stride_length", 0, NULL, 0); +#endif +} + +static void draw_actuator_sound(uiLayout *layout, PointerRNA *ptr, bContext *C) +{ + uiLayout *row, *col; + + uiTemplateID(layout, C, ptr, "sound", NULL, "SOUND_OT_open", NULL); + if (!RNA_pointer_get(ptr, "sound").data) + { + uiItemL(layout, "Select a sound from the list or load a new one", 0); + return; + } + uiItemR(layout, ptr, "mode", 0, NULL, 0); + + row = uiLayoutRow(layout, 0); + uiItemR(row, ptr, "volume", 0, NULL, 0); + uiItemR(row, ptr, "pitch", 0, NULL, 0); + + uiItemR(layout, ptr, "use_sound_3d", 0, NULL, 0); + + col = uiLayoutColumn(layout, 0); + uiLayoutSetActive(col, RNA_boolean_get(ptr, "use_sound_3d")==1); + + row = uiLayoutRow(col, 0); + uiItemR(row, ptr, "gain_3d_min", 0, NULL, 0); + uiItemR(row, ptr, "gain_3d_max", 0, NULL, 0); + + row = uiLayoutRow(col, 0); + uiItemR(row, ptr, "distance_3d_reference", 0, NULL, 0); + uiItemR(row, ptr, "distance_3d_max", 0, NULL, 0); + + row = uiLayoutRow(col, 0); + uiItemR(row, ptr, "rolloff_factor_3d", 0, NULL, 0); + uiItemR(row, ptr, "cone_outer_gain_3d", 0, NULL, 0); + + row = uiLayoutRow(col, 0); + uiItemR(row, ptr, "cone_outer_angle_3d", 0, NULL, 0); + uiItemR(row, ptr, "cone_inner_angle_3d", 0, NULL, 0); +} + +static void draw_actuator_state(uiLayout *layout, PointerRNA *ptr) +{ + uiLayout *split; + Object *ob = (Object *)ptr->id.data; + PointerRNA settings_ptr; + RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); + + split = uiLayoutSplit(layout, 0.35, 0); + uiItemR(split, ptr, "operation", 0, NULL, 0); + + uiTemplateLayers(split, ptr, "states", &settings_ptr, "used_states", 0); +} + +static void draw_actuator_visibility(uiLayout *layout, PointerRNA *ptr) +{ + uiLayout *row; + row = uiLayoutRow(layout, 0); + + uiItemR(row, ptr, "use_visible", 0, NULL, 0); + uiItemR(row, ptr, "use_occlusion", 0, NULL, 0); + uiItemR(row, ptr, "apply_to_children", 0, NULL, 0); +} + +void draw_brick_actuator(uiLayout *layout, PointerRNA *ptr, bContext *C) +{ + uiLayout *box; + + if (!RNA_boolean_get(ptr, "show_expanded")) + return; + + box = uiLayoutBox(layout); + + switch (RNA_enum_get(ptr, "type")) { + case ACT_ACTION: + draw_actuator_action(box, ptr); + break; + case ACT_ARMATURE: + draw_actuator_armature(box, ptr); + break; + case ACT_CAMERA: + draw_actuator_camera(box, ptr); + break; + case ACT_CONSTRAINT: + draw_actuator_constraint(box, ptr, C); + break; + case ACT_EDIT_OBJECT: + draw_actuator_edit_object(box, ptr); + break; + case ACT_2DFILTER: + draw_actuator_filter_2d(box, ptr); + break; + case ACT_GAME: + draw_actuator_game(box, ptr); + break; + case ACT_IPO: + draw_actuator_ipo(box, ptr); + break; + case ACT_MESSAGE: + draw_actuator_message(box, ptr, C); + break; + case ACT_OBJECT: + draw_actuator_motion(box, ptr); + break; + case ACT_PARENT: + draw_actuator_parent(box, ptr); + break; + case ACT_PROPERTY: + draw_actuator_property(box, ptr); + break; + case ACT_RANDOM: + draw_actuator_random(box, ptr); + break; + case ACT_SCENE: + draw_actuator_scene(box, ptr); + break; + case ACT_SHAPEACTION: + draw_actuator_shape_action(box, ptr); + break; + case ACT_SOUND: + draw_actuator_sound(box, ptr, C); + break; + case ACT_STATE: + draw_actuator_state(box, ptr); + break; + case ACT_VISIBILITY: + draw_actuator_visibility(box, ptr); + break; + } +} + +static void logic_buttons_new(bContext *C, ARegion *ar) +{ + SpaceLogic *slogic= CTX_wm_space_logic(C); + Object *ob= CTX_data_active_object(C); + Object *act_ob= ob; + ID **idar; + + PointerRNA logic_ptr, settings_ptr; + + uiLayout *layout, *row, *box; + uiBlock *block; + uiBut *but; + char name[32]; + short a, count; + int xco, yco, width; + + if(ob==NULL) return; + + RNA_pointer_create(NULL, &RNA_SpaceLogicEditor, slogic, &logic_ptr); + idar= get_selected_and_linked_obs(C, &count, slogic->scaflag); + + sprintf(name, "buttonswin %p", ar); + block= uiBeginBlock(C, ar, name, UI_EMBOSS); + uiBlockSetHandleFunc(block, do_logic_buts, NULL); + + /* loop over all objects and set visible/linked flags for the logic bricks */ + for(a=0; a<count; a++) { + bActuator *act; + bSensor *sens; + bController *cont; + int iact; + short flag; + + ob= (Object *)idar[a]; + + /* clean ACT_LINKED and ACT_VISIBLE of all potentially visible actuators so that we can determine which is actually linked/visible */ + act = ob->actuators.first; + while(act) { + act->flag &= ~(ACT_LINKED|ACT_VISIBLE); + act = act->next; + } + /* same for sensors */ + sens= ob->sensors.first; + while(sens) { + sens->flag &= ~(SENS_VISIBLE); + sens = sens->next; + } + + /* mark the linked and visible actuators */ + cont= ob->controllers.first; + while(cont) { + flag = ACT_LINKED; + + /* this controller is visible, mark all its actuator */ + if ((ob->scaflag & OB_ALLSTATE) || (ob->state & cont->state_mask)) + flag |= ACT_VISIBLE; + + for (iact=0; iact<cont->totlinks; iact++) { + act = cont->links[iact]; + if (act) + act->flag |= flag; + } + cont = cont->next; + } + } + + /* ****************** Controllers ****************** */ + + xco= 420; yco= 170; width= 300; + layout= uiBlockLayout(block, UI_LAYOUT_VERTICAL, UI_LAYOUT_PANEL, xco, yco, width, 20, U.uistyles.first); + row = uiLayoutRow(layout, 1); + + uiDefBlockBut(block, controller_menu, NULL, "Controllers", xco-10, yco, 300, UI_UNIT_Y, ""); /* replace this with uiLayout stuff later */ + + uiItemR(row, &logic_ptr, "show_controllers_selected_objects", 0, "Sel", 0); + uiItemR(row, &logic_ptr, "show_controllers_active_object", 0, "Act", 0); + uiItemR(row, &logic_ptr, "show_controllers_linked_controller", 0, "Link", 0); + + for(a=0; a<count; a++) { + bController *cont; + PointerRNA ptr; + uiLayout *split, *subsplit, *col; + + + ob= (Object *)idar[a]; + + /* only draw the controller common header if "use_visible" */ + if( (ob->scavisflag & OB_VIS_CONT) == 0) continue; + + /* Drawing the Controller Header common to all Selected Objects */ + + RNA_pointer_create((ID *)ob, &RNA_GameObjectSettings, ob, &settings_ptr); + + split= uiLayoutSplit(layout, 0.05, 0); + uiItemR(split, &settings_ptr, "show_state_panel", UI_ITEM_R_NO_BG, "", ICON_DISCLOSURE_TRI_RIGHT); + + row = uiLayoutRow(split, 1); + 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"); + if (ob == act_ob) + uiItemMenuEnumO(row, "LOGIC_OT_controller_add", "type", "Add Controller", 0); + + if (RNA_boolean_get(&settings_ptr, "show_state_panel")) { + + box= uiLayoutBox(layout); + split= uiLayoutSplit(box, 0.2, 0); + + col= uiLayoutColumn(split, 0); + uiItemL(col, "Visible", 0); + uiItemL(col, "Initial", 0); + + subsplit= uiLayoutSplit(split, 0.85, 0); + col= uiLayoutColumn(subsplit, 0); + row= uiLayoutRow(col, 0); + uiLayoutSetActive(row, RNA_boolean_get(&settings_ptr, "use_all_states")==0); + uiTemplateLayers(row, &settings_ptr, "states_visible", &settings_ptr, "used_states", 0); + row= uiLayoutRow(col, 0); + uiTemplateLayers(row, &settings_ptr, "states_initial", &settings_ptr, "used_states", 0); + + col= uiLayoutColumn(subsplit, 0); + uiItemR(col, &settings_ptr, "use_all_states", UI_ITEM_R_TOGGLE, NULL, 0); + uiItemR(col, &settings_ptr, "show_debug_state", 0, "", 0); + } + + /* End of Drawing the Controller Header common to all Selected Objects */ + + if ((ob->scaflag & OB_SHOWCONT) == 0) continue; + + + uiItemS(layout); + + for(cont= ob->controllers.first; cont; cont=cont->next) { + RNA_pointer_create((ID *)ob, &RNA_Controller, cont, &ptr); + + if (!(ob->scaflag & OB_ALLSTATE) && !(ob->state & cont->state_mask)) + continue; + + /* use two nested splits to align inlinks/links properly */ + split = uiLayoutSplit(layout, 0.05, 0); + + /* put inlink button to the left */ + col = uiLayoutColumn(split, 0); + uiLayoutSetAlignment(col, UI_LAYOUT_ALIGN_LEFT); + uiDefIconBut(block, INLINK, 0, ICON_INLINK, 0, 0, UI_UNIT_X, UI_UNIT_Y, cont, LINK_CONTROLLER, 0, 0, 0, ""); + + //col = uiLayoutColumn(split, 1); + /* nested split for middle and right columns */ + subsplit = uiLayoutSplit(split, 0.95, 0); + + col = uiLayoutColumn(subsplit, 1); + uiLayoutSetContextPointer(col, "controller", &ptr); + + /* should make UI template for controller header.. function will do for now */ +// draw_controller_header(col, &ptr); + draw_controller_header(col, &ptr, xco, width, yco); //provisory for 2.50 beta + + /* draw the brick contents */ + draw_brick_controller(col, &ptr); + + + /* put link button to the right */ + col = uiLayoutColumn(subsplit, 0); + uiLayoutSetAlignment(col, UI_LAYOUT_ALIGN_LEFT); + but= uiDefIconBut(block, LINK, 0, ICON_LINK, 0, 0, UI_UNIT_X, UI_UNIT_Y, NULL, 0, 0, 0, 0, ""); + uiSetButLink(but, NULL, (void ***)&(cont->links), &cont->totlinks, LINK_CONTROLLER, LINK_ACTUATOR); + } + } + uiBlockLayoutResolve(block, NULL, &yco); /* stores final height in yco */ + + + /* ****************** Sensors ****************** */ + + xco= 10; yco= 170; width= 340; + layout= uiBlockLayout(block, UI_LAYOUT_VERTICAL, UI_LAYOUT_PANEL, xco, yco, width, 20, U.uistyles.first); + row = uiLayoutRow(layout, 1); + + uiDefBlockBut(block, sensor_menu, NULL, "Sensors", xco-10, yco, 300, UI_UNIT_Y, ""); /* replace this with uiLayout stuff later */ + + uiItemR(row, &logic_ptr, "show_sensors_selected_objects", 0, "Sel", 0); + uiItemR(row, &logic_ptr, "show_sensors_active_object", 0, "Act", 0); + uiItemR(row, &logic_ptr, "show_sensors_linked_controller", 0, "Link", 0); + uiItemR(row, &logic_ptr, "show_sensors_active_states", 0, "State", 0); + + for(a=0; a<count; a++) { + bSensor *sens; + PointerRNA ptr; + + ob= (Object *)idar[a]; + + /* only draw the sensor common header if "use_visible" */ + if((ob->scavisflag & OB_VIS_SENS) == 0) continue; + + row = uiLayoutRow(layout, 1); + 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"); + if (ob == act_ob) + uiItemMenuEnumO(row, "LOGIC_OT_sensor_add", "type", "Add Sensor", 0); + + if ((ob->scaflag & OB_SHOWSENS) == 0) continue; + + uiItemS(layout); + + for(sens= ob->sensors.first; sens; sens=sens->next) { + RNA_pointer_create((ID *)ob, &RNA_Sensor, sens, &ptr); + + if ((ob->scaflag & OB_ALLSTATE) || + !(slogic->scaflag & BUTS_SENS_STATE) || + (sens->totlinks == 0) || /* always display sensor without links so that is can be edited */ + (sens->flag & SENS_PIN && slogic->scaflag & BUTS_SENS_STATE) || /* states can hide some sensors, pinned sensors ignore the visible state */ + (is_sensor_linked(block, sens)) + ) + { // gotta check if the current state is visible or not + uiLayout *split, *col; + + /* make as visible, for move operator */ + sens->flag |= SENS_VISIBLE; + + split = uiLayoutSplit(layout, 0.95, 0); + col = uiLayoutColumn(split, 1); + uiLayoutSetContextPointer(col, "sensor", &ptr); + + /* should make UI template for sensor header.. function will do for now */ + draw_sensor_header(col, &ptr, &logic_ptr); + + /* draw the brick contents */ + draw_brick_sensor(col, &ptr, C); + + /* put link button to the right */ + col = uiLayoutColumn(split, 0); + /* use oldskool uiButtons for links for now */ + but= uiDefIconBut(block, LINK, 0, ICON_LINK, 0, 0, UI_UNIT_X, UI_UNIT_Y, NULL, 0, 0, 0, 0, ""); + uiSetButLink(but, NULL, (void ***)&(sens->links), &sens->totlinks, LINK_SENSOR, LINK_CONTROLLER); + } + } + } + uiBlockLayoutResolve(block, NULL, &yco); /* stores final height in yco */ + + /* ****************** Actuators ****************** */ + + xco= 800; yco= 170; width= 340; + layout= uiBlockLayout(block, UI_LAYOUT_VERTICAL, UI_LAYOUT_PANEL, xco, yco, width, 20, U.uistyles.first); + row = uiLayoutRow(layout, 1); + + uiDefBlockBut(block, actuator_menu, NULL, "Actuators", xco-10, yco, 300, UI_UNIT_Y, ""); /* replace this with uiLayout stuff later */ + + uiItemR(row, &logic_ptr, "show_actuators_selected_objects", 0, "Sel", 0); + uiItemR(row, &logic_ptr, "show_actuators_active_object", 0, "Act", 0); + uiItemR(row, &logic_ptr, "show_actuators_linked_controller", 0, "Link", 0); + uiItemR(row, &logic_ptr, "show_actuators_active_states", 0, "State", 0); + + for(a=0; a<count; a++) { + bActuator *act; + PointerRNA ptr; + + ob= (Object *)idar[a]; + + /* only draw the actuator common header if "use_visible" */ + if( (ob->scavisflag & OB_VIS_ACT) == 0) continue; + + row = uiLayoutRow(layout, 1); + 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"); + if (ob == act_ob) + uiItemMenuEnumO(row, "LOGIC_OT_actuator_add", "type", "Add Actuator", 0); + + if ((ob->scaflag & OB_SHOWACT) == 0) continue; + + uiItemS(layout); + + for(act= ob->actuators.first; act; act=act->next) { + + RNA_pointer_create((ID *)ob, &RNA_Actuator, act, &ptr); + + if ((ob->scaflag & OB_ALLSTATE) || + !(slogic->scaflag & BUTS_ACT_STATE) || + !(act->flag & ACT_LINKED) || /* always display actuators without links so that is can be edited */ + (act->flag & ACT_VISIBLE) || /* this actuator has visible connection, display it */ + (act->flag & ACT_PIN && slogic->scaflag & BUTS_ACT_STATE) /* states can hide some sensors, pinned sensors ignore the visible state */ + ) + { // gotta check if the current state is visible or not + uiLayout *split, *col; + + /* make as visible, for move operator */ + act->flag |= ACT_VISIBLE; + + split = uiLayoutSplit(layout, 0.05, 0); + + /* put inlink button to the left */ + col = uiLayoutColumn(split, 0); + uiDefIconBut(block, INLINK, 0, ICON_INLINK, 0, 0, UI_UNIT_X, UI_UNIT_Y, act, LINK_ACTUATOR, 0, 0, 0, ""); + + col = uiLayoutColumn(split, 1); + uiLayoutSetContextPointer(col, "actuator", &ptr); + + /* should make UI template for actuator header.. function will do for now */ + draw_actuator_header(col, &ptr, &logic_ptr); + + /* draw the brick contents */ + draw_brick_actuator(col, &ptr, C); + + } + } + } + uiBlockLayoutResolve(block, NULL, &yco); /* stores final height in yco */ + + + uiComposeLinks(block); + + uiEndBlock(C, block); + uiDrawBlock(C, block); + + if(idar) MEM_freeN(idar); +} void logic_buttons(bContext *C, ARegion *ar) { + Main *bmain= CTX_data_main(C); SpaceLogic *slogic= CTX_wm_space_logic(C); Object *ob= CTX_data_active_object(C); ID **idar; @@ -3179,13 +4717,20 @@ void logic_buttons(bContext *C, ARegion *ar) bActuator *act; uiBlock *block; uiBut *but; + PointerRNA logic_ptr; int a, iact, stbit, offset; - short xco, yco, count, width, ycoo; + int xco, yco, width, ycoo; + short count; char name[32]; /* pin is a bool used for actuator and sensor drawing with states * pin so changing states dosnt hide the logic brick */ char pin; + if (G.rt == 0) { + logic_buttons_new(C, ar); + return; + } + if(ob==NULL) return; // uiSetButLock(object_is_libdata(ob), ERROR_LIBDATA_MESSAGE); @@ -3193,6 +4738,8 @@ void logic_buttons(bContext *C, ARegion *ar) block= uiBeginBlock(C, ar, name, UI_EMBOSS); uiBlockSetHandleFunc(block, do_logic_buts, NULL); + RNA_pointer_create(NULL, &RNA_SpaceLogicEditor, slogic, &logic_ptr); + idar= get_selected_and_linked_obs(C, &count, slogic->scaflag); /* clean ACT_LINKED and ACT_VISIBLE of all potentially visible actuators so that @@ -3276,7 +4823,7 @@ void logic_buttons(bContext *C, ARegion *ar) } } uiBlockBeginAlign(block); - uiDefButBitS(block, TOG, OB_SETSTBIT, B_SET_STATE_BIT, "All",(short)(xco+226), yco-10, 22, UI_UNIT_Y, &ob->scaflag, 0, 0, 0, 0, "Set all state bits"); + 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"); 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"); 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"); uiBlockEndAlign(block); @@ -3323,15 +4870,15 @@ void logic_buttons(bContext *C, ARegion *ar) cpack(0x999999); glRecti(xco+22, yco, xco+width-22,yco+19); but= uiDefBut(block, LABEL, 0, controller_name(cont->type), (short)(xco+22), yco, 70, UI_UNIT_Y, cont, 0, 0, 0, 0, "Controller type"); - //uiButSetFunc(but, sca_move_controller, cont, NULL); + //uiButSetFunc(but, old_sca_move_controller, cont, NULL); but= uiDefBut(block, LABEL, 0, cont->name,(short)(xco+92), yco,(short)(width-158), UI_UNIT_Y, cont, 0, 0, 0, 0, "Controller name"); - //uiButSetFunc(but, sca_move_controller, cont, NULL); + //uiButSetFunc(but, old_sca_move_controller, cont, NULL); uiBlockBeginAlign(block); 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"); - uiButSetFunc(but, sca_move_controller, cont, (void *)TRUE); + uiButSetFunc(but, old_sca_move_controller, cont, (void *)TRUE); 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"); - uiButSetFunc(but, sca_move_controller, cont, (void *)FALSE); + uiButSetFunc(but, old_sca_move_controller, cont, (void *)FALSE); uiBlockEndAlign(block); ycoo= yco; @@ -3352,7 +4899,7 @@ void logic_buttons(bContext *C, ARegion *ar) yco-= 6; } } - + /* ******************************* */ xco= 10; yco= 170; width= 300; @@ -3415,15 +4962,15 @@ void logic_buttons(bContext *C, ARegion *ar) set_col_sensor(sens->type, 1); glRecti(xco+22, yco, xco+width-22,yco+19); but= uiDefBut(block, LABEL, 0, sensor_name(sens->type), (short)(xco+22), yco, 80, UI_UNIT_Y, sens, 0, 0, 0, 0, ""); - //uiButSetFunc(but, sca_move_sensor, sens, NULL); + //uiButSetFunc(but, old_sca_move_sensor, sens, NULL); but= uiDefBut(block, LABEL, 0, sens->name, (short)(xco+102), yco, (short)(width-(pin?146:124)), UI_UNIT_Y, sens, 0, 31, 0, 0, ""); - //uiButSetFunc(but, sca_move_sensor, sens, NULL); + //uiButSetFunc(but, old_sca_move_sensor, sens, NULL); uiBlockBeginAlign(block); 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"); - uiButSetFunc(but, sca_move_sensor, sens, (void *)TRUE); + uiButSetFunc(but, old_sca_move_sensor, sens, (void *)TRUE); 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"); - uiButSetFunc(but, sca_move_sensor, sens, (void *)FALSE); + uiButSetFunc(but, old_sca_move_sensor, sens, (void *)FALSE); uiBlockEndAlign(block); } @@ -3437,10 +4984,8 @@ void logic_buttons(bContext *C, ARegion *ar) yco-= 6; } } - /* ******************************* */ xco= 800; yco= 170; width= 300; - uiDefBlockBut(block, actuator_menu, NULL, "Actuators", xco-10, yco+35, 90, UI_UNIT_Y, ""); uiBlockBeginAlign(block); @@ -3488,22 +5033,22 @@ void logic_buttons(bContext *C, ARegion *ar) uiButSetFunc(but, make_unique_prop_names_cb, act->name, (void*) 0); ycoo= yco; - yco= draw_actuatorbuttons(ob, act, block, xco, yco, width); + yco= draw_actuatorbuttons(bmain, ob, act, block, xco, yco, width); if(yco-6 < ycoo) ycoo= (yco+ycoo-20)/2; } else { set_col_actuator(act->type, 1); glRecti((short)(xco+22), yco, (short)(xco+width-22),(short)(yco+19)); but= uiDefBut(block, LABEL, 0, actuator_name(act->type), (short)(xco+22), yco, 90, UI_UNIT_Y, act, 0, 0, 0, 0, "Actuator type"); - // uiButSetFunc(but, sca_move_actuator, act, NULL); + // uiButSetFunc(but, old_sca_move_actuator, act, NULL); 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"); - // uiButSetFunc(but, sca_move_actuator, act, NULL); + // uiButSetFunc(but, old_sca_move_actuator, act, NULL); uiBlockBeginAlign(block); 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"); - uiButSetFunc(but, sca_move_actuator, act, (void *)TRUE); + uiButSetFunc(but, old_sca_move_actuator, act, (void *)TRUE); 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"); - uiButSetFunc(but, sca_move_actuator, act, (void *)FALSE); + uiButSetFunc(but, old_sca_move_actuator, act, (void *)FALSE); uiBlockEndAlign(block); ycoo= yco; diff --git a/source/blender/editors/space_logic/space_logic.c b/source/blender/editors/space_logic/space_logic.c index e15d68b36a5..01af324334b 100644 --- a/source/blender/editors/space_logic/space_logic.c +++ b/source/blender/editors/space_logic/space_logic.c @@ -37,12 +37,10 @@ #include "BKE_context.h" #include "BKE_screen.h" -#include "BKE_utildefines.h" #include "ED_screen.h" #include "BIF_gl.h" -#include "BIF_glutil.h" #include "WM_api.h" @@ -182,6 +180,7 @@ void logic_keymap(struct wmKeyConfig *keyconf) WM_keymap_add_item(keymap, "LOGIC_OT_properties", NKEY, KM_PRESS, 0, 0); WM_keymap_add_item(keymap, "LOGIC_OT_links_cut", LEFTMOUSE, KM_PRESS, KM_CTRL, 0); + WM_keymap_add_menu(keymap, "LOGIC_MT_logicbricks_add", AKEY, KM_PRESS, KM_SHIFT, 0); } static void logic_refresh(const bContext *C, ScrArea *sa) @@ -195,6 +194,9 @@ static void logic_listener(ARegion *ar, wmNotifier *wmn) { /* context changes */ switch(wmn->category) { + case NC_LOGIC: + ED_region_tag_redraw(ar); + break; case NC_SCENE: switch(wmn->data) { case ND_FRAME: @@ -244,11 +246,9 @@ static void logic_main_area_draw(const bContext *C, ARegion *ar) // SpaceLogic *slogic= CTX_wm_space_logic(C); View2D *v2d= &ar->v2d; View2DScrollers *scrollers; - float col[3]; /* clear and setup matrix */ - UI_GetThemeColor3fv(TH_BACK, col); - glClearColor(col[0], col[1], col[2], 0.0); + UI_ThemeClearColor(TH_BACK); glClear(GL_COLOR_BUFFER_BIT); UI_view2d_view_ortho(C, v2d); @@ -294,24 +294,7 @@ static void logic_header_area_init(wmWindowManager *wm, ARegion *ar) static void logic_header_area_draw(const bContext *C, ARegion *ar) { - float col[3]; - - /* clear */ - if(ED_screen_area_active(C)) - UI_GetThemeColor3fv(TH_HEADER, col); - else - UI_GetThemeColor3fv(TH_HEADERDESEL, col); - - glClearColor(col[0], col[1], col[2], 0.0); - glClear(GL_COLOR_BUFFER_BIT); - - /* set view2d view matrix for scrolling (without scrollers) */ - UI_view2d_view_ortho(C, &ar->v2d); - - logic_header_buttons(C, ar); - - /* restore view matrix? */ - UI_view2d_view_restore(C); + ED_region_header(C, ar); } /**************************** spacetype *****************************/ |