Commit: 642b77ef0e394baf090b417f93c094093c885aa6
Author: Campbell Barton
Date:   Wed Dec 23 05:04:52 2015 +1100
Branches: master
https://developer.blender.org/rB642b77ef0e394baf090b417f93c094093c885aa6

Fix T31605: Nupad ignores Rotate around selection

Add support for smooth-view orbiting a point besides the view center.

===================================================================

M       source/blender/editors/space_view3d/view3d_edit.c
M       source/blender/editors/space_view3d/view3d_intern.h
M       source/blender/editors/space_view3d/view3d_view.c

===================================================================

diff --git a/source/blender/editors/space_view3d/view3d_edit.c 
b/source/blender/editors/space_view3d/view3d_edit.c
index c45e3aa..84ab52f 100644
--- a/source/blender/editors/space_view3d/view3d_edit.c
+++ b/source/blender/editors/space_view3d/view3d_edit.c
@@ -609,18 +609,18 @@ static void viewops_data_alloc(bContext *C, wmOperator 
*op)
        vod->rv3d = vod->ar->regiondata;
 }
 
-static void view3d_orbit_apply_dyn_ofs(
-        float r_ofs[3], const float dyn_ofs[3],
-        const float oldquat[4], const float viewquat[4])
+void view3d_orbit_apply_dyn_ofs(
+        float r_ofs[3], const float ofs_old[3], const float viewquat_old[4],
+        const float viewquat_new[4], const float dyn_ofs[3])
 {
-       float q1[4];
-       invert_qt_qt_normalized(q1, oldquat);
-       mul_qt_qtqt(q1, q1, viewquat);
+       float q[4];
+       invert_qt_qt_normalized(q, viewquat_old);
+       mul_qt_qtqt(q, q, viewquat_new);
 
-       invert_qt_normalized(q1);
+       invert_qt_normalized(q);
 
-       sub_v3_v3(r_ofs, dyn_ofs);
-       mul_qt_v3(q1, r_ofs);
+       sub_v3_v3v3(r_ofs, ofs_old, dyn_ofs);
+       mul_qt_v3(q, r_ofs);
        add_v3_v3(r_ofs, dyn_ofs);
 }
 
@@ -910,12 +910,11 @@ void viewrotate_modal_keymap(wmKeyConfig *keyconf)
 
 }
 
-static void viewrotate_apply_dyn_ofs(ViewOpsData *vod, const float viewquat[4])
+static void viewrotate_apply_dyn_ofs(ViewOpsData *vod, const float 
viewquat_new[4])
 {
        if (vod->use_dyn_ofs) {
                RegionView3D *rv3d = vod->rv3d;
-               copy_v3_v3(rv3d->ofs, vod->ofs);
-               view3d_orbit_apply_dyn_ofs(rv3d->ofs, vod->dyn_ofs, 
vod->oldquat, viewquat);
+               view3d_orbit_apply_dyn_ofs(rv3d->ofs, vod->ofs, vod->oldquat, 
viewquat_new, vod->dyn_ofs);
        }
 }
 
@@ -3807,10 +3806,21 @@ static void axis_set_view(bContext *C, View3D *v3d, 
ARegion *ar,
                        &(const V3D_SmoothParams){.ofs = ofs, .quat = quat, 
.dist = &dist});
        }
        else {
+               /* rotate around selection */
+               const float *dyn_ofs_pt = NULL;
+               float dyn_ofs[3];
+
+               if (U.uiflag & USER_ORBIT_SELECTION) {
+                       if (view3d_orbit_calc_center(C, dyn_ofs)) {
+                               negate_v3(dyn_ofs);
+                               dyn_ofs_pt = dyn_ofs;
+                       }
+               }
+
                /* no camera involved */
                ED_view3d_smooth_view(
                        C, v3d, ar, smooth_viewtx,
-                       &(const V3D_SmoothParams){.quat = quat});
+                       &(const V3D_SmoothParams){.quat = quat, .dyn_ofs = 
dyn_ofs_pt});
        }
 }
 
@@ -3984,8 +3994,6 @@ static int vieworbit_exec(bContext *C, wmOperator *op)
                        int smooth_viewtx = WM_operator_smooth_viewtx_get(op);
                        float quat_mul[4];
                        float quat_new[4];
-                       float ofs_new[3];
-                       float *ofs_new_pt = NULL;
 
                        if (view_opposite == RV3D_VIEW_USER) {
                                view3d_ensure_persp(v3d, ar);
@@ -4020,25 +4028,19 @@ static int vieworbit_exec(bContext *C, wmOperator *op)
                                rv3d->view = RV3D_VIEW_USER;
                        }
 
