Changeset View
Changeset View
Standalone View
Standalone View
source/blender/editors/transform/transform_convert_gpencil.c
| Show All 29 Lines | |||||
| #include "BKE_colortools.h" | #include "BKE_colortools.h" | ||||
| #include "BKE_context.h" | #include "BKE_context.h" | ||||
| #include "BKE_gpencil.h" | #include "BKE_gpencil.h" | ||||
| #include "ED_gpencil.h" | #include "ED_gpencil.h" | ||||
| #include "transform.h" | #include "transform.h" | ||||
| #include "transform_convert.h" | #include "transform_convert.h" | ||||
| #include "transform_data.h" | |||||
| /* -------------------------------------------------------------------- */ | /* -------------------------------------------------------------------- */ | ||||
| /** \name Gpencil Transform Creation | /** \name Gpencil Transform Creation | ||||
| * | * | ||||
| * \{ */ | * \{ */ | ||||
| static void createTransGPencil_center_get(bGPDstroke *gps, float r_center[3]) | static void createTransGPencil_center_get(bGPDstroke *gps, float r_center[3]) | ||||
| { | { | ||||
| Show All 24 Lines | void createTransGPencil(bContext *C, TransInfo *t) | ||||
| bGPdata *gpd = ED_gpencil_data_get_active(C); | bGPdata *gpd = ED_gpencil_data_get_active(C); | ||||
| ToolSettings *ts = CTX_data_tool_settings(C); | ToolSettings *ts = CTX_data_tool_settings(C); | ||||
| bool is_multiedit = (bool)GPENCIL_MULTIEDIT_SESSIONS_ON(gpd); | bool is_multiedit = (bool)GPENCIL_MULTIEDIT_SESSIONS_ON(gpd); | ||||
| bool use_multiframe_falloff = (ts->gp_sculpt.flag & GP_SCULPT_SETT_FLAG_FRAME_FALLOFF) != 0; | bool use_multiframe_falloff = (ts->gp_sculpt.flag & GP_SCULPT_SETT_FLAG_FRAME_FALLOFF) != 0; | ||||
| Object *obact = CTX_data_active_object(C); | Object *obact = CTX_data_active_object(C); | ||||
| bGPDlayer *gpl; | bGPDlayer *gpl; | ||||
| TransData *td = NULL; | |||||
| float mtx[3][3], smtx[3][3]; | float mtx[3][3], smtx[3][3]; | ||||
| const Scene *scene = CTX_data_scene(C); | const Scene *scene = CTX_data_scene(C); | ||||
| const int cfra_scene = CFRA; | const int cfra_scene = CFRA; | ||||
| const bool is_prop_edit = (t->flag & T_PROP_EDIT) != 0; | const bool is_prop_edit = (t->flag & T_PROP_EDIT) != 0; | ||||
| const bool is_prop_edit_connected = (t->flag & T_PROP_CONNECTED) != 0; | const bool is_prop_edit_connected = (t->flag & T_PROP_CONNECTED) != 0; | ||||
| const bool is_scale_thickness = ((t->mode == TFM_GPENCIL_SHRINKFATTEN) || | const bool is_scale_thickness = ((t->mode == TFM_GPENCIL_SHRINKFATTEN) || | ||||
| ▲ Show 20 Lines • Show All 81 Lines • ▼ Show 20 Lines | void createTransGPencil(bContext *C, TransInfo *t) | ||||
| } | } | ||||
| /* Stop trying if nothing selected */ | /* Stop trying if nothing selected */ | ||||
| if (tc->data_len == 0) { | if (tc->data_len == 0) { | ||||
| return; | return; | ||||
| } | } | ||||
| /* Allocate memory for data */ | /* Allocate memory for data */ | ||||
| tc->data = MEM_callocN(tc->data_len * sizeof(TransData), "TransData(GPencil)"); | TransData *td = tc->data = transform_data_alloc(tc->data_len, TD_BASIC_COMP); | ||||
| td = tc->data; | int tdi = 0; | ||||
| unit_m3(smtx); | unit_m3(smtx); | ||||
| unit_m3(mtx); | unit_m3(mtx); | ||||
| /* Second Pass: Build transdata array */ | /* Second Pass: Build transdata array */ | ||||
| for (gpl = gpd->layers.first; gpl; gpl = gpl->next) { | for (gpl = gpd->layers.first; gpl; gpl = gpl->next) { | ||||
| /* only editable and visible layers are considered */ | /* only editable and visible layers are considered */ | ||||
| if (BKE_gpencil_layer_is_editable(gpl) && (gpl->actframe != NULL)) { | if (BKE_gpencil_layer_is_editable(gpl) && (gpl->actframe != NULL)) { | ||||
| ▲ Show 20 Lines • Show All 47 Lines • ▼ Show 20 Lines | if (BKE_gpencil_layer_is_editable(gpl) && (gpl->actframe != NULL)) { | ||||
| if ((is_multiedit) && (use_multiframe_falloff)) { | if ((is_multiedit) && (use_multiframe_falloff)) { | ||||
| /* Falloff depends on distance to active frame | /* Falloff depends on distance to active frame | ||||
| * (relative to the overall frame range). */ | * (relative to the overall frame range). */ | ||||
| falloff = BKE_gpencil_multiframe_falloff_calc( | falloff = BKE_gpencil_multiframe_falloff_calc( | ||||
| gpf, gpl->actframe->framenum, f_init, f_end, ts->gp_sculpt.cur_falloff); | gpf, gpl->actframe->framenum, f_init, f_end, ts->gp_sculpt.cur_falloff); | ||||
| } | } | ||||
| for (gps = gpf->strokes.first; gps; gps = gps->next) { | for (gps = gpf->strokes.first; gps; gps = gps->next) { | ||||
| TransData *head = td; | int head = tdi; | ||||
| TransData *tail = td; | int tail = tdi; | ||||
| bool stroke_ok; | bool stroke_ok; | ||||
| /* skip strokes that are invalid for current view */ | /* skip strokes that are invalid for current view */ | ||||
| if (ED_gpencil_stroke_can_use(C, gps) == false) { | if (ED_gpencil_stroke_can_use(C, gps) == false) { | ||||
| continue; | continue; | ||||
| } | } | ||||
| /* check if the color is editable */ | /* check if the color is editable */ | ||||
| if (ED_gpencil_stroke_color_use(obact, gpl, gps) == false) { | if (ED_gpencil_stroke_color_use(obact, gpl, gps) == false) { | ||||
| Show All 38 Lines | if (BKE_gpencil_layer_is_editable(gpl) && (gpl->actframe != NULL)) { | ||||
| } | } | ||||
| else { | else { | ||||
| /* Only selected points in selected strokes */ | /* Only selected points in selected strokes */ | ||||
| point_ok = (pt->flag & GP_SPOINT_SELECT) != 0; | point_ok = (pt->flag & GP_SPOINT_SELECT) != 0; | ||||
| } | } | ||||
| /* do point... */ | /* do point... */ | ||||
| if (point_ok) { | if (point_ok) { | ||||
| copy_v3_v3(td->iloc, &pt->x); | copy_v3_v3(td->basic[tdi].iloc, &pt->x); | ||||
| /* only copy center in local origins. | /* only copy center in local origins. | ||||
| * This allows get interesting effects also when move | * This allows get interesting effects also when move | ||||
| * using proportional editing */ | * using proportional editing */ | ||||
| if ((gps->flag & GP_STROKE_SELECT) && | if ((gps->flag & GP_STROKE_SELECT) && | ||||
| (ts->transform_pivot_point == V3D_AROUND_LOCAL_ORIGINS)) { | (ts->transform_pivot_point == V3D_AROUND_LOCAL_ORIGINS)) { | ||||
| copy_v3_v3(td->center, center); | copy_v3_v3(td->center[tdi], center); | ||||
| } | } | ||||
| else { | else { | ||||
| copy_v3_v3(td->center, &pt->x); | copy_v3_v3(td->center[tdi], &pt->x); | ||||
| } | } | ||||
| td->loc = &pt->x; | td->basic[tdi].loc = &pt->x; | ||||
| td->flag = 0; | td->basic[tdi].flag = 0; | ||||
| if (pt->flag & GP_SPOINT_SELECT) { | if (pt->flag & GP_SPOINT_SELECT) { | ||||
| td->flag |= TD_SELECTED; | td->basic[tdi].flag |= TD_SELECTED; | ||||
| } | } | ||||
| /* for other transform modes (e.g. shrink-fatten), need to additional data | /* for other transform modes (e.g. shrink-fatten), need to additional data | ||||
| * but never for mirror | * but never for mirror | ||||
| */ | */ | ||||
| if ((t->mode != TFM_MIRROR) && (is_scale_thickness)) { | if ((t->mode != TFM_MIRROR) && (is_scale_thickness)) { | ||||
| if (t->mode != TFM_GPENCIL_OPACITY) { | if (t->mode != TFM_GPENCIL_OPACITY) { | ||||
| td->val = &pt->pressure; | td->special[tdi].val = &pt->pressure; | ||||
| td->ival = pt->pressure; | td->special[tdi].ival = pt->pressure; | ||||
| } | } | ||||
| else { | else { | ||||
| td->val = &pt->strength; | td->special[tdi].val = &pt->strength; | ||||
| td->ival = pt->strength; | td->special[tdi].ival = pt->strength; | ||||
| } | } | ||||
| } | } | ||||
| /* screenspace needs special matrices... */ | /* screenspace needs special matrices... */ | ||||
| if ((gps->flag & (GP_STROKE_3DSPACE | GP_STROKE_2DSPACE | GP_STROKE_2DIMAGE)) == | if ((gps->flag & (GP_STROKE_3DSPACE | GP_STROKE_2DSPACE | GP_STROKE_2DIMAGE)) == | ||||
| 0) { | 0) { | ||||
| /* screenspace */ | /* screenspace */ | ||||
| td->protectflag = OB_LOCK_LOCZ | OB_LOCK_ROTZ | OB_LOCK_SCALEZ; | td->object[tdi].protectflag = OB_LOCK_LOCZ | OB_LOCK_ROTZ | OB_LOCK_SCALEZ; | ||||
| } | } | ||||
| else { | else { | ||||
| /* configure 2D dataspace points so that they don't play up... */ | /* configure 2D dataspace points so that they don't play up... */ | ||||
| if (gps->flag & (GP_STROKE_2DSPACE | GP_STROKE_2DIMAGE)) { | if (gps->flag & (GP_STROKE_2DSPACE | GP_STROKE_2DIMAGE)) { | ||||
| td->protectflag = OB_LOCK_LOCZ | OB_LOCK_ROTZ | OB_LOCK_SCALEZ; | td->object[tdi].protectflag = OB_LOCK_LOCZ | OB_LOCK_ROTZ | OB_LOCK_SCALEZ; | ||||
| } | } | ||||
| } | } | ||||
| /* apply parent transformations */ | /* apply parent transformations */ | ||||
| copy_m3_m4(td->smtx, inverse_diff_mat); /* final position */ | copy_m3_m4(td->space[tdi].smtx, inverse_diff_mat); /* final position */ | ||||
| copy_m3_m4(td->mtx, diff_mat); /* display position */ | copy_m3_m4(td->space[tdi].mtx, diff_mat); /* display position */ | ||||
| copy_m3_m4(td->axismtx, diff_mat); /* axis orientation */ | copy_m3_m4(td->space[tdi].axismtx, diff_mat); /* axis orientation */ | ||||
| /* Triangulation must be calculated again, | /* Triangulation must be calculated again, | ||||
| * so save the stroke for recalc function */ | * so save the stroke for recalc function */ | ||||
| td->extra = gps; | td->basic[tdi].extra = gps; | ||||
| /* save pointer to object */ | /* save pointer to object */ | ||||
| td->ob = obact; | td->object[tdi].ob = obact; | ||||
| td++; | tdi++; | ||||
| tail++; | tail++; | ||||
| } | } | ||||
| } | } | ||||
| /* March over these points, and calculate the proportional editing distances */ | /* March over these points, and calculate the proportional editing distances */ | ||||
| if (is_prop_edit && (head != tail)) { | if (is_prop_edit && (head != tail)) { | ||||
| /* XXX: for now, we are similar enough that this works... */ | /* XXX: for now, we are similar enough that this works... */ | ||||
| calc_distanceCurveVerts(head, tail - 1); | calc_distanceCurveVerts(tc->data, head, tail - 1); | ||||
| } | } | ||||
| } | } | ||||
| } | } | ||||
| } | } | ||||
| /* if not multiedit out of loop */ | /* if not multiedit out of loop */ | ||||
| if (!is_multiedit) { | if (!is_multiedit) { | ||||
| break; | break; | ||||
| } | } | ||||
| } | } | ||||
| } | } | ||||
| } | } | ||||
| } | } | ||||
| /** \} */ | /** \} */ | ||||