mirror of
https://github.com/lucaspalomodevelop/meshlab.git
synced 2026-03-20 03:16:10 +00:00
Improved Area Selection Filter
Added cursor icon and switched to a buffer based in-polygon test
This commit is contained in:
parent
810e450a52
commit
5bbb4f48f0
@ -151,100 +151,87 @@ void EditSelectPlugin::keyReleaseEvent(QKeyEvent *e, MeshModel &m, GLArea *gla)
|
||||
gla->update();
|
||||
e->accept();
|
||||
}
|
||||
|
||||
gla->setCursor(QCursor(QPixmap(":/images/sel_area.png"), 1, 1));
|
||||
}
|
||||
|
||||
gla->setCursor(QCursor(QPixmap(":/images/sel_rect.png"), 1, 1));
|
||||
|
||||
}
|
||||
|
||||
void EditSelectPlugin::doSelection(MeshModel &m, GLArea *gla, int mode)
|
||||
{
|
||||
//polyLine -> polygon
|
||||
std::vector<Segment2m > pgon;
|
||||
pgon.clear();
|
||||
for (int ii = 0; ii < selPolyLine.size(); ii++)
|
||||
pgon.push_back(Segment2m(selPolyLine[ii], selPolyLine[(ii + 1) % selPolyLine.size()]));
|
||||
QImage bufQImg(this->viewpSize[2],this->viewpSize[3],QImage::Format_RGB32);
|
||||
bufQImg.fill(Qt::white);
|
||||
QPainter bufQPainter(&bufQImg);
|
||||
vector<QPointF> qpoints;
|
||||
for(int i=0;i<selPolyLine.size();++i)
|
||||
qpoints.push_back(QPointF(selPolyLine[i][0],selPolyLine[i][1]));
|
||||
bufQPainter.setBrush(QBrush(Qt::black));
|
||||
bufQPainter.drawPolygon(&qpoints[0],qpoints.size(), Qt::WindingFill);
|
||||
QRgb blk=QColor(Qt::black).rgb();
|
||||
|
||||
|
||||
static Eigen::Matrix<Scalarm,4,4> LastSelMatrix;
|
||||
static vector<Point3m> projVec;
|
||||
static MeshModel *lastMeshModel=0;
|
||||
if((LastSelMatrix != SelMatrix) || lastMeshModel != &m)
|
||||
{
|
||||
int t0=clock();
|
||||
GLPickTri<CMeshO>::FillProjectedVector(m.cm,projVec,this->SelMatrix,this->SelViewport);
|
||||
LastSelMatrix=this->SelMatrix;
|
||||
lastMeshModel=&m;
|
||||
qDebug("proj Time %4.5f",float(clock()-t0)/CLOCKS_PER_SEC);
|
||||
}
|
||||
static Eigen::Matrix<Scalarm,4,4> LastSelMatrix;
|
||||
static vector<Point3m> projVec;
|
||||
static MeshModel *lastMeshModel=0;
|
||||
if((LastSelMatrix != SelMatrix) || lastMeshModel != &m)
|
||||
{
|
||||
int t0=clock();
|
||||
GLPickTri<CMeshO>::FillProjectedVector(m.cm,projVec,this->SelMatrix,this->SelViewport);
|
||||
LastSelMatrix=this->SelMatrix;
|
||||
lastMeshModel=&m;
|
||||
}
|
||||
|
||||
if (areaMode == 0) // vertices
|
||||
{
|
||||
for (size_t vi = 0; vi<m.cm.vert.size(); ++vi) if (!m.cm.vert[vi].IsD())
|
||||
{
|
||||
bool res=false;
|
||||
if ((projVec[vi][2] <= -1.0) || (projVec[vi][2] >= 1.0))
|
||||
res = false;
|
||||
else
|
||||
res = PointInsidePolygon<CMeshO::ScalarType>(Point2m(projVec[vi][0],projVec[vi][1]), pgon);
|
||||
if (res)
|
||||
{
|
||||
if (mode == 0) //add
|
||||
m.cm.vert[vi].SetS();
|
||||
else if (mode == 1) //sub
|
||||
m.cm.vert[vi].ClearS();
|
||||
else if (mode == 2) //invert
|
||||
{
|
||||
if (m.cm.vert[vi].IsS())
|
||||
m.cm.vert[vi].ClearS();
|
||||
else
|
||||
m.cm.vert[vi].SetS();
|
||||
}
|
||||
}
|
||||
}
|
||||
gla->updateSelection(m.id(), true, false);
|
||||
}
|
||||
else if (areaMode == 1) //faces
|
||||
{
|
||||
int t0=clock();
|
||||
for (size_t vi = 0; vi<m.cm.vert.size(); ++vi) if (!m.cm.vert[vi].IsD())
|
||||
{
|
||||
bool res=false;
|
||||
if ((projVec[vi][2] <= -1.0) || (projVec[vi][2] >= 1.0) ||
|
||||
(projVec[vi][0] <= 0) || (projVec[vi][0] >= this->viewpSize[2]) ||
|
||||
(projVec[vi][1] <= 0) || (projVec[vi][1] >= this->viewpSize[3]))
|
||||
res = false;
|
||||
else
|
||||
{
|
||||
res = (bufQImg.pixel( projVec[vi][0],projVec[vi][1]) == blk);
|
||||
}
|
||||
if (res)
|
||||
switch(mode){
|
||||
case 0: m.cm.vert[vi].SetS(); break;
|
||||
case 1: m.cm.vert[vi].ClearS(); break;
|
||||
case 2: m.cm.vert[vi].IsS() ? m.cm.vert[vi].ClearS() : m.cm.vert[vi].SetS();
|
||||
}
|
||||
}
|
||||
gla->updateSelection(m.id(), true, false);
|
||||
}
|
||||
else if (areaMode == 1) //faces
|
||||
{
|
||||
for (size_t fi = 0; fi < m.cm.face.size(); ++fi) if (!m.cm.face[fi].IsD())
|
||||
{
|
||||
bool res=false;
|
||||
for (int vi = 0; vi < 3; vi++)
|
||||
for (int vi = 0; vi < 3 && !res ; vi++)
|
||||
{
|
||||
int vInd=tri::Index(m.cm,m.cm.face[fi].V(vi));
|
||||
if ((projVec[vInd][2] <= -1.0) || (projVec[vInd][2] >= 1.0))
|
||||
res = false;
|
||||
if ((projVec[vInd][2] <= -1.0) || (projVec[vInd][2] >= 1.0) ||
|
||||
(projVec[vInd][0] <= 0) || (projVec[vInd][0] >= this->viewpSize[2]) ||
|
||||
(projVec[vInd][1] <= 0) || (projVec[vInd][1] >= this->viewpSize[3]))
|
||||
res = false;
|
||||
else
|
||||
res = PointInsidePolygon<CMeshO::ScalarType>(Point2m(projVec[vInd][0],projVec[vInd][1]), pgon);
|
||||
|
||||
if (res)
|
||||
break; //early out, we already know it is inside, no need for further testing
|
||||
res = (bufQImg.pixel( projVec[vInd][0],projVec[vInd][1]) == blk);
|
||||
}
|
||||
|
||||
if (!res) // now test segment-segment
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
if (res) // do the actual selection
|
||||
{
|
||||
if (mode == 0) //add
|
||||
m.cm.face[fi].SetS();
|
||||
else if (mode == 1) //sub
|
||||
m.cm.face[fi].ClearS();
|
||||
else if (mode == 2) //invert
|
||||
{
|
||||
if (m.cm.face[fi].IsS())
|
||||
m.cm.face[fi].ClearS();
|
||||
else
|
||||
m.cm.face[fi].SetS();
|
||||
switch(mode){
|
||||
case 0: m.cm.face[fi].SetS(); break;
|
||||
case 1: m.cm.face[fi].ClearS(); break;
|
||||
case 2: m.cm.face[fi].IsS() ? m.cm.face[fi].ClearS() : m.cm.face[fi].SetS();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
gla->updateSelection(m.id(), false, true);
|
||||
}
|
||||
|
||||
|
||||
|
||||
//this->Log(GLLogStream::FILTER, "%i ");
|
||||
}
|
||||
|
||||
void EditSelectPlugin::keyPressEvent(QKeyEvent */*event*/, MeshModel &/*m*/, GLArea *gla)
|
||||
@ -381,7 +368,7 @@ void EditSelectPlugin::DrawXORPolyLine(GLArea * gla)
|
||||
glColor3f(1, 1, 1);
|
||||
glLineStipple(1, 0xAAAA);
|
||||
glEnable(GL_LINE_STIPPLE);
|
||||
|
||||
glLineWidth(QTLogicalToDevice(gla,1));
|
||||
//draw PolyLine
|
||||
if (selPolyLine.size() == 1)
|
||||
{
|
||||
@ -614,6 +601,7 @@ bool EditSelectPlugin::StartEdit(MeshModel & m, GLArea * gla, MLSceneGLSharedDat
|
||||
if (selectionMode == SELECT_AREA_MODE)
|
||||
{
|
||||
selPolyLine.clear();
|
||||
gla->setCursor(QCursor(QPixmap(":/images/sel_area.png"), 1, 1));
|
||||
}
|
||||
|
||||
if (selectionMode == SELECT_VERT_MODE)
|
||||
|
||||
@ -10,5 +10,6 @@
|
||||
<file>images/sel_rect_plus_eye.png</file>
|
||||
<file>images/sel_rect_minus_eye.png</file>
|
||||
<file>images/select_area.png</file>
|
||||
<file>images/sel_area.png</file>
|
||||
</qresource>
|
||||
</RCC>
|
||||
|
||||
BIN
src/meshlabplugins/edit_select/images/sel_area.png
Normal file
BIN
src/meshlabplugins/edit_select/images/sel_area.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 368 B |
Loading…
x
Reference in New Issue
Block a user