Sketcher: Restore internal geometry tool refactoring and extended support
========================================================================= - Long felt need of refactoring the code so as not to repeat code already existing in SketchObject. - Refactored code supports preexisting Ellipse and Arc of Ellipse and adds support for Arcs of Hyperbola and Parabola.
This commit is contained in:
parent
1a535e5f4e
commit
ebfbe29d2f
|
@ -762,206 +762,29 @@ void CmdSketcherRestoreInternalAlignmentGeometry::activated(int iMsg)
|
||||||
|
|
||||||
const Part::Geometry *geo = Obj->getGeometry(GeoId);
|
const Part::Geometry *geo = Obj->getGeometry(GeoId);
|
||||||
// Only for supported types
|
// Only for supported types
|
||||||
if(geo->getTypeId() == Part::GeomEllipse::getClassTypeId() || geo->getTypeId() == Part::GeomArcOfEllipse::getClassTypeId()) {
|
if( geo->getTypeId() == Part::GeomEllipse::getClassTypeId() ||
|
||||||
// First we search what has to be restored
|
geo->getTypeId() == Part::GeomArcOfEllipse::getClassTypeId() ||
|
||||||
bool major=false;
|
geo->getTypeId() == Part::GeomArcOfHyperbola::getClassTypeId() ||
|
||||||
bool minor=false;
|
geo->getTypeId() == Part::GeomArcOfParabola::getClassTypeId() ) {
|
||||||
bool focus1=false;
|
|
||||||
bool focus2=false;
|
|
||||||
|
|
||||||
int majorelementindex=-1;
|
int currentgeoid = Obj->getHighestCurveIndex();
|
||||||
int minorelementindex=-1;
|
|
||||||
int focus1elementindex=-1;
|
|
||||||
int focus2elementindex=-1;
|
|
||||||
|
|
||||||
const std::vector< Sketcher::Constraint * > &vals = Obj->Constraints.getValues();
|
try {
|
||||||
|
Gui::Command::openCommand("Exposing Internal Geometry");
|
||||||
|
|
||||||
for (std::vector< Sketcher::Constraint * >::const_iterator it= vals.begin();
|
Gui::Command::doCommand(Gui::Command::Doc,
|
||||||
it != vals.end(); ++it) {
|
"App.ActiveDocument.%s.ExposeInternalGeometry(%d)",
|
||||||
if((*it)->Type == Sketcher::InternalAlignment && (*it)->Second == GeoId)
|
|
||||||
{
|
|
||||||
switch((*it)->AlignmentType){
|
|
||||||
case Sketcher::EllipseMajorDiameter:
|
|
||||||
major=true;
|
|
||||||
majorelementindex=(*it)->First;
|
|
||||||
break;
|
|
||||||
case Sketcher::EllipseMinorDiameter:
|
|
||||||
minor=true;
|
|
||||||
minorelementindex=(*it)->First;
|
|
||||||
break;
|
|
||||||
case Sketcher::EllipseFocus1:
|
|
||||||
focus1=true;
|
|
||||||
focus1elementindex=(*it)->First;
|
|
||||||
break;
|
|
||||||
case Sketcher::EllipseFocus2:
|
|
||||||
focus2=true;
|
|
||||||
focus2elementindex=(*it)->First;
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if(major && minor && focus1 && focus2)
|
|
||||||
{
|
|
||||||
// Hide unused geometry here
|
|
||||||
int majorconstraints=0; // number of constraints associated to the geoid of the major axis
|
|
||||||
int minorconstraints=0;
|
|
||||||
int focus1constraints=0;
|
|
||||||
int focus2constraints=0;
|
|
||||||
|
|
||||||
for (std::vector< Sketcher::Constraint * >::const_iterator it= vals.begin();
|
|
||||||
it != vals.end(); ++it) {
|
|
||||||
|
|
||||||
if((*it)->Second == majorelementindex || (*it)->First == majorelementindex || (*it)->Third == majorelementindex)
|
|
||||||
majorconstraints++;
|
|
||||||
else if((*it)->Second == minorelementindex || (*it)->First == minorelementindex || (*it)->Third == minorelementindex)
|
|
||||||
minorconstraints++;
|
|
||||||
else if((*it)->Second == focus1elementindex || (*it)->First == focus1elementindex || (*it)->Third == focus1elementindex)
|
|
||||||
focus1constraints++;
|
|
||||||
else if((*it)->Second == focus2elementindex || (*it)->First == focus2elementindex || (*it)->Third == focus2elementindex)
|
|
||||||
focus2constraints++;
|
|
||||||
}
|
|
||||||
// those with less than 2 constraints must be removed
|
|
||||||
if(majorconstraints>=2 && minorconstraints>=2 && focus1constraints>=2 && focus2constraints>=2)
|
|
||||||
return; // nothing to delete
|
|
||||||
|
|
||||||
App::Document* doc = App::GetApplication().getActiveDocument();
|
|
||||||
|
|
||||||
if (!doc) return;
|
|
||||||
|
|
||||||
doc->openTransaction("Delete");
|
|
||||||
|
|
||||||
if(majorconstraints<2) {
|
|
||||||
ss.str(std::string());
|
|
||||||
ss << "Edge" << majorelementindex + 1;
|
|
||||||
Gui::Selection().addSelection(doc_name.c_str(), obj_name.c_str(), ss.str().c_str());
|
|
||||||
}
|
|
||||||
|
|
||||||
if(minorconstraints<2) {
|
|
||||||
ss.str(std::string());
|
|
||||||
ss << "Edge" << minorelementindex + 1;
|
|
||||||
Gui::Selection().addSelection(doc_name.c_str(), obj_name.c_str(), ss.str().c_str());
|
|
||||||
}
|
|
||||||
|
|
||||||
if(focus1constraints<2) {
|
|
||||||
ss.str(std::string());
|
|
||||||
int vertex = Obj->getVertexIndexGeoPos(focus1elementindex,Sketcher::start);
|
|
||||||
if(vertex>-1){
|
|
||||||
ss << "Vertex" << vertex + 1;
|
|
||||||
Gui::Selection().addSelection(doc_name.c_str(), obj_name.c_str(), ss.str().c_str());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if(focus2constraints<2) {
|
|
||||||
ss.str(std::string());
|
|
||||||
int vertex = Obj->getVertexIndexGeoPos(focus2elementindex,Sketcher::start);
|
|
||||||
if(vertex>-1){
|
|
||||||
ss << "Vertex" << vertex + 1;
|
|
||||||
Gui::Selection().addSelection(doc_name.c_str(), obj_name.c_str(), ss.str().c_str());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
SketcherGui::ViewProviderSketch* vp = dynamic_cast<SketcherGui::ViewProviderSketch*>(getActiveGuiDocument()->getInEdit());
|
|
||||||
|
|
||||||
if (vp) {
|
|
||||||
std::vector<Gui::SelectionObject> sel = Gui::Selection().getSelectionEx(doc->getName());
|
|
||||||
vp->onDelete(sel[0].getSubNames());
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
doc->commitTransaction();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
Gui::Command::openCommand("Expose ellipse internal geometry");
|
|
||||||
|
|
||||||
int currentgeoid= Obj->getHighestCurveIndex();
|
|
||||||
int incrgeo= 0;
|
|
||||||
|
|
||||||
Base::Vector3d center;
|
|
||||||
double majord;
|
|
||||||
double minord;
|
|
||||||
Base::Vector3d majdir;
|
|
||||||
|
|
||||||
if(geo->getTypeId() == Part::GeomEllipse::getClassTypeId()){
|
|
||||||
const Part::GeomEllipse *ellipse = static_cast<const Part::GeomEllipse *>(geo);
|
|
||||||
|
|
||||||
center=ellipse->getCenter();
|
|
||||||
majord=ellipse->getMajorRadius();
|
|
||||||
minord=ellipse->getMinorRadius();
|
|
||||||
majdir=ellipse->getMajorAxisDir();
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
const Part::GeomArcOfEllipse *aoe = static_cast<const Part::GeomArcOfEllipse *>(geo);
|
|
||||||
|
|
||||||
center=aoe->getCenter();
|
|
||||||
majord=aoe->getMajorRadius();
|
|
||||||
minord=aoe->getMinorRadius();
|
|
||||||
majdir=aoe->getMajorAxisDir();
|
|
||||||
}
|
|
||||||
|
|
||||||
Base::Vector3d mindir = Base::Vector3d(-majdir.y, majdir.x, 0.0);
|
|
||||||
|
|
||||||
Base::Vector3d majorpositiveend = center + majord * majdir;
|
|
||||||
Base::Vector3d majornegativeend = center - majord * majdir;
|
|
||||||
Base::Vector3d minorpositiveend = center + minord * mindir;
|
|
||||||
Base::Vector3d minornegativeend = center - minord * mindir;
|
|
||||||
|
|
||||||
double df= sqrt(majord*majord-minord*minord);
|
|
||||||
|
|
||||||
Base::Vector3d focus1P = center + df * majdir;
|
|
||||||
Base::Vector3d focus2P = center - df * majdir;
|
|
||||||
|
|
||||||
try{
|
|
||||||
if(!major)
|
|
||||||
{
|
|
||||||
Gui::Command::doCommand(Gui::Command::Doc,"App.ActiveDocument.%s.addGeometry(Part.LineSegment(App.Vector(%f,%f,0),App.Vector(%f,%f,0)),True)",
|
|
||||||
Obj->getNameInDocument(),
|
Obj->getNameInDocument(),
|
||||||
majorpositiveend.x,majorpositiveend.y,majornegativeend.x,majornegativeend.y); // create line for major axis
|
GeoId);
|
||||||
|
|
||||||
Gui::Command::doCommand(Doc,"App.ActiveDocument.%s.addConstraint(Sketcher.Constraint('InternalAlignment:EllipseMajorDiameter',%d,%d)) ",
|
int aftergeoid = Obj->getHighestCurveIndex();
|
||||||
selection[0].getFeatName(),currentgeoid+incrgeo+1,GeoId); // constrain major axis
|
|
||||||
incrgeo++;
|
if(aftergeoid == currentgeoid) { // if we did not expose anything, deleteunused
|
||||||
}
|
Gui::Command::doCommand(Gui::Command::Doc,
|
||||||
if(!minor)
|
"App.ActiveDocument.%s.DeleteUnusedInternalGeometry(%d)",
|
||||||
{
|
|
||||||
Gui::Command::doCommand(Gui::Command::Doc,"App.ActiveDocument.%s.addGeometry(Part.LineSegment(App.Vector(%f,%f,0),App.Vector(%f,%f,0)),True)",
|
|
||||||
Obj->getNameInDocument(),
|
Obj->getNameInDocument(),
|
||||||
minorpositiveend.x,minorpositiveend.y,minornegativeend.x,minornegativeend.y); // create line for minor axis
|
GeoId);
|
||||||
|
|
||||||
Gui::Command::doCommand(Doc,"App.ActiveDocument.%s.addConstraint(Sketcher.Constraint('InternalAlignment:EllipseMinorDiameter',%d,%d)) ",
|
|
||||||
selection[0].getFeatName(),currentgeoid+incrgeo+1,GeoId); // constrain minor axis
|
|
||||||
incrgeo++;
|
|
||||||
}
|
}
|
||||||
if(!focus1)
|
|
||||||
{
|
|
||||||
Gui::Command::doCommand(Gui::Command::Doc,"App.ActiveDocument.%s.addGeometry(Part.Point(App.Vector(%f,%f,0)))",
|
|
||||||
Obj->getNameInDocument(),
|
|
||||||
focus1P.x,focus1P.y);
|
|
||||||
|
|
||||||
Gui::Command::doCommand(Doc,"App.ActiveDocument.%s.addConstraint(Sketcher.Constraint('InternalAlignment:EllipseFocus1',%d,%d,%d)) ",
|
|
||||||
selection[0].getFeatName(),currentgeoid+incrgeo+1,Sketcher::start,GeoId); // constrain major axis
|
|
||||||
incrgeo++;
|
|
||||||
}
|
|
||||||
if(!focus2)
|
|
||||||
{
|
|
||||||
Gui::Command::doCommand(Gui::Command::Doc,"App.ActiveDocument.%s.addGeometry(Part.Point(App.Vector(%f,%f,0)))",
|
|
||||||
Obj->getNameInDocument(),
|
|
||||||
focus2P.x,focus2P.y);
|
|
||||||
|
|
||||||
Gui::Command::doCommand(Doc,"App.ActiveDocument.%s.addConstraint(Sketcher.Constraint('InternalAlignment:EllipseFocus2',%d,%d,%d)) ",
|
|
||||||
Obj->getNameInDocument(),currentgeoid+incrgeo+1,Sketcher::start,GeoId); // constrain major axis
|
|
||||||
}
|
|
||||||
|
|
||||||
Gui::Command::commitCommand();
|
|
||||||
|
|
||||||
ParameterGrp::handle hGrp = App::GetApplication().GetParameterGroupByPath("User parameter:BaseApp/Preferences/Mod/Sketcher");
|
|
||||||
bool autoRecompute = hGrp->GetBool("AutoRecompute",false);
|
|
||||||
|
|
||||||
if(autoRecompute)
|
|
||||||
Gui::Command::updateActive();
|
|
||||||
|
|
||||||
}
|
}
|
||||||
catch (const Base::Exception& e) {
|
catch (const Base::Exception& e) {
|
||||||
|
@ -973,14 +796,22 @@ void CmdSketcherRestoreInternalAlignmentGeometry::activated(int iMsg)
|
||||||
|
|
||||||
if(autoRecompute)
|
if(autoRecompute)
|
||||||
Gui::Command::updateActive();
|
Gui::Command::updateActive();
|
||||||
|
else
|
||||||
|
static_cast<Sketcher::SketchObject *>(Obj)->solve();
|
||||||
|
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
} // if(geo->getTypeId() == Part::GeomEllipse::getClassTypeId())
|
Gui::Command::commitCommand();
|
||||||
else {
|
|
||||||
QMessageBox::warning(Gui::getMainWindow(), QObject::tr("Wrong selection"),
|
|
||||||
QObject::tr("Currently internal geometry is only supported for ellipse and arc of ellipse. The last selected element must be an ellipse or an arc of ellipse."));
|
|
||||||
}
|
|
||||||
|
|
||||||
|
ParameterGrp::handle hGrp = App::GetApplication().GetParameterGroupByPath("User parameter:BaseApp/Preferences/Mod/Sketcher");
|
||||||
|
bool autoRecompute = hGrp->GetBool("AutoRecompute",false);
|
||||||
|
|
||||||
|
if(autoRecompute)
|
||||||
|
Gui::Command::updateActive();
|
||||||
|
else
|
||||||
|
static_cast<Sketcher::SketchObject *>(Obj)->solve();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue
Block a user