Changeset View
Changeset View
Standalone View
Standalone View
source/blender/editors/object/object_add.c
| Show First 20 Lines • Show All 65 Lines • ▼ Show 20 Lines | |||||
| #include "BKE_collection.h" | #include "BKE_collection.h" | ||||
| #include "BKE_context.h" | #include "BKE_context.h" | ||||
| #include "BKE_constraint.h" | #include "BKE_constraint.h" | ||||
| #include "BKE_curve.h" | #include "BKE_curve.h" | ||||
| #include "BKE_DerivedMesh.h" | #include "BKE_DerivedMesh.h" | ||||
| #include "BKE_displist.h" | #include "BKE_displist.h" | ||||
| #include "BKE_effect.h" | #include "BKE_effect.h" | ||||
| #include "BKE_font.h" | #include "BKE_font.h" | ||||
| #include "BKE_gpencil.h" | |||||
| #include "BKE_lamp.h" | #include "BKE_lamp.h" | ||||
| #include "BKE_lattice.h" | #include "BKE_lattice.h" | ||||
| #include "BKE_layer.h" | #include "BKE_layer.h" | ||||
| #include "BKE_library.h" | #include "BKE_library.h" | ||||
| #include "BKE_library_query.h" | #include "BKE_library_query.h" | ||||
| #include "BKE_library_remap.h" | #include "BKE_library_remap.h" | ||||
| #include "BKE_key.h" | #include "BKE_key.h" | ||||
| #include "BKE_main.h" | #include "BKE_main.h" | ||||
| Show All 16 Lines | |||||
| #include "RNA_define.h" | #include "RNA_define.h" | ||||
| #include "RNA_enum_types.h" | #include "RNA_enum_types.h" | ||||
| #include "WM_api.h" | #include "WM_api.h" | ||||
| #include "WM_types.h" | #include "WM_types.h" | ||||
| #include "ED_armature.h" | #include "ED_armature.h" | ||||
| #include "ED_curve.h" | #include "ED_curve.h" | ||||
| #include "ED_gpencil.h" | |||||
| #include "ED_mball.h" | #include "ED_mball.h" | ||||
| #include "ED_mesh.h" | #include "ED_mesh.h" | ||||
| #include "ED_node.h" | #include "ED_node.h" | ||||
| #include "ED_object.h" | #include "ED_object.h" | ||||
| #include "ED_physics.h" | #include "ED_physics.h" | ||||
| #include "ED_render.h" | #include "ED_render.h" | ||||
| #include "ED_screen.h" | #include "ED_screen.h" | ||||
| #include "ED_transform.h" | #include "ED_transform.h" | ||||
| ▲ Show 20 Lines • Show All 866 Lines • ▼ Show 20 Lines | void OBJECT_OT_drop_named_image(wmOperatorType *ot) | ||||
| RNA_def_property_flag(prop, PROP_HIDDEN | PROP_SKIP_SAVE); | RNA_def_property_flag(prop, PROP_HIDDEN | PROP_SKIP_SAVE); | ||||
| RNA_def_boolean(ot->srna, "relative_path", true, "Relative Path", "Select the file relative to the blend file"); | RNA_def_boolean(ot->srna, "relative_path", true, "Relative Path", "Select the file relative to the blend file"); | ||||
| RNA_def_property_flag(prop, PROP_HIDDEN | PROP_SKIP_SAVE); | RNA_def_property_flag(prop, PROP_HIDDEN | PROP_SKIP_SAVE); | ||||
| prop = RNA_def_string(ot->srna, "name", NULL, MAX_ID_NAME - 2, "Name", "Image name to assign"); | prop = RNA_def_string(ot->srna, "name", NULL, MAX_ID_NAME - 2, "Name", "Image name to assign"); | ||||
| RNA_def_property_flag(prop, PROP_HIDDEN | PROP_SKIP_SAVE); | RNA_def_property_flag(prop, PROP_HIDDEN | PROP_SKIP_SAVE); | ||||
| ED_object_add_generic_props(ot, false); | ED_object_add_generic_props(ot, false); | ||||
| } | } | ||||
| /********************* Add Gpencil Operator ********************/ | |||||
| static int object_gpencil_add_exec(bContext *C, wmOperator *op) | |||||
| { | |||||
| Object *ob = CTX_data_active_object(C); | |||||
| bGPdata *gpd = (ob && (ob->type == OB_GPENCIL)) ? ob->data : NULL; | |||||
| const int type = RNA_enum_get(op->ptr, "type"); | |||||
| float loc[3], rot[3]; | |||||
| unsigned int layer; | |||||
| bool newob = false; | |||||
| /* Hack: Force view-align to be on by default | |||||
| * since it's not nice for adding shapes in 2D | |||||
| * for them to end up aligned oddly | |||||
| */ | |||||
| if (RNA_struct_property_is_set(op->ptr, "view_align") == false) | |||||
| RNA_boolean_set(op->ptr, "view_align", true); | |||||
| /* Note: We use 'Y' here (not 'Z'), as */ | |||||
| WM_operator_view3d_unit_defaults(C, op); | |||||
| if (!ED_object_add_generic_get_opts(C, op, 'Y', loc, rot, NULL, &layer, NULL)) | |||||
| return OPERATOR_CANCELLED; | |||||
| /* add new object if not currently editing a GP object, | |||||
| * or if "empty" was chosen (i.e. user wants a blank GP canvas) | |||||
| */ | |||||
| if ((gpd == NULL) || (GPENCIL_ANY_MODE(gpd) == false) || (type == GP_EMPTY)) { | |||||
| const char *ob_name = (type == GP_MONKEY) ? "Suzanne" : NULL; | |||||
| float radius = RNA_float_get(op->ptr, "radius"); | |||||
| ob = ED_object_add_type(C, OB_GPENCIL, ob_name, loc, rot, true, layer); | |||||
| gpd = ob->data; | |||||
| newob = true; | |||||
| BKE_object_obdata_size_init(ob, GP_OBGPENCIL_DEFAULT_SIZE * radius); | |||||
| } | |||||
| else { | |||||
| DEG_id_tag_update(&ob->id, OB_RECALC_DATA); | |||||
| WM_event_add_notifier(C, NC_GPENCIL | ND_DATA | NA_ADDED, NULL); | |||||
| } | |||||
| /* create relevant geometry */ | |||||
| switch (type) { | |||||
| case GP_MONKEY: | |||||
| { | |||||
| float radius = RNA_float_get(op->ptr, "radius"); | |||||
| float mat[4][4]; | |||||
| ED_object_new_primitive_matrix(C, ob, loc, rot, mat); | |||||
| mul_v3_fl(mat[0], radius); | |||||
| mul_v3_fl(mat[1], radius); | |||||
| mul_v3_fl(mat[2], radius); | |||||
| ED_gpencil_create_monkey(C, mat); | |||||
| break; | |||||
| } | |||||
| case GP_EMPTY: | |||||
| /* do nothing */ | |||||
| break; | |||||
| default: | |||||
| BKE_report(op->reports, RPT_WARNING, "Not implemented"); | |||||
| break; | |||||
| } | |||||
| /* if this is a new object, initialise default stuff (colors, etc.) */ | |||||
| if (newob) { | |||||
| ED_gpencil_add_defaults(C); | |||||
| } | |||||
| return OPERATOR_FINISHED; | |||||
| } | |||||
| void OBJECT_OT_gpencil_add(wmOperatorType *ot) | |||||
| { | |||||
| /* identifiers */ | |||||
| ot->name = "Add GPencil"; | |||||
| ot->description = "Add a grease pencil object to the scene"; | |||||
| ot->idname = "OBJECT_OT_gpencil_add"; | |||||
| /* api callbacks */ | |||||
| ot->invoke = WM_menu_invoke; | |||||
| ot->exec = object_gpencil_add_exec; | |||||
| ot->poll = ED_operator_scene_editable; | |||||
| /* flags */ | |||||
| ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO; | |||||
| /* properties */ | |||||
| ED_object_add_unit_props(ot); | |||||
| ED_object_add_generic_props(ot, false); | |||||
| ot->prop = RNA_def_enum(ot->srna, "type", rna_enum_object_gpencil_type_items, 0, "Type", ""); | |||||
| } | |||||
| /********************* Add Light Operator ********************/ | /********************* Add Light Operator ********************/ | ||||
| static const char *get_light_defname(int type) | static const char *get_light_defname(int type) | ||||
| { | { | ||||
| switch (type) { | switch (type) { | ||||
| case LA_LOCAL: return CTX_DATA_(BLT_I18NCONTEXT_ID_LAMP, "Point"); | case LA_LOCAL: return CTX_DATA_(BLT_I18NCONTEXT_ID_LAMP, "Point"); | ||||
| case LA_SUN: return CTX_DATA_(BLT_I18NCONTEXT_ID_LAMP, "Sun"); | case LA_SUN: return CTX_DATA_(BLT_I18NCONTEXT_ID_LAMP, "Sun"); | ||||
| case LA_SPOT: return CTX_DATA_(BLT_I18NCONTEXT_ID_LAMP, "Spot"); | case LA_SPOT: return CTX_DATA_(BLT_I18NCONTEXT_ID_LAMP, "Spot"); | ||||
| ▲ Show 20 Lines • Show All 780 Lines • ▼ Show 20 Lines | if (ob->flag & OB_DONE || !IS_TAGGED(ob->data)) { | ||||
| /* obdata already modified */ | /* obdata already modified */ | ||||
| if (!IS_TAGGED(ob->data)) { | if (!IS_TAGGED(ob->data)) { | ||||
| /* When 2 objects with linked data are selected, converting both | /* When 2 objects with linked data are selected, converting both | ||||
| * would keep modifiers on all but the converted object [#26003] */ | * would keep modifiers on all but the converted object [#26003] */ | ||||
| if (ob->type == OB_MESH) { | if (ob->type == OB_MESH) { | ||||
| BKE_object_free_modifiers(ob, 0); /* after derivedmesh calls! */ | BKE_object_free_modifiers(ob, 0); /* after derivedmesh calls! */ | ||||
| } | } | ||||
| if (ob->type == OB_GPENCIL) { | |||||
| BKE_object_free_modifiers(ob, 0); /* after derivedmesh calls! */ | |||||
| BKE_object_free_shaderfx(ob, 0); | |||||
| } | |||||
| } | } | ||||
| } | } | ||||
| else if (ob->type == OB_MESH && target == OB_CURVE) { | else if (ob->type == OB_MESH && target == OB_CURVE) { | ||||
| ob->flag |= OB_DONE; | ob->flag |= OB_DONE; | ||||
| if (keep_original) { | if (keep_original) { | ||||
| basen = duplibase_for_convert(bmain, scene, view_layer, base, NULL); | basen = duplibase_for_convert(bmain, scene, view_layer, base, NULL); | ||||
| newob = basen->object; | newob = basen->object; | ||||
| ▲ Show 20 Lines • Show All 325 Lines • ▼ Show 20 Lines | else { | ||||
| if (dupflag & USER_DUP_MAT) { | if (dupflag & USER_DUP_MAT) { | ||||
| for (a = 0; a < obn->totcol; a++) { | for (a = 0; a < obn->totcol; a++) { | ||||
| id = (ID *)obn->mat[a]; | id = (ID *)obn->mat[a]; | ||||
| if (id) { | if (id) { | ||||
| ID_NEW_REMAP_US(obn->mat[a]) | ID_NEW_REMAP_US(obn->mat[a]) | ||||
| else { | else { | ||||
| obn->mat[a] = ID_NEW_SET(obn->mat[a], BKE_material_copy(bmain, obn->mat[a])); | obn->mat[a] = ID_NEW_SET(obn->mat[a], BKE_material_copy(bmain, obn->mat[a])); | ||||
| /* duplicate grease pencil settings */ | |||||
| if (ob->mat[a]->gp_style) { | |||||
| obn->mat[a]->gp_style = MEM_dupallocN(ob->mat[a]->gp_style); | |||||
| } | |||||
| } | } | ||||
| id_us_min(id); | id_us_min(id); | ||||
| if (dupflag & USER_DUP_ACT) { | if (dupflag & USER_DUP_ACT) { | ||||
| BKE_animdata_copy_id_action(bmain, &obn->mat[a]->id, true); | BKE_animdata_copy_id_action(bmain, &obn->mat[a]->id, true); | ||||
| } | } | ||||
| } | } | ||||
| } | } | ||||
| ▲ Show 20 Lines • Show All 120 Lines • ▼ Show 20 Lines | switch (obn->type) { | ||||
| ID_NEW_REMAP_US2(obn->data) | ID_NEW_REMAP_US2(obn->data) | ||||
| else { | else { | ||||
| obn->data = ID_NEW_SET(obn->data, BKE_speaker_copy(bmain, obn->data)); | obn->data = ID_NEW_SET(obn->data, BKE_speaker_copy(bmain, obn->data)); | ||||
| didit = 1; | didit = 1; | ||||
| } | } | ||||
| id_us_min(id); | id_us_min(id); | ||||
| } | } | ||||
| break; | break; | ||||
| case OB_GPENCIL: | |||||
| if (dupflag != 0) { | |||||
| ID_NEW_REMAP_US2(obn->data) | |||||
| else { | |||||
| obn->data = ID_NEW_SET(obn->data, BKE_gpencil_copy(bmain, obn->data)); | |||||
| didit = 1; | |||||
| } | |||||
| id_us_min(id); | |||||
| } | |||||
| break; | |||||
| } | } | ||||
| /* check if obdata is copied */ | /* check if obdata is copied */ | ||||
| if (didit) { | if (didit) { | ||||
| Key *key = BKE_key_from_object(obn); | Key *key = BKE_key_from_object(obn); | ||||
| Key *oldkey = BKE_key_from_object(ob); | Key *oldkey = BKE_key_from_object(ob); | ||||
| if (oldkey != NULL) { | if (oldkey != NULL) { | ||||
| ▲ Show 20 Lines • Show All 208 Lines • ▼ Show 20 Lines | |||||
| /**************************** Join *************************/ | /**************************** Join *************************/ | ||||
| static bool join_poll(bContext *C) | static bool join_poll(bContext *C) | ||||
| { | { | ||||
| Object *ob = CTX_data_active_object(C); | Object *ob = CTX_data_active_object(C); | ||||
| if (!ob || ID_IS_LINKED(ob)) return 0; | if (!ob || ID_IS_LINKED(ob)) return 0; | ||||
| if (ELEM(ob->type, OB_MESH, OB_CURVE, OB_SURF, OB_ARMATURE)) | if (ELEM(ob->type, OB_MESH, OB_CURVE, OB_SURF, OB_ARMATURE, OB_GPENCIL)) | ||||
| return ED_operator_screenactive(C); | return ED_operator_screenactive(C); | ||||
| else | else | ||||
| return 0; | return 0; | ||||
| } | } | ||||
| static int join_exec(bContext *C, wmOperator *op) | static int join_exec(bContext *C, wmOperator *op) | ||||
| { | { | ||||
| Object *ob = CTX_data_active_object(C); | Object *ob = CTX_data_active_object(C); | ||||
| if (ob->mode & OB_MODE_EDIT) { | if (ob->mode & OB_MODE_EDIT) { | ||||
| BKE_report(op->reports, RPT_ERROR, "This data does not support joining in edit mode"); | BKE_report(op->reports, RPT_ERROR, "This data does not support joining in edit mode"); | ||||
| return OPERATOR_CANCELLED; | return OPERATOR_CANCELLED; | ||||
| } | } | ||||
| else if (BKE_object_obdata_is_libdata(ob)) { | else if (BKE_object_obdata_is_libdata(ob)) { | ||||
| BKE_report(op->reports, RPT_ERROR, "Cannot edit external libdata"); | BKE_report(op->reports, RPT_ERROR, "Cannot edit external libdata"); | ||||
| return OPERATOR_CANCELLED; | return OPERATOR_CANCELLED; | ||||
| } | } | ||||
| else if (ob->type == OB_GPENCIL) { | |||||
| bGPdata *gpd = (bGPdata *)ob->data; | |||||
| if ((!gpd) || GPENCIL_ANY_MODE(gpd)) { | |||||
| BKE_report(op->reports, RPT_ERROR, "This data does not support joining in this mode"); | |||||
| return OPERATOR_CANCELLED; | |||||
| } | |||||
| } | |||||
| if (ob->type == OB_MESH) | if (ob->type == OB_MESH) | ||||
| return join_mesh_exec(C, op); | return join_mesh_exec(C, op); | ||||
| else if (ELEM(ob->type, OB_CURVE, OB_SURF)) | else if (ELEM(ob->type, OB_CURVE, OB_SURF)) | ||||
| return join_curve_exec(C, op); | return join_curve_exec(C, op); | ||||
| else if (ob->type == OB_ARMATURE) | else if (ob->type == OB_ARMATURE) | ||||
| return join_armature_exec(C, op); | return join_armature_exec(C, op); | ||||
| else if (ob->type == OB_GPENCIL) | |||||
| return ED_gpencil_join_objects_exec(C, op); | |||||
| return OPERATOR_CANCELLED; | return OPERATOR_CANCELLED; | ||||
| } | } | ||||
| void OBJECT_OT_join(wmOperatorType *ot) | void OBJECT_OT_join(wmOperatorType *ot) | ||||
| { | { | ||||
| /* identifiers */ | /* identifiers */ | ||||
| ot->name = "Join"; | ot->name = "Join"; | ||||
| ▲ Show 20 Lines • Show All 59 Lines • Show Last 20 Lines | |||||