From fdee687f012fc20143a39bb34dca8d888879c43b Mon Sep 17 00:00:00 2001 From: vdwalts Date: Mon, 1 Aug 2016 21:56:50 +0100 Subject: [PATCH] FEM: constraint plane rotation: object implementation --- src/Mod/Fem/App/AppFem.cpp | 6 +- src/Mod/Fem/App/CMakeLists.txt | 2 + .../Fem/App/FemConstraintPlaneRotation.cpp | 78 ++++ src/Mod/Fem/App/FemConstraintPlaneRotation.h | 59 ++++ src/Mod/Fem/Gui/AppFemGui.cpp | 6 +- src/Mod/Fem/Gui/CMakeLists.txt | 7 + src/Mod/Fem/Gui/Command.cpp | 44 ++- .../Gui/TaskFemConstraintPlaneRotation.cpp | 332 ++++++++++++++++++ .../Fem/Gui/TaskFemConstraintPlaneRotation.h | 85 +++++ .../Fem/Gui/TaskFemConstraintPlaneRotation.ui | 49 +++ ...ViewProviderFemConstraintPlaneRotation.cpp | 191 ++++++++++ .../ViewProviderFemConstraintPlaneRotation.h | 48 +++ src/Mod/Fem/Gui/Workbench.cpp | 2 + 13 files changed, 904 insertions(+), 5 deletions(-) create mode 100644 src/Mod/Fem/App/FemConstraintPlaneRotation.cpp create mode 100644 src/Mod/Fem/App/FemConstraintPlaneRotation.h create mode 100644 src/Mod/Fem/Gui/TaskFemConstraintPlaneRotation.cpp create mode 100644 src/Mod/Fem/Gui/TaskFemConstraintPlaneRotation.h create mode 100644 src/Mod/Fem/Gui/TaskFemConstraintPlaneRotation.ui create mode 100644 src/Mod/Fem/Gui/ViewProviderFemConstraintPlaneRotation.cpp create mode 100644 src/Mod/Fem/Gui/ViewProviderFemConstraintPlaneRotation.h diff --git a/src/Mod/Fem/App/AppFem.cpp b/src/Mod/Fem/App/AppFem.cpp index 611a5ec69572..2929d8eaffa5 100644 --- a/src/Mod/Fem/App/AppFem.cpp +++ b/src/Mod/Fem/App/AppFem.cpp @@ -51,6 +51,7 @@ #include "FemConstraintGear.h" #include "FemConstraintPulley.h" #include "FemConstraintDisplacement.h" +#include "FemConstraintPlaneRotation.h" #include "FemConstraintContact.h" #include "FemResultObject.h" @@ -148,12 +149,13 @@ PyMODINIT_FUNC initFem() Fem::ConstraintGear ::init(); Fem::ConstraintPulley ::init(); Fem::ConstraintDisplacement ::init(); - Fem::ConstraintContact ::init(); + Fem::ConstraintPlaneRotation ::init(); + Fem::ConstraintContact ::init(); Fem::FemResultObject ::init(); Fem::FemSolverObject ::init(); Fem::FemSolverObjectPython ::init(); - + #ifdef FC_USE_VTK Fem::FemPostObject ::init(); Fem::FemPostPipeline ::init(); diff --git a/src/Mod/Fem/App/CMakeLists.txt b/src/Mod/Fem/App/CMakeLists.txt index eab2910dd851..770af3c8c643 100755 --- a/src/Mod/Fem/App/CMakeLists.txt +++ b/src/Mod/Fem/App/CMakeLists.txt @@ -200,6 +200,8 @@ SET(FemConstraints_SRCS FemConstraintPulley.h FemConstraintDisplacement.h FemConstraintDisplacement.cpp + FemConstraintPlaneRotation.cpp + FemConstraintPlaneRotation.h FemConstraintContact.cpp FemConstraintContact.h ) diff --git a/src/Mod/Fem/App/FemConstraintPlaneRotation.cpp b/src/Mod/Fem/App/FemConstraintPlaneRotation.cpp new file mode 100644 index 000000000000..15892160626e --- /dev/null +++ b/src/Mod/Fem/App/FemConstraintPlaneRotation.cpp @@ -0,0 +1,78 @@ +/*************************************************************************** + * Copyright (c) 2013 Jan Rheinländer * + * * + * This file is part of the FreeCAD CAx development system. * + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Library General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + * This library is distributed in the hope that it will be useful, * + * but WITHOUT ANY WARRANTY; without even the implied warranty of * + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * + * GNU Library General Public License for more details. * + * * + * You should have received a copy of the GNU Library General Public * + * License along with this library; see the file COPYING.LIB. If not, * + * write to the Free Software Foundation, Inc., 59 Temple Place, * + * Suite 330, Boston, MA 02111-1307, USA * + * * + ***************************************************************************/ + + +#include "PreCompiled.h" + +#ifndef _PreComp_ +#include +#include +#include +#include +#include +#include +#include +#endif + +#include "FemConstraintPlaneRotation.h" + +using namespace Fem; + +PROPERTY_SOURCE(Fem::ConstraintPlaneRotation, Fem::Constraint); + +ConstraintPlaneRotation::ConstraintPlaneRotation() +{ + + ADD_PROPERTY_TYPE(Points,(Base::Vector3d()),"ConstraintPlaneRotation",App::PropertyType(App::Prop_ReadOnly|App::Prop_Output), + "Points where symbols are drawn"); + ADD_PROPERTY_TYPE(Normals,(Base::Vector3d()),"ConstraintPlaneRotation",App::PropertyType(App::Prop_ReadOnly|App::Prop_Output), + "Normals where symbols are drawn"); + Points.setValues(std::vector()); + Normals.setValues(std::vector()); +} + +App::DocumentObjectExecReturn *ConstraintPlaneRotation::execute(void) +{ + return Constraint::execute(); +} + +const char* ConstraintPlaneRotation::getViewProviderName(void) const +{ + return "FemGui::ViewProviderFemConstraintPlaneRotation"; +} + +void ConstraintPlaneRotation::onChanged(const App::Property* prop) +{ + Constraint::onChanged(prop); + + if (prop == &References) { + std::vector points; + std::vector normals; + int scale = 1; //OvG: Enforce use of scale + if (getPoints(points, normals, &scale)) { + Points.setValues(points); + Normals.setValues(normals); + Scale.setValue(scale); //OvG: Scale + Points.touch(); // This triggers ViewProvider::updateData() + } + } +} diff --git a/src/Mod/Fem/App/FemConstraintPlaneRotation.h b/src/Mod/Fem/App/FemConstraintPlaneRotation.h new file mode 100644 index 000000000000..0a76ba10e0e5 --- /dev/null +++ b/src/Mod/Fem/App/FemConstraintPlaneRotation.h @@ -0,0 +1,59 @@ +/*************************************************************************** + * Copyright (c) 2013 Jan Rheinländer * + * * + * This file is part of the FreeCAD CAx development system. * + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Library General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + * This library is distributed in the hope that it will be useful, * + * but WITHOUT ANY WARRANTY; without even the implied warranty of * + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * + * GNU Library General Public License for more details. * + * * + * You should have received a copy of the GNU Library General Public * + * License along with this library; see the file COPYING.LIB. If not, * + * write to the Free Software Foundation, Inc., 59 Temple Place, * + * Suite 330, Boston, MA 02111-1307, USA * + * * + ***************************************************************************/ + + +#ifndef FEM_CONSTRAINTPLANEROTATION_H +#define FEM_CONSTRAINTPLANEROTATION_H + +#include "FemConstraint.h" + +namespace Fem +{ + +class AppFemExport ConstraintPlaneRotation : public Fem::Constraint +{ + PROPERTY_HEADER(Fem::ConstraintPlaneRotation); + +public: + /// Constructor + ConstraintPlaneRotation(void); + + // Read-only (calculated values). These trigger changes in the ViewProvider + App::PropertyVectorList Points; + App::PropertyVectorList Normals; + + + /// recalculate the object + virtual App::DocumentObjectExecReturn *execute(void); + + /// returns the type name of the ViewProvider + const char* getViewProviderName(void) const; + +protected: + virtual void onChanged(const App::Property* prop); + +}; + +} //namespace Fem + + +#endif // FEM_CONSTRAINTPLANEROTATION_H diff --git a/src/Mod/Fem/Gui/AppFemGui.cpp b/src/Mod/Fem/Gui/AppFemGui.cpp index 2967741ca0be..3c6919954b37 100644 --- a/src/Mod/Fem/Gui/AppFemGui.cpp +++ b/src/Mod/Fem/Gui/AppFemGui.cpp @@ -51,6 +51,7 @@ #include "ViewProviderFemConstraintGear.h" #include "ViewProviderFemConstraintPulley.h" #include "ViewProviderFemConstraintDisplacement.h" +#include "ViewProviderFemConstraintPlaneRotation.h" #include "ViewProviderFemConstraintContact.h" #include "ViewProviderResult.h" #include "Workbench.h" @@ -117,11 +118,12 @@ PyMODINIT_FUNC initFemGui() FemGui::ViewProviderFemConstraintGear ::init(); FemGui::ViewProviderFemConstraintPulley ::init(); FemGui::ViewProviderFemConstraintDisplacement ::init(); - FemGui::ViewProviderFemConstraintContact ::init(); + FemGui::ViewProviderFemConstraintPlaneRotation::init(); + FemGui::ViewProviderFemConstraintContact ::init(); FemGui::ViewProviderResult ::init(); FemGui::ViewProviderResultPython ::init(); FemGui::PropertyFemMeshItem ::init(); - + #ifdef FC_USE_VTK FemGui::ViewProviderFemPostObject ::init(); FemGui::ViewProviderFemPostPipeline ::init(); diff --git a/src/Mod/Fem/Gui/CMakeLists.txt b/src/Mod/Fem/Gui/CMakeLists.txt index 8f0fd0f1dadb..aa22a2ecdfc0 100755 --- a/src/Mod/Fem/Gui/CMakeLists.txt +++ b/src/Mod/Fem/Gui/CMakeLists.txt @@ -64,6 +64,7 @@ set(FemGui_MOC_HDRS TaskFemConstraintGear.h TaskFemConstraintPulley.h TaskFemConstraintDisplacement.h + TaskFemConstraintPlaneRotation.h TaskFemConstraintContact.h TaskTetParameter.h TaskAnalysisInfo.h @@ -91,6 +92,7 @@ set(FemGui_UIC_SRCS TaskFemConstraintForce.ui TaskFemConstraintPressure.ui TaskFemConstraintDisplacement.ui + TaskFemConstraintPlaneRotation.ui TaskFemConstraintContact.ui TaskTetParameter.ui TaskAnalysisInfo.ui @@ -137,6 +139,9 @@ SET(FemGui_DLG_SRCS TaskFemConstraintDisplacement.ui TaskFemConstraintDisplacement.cpp TaskFemConstraintDisplacement.h + TaskFemConstraintPlaneRotation.ui + TaskFemConstraintPlaneRotation.cpp + TaskFemConstraintPlaneRotation.h TaskFemConstraintContact.ui TaskFemConstraintContact.cpp TaskFemConstraintContact.h @@ -184,6 +189,8 @@ SET(FemGui_SRCS_ViewProvider ViewProviderFemConstraintPulley.h ViewProviderFemConstraintDisplacement.cpp ViewProviderFemConstraintDisplacement.h + ViewProviderFemConstraintPlaneRotation.cpp + ViewProviderFemConstraintPlaneRotation.h ViewProviderFemConstraintContact.cpp ViewProviderFemConstraintContact.h ViewProviderResult.cpp diff --git a/src/Mod/Fem/Gui/Command.cpp b/src/Mod/Fem/Gui/Command.cpp index 9b577520b9d8..a52ee34da027 100644 --- a/src/Mod/Fem/Gui/Command.cpp +++ b/src/Mod/Fem/Gui/Command.cpp @@ -354,6 +354,47 @@ bool CmdFemConstraintFixed::isActive(void) //===================================================================================== +DEF_STD_CMD_A(CmdFemConstraintPlaneRotation); + +CmdFemConstraintPlaneRotation::CmdFemConstraintPlaneRotation() + : Command("Fem_ConstraintPlaneRotation") +{ + sAppModule = "Fem"; + sGroup = QT_TR_NOOP("Fem"); + sMenuText = QT_TR_NOOP("Constraint plane rotation"); + sToolTipText = QT_TR_NOOP("Creates a FEM constraint for plane rotation face"); + sWhatsThis = "Fem_ConstraintPlaneRotation"; + sStatusTip = sToolTipText; + sPixmap = "fem-constraint-planerotation"; +} + +void CmdFemConstraintPlaneRotation::activated(int iMsg) +{ + Fem::FemAnalysis *Analysis; + + if(getConstraintPrerequisits(&Analysis)) + return; + + std::string FeatName = getUniqueObjectName("FemConstraintPlaneRotation"); + + openCommand("Make FEM constraint Plane Rotation face"); + doCommand(Doc,"App.activeDocument().addObject(\"Fem::ConstraintPlaneRotation\",\"%s\")",FeatName.c_str()); + doCommand(Doc,"App.activeDocument().%s.Scale = 1",FeatName.c_str()); //OvG: set initial scale to 1 + doCommand(Doc,"App.activeDocument().%s.Member = App.activeDocument().%s.Member + [App.activeDocument().%s]",Analysis->getNameInDocument(),Analysis->getNameInDocument(),FeatName.c_str()); + + doCommand(Doc,"%s",gethideMeshShowPartStr(FeatName).c_str()); //OvG: Hide meshes and show parts + + updateActive(); + + doCommand(Gui,"Gui.activeDocument().setEdit('%s')",FeatName.c_str()); +} + +bool CmdFemConstraintPlaneRotation::isActive(void) +{ + return FemGui::ActiveAnalysisObserver::instance()->hasActiveObject(); +} + +//===================================================================================== DEF_STD_CMD_A(CmdFemConstraintContact); CmdFemConstraintContact::CmdFemConstraintContact() @@ -1188,7 +1229,8 @@ void CreateFemCommands(void) rcCmdMgr.addCommand(new CmdFemConstraintGear()); rcCmdMgr.addCommand(new CmdFemConstraintPulley()); rcCmdMgr.addCommand(new CmdFemConstraintDisplacement()); - rcCmdMgr.addCommand(new CmdFemConstraintContact()); + rcCmdMgr.addCommand(new CmdFemConstraintPlaneRotation()); + rcCmdMgr.addCommand(new CmdFemConstraintContact()); #ifdef FC_USE_VTK rcCmdMgr.addCommand(new CmdFemPostCreateClipFilter); diff --git a/src/Mod/Fem/Gui/TaskFemConstraintPlaneRotation.cpp b/src/Mod/Fem/Gui/TaskFemConstraintPlaneRotation.cpp new file mode 100644 index 000000000000..3a93e43f0119 --- /dev/null +++ b/src/Mod/Fem/Gui/TaskFemConstraintPlaneRotation.cpp @@ -0,0 +1,332 @@ +/*************************************************************************** + * Copyright (c) 2015 FreeCAD Developers * + * Authors: Michael Hindley * + * Ruan Olwagen * + * Oswald van Ginkel * + * Based on Force constraint by Jan Rheinländer * + * This file is part of the FreeCAD CAx development system. * + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Library General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + * This library is distributed in the hope that it will be useful, * + * but WITHOUT ANY WARRANTY; without even the implied warranty of * + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * + * GNU Library General Public License for more details. * + * * + * You should have received a copy of the GNU Library General Public * + * License along with this library; see the file COPYING.LIB. If not, * + * write to the Free Software Foundation, Inc., 59 Temple Place, * + * Suite 330, Boston, MA 02111-1307, USA * + * * + ***************************************************************************/ + +#include "PreCompiled.h" + +#ifndef _PreComp_ +# include +# include +# include +# include +# include +# include +# include +# include +# include +# include +# include +# include +# include +#endif + +#include "TaskFemConstraintPlaneRotation.h" +#include "ui_TaskFemConstraintPlaneRotation.h" +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include + + +using namespace FemGui; +using namespace Gui; + +/* TRANSLATOR FemGui::TaskFemConstraintPlaneRotation */ + +TaskFemConstraintPlaneRotation::TaskFemConstraintPlaneRotation(ViewProviderFemConstraintPlaneRotation *ConstraintView,QWidget *parent) + : TaskFemConstraint(ConstraintView, parent, "fem-constraint-planerotation") +{ //Note change "planerotation" in line above to new constraint name + proxy = new QWidget(this); + ui = new Ui_TaskFemConstraintPlaneRotation(); + ui->setupUi(proxy); + QMetaObject::connectSlotsByName(this); + + QAction* action = new QAction(tr("Delete"), ui->lw_references); + action->connect(action, SIGNAL(triggered()), this, SLOT(onReferenceDeleted())); + ui->lw_references->addAction(action); + ui->lw_references->setContextMenuPolicy(Qt::ActionsContextMenu); + + connect(ui->lw_references, SIGNAL(currentItemChanged(QListWidgetItem*,QListWidgetItem*)), + this, SLOT(setSelection(QListWidgetItem*))); + + this->groupLayout()->addWidget(proxy); + +/* Note: */ + // Get the feature data + Fem::ConstraintPlaneRotation* pcConstraint = static_cast(ConstraintView->getObject()); + + std::vector Objects = pcConstraint->References.getValues(); + std::vector SubElements = pcConstraint->References.getSubValues(); + + // Fill data into dialog elements + + ui->lw_references->clear(); + for (std::size_t i = 0; i < Objects.size(); i++) { + ui->lw_references->addItem(makeRefText(Objects[i], SubElements[i])); + } + if (Objects.size() > 0) { + ui->lw_references->setCurrentRow(0, QItemSelectionModel::ClearAndSelect); + } + + //Selection buttons + connect(ui->btnAdd, SIGNAL(clicked()), this, SLOT(addToSelection())); + connect(ui->btnRemove, SIGNAL(clicked()), this, SLOT(removeFromSelection())); + + updateUI(); +} + +TaskFemConstraintPlaneRotation::~TaskFemConstraintPlaneRotation() +{ + delete ui; +} + +void TaskFemConstraintPlaneRotation::updateUI() +{ + if (ui->lw_references->model()->rowCount() == 0) { + // Go into reference selection mode if no reference has been selected yet + onButtonReference(true); + return; + } +} + +void TaskFemConstraintPlaneRotation::addToSelection() +{ + int rows = ui->lw_references->model()->rowCount(); + if (rows==1){ + QMessageBox::warning(this, tr("Selection error"), tr("Only one face can be selected for a plane rotation constraint!")); + Gui::Selection().clearSelection(); + return; + } + else { + + std::vector selection = Gui::Selection().getSelectionEx(); //gets vector of selected objects of active document + if (selection.size()==0){ + QMessageBox::warning(this, tr("Selection error"), tr("Nothing selected!")); + return; + } + Fem::ConstraintPlaneRotation* pcConstraint = static_cast(ConstraintView->getObject()); + std::vector Objects = pcConstraint->References.getValues(); + std::vector SubElements = pcConstraint->References.getSubValues(); + + for (std::vector::iterator it = selection.begin(); it != selection.end(); ++it){//for every selected object + if (static_cast(it->getTypeName()).substr(0,4).compare(std::string("Part"))!=0){ + QMessageBox::warning(this, tr("Selection error"),tr("Selected object is not a part!")); + return; + } + + std::vector subNames=it->getSubNames(); + App::DocumentObject* obj = ConstraintView->getObject()->getDocument()->getObject(it->getFeatName()); + + if (subNames.size()==1){ + for (unsigned int subIt=0;subIt<(subNames.size());++subIt){// for every selected sub element + bool addMe=true; + if ((subNames[subIt].substr(0,4) != "Face")) { + QMessageBox::warning(this, tr("Selection error"), tr("Only faces can be picked")); + return; + } + Part::Feature* feat = static_cast(obj); + TopoDS_Shape ref = feat->Shape.getShape().getSubShape(subNames[subIt].c_str()); + if ((subNames[subIt].substr(0,4) == "Face")) { + if (!Fem::Tools::isPlanar(TopoDS::Face(ref))) { + QMessageBox::warning(this, tr("Selection error"), tr("Only planar faces can be picked")); + return; + } + } + for (std::vector::iterator itr=std::find(SubElements.begin(),SubElements.end(),subNames[subIt]); + itr!= SubElements.end(); + itr = std::find(++itr,SubElements.end(),subNames[subIt])) + {// for every sub element in selection that matches one in old list + if (obj==Objects[std::distance(SubElements.begin(),itr)]){//if selected sub element's object equals the one in old list then it was added before so don't add + addMe=false; + } + } + if (addMe){ + disconnect(ui->lw_references, SIGNAL(currentItemChanged(QListWidgetItem*,QListWidgetItem*)), + this, SLOT(setSelection(QListWidgetItem*))); + Objects.push_back(obj); + SubElements.push_back(subNames[subIt]); + ui->lw_references->addItem(makeRefText(obj, subNames[subIt])); + connect(ui->lw_references, SIGNAL(currentItemChanged(QListWidgetItem*,QListWidgetItem*)), + this, SLOT(setSelection(QListWidgetItem*))); + } + } + } + else { + QMessageBox::warning(this, tr("Selection error"), tr("Only one face can be selected for a plane rotation constraint!")); + Gui::Selection().clearSelection(); + return; + } + //Update UI + pcConstraint->References.setValues(Objects,SubElements); + updateUI(); + } + } +} + +void TaskFemConstraintPlaneRotation::removeFromSelection() +{ + std::vector selection = Gui::Selection().getSelectionEx(); //gets vector of selected objects of active document + if (selection.size()==0){ + QMessageBox::warning(this, tr("Selection error"), tr("Nothing selected!")); + return; + } + + Fem::ConstraintPlaneRotation* pcConstraint = static_cast(ConstraintView->getObject()); + std::vector Objects = pcConstraint->References.getValues(); + std::vector SubElements = pcConstraint->References.getSubValues(); + std::vector itemsToDel; + for (std::vector::iterator it = selection.begin(); it != selection.end(); ++it){//for every selected object + if (static_cast(it->getTypeName()).substr(0,4).compare(std::string("Part"))!=0){ + QMessageBox::warning(this, tr("Selection error"),tr("Selected object is not a part!")); + return; + } + + std::vector subNames=it->getSubNames(); + App::DocumentObject* obj = ConstraintView->getObject()->getDocument()->getObject(it->getFeatName()); + + for (unsigned int subIt=0;subIt<(subNames.size());++subIt){// for every selected sub element + for (std::vector::iterator itr=std::find(SubElements.begin(),SubElements.end(),subNames[subIt]); + itr!= SubElements.end(); + itr = std::find(++itr,SubElements.end(),subNames[subIt])) + {// for every sub element in selection that matches one in old list + if (obj==Objects[std::distance(SubElements.begin(),itr)]){//if selected sub element's object equals the one in old list then it was added before so mark for deletion + itemsToDel.push_back(std::distance(SubElements.begin(),itr)); + } + } + } + } + + std::sort(itemsToDel.begin(),itemsToDel.end()); + while (itemsToDel.size()>0){ + Objects.erase(Objects.begin()+itemsToDel.back()); + SubElements.erase(SubElements.begin()+itemsToDel.back()); + itemsToDel.pop_back(); + } + //Update UI + disconnect(ui->lw_references, SIGNAL(currentItemChanged(QListWidgetItem*,QListWidgetItem*)), + this, SLOT(setSelection(QListWidgetItem*))); + + ui->lw_references->clear(); + for (unsigned int j=0;jlw_references->addItem(makeRefText(Objects[j], SubElements[j])); + } + connect(ui->lw_references, SIGNAL(currentItemChanged(QListWidgetItem*,QListWidgetItem*)), + this, SLOT(setSelection(QListWidgetItem*))); + + pcConstraint->References.setValues(Objects,SubElements); + updateUI(); +} + +void TaskFemConstraintPlaneRotation::setSelection(QListWidgetItem* item){ + std::string docName=ConstraintView->getObject()->getDocument()->getName(); + + std::string s = item->text().toStdString(); + std::string delimiter = ":"; + + size_t pos = 0; + std::string objName; + std::string subName; + pos = s.find(delimiter); + objName = s.substr(0, pos); + s.erase(0, pos + delimiter.length()); + subName=s; + + Gui::Selection().clearSelection(); + Gui::Selection().addSelection(docName.c_str(),objName.c_str(),subName.c_str(),0,0,0); +} + +void TaskFemConstraintPlaneRotation::onReferenceDeleted() { + TaskFemConstraintPlaneRotation::removeFromSelection(); +} + +const std::string TaskFemConstraintPlaneRotation::getReferences() const +{ + int rows = ui->lw_references->model()->rowCount(); + std::vector items; + for (int r = 0; r < rows; r++) { + items.push_back(ui->lw_references->item(r)->text().toStdString()); + } + return TaskFemConstraint::getReferences(items); +} + + +void TaskFemConstraintPlaneRotation::changeEvent(QEvent *e){ +} + +//************************************************************************** +// TaskDialog +//++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ + +TaskDlgFemConstraintPlaneRotation::TaskDlgFemConstraintPlaneRotation(ViewProviderFemConstraintPlaneRotation *ConstraintView) +{ + this->ConstraintView = ConstraintView; + assert(ConstraintView); + this->parameter = new TaskFemConstraintPlaneRotation(ConstraintView);; + + Content.push_back(parameter); +} + +//==== calls from the TaskView =============================================================== + +void TaskDlgFemConstraintPlaneRotation::open() +{ + // a transaction is already open at creation time of the panel + if (!Gui::Command::hasPendingCommand()) { + QString msg = QObject::tr("Constraint planerotation"); + Gui::Command::openCommand((const char*)msg.toUtf8()); + ConstraintView->setVisible(true); + Gui::Command::doCommand(Gui::Command::Doc,ViewProviderFemConstraint::gethideMeshShowPartStr((static_cast(ConstraintView->getObject()))->getNameInDocument()).c_str()); //OvG: Hide meshes and show parts + } +} + +bool TaskDlgFemConstraintPlaneRotation::accept() +{ + std::string name = ConstraintView->getObject()->getNameInDocument(); + const TaskFemConstraintPlaneRotation* parameters = static_cast(parameter); + std::string scale = parameters->getScale(); //OvG: determine modified scale + Gui::Command::doCommand(Gui::Command::Doc,"App.ActiveDocument.%s.Scale = %s", name.c_str(), scale.c_str()); //OvG: implement modified scale + return TaskDlgFemConstraint::accept(); +} + +bool TaskDlgFemConstraintPlaneRotation::reject() +{ + Gui::Command::abortCommand(); + Gui::Command::doCommand(Gui::Command::Gui,"Gui.activeDocument().resetEdit()"); + Gui::Command::updateActive(); + + return true; +} + +#include "moc_TaskFemConstraintPlaneRotation.cpp" diff --git a/src/Mod/Fem/Gui/TaskFemConstraintPlaneRotation.h b/src/Mod/Fem/Gui/TaskFemConstraintPlaneRotation.h new file mode 100644 index 000000000000..4d4c350e313e --- /dev/null +++ b/src/Mod/Fem/Gui/TaskFemConstraintPlaneRotation.h @@ -0,0 +1,85 @@ +/*************************************************************************** + * Copyright (c) 2015 FreeCAD Developers * + * Authors: Michael Hindley * + * Ruan Olwagen * + * Oswald van Ginkel * + * Based on Force constraint by Jan Rheinländer * + * This file is part of the FreeCAD CAx development system. * + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Library General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + * This library is distributed in the hope that it will be useful, * + * but WITHOUT ANY WARRANTY; without even the implied warranty of * + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * + * GNU Library General Public License for more details. * + * * + * You should have received a copy of the GNU Library General Public * + * License along with this library; see the file COPYING.LIB. If not, * + * write to the Free Software Foundation, Inc., 59 Temple Place, * + * Suite 330, Boston, MA 02111-1307, USA * + * * + ***************************************************************************/ + + +#ifndef GUI_TASKVIEW_TaskFemConstraintPlaneRotation_H +#define GUI_TASKVIEW_TaskFemConstraintPlaneRotation_H + +#include +#include +#include +#include + +#include "TaskFemConstraint.h" +#include "ViewProviderFemConstraintPlaneRotation.h" + +#include +#include +#include +#include + +class Ui_TaskFemConstraintPlaneRotation; + +namespace FemGui { +class TaskFemConstraintPlaneRotation : public TaskFemConstraint +{ + Q_OBJECT + +public: + TaskFemConstraintPlaneRotation(ViewProviderFemConstraintPlaneRotation *ConstraintView,QWidget *parent = 0); + ~TaskFemConstraintPlaneRotation(); + const std::string getReferences() const; + +private Q_SLOTS: + void onReferenceDeleted(void); + + void addToSelection(); + void removeFromSelection(); + void setSelection(QListWidgetItem* item); + +protected: + void changeEvent(QEvent *e); + +private: + //void onSelectionChanged(const Gui::SelectionChanges& msg); + void updateUI(); + Ui_TaskFemConstraintPlaneRotation* ui; + +}; + +class TaskDlgFemConstraintPlaneRotation : public TaskDlgFemConstraint +{ + Q_OBJECT + +public: + TaskDlgFemConstraintPlaneRotation(ViewProviderFemConstraintPlaneRotation *ConstraintView); + void open(); + bool accept(); + bool reject(); +}; + +} //namespace FemGui + +#endif // GUI_TASKVIEW_TaskFemConstraintPlaneRotation_H diff --git a/src/Mod/Fem/Gui/TaskFemConstraintPlaneRotation.ui b/src/Mod/Fem/Gui/TaskFemConstraintPlaneRotation.ui new file mode 100644 index 000000000000..4b9da04766b5 --- /dev/null +++ b/src/Mod/Fem/Gui/TaskFemConstraintPlaneRotation.ui @@ -0,0 +1,49 @@ + + + TaskFemConstraintPlaneRotation + + + + 0 + 0 + 309 + 207 + + + + Form + + + + + + Select a single face, click Add or Remove + + + + + + + + + Add + + + + + + + Remove + + + + + + + + + + + + + diff --git a/src/Mod/Fem/Gui/ViewProviderFemConstraintPlaneRotation.cpp b/src/Mod/Fem/Gui/ViewProviderFemConstraintPlaneRotation.cpp new file mode 100644 index 000000000000..b49a2d5511ea --- /dev/null +++ b/src/Mod/Fem/Gui/ViewProviderFemConstraintPlaneRotation.cpp @@ -0,0 +1,191 @@ +/*************************************************************************** + * Copyright (c) 2015 FreeCAD Developers * + * Authors: Michael Hindley * + * Ruan Olwagen * + * Oswald van Ginkel * + * Based on Force constraint by Jan Rheinländer * + * This file is part of the FreeCAD CAx development system. * + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Library General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + * This library is distributed in the hope that it will be useful, * + * but WITHOUT ANY WARRANTY; without even the implied warranty of * + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * + * GNU Library General Public License for more details. * + * * + * You should have received a copy of the GNU Library General Public * + * License along with this library; see the file COPYING.LIB. If not, * + * write to the Free Software Foundation, Inc., 59 Temple Place, * + * Suite 330, Boston, MA 02111-1307, USA * + * * + ***************************************************************************/ + + +#include "PreCompiled.h" + +#ifndef _PreComp_ +# include +# include +# include +# include +# include +# include +# include +# include +# include +# include +# include +# include +# include +#endif + +#include "Mod/Fem/App/FemConstraintPlaneRotation.h" +#include "TaskFemConstraintPlaneRotation.h" +#include "ViewProviderFemConstraintPlaneRotation.h" +#include +#include + +using namespace FemGui; + +PROPERTY_SOURCE(FemGui::ViewProviderFemConstraintPlaneRotation, FemGui::ViewProviderFemConstraint) + +ViewProviderFemConstraintPlaneRotation::ViewProviderFemConstraintPlaneRotation() +{ + sPixmap = "fem-constraint-planerotation"; + //Note change "planerotation" in line above to new constraint name, make sure it is the same as in taskFem* cpp file + ADD_PROPERTY(FaceColor,(0.2f,0.3f,0.2f)); +} + +ViewProviderFemConstraintPlaneRotation::~ViewProviderFemConstraintPlaneRotation() +{ +} + +//FIXME setEdit needs a careful review +bool ViewProviderFemConstraintPlaneRotation::setEdit(int ModNum) +{ + if (ModNum == ViewProvider::Default) { + // When double-clicking on the item for this constraint the + // object unsets and sets its edit mode without closing + // the task panel + Gui::TaskView::TaskDialog *dlg = Gui::Control().activeDialog(); + TaskDlgFemConstraintPlaneRotation *constrDlg = qobject_cast(dlg); + if (constrDlg && constrDlg->getConstraintView() != this) + constrDlg = 0; // another constraint left open its task panel + if (dlg && !constrDlg) { + if (constraintDialog != NULL) { + // Ignore the request to open another dialog + return false; + } else { + constraintDialog = new TaskFemConstraintPlaneRotation(this); + return true; + } + } + + // clear the selection (convenience) + Gui::Selection().clearSelection(); + + // start the edit dialog + if (constrDlg) + Gui::Control().showDialog(constrDlg); + else + Gui::Control().showDialog(new TaskDlgFemConstraintPlaneRotation(this)); + return true; + } + else { + return ViewProviderDocumentObject::setEdit(ModNum); + } +} + +#define HEIGHT (0.5) +#define RADIUS (5) +//#define USE_MULTIPLE_COPY //OvG: MULTICOPY fails to update scaled display on initial drawing - so disable + +void ViewProviderFemConstraintPlaneRotation::updateData(const App::Property* prop) +{ + // Gets called whenever a property of the attached object changes + Fem::ConstraintPlaneRotation* pcConstraint = static_cast(this->getObject()); + float scaledradius = RADIUS * pcConstraint->Scale.getValue(); //OvG: Calculate scaled values once only + float scaledheight = HEIGHT * pcConstraint->Scale.getValue(); + + if (strcmp(prop->getName(),"Points") == 0) { + const std::vector& points = pcConstraint->Points.getValues(); + const std::vector& normals = pcConstraint->Normals.getValues(); + if (points.size() != normals.size()) + return; + std::vector::const_iterator n = normals.begin(); + + // Points and Normals are always updated together + pShapeSep->removeAllChildren(); + + for (std::vector::const_iterator p = points.begin(); p != points.end(); p++) { + //Define base and normal directions + SbVec3f base(p->x, p->y, p->z); + SbVec3f dir(n->x, n->y, n->z);//normal + + /* Note: + * This next part draws a temperature gauge in 3D to indicate the constraint visually. + * This serves as an example. Change or remove as needs be. + * It is possible to draw almost any basic 3D shape. See inventor's documentation + * This gets drawn at every point. + * */ + + ///Visual indication + //define separator + SoSeparator* sep = new SoSeparator(); + + ///draw a temp gauge,with sphere and a cylinder + //first move to correct postion + SoTranslation* trans = new SoTranslation(); + SbVec3f newPos=base+scaledradius*dir*0.08; + trans->translation.setValue(newPos); + sep->addChild(trans); + + //adjust orientation + SoRotation* rot = new SoRotation(); + rot->rotation.setValue(SbRotation(SbVec3f(1,0,0),dir)); + sep->addChild(rot); + + //define color of shape + SoMaterial* myMaterial = new SoMaterial; + myMaterial->diffuseColor.set1Value(0,SbColor(0,1,0));//RGB + //myMaterial->diffuseColor.set1Value(1,SbColor(0,0,1));//possible to adjust sides separately + sep->addChild(myMaterial); + + //draw a sphere + //SoSphere* sph = new SoSphere(); + //sph->radius.setValue(scaledradius*0.75); + //sep->addChild(sph); + //translate postion + //SoTranslation* trans2 = new SoTranslation(); + //trans2->translation.setValue(SbVec3f(0,scaledheight*0.375,0)); + //sep->addChild(trans2); + //draw a cylinder + SoCylinder* cyl = new SoCylinder(); + cyl->height.setValue(scaledheight*0.5); + cyl->radius.setValue(scaledradius*0.375); + sep->addChild(cyl); + //translate postion + //SoTranslation* trans3 = new SoTranslation(); + //trans3->translation.setValue(SbVec3f(0,scaledheight*0.05,0)); + //sep->addChild(trans3); + //define color of shape + SoMaterial *myMaterial2 = new SoMaterial; + myMaterial2->diffuseColor.set1Value(0,SbColor(1,1,1));//RGB + sep->addChild(myMaterial2); + //draw a cylinder + //SoCylinder* cyl2 = new SoCylinder(); + //cyl2->height.setValue(scaledheight*0.25); + //cyl2->radius.setValue(scaledradius*0.375); + //sep->addChild(cyl2); + + pShapeSep->addChild(sep); + + n++; + } + } + // Gets called whenever a property of the attached object changes + ViewProviderFemConstraint::updateData(prop); +} diff --git a/src/Mod/Fem/Gui/ViewProviderFemConstraintPlaneRotation.h b/src/Mod/Fem/Gui/ViewProviderFemConstraintPlaneRotation.h new file mode 100644 index 000000000000..3ede68a48a01 --- /dev/null +++ b/src/Mod/Fem/Gui/ViewProviderFemConstraintPlaneRotation.h @@ -0,0 +1,48 @@ +/*************************************************************************** + * Copyright (c) 2015 FreeCAD Developers * + * Authors: Michael Hindley * + * Ruan Olwagen * + * Oswald van Ginkel * + * Based on Force constraint by Jan Rheinländer * + * This file is part of the FreeCAD CAx development system. * + * * + * This library is free software; you can redistribute it and/or * + * modify it under the terms of the GNU Library General Public * + * License as published by the Free Software Foundation; either * + * version 2 of the License, or (at your option) any later version. * + * * + * This library is distributed in the hope that it will be useful, * + * but WITHOUT ANY WARRANTY; without even the implied warranty of * + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * + * GNU Library General Public License for more details. * + * * + * You should have received a copy of the GNU Library General Public * + * License along with this library; see the file COPYING.LIB. If not, * + * write to the Free Software Foundation, Inc., 59 Temple Place, * + * Suite 330, Boston, MA 02111-1307, USA * + * * + ***************************************************************************/ + +#ifndef GUI_VIEWPROVIDERFEMCONSTRAINTPLANEROTATION_H +#define GUI_VIEWPROVIDERFEMCONSTRAINTPLANEROTATION_H + +#include "ViewProviderFemConstraint.h" + +namespace FemGui { + +class FemGuiExport ViewProviderFemConstraintPlaneRotation : public FemGui::ViewProviderFemConstraint +{ + PROPERTY_HEADER(FemGui::ViewProviderFemConstraintPlaneRotation); + +public: + ViewProviderFemConstraintPlaneRotation(); + virtual ~ViewProviderFemConstraintPlaneRotation(); + virtual void updateData(const App::Property*); + +protected: + virtual bool setEdit(int ModNum); +}; + +} + +#endif // GUI_VIEWPROVIDERFEMCONSTRAINTPLANEROTATION_H diff --git a/src/Mod/Fem/Gui/Workbench.cpp b/src/Mod/Fem/Gui/Workbench.cpp index 18f69402730b..032c1fedbff2 100755 --- a/src/Mod/Fem/Gui/Workbench.cpp +++ b/src/Mod/Fem/Gui/Workbench.cpp @@ -67,6 +67,7 @@ Gui::ToolBarItem* Workbench::setupToolBars() const << "Separator" << "Fem_ConstraintFixed" << "Fem_ConstraintDisplacement" + << "Fem_ConstraintPlaneRotation" << "Fem_ConstraintContact" << "Separator" << "Fem_ConstraintSelfWeight" @@ -119,6 +120,7 @@ Gui::MenuItem* Workbench::setupMenuBar() const << "Separator" << "Fem_ConstraintFixed" << "Fem_ConstraintDisplacement" + << "Fem_ConstraintPlaneRotation" << "Fem_ConstraintContact" << "Separator" << "Fem_ConstraintSelfWeight"