mirror of
https://github.com/NGSolve/netgen.git
synced 2025-04-09 06:47:28 +05:00
Merge branch 'faster_dbl_click' into 'master'
Speed up face/point selection in mesh scene See merge request ngsolve/netgen!564
This commit is contained in:
commit
9180f9b972
@ -77,9 +77,11 @@ namespace netgen
|
|||||||
int VisualScene :: locpi;
|
int VisualScene :: locpi;
|
||||||
int VisualScene :: seledge;
|
int VisualScene :: seledge;
|
||||||
|
|
||||||
int VisualScene :: selecttimestamp;
|
|
||||||
optional<Point<3>> VisualScene :: marker = nullopt;
|
optional<Point<3>> VisualScene :: marker = nullopt;
|
||||||
|
|
||||||
|
int VisualScene :: subdivision_timestamp = -1;
|
||||||
|
int VisualScene :: subdivisions = 2;
|
||||||
|
|
||||||
int VisualScene :: viewport[4];
|
int VisualScene :: viewport[4];
|
||||||
|
|
||||||
VisualizationParameters :: VisualizationParameters()
|
VisualizationParameters :: VisualizationParameters()
|
||||||
|
@ -31,9 +31,10 @@ namespace netgen
|
|||||||
static int locpi;
|
static int locpi;
|
||||||
static int NGGUI_API seledge;
|
static int NGGUI_API seledge;
|
||||||
|
|
||||||
static int selecttimestamp;
|
|
||||||
static optional<Point<3>> marker;
|
static optional<Point<3>> marker;
|
||||||
|
|
||||||
|
static int subdivision_timestamp;
|
||||||
|
static int subdivisions;
|
||||||
public:
|
public:
|
||||||
static int viewport[4];
|
static int viewport[4];
|
||||||
static GLuint coltexname;
|
static GLuint coltexname;
|
||||||
@ -126,35 +127,54 @@ namespace netgen
|
|||||||
|
|
||||||
class VisualSceneMesh : public VisualScene
|
class VisualSceneMesh : public VisualScene
|
||||||
{
|
{
|
||||||
int filledlist;
|
int filledlist = 0;
|
||||||
int linelist;
|
int linelist = 0;
|
||||||
int edgelist;
|
int edgelist = 0;
|
||||||
int pointnumberlist;
|
int pointnumberlist = 0;
|
||||||
|
|
||||||
int tetlist;
|
int tetlist = 0;
|
||||||
int prismlist;
|
int prismlist = 0;
|
||||||
int pyramidlist;
|
int pyramidlist = 0;
|
||||||
int hexlist;
|
int hexlist = 0;
|
||||||
|
|
||||||
int badellist;
|
int badellist = 0;
|
||||||
int identifiedlist;
|
int identifiedlist = 0;
|
||||||
int domainsurflist;
|
int domainsurflist = 0;
|
||||||
|
|
||||||
int vstimestamp;//, selecttimestamp;
|
int vstimestamp = -1;
|
||||||
int filledtimestamp;
|
int filledtimestamp = -1;
|
||||||
int linetimestamp;
|
int linetimestamp = -1;
|
||||||
int edgetimestamp;
|
int edgetimestamp = -1;
|
||||||
int pointnumbertimestamp;
|
int pointnumbertimestamp = -1;
|
||||||
|
|
||||||
int tettimestamp;
|
int tettimestamp = -1;
|
||||||
int prismtimestamp;
|
int prismtimestamp = -1;
|
||||||
int pyramidtimestamp;
|
int pyramidtimestamp = -1;
|
||||||
int hextimestamp;
|
int hextimestamp = -1;
|
||||||
|
|
||||||
int badeltimestamp;
|
int badeltimestamp = -1;
|
||||||
int identifiedtimestamp;
|
int identifiedtimestamp = -1;
|
||||||
int domainsurftimestamp;
|
int domainsurftimestamp = -1;
|
||||||
|
|
||||||
|
struct {
|
||||||
|
unsigned texture = -1;
|
||||||
|
int width = 0;
|
||||||
|
int height = 0;
|
||||||
|
int size = 0;
|
||||||
|
} colors;
|
||||||
|
|
||||||
|
struct {
|
||||||
|
unsigned framebuffer = 0;
|
||||||
|
unsigned render_buffers[2];
|
||||||
|
unsigned width = 0;
|
||||||
|
unsigned height = 0;
|
||||||
|
unsigned x = 0;
|
||||||
|
unsigned y = 0;
|
||||||
|
int list = 0;
|
||||||
|
int list_timestamp = -1;
|
||||||
|
double projmat[16];
|
||||||
|
int viewport[4];
|
||||||
|
} select;
|
||||||
|
|
||||||
#ifdef PARALLELGL
|
#ifdef PARALLELGL
|
||||||
NgArray<int> par_linelists;
|
NgArray<int> par_linelists;
|
||||||
@ -200,7 +220,9 @@ namespace netgen
|
|||||||
{ return selelement; }
|
{ return selelement; }
|
||||||
NGGUI_API int SelectedPoint () const
|
NGGUI_API int SelectedPoint () const
|
||||||
{ return selpoint; }
|
{ return selpoint; }
|
||||||
void BuildFilledList (bool names);
|
void BuildFilledList (bool select);
|
||||||
|
void BuildColorTexture();
|
||||||
|
void SelectCenter(int zoomall);
|
||||||
// private:
|
// private:
|
||||||
void BuildLineList();
|
void BuildLineList();
|
||||||
void BuildEdgeList();
|
void BuildEdgeList();
|
||||||
@ -215,7 +237,9 @@ namespace netgen
|
|||||||
void BuildIdentifiedList();
|
void BuildIdentifiedList();
|
||||||
void BuildDomainSurfList();
|
void BuildDomainSurfList();
|
||||||
|
|
||||||
bool Unproject (int px, int py, Point<3> &p);
|
bool SelectSurfaceElement (int px, int py, Point<3> &p, bool select_on_clipping_plane);
|
||||||
|
bool Unproject(int px, int py, Point<3> &p);
|
||||||
|
ngcore::INT<2> Project(Point<3> p);
|
||||||
};
|
};
|
||||||
|
|
||||||
NGGUI_API extern VisualSceneMesh vsmesh;
|
NGGUI_API extern VisualSceneMesh vsmesh;
|
||||||
|
File diff suppressed because it is too large
Load Diff
@ -791,35 +791,7 @@ namespace netgen
|
|||||||
if (mesh->GetTimeStamp() > surfeltimestamp || zoomall)
|
if (mesh->GetTimeStamp() > surfeltimestamp || zoomall)
|
||||||
{
|
{
|
||||||
// mesh has changed
|
// mesh has changed
|
||||||
|
vsmesh.SelectCenter(zoomall);
|
||||||
Point3d pmin, pmax;
|
|
||||||
static double oldrad = 0;
|
|
||||||
|
|
||||||
mesh->GetBox (pmin, pmax, -1);
|
|
||||||
if(vispar.use_center_coords && zoomall == 2)
|
|
||||||
{
|
|
||||||
center.X() = vispar.centerx;
|
|
||||||
center.Y() = vispar.centery;
|
|
||||||
center.Z() = vispar.centerz;
|
|
||||||
}
|
|
||||||
else if(selpoint >= 1 && zoomall == 2)
|
|
||||||
center = mesh->Point(selpoint);
|
|
||||||
else if(vispar.centerpoint >= 1 && zoomall == 2)
|
|
||||||
center = mesh->Point(vispar.centerpoint);
|
|
||||||
else
|
|
||||||
center = Center (pmin, pmax);
|
|
||||||
rad = 0.5 * Dist (pmin, pmax);
|
|
||||||
if(rad == 0) rad = 1e-6;
|
|
||||||
|
|
||||||
glEnable (GL_NORMALIZE);
|
|
||||||
|
|
||||||
if (rad > 1.2 * oldrad ||
|
|
||||||
mesh->GetMajorTimeStamp() > surfeltimestamp ||
|
|
||||||
zoomall)
|
|
||||||
{
|
|
||||||
CalcTransformationMatrices();
|
|
||||||
oldrad = rad;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
DrawSurfaceElements();
|
DrawSurfaceElements();
|
||||||
@ -4775,6 +4747,7 @@ namespace netgen
|
|||||||
auto printScalValue = [&formatComplex]
|
auto printScalValue = [&formatComplex]
|
||||||
(SolData & sol, int comp, double value, double imag=0., bool iscomplex=false)
|
(SolData & sol, int comp, double value, double imag=0., bool iscomplex=false)
|
||||||
{
|
{
|
||||||
|
cout << '\t';
|
||||||
if(sol.components>1)
|
if(sol.components>1)
|
||||||
{
|
{
|
||||||
if(comp==0)
|
if(comp==0)
|
||||||
@ -4806,91 +4779,79 @@ namespace netgen
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
// Check if clipping plane is drawn at current mouse cursor position
|
|
||||||
if(dim==3 && clipsolution && vispar.clipping.enable)
|
|
||||||
{
|
|
||||||
GLint viewport[4];
|
|
||||||
GLdouble projection[16];
|
|
||||||
glGetDoublev(GL_PROJECTION_MATRIX, &projection[0]);
|
|
||||||
|
|
||||||
glGetIntegerv(GL_VIEWPORT, &viewport[0]);
|
|
||||||
|
|
||||||
int hy = viewport[3]-py;
|
|
||||||
|
|
||||||
// manually intersect the view vector with the clipping plane (also working if clipping vectors are shown)
|
|
||||||
Point<3> p_clipping_plane;
|
|
||||||
gluUnProject(px, hy, 1.0, transformationmat, projection, viewport,
|
|
||||||
&p_clipping_plane[0], &p_clipping_plane[1], &p_clipping_plane[2]);
|
|
||||||
|
|
||||||
Point<3> eye;
|
|
||||||
gluUnProject( (viewport[2]-viewport[0])/2 , (viewport[3]-viewport[1])/2,
|
|
||||||
0.0, transformationmat, projection, viewport, &eye[0], &eye[1], &eye[2]);
|
|
||||||
|
|
||||||
Vec<3> n{vispar.clipping.normal};
|
|
||||||
n.Normalize();
|
|
||||||
Vec<3> view = p_clipping_plane-eye;
|
|
||||||
|
|
||||||
// check if we look at the clipping plane from the right direction
|
|
||||||
if(n*view > 1e-8)
|
|
||||||
{
|
|
||||||
double lam = vispar.clipping.dist - Vec<3>{eye}*n;
|
|
||||||
lam /= n*view;
|
|
||||||
p_clipping_plane = eye + lam*view;
|
|
||||||
|
|
||||||
double lami[3];
|
|
||||||
if(auto el3d = mesh->GetElementOfPoint( p_clipping_plane, lami ))
|
|
||||||
{
|
|
||||||
cout << endl << "Selected point " << p_clipping_plane << " on clipping plane" << endl;
|
|
||||||
marker = p_clipping_plane;
|
|
||||||
|
|
||||||
bool have_scal_func = scalfunction!=-1 && soldata[scalfunction]->draw_volume;
|
|
||||||
bool have_vec_func = vecfunction!=-1 && soldata[vecfunction]->draw_volume;
|
|
||||||
|
|
||||||
if(have_scal_func)
|
|
||||||
{
|
|
||||||
auto & sol = *soldata[scalfunction];
|
|
||||||
double val;
|
|
||||||
double imag = 0;
|
|
||||||
int rcomponent = scalcomp;
|
|
||||||
int comp = scalcomp;
|
|
||||||
if(sol.iscomplex && rcomponent != 0)
|
|
||||||
{
|
|
||||||
rcomponent = 2 * ((rcomponent-1)/2) + 1;
|
|
||||||
GetValue(&sol, el3d-1, lami[0], lami[1], lami[2], rcomponent+1,
|
|
||||||
imag);
|
|
||||||
comp = (scalcomp-1)/2 + 1;
|
|
||||||
}
|
|
||||||
GetValue(&sol, el3d-1, lami[0], lami[1], lami[2], rcomponent, val);
|
|
||||||
printScalValue(sol, comp, val, imag, sol.iscomplex && comp > 0);
|
|
||||||
}
|
|
||||||
if(vecfunction!=-1 && soldata[vecfunction]->draw_volume)
|
|
||||||
{
|
|
||||||
auto & sol = *soldata[vecfunction];
|
|
||||||
ArrayMem<double, 10> values(sol.components);
|
|
||||||
GetValues(&sol, el3d-1, lami[0], lami[1], lami[2], &values[0]);
|
|
||||||
printVecValue(sol, values);
|
|
||||||
}
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// no point on clipping plane found -> continue searching for surface element
|
|
||||||
|
|
||||||
Point<3> p;
|
Point<3> p;
|
||||||
bool found_point = vsmesh.Unproject(px, py, p);
|
bool found_point = vsmesh.SelectSurfaceElement(px, py, p, showclipsolution && clipsolution);
|
||||||
if(!found_point)
|
if(!found_point)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
marker = p;
|
// marker = p;
|
||||||
|
|
||||||
if(selelement<=0)
|
// found point on clipping plane
|
||||||
return;
|
if(selelement==0)
|
||||||
|
{
|
||||||
|
GLint viewport[4];
|
||||||
|
GLdouble projection[16];
|
||||||
|
glGetDoublev(GL_PROJECTION_MATRIX, &projection[0]);
|
||||||
|
|
||||||
|
glGetIntegerv(GL_VIEWPORT, &viewport[0]);
|
||||||
|
|
||||||
|
Point<3> eye;
|
||||||
|
gluUnProject( (viewport[2]-viewport[0])/2 , (viewport[3]-viewport[1])/2,
|
||||||
|
0.0, transformationmat, projection, viewport, &eye[0], &eye[1], &eye[2]);
|
||||||
|
|
||||||
|
Vec<3> n{vispar.clipping.normal};
|
||||||
|
n.Normalize();
|
||||||
|
Vec<3> view = p-eye;
|
||||||
|
|
||||||
|
// check if we look at the clipping plane from the right direction
|
||||||
|
if(n*view > 1e-8)
|
||||||
|
{
|
||||||
|
double lam = vispar.clipping.dist - Vec<3>{eye}*n;
|
||||||
|
lam /= n*view;
|
||||||
|
p = eye + lam*view;
|
||||||
|
|
||||||
|
double lami[3];
|
||||||
|
if(auto el3d = mesh->GetElementOfPoint( p, lami ))
|
||||||
|
{
|
||||||
|
cout << endl << "Selected point " << p << " on clipping plane" << endl;
|
||||||
|
// marker = p;
|
||||||
|
|
||||||
|
bool have_scal_func = scalfunction!=-1 && soldata[scalfunction]->draw_volume;
|
||||||
|
bool have_vec_func = vecfunction!=-1 && soldata[vecfunction]->draw_volume;
|
||||||
|
|
||||||
|
if(have_scal_func)
|
||||||
|
{
|
||||||
|
auto & sol = *soldata[scalfunction];
|
||||||
|
double val;
|
||||||
|
double imag = 0;
|
||||||
|
int rcomponent = scalcomp;
|
||||||
|
int comp = scalcomp;
|
||||||
|
if(sol.iscomplex && rcomponent != 0)
|
||||||
|
{
|
||||||
|
rcomponent = 2 * ((rcomponent-1)/2) + 1;
|
||||||
|
GetValue(&sol, el3d-1, lami[0], lami[1], lami[2], rcomponent+1,
|
||||||
|
imag);
|
||||||
|
comp = (scalcomp-1)/2 + 1;
|
||||||
|
}
|
||||||
|
GetValue(&sol, el3d-1, lami[0], lami[1], lami[2], rcomponent, val);
|
||||||
|
printScalValue(sol, comp, val, imag, sol.iscomplex && comp > 0);
|
||||||
|
}
|
||||||
|
if(vecfunction!=-1 && soldata[vecfunction]->draw_volume)
|
||||||
|
{
|
||||||
|
auto & sol = *soldata[vecfunction];
|
||||||
|
ArrayMem<double, 10> values(sol.components);
|
||||||
|
GetValues(&sol, el3d-1, lami[0], lami[1], lami[2], &values[0]);
|
||||||
|
printVecValue(sol, values);
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
double lami[3] = {0.0, 0.0, 0.0};
|
double lami[3] = {0.0, 0.0, 0.0};
|
||||||
// Check if unprojected Point is close to surface element (eps of 1e-3 due to z-Buffer accuracy)
|
// Check if unprojected Point is close to surface element (eps of 1e-3 due to z-Buffer accuracy)
|
||||||
bool found_2del = false;
|
bool found_2del = false;
|
||||||
if(mesh->PointContainedIn2DElement(p, lami, selelement, false && fabs(lami[2])<1e-3))
|
if(selelement>0 && mesh->PointContainedIn2DElement(p, lami, selelement, false && fabs(lami[2])<1e-3))
|
||||||
{
|
{
|
||||||
// Found it, use coordinates of point projected to surface element
|
// Found it, use coordinates of point projected to surface element
|
||||||
mesh->GetCurvedElements().CalcSurfaceTransformation({1.0-lami[0]-lami[1], lami[0]}, selelement-1, p);
|
mesh->GetCurvedElements().CalcSurfaceTransformation({1.0-lami[0]-lami[1], lami[0]}, selelement-1, p);
|
||||||
|
@ -94,7 +94,6 @@ class NGGUI_API VisualSceneSolution : public VisualScene
|
|||||||
int fieldlinestimestamp, surface_vector_timestamp;
|
int fieldlinestimestamp, surface_vector_timestamp;
|
||||||
int pointcurve_timestamp;
|
int pointcurve_timestamp;
|
||||||
int isosurface_timestamp;
|
int isosurface_timestamp;
|
||||||
int subdivision_timestamp;
|
|
||||||
int timetimestamp;
|
int timetimestamp;
|
||||||
double minval, maxval;
|
double minval, maxval;
|
||||||
|
|
||||||
@ -174,7 +173,6 @@ public:
|
|||||||
int autoscale, logscale;
|
int autoscale, logscale;
|
||||||
double mminval, mmaxval;
|
double mminval, mmaxval;
|
||||||
int numisolines;
|
int numisolines;
|
||||||
int subdivisions;
|
|
||||||
|
|
||||||
bool showclipsolution;
|
bool showclipsolution;
|
||||||
bool showsurfacesolution;
|
bool showsurfacesolution;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user