-                       if (U.uiflag & USER_ORBIT_SELECTION) {
-                               float dyn_ofs[3];
 
-                               view3d_orbit_calc_center(C, dyn_ofs);
-                               negate_v3(dyn_ofs);
-
-                               copy_v3_v3(ofs_new, rv3d->ofs);
-
-                               view3d_orbit_apply_dyn_ofs(ofs_new, dyn_ofs, 
rv3d->viewquat, quat_new);
-                               ofs_new_pt = ofs_new;
+                       float dyn_ofs[3], *dyn_ofs_pt = NULL;
 
-                               /* disable smoothview in this case
-                                * although it works OK, it looks a little odd. 
*/
-                               smooth_viewtx = 0;
+                       if (U.uiflag & USER_ORBIT_SELECTION) {
+                               if (view3d_orbit_calc_center(C, dyn_ofs)) {
+                                       negate_v3(dyn_ofs);
+                                       dyn_ofs_pt = dyn_ofs;
+                               }
                        }
 
                        ED_view3d_smooth_view(
                                C, v3d, ar, smooth_viewtx,
-                               &(const V3D_SmoothParams){.ofs = ofs_new_pt, 
.quat = quat_new});
+                               &(const V3D_SmoothParams){.quat = quat_new, 
.dyn_ofs = dyn_ofs_pt});
 
                        return OPERATOR_FINISHED;
                }
diff --git a/source/blender/editors/space_view3d/view3d_intern.h 
b/source/blender/editors/space_view3d/view3d_intern.h
index 52b14d67..855c8a9 100644
--- a/source/blender/editors/space_view3d/view3d_intern.h
+++ b/source/blender/editors/space_view3d/view3d_intern.h
@@ -106,6 +106,10 @@ void VIEW3D_OT_zoom_border(struct wmOperatorType *ot);
 
 void view3d_boxview_copy(ScrArea *sa, ARegion *ar);
 
+void view3d_orbit_apply_dyn_ofs(
+        float r_ofs[3], const float ofs_old[3], const float viewquat_old[4],
+        const float viewquat_new[4], const float dyn_ofs[3]);
+
 void view3d_ndof_fly(
         const struct wmNDOFMotionData *ndof,
         struct View3D *v3d, struct RegionView3D *rv3d,
@@ -211,6 +215,8 @@ bool ED_view3d_boundbox_clip(RegionView3D *rv3d, const 
struct BoundBox *bb);
 typedef struct V3D_SmoothParams {
        struct Object *camera_old, *camera;
        const float *ofs, *quat, *dist, *lens;
+       /* alternate rotation center (ofs = must be NULL) */
+       const float *dyn_ofs;
 } V3D_SmoothParams;
 
 void ED_view3d_smooth_view_ex(
diff --git a/source/blender/editors/space_view3d/view3d_view.c 
b/source/blender/editors/space_view3d/view3d_view.c
index 1201f70..1b1ebc9 100644
--- a/source/blender/editors/space_view3d/view3d_view.c
+++ b/source/blender/editors/space_view3d/view3d_view.c
@@ -138,6 +138,9 @@ struct SmoothView3DStore {
 
        bool to_camera;
 
+       bool use_dyn_ofs;
+       float dyn_ofs[3];
+
        /* When smooth-view is enabled, store the 'rv3d->view' here,
         * assign back when the view motion is completed. */
        char org_view;
@@ -211,6 +214,17 @@ void ED_view3d_smooth_view_ex(
        if (sview->lens)
                sms.dst.lens = *sview->lens;
 
+       if (sview->dyn_ofs) {
+               BLI_assert(sview->ofs  == NULL);
+               BLI_assert(sview->quat != NULL);
+
+               copy_v3_v3(sms.dyn_ofs, sview->dyn_ofs);
+               sms.use_dyn_ofs = true;
+
+               /* calcualte the final destination offset */
+               view3d_orbit_apply_dyn_ofs(sms.dst.ofs, sms.src.ofs, 
sms.src.quat, sms.dst.quat, sms.dyn_ofs);
+       }
+
        if (sview->camera) {
                sms.dst.dist = ED_view3d_offset_distance(sview->camera->obmat, 
sview->ofs, VIEW3D_DIST_FALLBACK);
                ED_view3d_from_object(sview->camera, sms.dst.ofs, sms.dst.quat, 
&sms.dst.dist, &sms.dst.lens);
@@ -380,8 +394,14 @@ static int view3d_smoothview_invoke(bContext *C, 
wmOperator *UNUSED(op), const w
 
                step_inv = 1.0f - step;
 
-               interp_v3_v3v3(rv3d->ofs,      sms->src.ofs,  sms->dst.ofs,  
step);
                interp_qt_qtqt(rv3d->viewquat, sms->src.quat, sms->dst.quat, 
step);
+
+               if (sms->use_dyn_ofs) {
+                       view3d_orbit_apply_dyn_ofs(rv3d->ofs, sms->src.ofs, 
sms->src.quat, rv3d->viewquat, sms->dyn_ofs);
+               }
+               else {
+                       interp_v3_v3v3(rv3d->ofs, sms->src.ofs,  sms->dst.ofs,  
step);
+               }
                
                rv3d->dist = sms->dst.dist * step + sms->src.dist * step_inv;
                v3d->lens  = sms->dst.lens * step + sms->src.lens * step_inv;

_______________________________________________
Bf-blender-cvs mailing list
[email protected]
http://lists.blender.org/mailman/listinfo/bf-blender-cvs

Reply via email to