diff options
Diffstat (limited to 'source/blender/editors/curve')
-rw-r--r-- | source/blender/editors/curve/curve_intern.h | 2 | ||||
-rw-r--r-- | source/blender/editors/curve/curve_ops.c | 3 | ||||
-rw-r--r-- | source/blender/editors/curve/editcurve.c | 131 | ||||
-rw-r--r-- | source/blender/editors/curve/editcurve_paint.c | 110 | ||||
-rw-r--r-- | source/blender/editors/curve/editfont.c | 74 |
5 files changed, 141 insertions, 179 deletions
diff --git a/source/blender/editors/curve/curve_intern.h b/source/blender/editors/curve/curve_intern.h index 856573ffab0..02c76a840f1 100644 --- a/source/blender/editors/curve/curve_intern.h +++ b/source/blender/editors/curve/curve_intern.h @@ -40,7 +40,7 @@ struct wmOperatorType; struct ViewContext; /* editfont.c */ -enum { DEL_ALL, DEL_NEXT_CHAR, DEL_PREV_CHAR, DEL_SELECTION, DEL_NEXT_SEL, DEL_PREV_SEL }; +enum { DEL_NEXT_CHAR, DEL_PREV_CHAR, DEL_NEXT_WORD, DEL_PREV_WORD, DEL_SELECTION, DEL_NEXT_SEL, DEL_PREV_SEL }; enum { CASE_LOWER, CASE_UPPER }; enum { LINE_BEGIN, LINE_END, PREV_CHAR, NEXT_CHAR, PREV_WORD, NEXT_WORD, PREV_LINE, NEXT_LINE, PREV_PAGE, NEXT_PAGE }; diff --git a/source/blender/editors/curve/curve_ops.c b/source/blender/editors/curve/curve_ops.c index fce6425b9be..5d637b113d8 100644 --- a/source/blender/editors/curve/curve_ops.c +++ b/source/blender/editors/curve/curve_ops.c @@ -178,9 +178,10 @@ void ED_keymap_curve(wmKeyConfig *keyconf) RNA_enum_set(WM_keymap_add_item(keymap, "FONT_OT_style_toggle", PKEY, KM_PRESS, KM_CTRL, 0)->ptr, "style", CU_CHINFO_SMALLCAPS); RNA_enum_set(WM_keymap_add_item(keymap, "FONT_OT_delete", DELKEY, KM_PRESS, 0, 0)->ptr, "type", DEL_NEXT_SEL); + RNA_enum_set(WM_keymap_add_item(keymap, "FONT_OT_delete", DELKEY, KM_PRESS, KM_CTRL, 0)->ptr, "type", DEL_NEXT_WORD); RNA_enum_set(WM_keymap_add_item(keymap, "FONT_OT_delete", BACKSPACEKEY, KM_PRESS, 0, 0)->ptr, "type", DEL_PREV_SEL); RNA_enum_set(WM_keymap_add_item(keymap, "FONT_OT_delete", BACKSPACEKEY, KM_PRESS, KM_SHIFT, 0)->ptr, "type", DEL_PREV_SEL); /* same as above [#26623] */ - RNA_enum_set(WM_keymap_add_item(keymap, "FONT_OT_delete", BACKSPACEKEY, KM_PRESS, KM_CTRL, 0)->ptr, "type", DEL_ALL); + RNA_enum_set(WM_keymap_add_item(keymap, "FONT_OT_delete", BACKSPACEKEY, KM_PRESS, KM_CTRL, 0)->ptr, "type", DEL_PREV_WORD); RNA_enum_set(WM_keymap_add_item(keymap, "FONT_OT_move", HOMEKEY, KM_PRESS, 0, 0)->ptr, "type", LINE_BEGIN); RNA_enum_set(WM_keymap_add_item(keymap, "FONT_OT_move", ENDKEY, KM_PRESS, 0, 0)->ptr, "type", LINE_END); diff --git a/source/blender/editors/curve/editcurve.c b/source/blender/editors/curve/editcurve.c index e40dde24ce2..844fcc7b379 100644 --- a/source/blender/editors/curve/editcurve.c +++ b/source/blender/editors/curve/editcurve.c @@ -91,14 +91,6 @@ typedef struct { int flag; } UndoCurve; -/* Definitions needed for shape keys */ -typedef struct { - void *orig_cv; - int key_index, nu_index, pt_index, vertex_index; - bool switched; - Nurb *orig_nu; -} CVKeyIndex; - void selectend_nurb(Object *obedit, enum eEndPoint_Types selfirst, bool doswap, bool selstatus); static void adduplicateflagNurb(Object *obedit, ListBase *newnurb, const short flag, const bool split); static int curve_delete_segments(Object *obedit, const bool split); @@ -138,9 +130,9 @@ void printknots(Object *obedit) /* ********************* Shape keys *************** */ -static CVKeyIndex *init_cvKeyIndex(void *cv, int key_index, int nu_index, int pt_index, int vertex_index, Nurb *orig_nu) +static CVKeyIndex *init_cvKeyIndex(void *cv, int key_index, int nu_index, int pt_index, int vertex_index) { - CVKeyIndex *cvIndex = MEM_callocN(sizeof(CVKeyIndex), "init_cvKeyIndex"); + CVKeyIndex *cvIndex = MEM_callocN(sizeof(CVKeyIndex), __func__); cvIndex->orig_cv = cv; cvIndex->key_index = key_index; @@ -148,7 +140,6 @@ static CVKeyIndex *init_cvKeyIndex(void *cv, int key_index, int nu_index, int pt cvIndex->pt_index = pt_index; cvIndex->vertex_index = vertex_index; cvIndex->switched = false; - cvIndex->orig_nu = orig_nu; return cvIndex; } @@ -174,7 +165,12 @@ static void init_editNurb_keyIndex(EditNurb *editnurb, ListBase *origBase) origbezt = orignu->bezt; pt_index = 0; while (a--) { - keyIndex = init_cvKeyIndex(origbezt, key_index, nu_index, pt_index, vertex_index, orignu); + /* We cannot keep *any* reference to curve obdata, + * it might be replaced and freed while editcurve remain in use (in viewport render case e.g.). + * Note that we could use a pool to avoid lots of malloc's here, but... not really a problem for now. */ + BezTriple *origbezt_cpy = MEM_mallocN(sizeof(*origbezt), __func__); + *origbezt_cpy = *origbezt; + keyIndex = init_cvKeyIndex(origbezt_cpy, key_index, nu_index, pt_index, vertex_index); BLI_ghash_insert(gh, bezt, keyIndex); key_index += 12; vertex_index += 3; @@ -189,7 +185,12 @@ static void init_editNurb_keyIndex(EditNurb *editnurb, ListBase *origBase) origbp = orignu->bp; pt_index = 0; while (a--) { - keyIndex = init_cvKeyIndex(origbp, key_index, nu_index, pt_index, vertex_index, orignu); + /* We cannot keep *any* reference to curve obdata, + * it might be replaced and freed while editcurve remain in use (in viewport render case e.g.). + * Note that we could use a pool to avoid lots of malloc's here, but... not really a problem for now. */ + BPoint *origbp_cpy = MEM_mallocN(sizeof(*origbp_cpy), __func__); + *origbp_cpy = *origbp; + keyIndex = init_cvKeyIndex(origbp_cpy, key_index, nu_index, pt_index, vertex_index); BLI_ghash_insert(gh, bp, keyIndex); key_index += 4; bp++; @@ -250,23 +251,22 @@ static int getKeyIndexOrig_keyIndex(EditNurb *editnurb, void *cv) return index->key_index; } -static void keyIndex_delCV(EditNurb *editnurb, const void *cv) +static void keyIndex_delBezt(EditNurb *editnurb, BezTriple *bezt) { if (!editnurb->keyindex) { return; } - BLI_ghash_remove(editnurb->keyindex, cv, NULL, MEM_freeN); -} - -static void keyIndex_delBezt(EditNurb *editnurb, BezTriple *bezt) -{ - keyIndex_delCV(editnurb, bezt); + BKE_curve_editNurb_keyIndex_delCV(editnurb->keyindex, bezt); } static void keyIndex_delBP(EditNurb *editnurb, BPoint *bp) { - keyIndex_delCV(editnurb, bp); + if (!editnurb->keyindex) { + return; + } + + BKE_curve_editNurb_keyIndex_delCV(editnurb->keyindex, bp); } static void keyIndex_delNurb(EditNurb *editnurb, Nurb *nu) @@ -282,7 +282,7 @@ static void keyIndex_delNurb(EditNurb *editnurb, Nurb *nu) a = nu->pntsu; while (a--) { - BLI_ghash_remove(editnurb->keyindex, bezt, NULL, MEM_freeN); + BKE_curve_editNurb_keyIndex_delCV(editnurb->keyindex, bezt); bezt++; } } @@ -291,7 +291,7 @@ static void keyIndex_delNurb(EditNurb *editnurb, Nurb *nu) a = nu->pntsu * nu->pntsv; while (a--) { - BLI_ghash_remove(editnurb->keyindex, bp, NULL, MEM_freeN); + BKE_curve_editNurb_keyIndex_delCV(editnurb->keyindex, bp); bp++; } } @@ -535,6 +535,7 @@ static GHash *dupli_keyIndexHash(GHash *keyindex) CVKeyIndex *newIndex = MEM_mallocN(sizeof(CVKeyIndex), "dupli_keyIndexHash index"); memcpy(newIndex, index, sizeof(CVKeyIndex)); + newIndex->orig_cv = MEM_dupallocN(index->orig_cv); BLI_ghash_insert(gh, cv, newIndex); } @@ -624,7 +625,7 @@ static void calc_keyHandles(ListBase *nurb, float *key) } } -static void calc_shapeKeys(Object *obedit) +static void calc_shapeKeys(Object *obedit, ListBase *newnurbs) { Curve *cu = (Curve *)obedit->data; @@ -636,7 +637,7 @@ static void calc_shapeKeys(Object *obedit) KeyBlock *actkey = BLI_findlink(&cu->key->block, editnurb->shapenr - 1); BezTriple *bezt, *oldbezt; BPoint *bp, *oldbp; - Nurb *nu; + Nurb *nu, *newnu; int totvert = BKE_nurbList_verts_count(&editnurb->nurbs); float (*ofs)[3] = NULL; @@ -706,20 +707,25 @@ static void calc_shapeKeys(Object *obedit) currkey = cu->key->block.first; while (currkey) { - int apply_offset = (ofs && (currkey != actkey) && (editnurb->shapenr - 1 == currkey->relative)); + const bool apply_offset = (ofs && (currkey != actkey) && (editnurb->shapenr - 1 == currkey->relative)); float *fp = newkey = MEM_callocN(cu->key->elemsize * totvert, "currkey->data"); ofp = oldkey = currkey->data; nu = editnurb->nurbs.first; + /* We need to restore to original curve into newnurb, *not* editcurve's nurbs. + * Otherwise, in case we update obdata *without* leaving editmode (e.g. viewport render), we would + * invalidate editcurve. */ + newnu = newnurbs->first; i = 0; while (nu) { if (currkey == actkey) { - int restore = actkey != cu->key->refkey; + const bool restore = actkey != cu->key->refkey; if (nu->bezt) { bezt = nu->bezt; a = nu->pntsu; + BezTriple *newbezt = newnu->bezt; while (a--) { int j; oldbezt = getKeyIndexOrig_bezt(editnurb, bezt); @@ -728,7 +734,7 @@ static void calc_shapeKeys(Object *obedit) copy_v3_v3(fp, bezt->vec[j]); if (restore && oldbezt) { - copy_v3_v3(bezt->vec[j], oldbezt->vec[j]); + copy_v3_v3(newbezt->vec[j], oldbezt->vec[j]); } fp += 3; @@ -736,16 +742,18 @@ static void calc_shapeKeys(Object *obedit) fp[0] = bezt->alfa; if (restore && oldbezt) { - bezt->alfa = oldbezt->alfa; + newbezt->alfa = oldbezt->alfa; } fp += 3; ++i; /* alphas */ bezt++; + newbezt++; } } else { bp = nu->bp; a = nu->pntsu * nu->pntsv; + BPoint *newbp = newnu->bp; while (a--) { oldbp = getKeyIndexOrig_bp(editnurb, bp); @@ -754,12 +762,13 @@ static void calc_shapeKeys(Object *obedit) fp[3] = bp->alfa; if (restore && oldbp) { - copy_v3_v3(bp->vec, oldbp->vec); - bp->alfa = oldbp->alfa; + copy_v3_v3(newbp->vec, oldbp->vec); + newbp->alfa = oldbp->alfa; } fp += 4; bp++; + newbp++; i += 2; } } @@ -1204,9 +1213,13 @@ void ED_curve_editnurb_load(Object *obedit) } } + /* We have to pass also new copied nurbs, since we want to restore original curve (without edited shapekey) + * on obdata, but *not* on editcurve itself (ED_curve_editnurb_load call does not always implies freeing + * of editcurve, e.g. when called to generate render data...). */ + calc_shapeKeys(obedit, &newnurb); + cu->nurb = newnurb; - calc_shapeKeys(obedit); ED_curve_updateAnimPaths(obedit->data); BKE_nurbList_free(&oldnurb); @@ -1227,13 +1240,11 @@ void ED_curve_editnurb_make(Object *obedit) if (actkey) { // XXX strcpy(G.editModeTitleExtra, "(Key) "); undo_editmode_clear(); - BKE_keyblock_convert_to_curve(actkey, cu, &cu->nurb); } if (editnurb) { BKE_nurbList_free(&editnurb->nurbs); - BKE_curve_editNurb_keyIndex_free(editnurb); - editnurb->keyindex = NULL; + BKE_curve_editNurb_keyIndex_free(&editnurb->keyindex); } else { editnurb = MEM_callocN(sizeof(EditNurb), "editnurb"); @@ -1248,12 +1259,16 @@ void ED_curve_editnurb_make(Object *obedit) nu = nu->next; } - if (actkey) - editnurb->shapenr = obedit->shapenr; - /* animation could be added in editmode even if there was no animdata in * object mode hence we always need CVs index be created */ init_editNurb_keyIndex(editnurb, &cu->nurb); + + if (actkey) { + editnurb->shapenr = obedit->shapenr; + /* Apply shapekey to new nurbs of editnurb, not those of original curve (and *after* we generated keyIndex), + * else we do not have valid 'original' data to properly restore curve when leaving editmode. */ + BKE_keyblock_convert_to_curve(actkey, cu, &editnurb->nurbs); + } } } @@ -1309,8 +1324,7 @@ static int separate_exec(bContext *C, wmOperator *op) ED_curve_editnurb_make(newob); newedit = newcu->editnurb; BKE_nurbList_free(&newedit->nurbs); - BKE_curve_editNurb_keyIndex_free(newedit); - newedit->keyindex = NULL; + BKE_curve_editNurb_keyIndex_free(&newedit->keyindex); BLI_movelisttolist(&newedit->nurbs, &newnurb); /* 4. put old object out of editmode and delete separated geometry */ @@ -4146,7 +4160,7 @@ static int make_segment_exec(bContext *C, wmOperator *op) */ bp = nu->bp; - if (bp[nu->pntsu - 1].f1 & SELECT) { + if (bp[nu->pntsu - 1].f1 & SELECT) { if (nu2 == NULL) { nu2 = nu; } @@ -4777,13 +4791,13 @@ static int ed_editcurve_addvert(Curve *cu, EditNurb *editnurb, const float locat { Nurb *nu; - float minmax[2][3]; + float center[3]; float temp[3]; - bool nu_has_select = false; - + uint verts_len; bool changed = false; - INIT_MINMAX(minmax[0], minmax[1]); + zero_v3(center); + verts_len = 0; for (nu = editnurb->nurbs.first; nu; nu = nu->next) { int i; @@ -4792,8 +4806,8 @@ static int ed_editcurve_addvert(Curve *cu, EditNurb *editnurb, const float locat for (i = 0, bezt = nu->bezt; i < nu->pntsu; i++, bezt++) { if (BEZT_ISSEL_ANY_HIDDENHANDLES(cu, bezt)) { - minmax_v3v3_v3(UNPACK2(minmax), bezt->vec[1]); - nu_has_select = true; + add_v3_v3(center, bezt->vec[1]); + verts_len += 1; } } } @@ -4802,18 +4816,18 @@ static int ed_editcurve_addvert(Curve *cu, EditNurb *editnurb, const float locat for (i = 0, bp = nu->bp; i < nu->pntsu; i++, bp++) { if (bp->f1 & SELECT) { - minmax_v3v3_v3(UNPACK2(minmax), bp->vec); - nu_has_select = true; + add_v3_v3(center, bp->vec); + verts_len += 1; } } } } - if (nu_has_select && ed_editcurve_extrude(cu, editnurb)) { - float ofs[3], center[3]; + if (verts_len && ed_editcurve_extrude(cu, editnurb)) { + float ofs[3]; int i; - mid_v3_v3v3(center, minmax[0], minmax[1]); + mul_v3_fl(center, 1.0f / (float)verts_len); sub_v3_v3v3(ofs, location_init, center); if ((cu->flag & CU_3D) == 0) { @@ -4993,7 +5007,7 @@ static int add_vertex_invoke(bContext *C, wmOperator *op, const wmEvent *event) copy_v3_v3(location, ED_view3d_cursor3d_get(vc.scene, vc.v3d)); } - ED_view3d_win_to_3d_int(vc.ar, location, event->mval, location); + ED_view3d_win_to_3d_int(vc.v3d, vc.ar, location, event->mval, location); if (use_proj) { const float mval[2] = {UNPACK2(event->mval)}; @@ -5836,6 +5850,7 @@ static int curve_dissolve_exec(bContext *C, wmOperator *UNUSED(op)) BLI_assert(points_stride + dims == points + (points_len * dims)); float tan_l[3], tan_r[3], error_sq_dummy; + unsigned int error_index_dummy; sub_v3_v3v3(tan_l, bezt_prev->vec[1], bezt_prev->vec[2]); normalize_v3(tan_l); @@ -5846,7 +5861,7 @@ static int curve_dissolve_exec(bContext *C, wmOperator *UNUSED(op)) points, points_len, NULL, dims, FLT_EPSILON, tan_l, tan_r, bezt_prev->vec[2], bezt_next->vec[0], - &error_sq_dummy); + &error_sq_dummy, &error_index_dummy); if (!ELEM(bezt_prev->h2, HD_FREE, HD_ALIGN)) { bezt_prev->h2 = (bezt_prev->h2 == HD_VECT) ? HD_FREE : HD_ALIGN; @@ -6033,6 +6048,9 @@ int join_curve_exec(bContext *C, wmOperator *op) cu = ob->data; BLI_movelisttolist(&cu->nurb, &tempbase); + /* Account for mixed 2D/3D curves when joining */ + BKE_curve_curve_dimension_update(cu); + DAG_relations_tag_update(bmain); // because we removed object(s), call before editmode! DAG_id_tag_update(&ob->id, OB_RECALC_OB | OB_RECALC_DATA); @@ -6110,7 +6128,7 @@ static void undoCurve_to_editCurve(void *ucu, void *UNUSED(edata), void *cu_v) BKE_nurbList_free(editbase); if (undoCurve->undoIndex) { - BLI_ghash_free(editnurb->keyindex, NULL, MEM_freeN); + BKE_curve_editNurb_keyIndex_free(&editnurb->keyindex); editnurb->keyindex = dupli_keyIndexHash(undoCurve->undoIndex); } @@ -6188,8 +6206,7 @@ static void free_undoCurve(void *ucv) BKE_nurbList_free(&undoCurve->nubase); - if (undoCurve->undoIndex) - BLI_ghash_free(undoCurve->undoIndex, NULL, MEM_freeN); + BKE_curve_editNurb_keyIndex_free(&undoCurve->undoIndex); free_fcurves(&undoCurve->fcurves); free_fcurves(&undoCurve->drivers); diff --git a/source/blender/editors/curve/editcurve_paint.c b/source/blender/editors/curve/editcurve_paint.c index 2d8fc76ee7e..4602945d11c 100644 --- a/source/blender/editors/curve/editcurve_paint.c +++ b/source/blender/editors/curve/editcurve_paint.c @@ -70,102 +70,6 @@ /* Distance between start/end points to consider cyclic */ #define STROKE_CYCLIC_DIST_PX 8 - -/* -------------------------------------------------------------------- */ - -/** \name Depth Utilities - * \{ */ - - -static float depth_read_zbuf(const ViewContext *vc, int x, int y) -{ - ViewDepths *vd = vc->rv3d->depths; - - if (vd && vd->depths && x > 0 && y > 0 && x < vd->w && y < vd->h) - return vd->depths[y * vd->w + x]; - else - return -1.0f; -} - -static bool depth_unproject( - const ARegion *ar, const bglMats *mats, - const int mval[2], const double depth, - float r_location_world[3]) -{ - double p[3]; - if (gluUnProject( - (double)ar->winrct.xmin + mval[0] + 0.5, - (double)ar->winrct.ymin + mval[1] + 0.5, - depth, mats->modelview, mats->projection, (const GLint *)mats->viewport, - &p[0], &p[1], &p[2])) - { - copy_v3fl_v3db(r_location_world, p); - return true; - } - return false; -} - -static bool depth_read_normal( - const ViewContext *vc, const bglMats *mats, const int mval[2], - float r_normal[3]) -{ - /* pixels surrounding */ - bool depths_valid[9] = {false}; - float coords[9][3] = {{0}}; - - ARegion *ar = vc->ar; - const ViewDepths *depths = vc->rv3d->depths; - - for (int x = 0, i = 0; x < 2; x++) { - for (int y = 0; y < 2; y++) { - const int mval_ofs[2] = {mval[0] + (x - 1), mval[1] + (y - 1)}; - - const double depth = (double)depth_read_zbuf(vc, mval_ofs[0], mval_ofs[1]); - if ((depth > depths->depth_range[0]) && (depth < depths->depth_range[1])) { - if (depth_unproject(ar, mats, mval_ofs, depth, coords[i])) { - depths_valid[i] = true; - } - } - i++; - } - } - - const int edges[2][6][2] = { - /* x edges */ - {{0, 1}, {1, 2}, - {3, 4}, {4, 5}, - {6, 7}, {7, 8}}, - /* y edges */ - {{0, 3}, {3, 6}, - {1, 4}, {4, 7}, - {2, 5}, {5, 8}}, - }; - - float cross[2][3] = {{0.0f}}; - - for (int i = 0; i < 6; i++) { - for (int axis = 0; axis < 2; axis++) { - if (depths_valid[edges[axis][i][0]] && depths_valid[edges[axis][i][1]]) { - float delta[3]; - sub_v3_v3v3(delta, coords[edges[axis][i][0]], coords[edges[axis][i][1]]); - add_v3_v3(cross[axis], delta); - } - } - } - - cross_v3_v3v3(r_normal, cross[0], cross[1]); - - if (normalize_v3(r_normal) != 0.0f) { - return true; - } - else { - return false; - } -} - -/** \} */ - - /* -------------------------------------------------------------------- */ /** \name StrokeElem / #RNA_OperatorStrokeElement Conversion Functions @@ -308,9 +212,9 @@ static bool stroke_elem_project( ((unsigned int)mval_i[0] < depths->w) && ((unsigned int)mval_i[1] < depths->h)) { - const double depth = (double)depth_read_zbuf(&cdd->vc, mval_i[0], mval_i[1]); + const double depth = (double)ED_view3d_depth_read_cached(&cdd->vc, mval_i); if ((depth > depths->depth_range[0]) && (depth < depths->depth_range[1])) { - if (depth_unproject(ar, &cdd->mats, mval_i, depth, r_location_world)) { + if (ED_view3d_depth_unproject(ar, &cdd->mats, mval_i, depth, r_location_world)) { is_location_world_set = true; if (r_normal_world) { zero_v3(r_normal_world); @@ -319,7 +223,7 @@ static bool stroke_elem_project( if (surface_offset != 0.0f) { const float offset = cdd->project.use_surface_offset_absolute ? 1.0f : radius; float normal[3]; - if (depth_read_normal(&cdd->vc, &cdd->mats, mval_i, normal)) { + if (ED_view3d_depth_read_cached_normal(&cdd->vc, &cdd->mats, mval_i, normal)) { madd_v3_v3fl(r_location_world, normal, offset * surface_offset); if (r_normal_world) { copy_v3_v3(r_normal_world, normal); @@ -353,7 +257,7 @@ static bool stroke_elem_project_fallback( surface_offset, radius, r_location_world, r_normal_world); if (is_depth_found == false) { - ED_view3d_win_to_3d(cdd->vc.ar, location_fallback_depth, mval_fl, r_location_world); + ED_view3d_win_to_3d(cdd->vc.v3d, cdd->vc.ar, location_fallback_depth, mval_fl, r_location_world); zero_v3(r_normal_local); } mul_v3_m4v3(r_location_local, cdd->vc.obedit->imat, r_location_world); @@ -627,7 +531,7 @@ static void curve_draw_event_add_first(wmOperator *op, const wmEvent *event) CURVE_PAINT_SURFACE_PLANE_NORMAL_VIEW, CURVE_PAINT_SURFACE_PLANE_NORMAL_SURFACE)) { - if (depth_read_normal(&cdd->vc, &cdd->mats, event->mval, normal)) { + if (ED_view3d_depth_read_cached_normal(&cdd->vc, &cdd->mats, event->mval, normal)) { if (cps->surface_plane == CURVE_PAINT_SURFACE_PLANE_NORMAL_VIEW) { float cross_a[3], cross_b[3]; cross_v3_v3v3(cross_a, rv3d->viewinv[2], normal); @@ -876,7 +780,7 @@ static int curve_draw_exec(bContext *C, wmOperator *op) const float radius_range = cps->radius_max - cps->radius_min; Nurb *nu = MEM_callocN(sizeof(Nurb), __func__); - nu->pntsv = 1; + nu->pntsv = 0; nu->resolu = cu->resolu; nu->resolv = cu->resolv; nu->flag |= CU_SMOOTH; @@ -1135,7 +1039,7 @@ static int curve_draw_invoke(bContext *C, wmOperator *op, const wmEvent *event) const float mval_fl[2] = {UNPACK2(event->mval)}; float center[3]; negate_v3_v3(center, cdd->vc.rv3d->ofs); - ED_view3d_win_to_3d(cdd->vc.ar, center, mval_fl, cdd->prev.location_world); + ED_view3d_win_to_3d(cdd->vc.v3d, cdd->vc.ar, center, mval_fl, cdd->prev.location_world); copy_v3_v3(cdd->prev.location_world_valid, cdd->prev.location_world); } diff --git a/source/blender/editors/curve/editfont.c b/source/blender/editors/curve/editfont.c index 57e731874b4..535e5d7bd28 100644 --- a/source/blender/editors/curve/editfont.c +++ b/source/blender/editors/curve/editfont.c @@ -1170,9 +1170,10 @@ void FONT_OT_line_break(wmOperatorType *ot) /******************* delete operator **********************/ static EnumPropertyItem delete_type_items[] = { - {DEL_ALL, "ALL", 0, "All", ""}, {DEL_NEXT_CHAR, "NEXT_CHARACTER", 0, "Next Character", ""}, {DEL_PREV_CHAR, "PREVIOUS_CHARACTER", 0, "Previous Character", ""}, + {DEL_NEXT_WORD, "NEXT_WORD", 0, "Next Word", ""}, + {DEL_PREV_WORD, "PREVIOUS_WORD", 0, "Previous Word", ""}, {DEL_SELECTION, "SELECTION", 0, "Selection", ""}, {DEL_NEXT_SEL, "NEXT_OR_SELECTION", 0, "Next or Selection", ""}, {DEL_PREV_SEL, "PREVIOUS_OR_SELECTION", 0, "Previous or Selection", ""}, @@ -1183,7 +1184,9 @@ static int delete_exec(bContext *C, wmOperator *op) Object *obedit = CTX_data_edit_object(C); Curve *cu = obedit->data; EditFont *ef = cu->editfont; - int x, selstart, selend, type = RNA_enum_get(op->ptr, "type"); + int selstart, selend, type = RNA_enum_get(op->ptr, "type"); + int range[2] = {0, 0}; + bool has_select = false; if (ef->len == 0) return OPERATOR_CANCELLED; @@ -1191,6 +1194,7 @@ static int delete_exec(bContext *C, wmOperator *op) if (BKE_vfont_select_get(obedit, &selstart, &selend)) { if (type == DEL_NEXT_SEL) type = DEL_SELECTION; else if (type == DEL_PREV_SEL) type = DEL_SELECTION; + has_select = true; } else { if (type == DEL_NEXT_SEL) type = DEL_NEXT_CHAR; @@ -1198,10 +1202,6 @@ static int delete_exec(bContext *C, wmOperator *op) } switch (type) { - case DEL_ALL: - ef->len = ef->pos = 0; - ef->textbuf[0] = 0; - break; case DEL_SELECTION: if (!kill_selection(obedit, 0)) return OPERATOR_CANCELLED; @@ -1210,29 +1210,69 @@ static int delete_exec(bContext *C, wmOperator *op) if (ef->pos <= 0) return OPERATOR_CANCELLED; - for (x = ef->pos; x <= ef->len; x++) - ef->textbuf[x - 1] = ef->textbuf[x]; - for (x = ef->pos; x <= ef->len; x++) - ef->textbufinfo[x - 1] = ef->textbufinfo[x]; + range[0] = ef->pos - 1; + range[1] = ef->pos; ef->pos--; - ef->textbuf[--ef->len] = '\0'; break; case DEL_NEXT_CHAR: if (ef->pos >= ef->len) return OPERATOR_CANCELLED; - for (x = ef->pos; x < ef->len; x++) - ef->textbuf[x] = ef->textbuf[x + 1]; - for (x = ef->pos; x < ef->len; x++) - ef->textbufinfo[x] = ef->textbufinfo[x + 1]; + range[0] = ef->pos; + range[1] = ef->pos + 1; + break; + case DEL_NEXT_WORD: + { + int pos = ef->pos; + BLI_str_cursor_step_wchar(ef->textbuf, ef->len, &pos, STRCUR_DIR_NEXT, STRCUR_JUMP_DELIM, true); + range[0] = ef->pos; + range[1] = pos; + break; + } - ef->textbuf[--ef->len] = '\0'; + case DEL_PREV_WORD: + { + int pos = ef->pos; + BLI_str_cursor_step_wchar(ef->textbuf, ef->len, &pos, STRCUR_DIR_PREV, STRCUR_JUMP_DELIM, true); + range[0] = pos; + range[1] = ef->pos; + ef->pos = pos; break; + } default: return OPERATOR_CANCELLED; } + if (range[0] != range[1]) { + BLI_assert(range[0] < range[1]); + int len_remove = range[1] - range[0]; + int len_tail = ef->len - range[1]; + if (has_select) { + for (int i = 0; i < 2; i++) { + int *sel = i ? &ef->selend : &ef->selstart; + if (*sel <= range[0]) { + /* pass */ + } + else if (*sel >= range[1]) { + *sel -= len_remove; + } + else if (*sel < range[1]) { + /* pass */ + *sel = range[0]; + } + } + } + + memmove(&ef->textbuf[range[0]], &ef->textbuf[range[1]], sizeof(*ef->textbuf) * len_tail); + memmove(&ef->textbufinfo[range[0]], &ef->textbufinfo[range[1]], sizeof(*ef->textbufinfo) * len_tail); + + ef->len -= len_remove; + ef->textbuf[ef->len] = '\0'; + + BKE_vfont_select_clamp(obedit); + } + text_update_edited(C, obedit, FO_EDIT); return OPERATOR_FINISHED; @@ -1253,7 +1293,7 @@ void FONT_OT_delete(wmOperatorType *ot) ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO; /* properties */ - RNA_def_enum(ot->srna, "type", delete_type_items, DEL_ALL, "Type", "Which part of the text to delete"); + RNA_def_enum(ot->srna, "type", delete_type_items, DEL_PREV_CHAR, "Type", "Which part of the text to delete"); } /*********************** insert text operator *************************/ |