Fix #145525: Scene switch should not affect viewport perspective mode
The existing behaviour traces back from pre-2.5 era. It seems like a general sanitization technique for any operator which may change the view transformation. While it still makes sense to switch to PERSPECTIVE mode when actively calling a view operator, I don't think the same should be said by simply switching the active scene. This PR makes it so a temporary flag is set when switching to a scene that has no camera. This flag is kept around until we deliberately change perspective mode. We can eventually make it so the flag is reset again in more occasions. But the patch is good as it is. Ref: !146364
This commit is contained in:
@@ -1453,33 +1453,41 @@ static void screen_set_3dview_camera(Scene *scene,
|
||||
ScrArea *area,
|
||||
View3D *v3d)
|
||||
{
|
||||
/* fix any cameras that are used in the 3d view but not in the scene */
|
||||
/* Fix any cameras that are used in the 3d view but not in the scene. */
|
||||
BKE_screen_view3d_sync(v3d, scene);
|
||||
|
||||
BKE_view_layer_synced_ensure(scene, view_layer);
|
||||
if (!v3d->camera || !BKE_view_layer_base_find(view_layer, v3d->camera)) {
|
||||
v3d->camera = BKE_view_layer_camera_find(scene, view_layer);
|
||||
// XXX if (screen == curscreen) handle_view3d_lock();
|
||||
}
|
||||
ListBase *regionbase;
|
||||
|
||||
/* regionbase is in different place depending if space is active. */
|
||||
if (v3d == area->spacedata.first) {
|
||||
regionbase = &area->regionbase;
|
||||
}
|
||||
else {
|
||||
regionbase = &v3d->regionbase;
|
||||
}
|
||||
|
||||
LISTBASE_FOREACH (ARegion *, region, regionbase) {
|
||||
if (region->regiontype != RGN_TYPE_WINDOW) {
|
||||
continue;
|
||||
}
|
||||
RegionView3D *rv3d = static_cast<RegionView3D *>(region->regiondata);
|
||||
/* Keep the information about RV3D_CAMOB even when no camera can be found.
|
||||
* This prevents jumping off the camera view while scrubbing through the
|
||||
* Sequencer with some Scene strips without scene. */
|
||||
if (!v3d->camera) {
|
||||
ListBase *regionbase;
|
||||
|
||||
/* regionbase is in different place depending if space is active */
|
||||
if (v3d == area->spacedata.first) {
|
||||
regionbase = &area->regionbase;
|
||||
}
|
||||
else {
|
||||
regionbase = &v3d->regionbase;
|
||||
}
|
||||
|
||||
LISTBASE_FOREACH (ARegion *, region, regionbase) {
|
||||
if (region->regiontype == RGN_TYPE_WINDOW) {
|
||||
RegionView3D *rv3d = static_cast<RegionView3D *>(region->regiondata);
|
||||
if (rv3d->persp == RV3D_CAMOB) {
|
||||
rv3d->persp = RV3D_PERSP;
|
||||
}
|
||||
}
|
||||
if (rv3d->persp == RV3D_CAMOB) {
|
||||
rv3d->persp = RV3D_PERSP;
|
||||
rv3d->rflag |= RV3D_WAS_CAMOB;
|
||||
}
|
||||
}
|
||||
else if ((rv3d->rflag & RV3D_WAS_CAMOB) != 0) {
|
||||
rv3d->persp = RV3D_CAMOB;
|
||||
rv3d->rflag &= ~RV3D_WAS_CAMOB;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -5020,6 +5020,7 @@ static void region_quadview_init_rv3d(
|
||||
ScrArea *area, ARegion *region, const char viewlock, const char view, const char persp)
|
||||
{
|
||||
RegionView3D *rv3d = static_cast<RegionView3D *>(region->regiondata);
|
||||
rv3d->rflag &= ~RV3D_WAS_CAMOB;
|
||||
|
||||
if (persp == RV3D_CAMOB) {
|
||||
ED_view3d_lastview_store(rv3d);
|
||||
|
||||
@@ -498,6 +498,7 @@ static wmOperatorStatus viewpersportho_exec(bContext *C, wmOperator * /*op*/)
|
||||
else {
|
||||
rv3d->persp = RV3D_PERSP;
|
||||
}
|
||||
rv3d->rflag &= ~RV3D_WAS_CAMOB;
|
||||
ED_region_tag_redraw(region);
|
||||
}
|
||||
|
||||
|
||||
@@ -445,12 +445,12 @@ enum {
|
||||
RV3D_NAVIGATING = 1 << 3,
|
||||
RV3D_GPULIGHT_UPDATE = 1 << 4,
|
||||
RV3D_PAINTING = 1 << 5,
|
||||
// RV3D_IS_GAME_ENGINE = 1 << 5, /* UNUSED */
|
||||
/**
|
||||
* Disable Z-buffer offset, skip calls to #ED_view3d_polygon_offset.
|
||||
* Use when precise surface depth is needed and picking bias isn't, see #45434).
|
||||
*/
|
||||
RV3D_ZOFFSET_DISABLED = 1 << 6,
|
||||
RV3D_WAS_CAMOB = 1 << 7,
|
||||
};
|
||||
|
||||
/** #RegionView3D.viewlock */
|
||||
|
||||
Reference in New Issue
Block a user