diff options
author | Campbell Barton <ideasman42@gmail.com> | 2008-03-20 23:03:13 +0300 |
---|---|---|
committer | Campbell Barton <ideasman42@gmail.com> | 2008-03-20 23:03:13 +0300 |
commit | 107bed017092bb3f0692a8aae22c3d9e6c51d5ad (patch) | |
tree | cb835b90bd74fd145185cfa99ac9349fc8fc366a | |
parent | af8c68ddc4a67b9c329d15b540a1bc0f07d98838 (diff) |
shift+b zoom in perspective mode, (apricot feature for better navigation on large maps)
-rw-r--r-- | source/blender/include/BSE_drawview.h | 2 | ||||
-rw-r--r-- | source/blender/src/drawview.c | 63 | ||||
-rw-r--r-- | source/blender/src/editview.c | 79 |
3 files changed, 135 insertions, 9 deletions
diff --git a/source/blender/include/BSE_drawview.h b/source/blender/include/BSE_drawview.h index c425cbc62ea..294c0ceb047 100644 --- a/source/blender/include/BSE_drawview.h +++ b/source/blender/include/BSE_drawview.h @@ -59,6 +59,8 @@ unsigned int sample_backbuf_rect(short mval[2], int size, unsigned int min, unsi void drawview3dspace(struct ScrArea *sa, void *spacedata); void drawview3d_render(struct View3D *v3d, int winx, int winy, float winmat[][4]); +void draw_depth(struct ScrArea *sa, void *spacedata); +void view3d_update_depths(struct View3D *v3d); int update_time(void); void calc_viewborder(struct View3D *v3d, struct rctf *viewborder_r); diff --git a/source/blender/src/drawview.c b/source/blender/src/drawview.c index 608aca7bfa1..66a33987a02 100644 --- a/source/blender/src/drawview.c +++ b/source/blender/src/drawview.c @@ -2889,6 +2889,69 @@ static void draw_sculpt_depths(View3D *v3d) } } +void draw_depth(ScrArea *sa, void *spacedata) +{ + View3D *v3d= spacedata; + Base *base; + Scene *sce; + short drawtype; + + /* temp set drawtype to solid */ + drawtype = v3d->drawtype; + v3d->drawtype = OB_SOLID; + + + setwinmatrixview3d(sa->winx, sa->winy, NULL); /* 0= no pick rect */ + setviewmatrixview3d(); /* note: calls where_is_object for camera... */ + + Mat4MulMat4(v3d->persmat, v3d->viewmat, sa->winmat); + Mat4Invert(v3d->persinv, v3d->persmat); + Mat4Invert(v3d->viewinv, v3d->viewmat); + + glClear(GL_DEPTH_BUFFER_BIT); + + myloadmatrix(v3d->viewmat); + persp(PERSP_STORE); // store correct view for persp(PERSP_VIEW) calls + + if(v3d->flag & V3D_CLIPPING) { + view3d_set_clipping(v3d); + } + + v3d->zbuf= TRUE; + glEnable(GL_DEPTH_TEST); + + /* draw set first */ + if(G.scene->set) { + for(SETLOOPER(G.scene->set, base)) { + + if(v3d->lay & base->lay) { + + /*BIF_ThemeColorBlend(TH_WIRE, TH_BACK, 0.6f);*/ /* not needed for depths */ + + draw_object(base, DRAW_CONSTCOLOR); + + if(base->object->transflag & OB_DUPLI) { + draw_dupli_objects_color(v3d, base, TH_WIRE); + } + } + } + } + + /* then draw not selected and the duplis, but skip editmode object */ + for(base= G.scene->base.first; base; base= base->next) { + if(v3d->lay & base->lay) { + + /* dupli drawing */ + if(base->object->transflag & OB_DUPLI) { + draw_dupli_objects(v3d, base); + } + draw_object(base, 0); + } + } + + v3d->drawtype = drawtype; +} + static void draw_viewport_fps(ScrArea *sa); diff --git a/source/blender/src/editview.c b/source/blender/src/editview.c index edaec5fb268..42e438b2022 100644 --- a/source/blender/src/editview.c +++ b/source/blender/src/editview.c @@ -2197,13 +2197,75 @@ void view3d_border_zoom(void) float new_dist; float new_ofs[3]; - /* doesn't work fine for perspective */ - if(G.vd->persp==1) - return; - val = get_border(&rect, 3); //box select input - if(val) - { + if(!val) return; + + if (G.vd->persp==1) { /* perspective */ + View3D *v3d = G.vd; + bglMats mats; + float depth, depth_close= MAXFLOAT; + double cent[2], p[3], p_corner[3]; + int xs, ys, had_depth = 0; + + /* convert border to 3d coordinates */ + bgl_get_mats(&mats); + + draw_depth(curarea, (void *)v3d); + + /* force updating */ + if (v3d->depths) { + had_depth = 1; + v3d->depths->damaged = 1; + } + + view3d_update_depths(v3d); + + /* Constrain rect to depth bounds */ + if (rect.xmin < 0) rect.xmin = 0; + if (rect.ymin < 0) rect.ymin = 0; + if (rect.xmax >= G.vd->depths->w) rect.xmax = G.vd->depths->w-1; + if (rect.ymax >= G.vd->depths->h) rect.ymax = G.vd->depths->h-1; + + for (xs=rect.xmin; xs < rect.xmax; xs++) { + for (ys=rect.ymin; ys < rect.ymax; ys++) { + depth= v3d->depths->depths[ys*v3d->depths->w+xs]; + if(depth < v3d->depths->depth_range[1] && depth > v3d->depths->depth_range[0]) { + if (depth_close > depth) { + depth_close = depth; + } + } + } + } + + if (had_depth==0) { + MEM_freeN(v3d->depths->depths); + v3d->depths->depths = NULL; + } + v3d->depths->damaged = 1; + + /* no depths to use*/ + if (depth_close==MAXFLOAT) + return; + + cent[0] = (((double)rect.xmin)+((double)rect.xmax)) / 2; + cent[1] = (((double)rect.ymin)+((double)rect.ymax)) / 2; + + if (( !gluUnProject(cent[0], cent[1], depth_close, mats.modelview, mats.projection, mats.viewport, &p[0], &p[1], &p[2])) || + ( !gluUnProject((double)rect.xmin, (double)rect.ymin, depth_close, mats.modelview, mats.projection, mats.viewport, &p_corner[0], &p_corner[1], &p_corner[2]))) + return; + + dvec[0] = p[0]-p_corner[0]; + dvec[1] = p[1]-p_corner[1]; + dvec[2] = p[2]-p_corner[2]; + + new_dist = VecLength(dvec); + if(new_dist <= G.vd->near*1.5) new_dist= G.vd->near*1.5; + + new_ofs[0] = -p[0]; + new_ofs[1] = -p[1]; + new_ofs[2] = -p[2]; + + } else { /* othographic */ /* find the current window width and height */ vb[0] = G.vd->area->winx; vb[1] = G.vd->area->winy; @@ -2228,10 +2290,9 @@ void view3d_border_zoom(void) /* zoom in as required, or as far as we can go */ new_dist = ((new_dist*scale) >= 0.001*G.vd->grid)? new_dist*scale:0.001*G.vd->grid; - - smooth_view(G.vd, new_ofs, NULL, &new_dist, NULL); - } + + smooth_view(G.vd, new_ofs, NULL, &new_dist, NULL); } void fly(void) |