diff --git a/src/Mod/Fem/Gui/ViewProviderFemMesh.cpp b/src/Mod/Fem/Gui/ViewProviderFemMesh.cpp index 3b98a34cf..f877dfb14 100755 --- a/src/Mod/Fem/Gui/ViewProviderFemMesh.cpp +++ b/src/Mod/Fem/Gui/ViewProviderFemMesh.cpp @@ -494,10 +494,6 @@ PyObject * ViewProviderFemMesh::getPyObject() void ViewProviderFemMesh::setColorByNodeId(const std::map &NodeColorMap) { - pcShapeMaterial->diffuseColor; - - pcMatBinding->value = SoMaterialBinding::PER_VERTEX_INDEXED; - long startId = NodeColorMap.begin()->first; long endId = (--NodeColorMap.end())->first; @@ -505,60 +501,34 @@ void ViewProviderFemMesh::setColorByNodeId(const std::map &Node for(std::map::const_iterator it=NodeColorMap.begin();it!=NodeColorMap.end();++it) colorVec[it->first-startId] = it->second; - // resizing and writing the color vector: - pcShapeMaterial->diffuseColor.setNum(vNodeElementIdx.size()); - SbColor* colors = pcShapeMaterial->diffuseColor.startEditing(); + setColorByNodeIdHelper(colorVec); - //int i=0; - //for(std::vector::const_iterator it=vNodeElementIdx.begin() - // ;it!=vNodeElementIdx.end() - // ;++it,i++){ - // const std::map::const_iterator pos = NodeColorMap.find(*it); - // if(pos == NodeColorMap.end()) - // colors[i] = SbColor(0,1,0); - // else - // colors[i] = SbColor(pos->second.r,pos->second.g,pos->second.b); - //} - - int i=0; - for(std::vector::const_iterator it=vNodeElementIdx.begin() - ;it!=vNodeElementIdx.end() - ;++it,i++) - colors[i] = SbColor(colorVec[*it-1].r,colorVec[*it-1].g,colorVec[*it-1].b); - - - pcShapeMaterial->diffuseColor.finishEditing(); } void ViewProviderFemMesh::setColorByNodeId(const std::vector &NodeIds,const std::vector &NodeColors) { - pcShapeMaterial->diffuseColor; - - pcMatBinding->value = SoMaterialBinding::PER_VERTEX_INDEXED; long startId = *(std::min_element(NodeIds.begin(), NodeIds.end())); long endId = *(std::max_element(NodeIds.begin(), NodeIds.end())); std::vector colorVec(endId-startId+2,App::Color(0,1,0)); - int i=0; + long i=0; for(std::vector::const_iterator it=NodeIds.begin();it!=NodeIds.end();++it,i++) colorVec[*it-startId] = NodeColors[i]; + + setColorByNodeIdHelper(colorVec); + +} + +void ViewProviderFemMesh::setColorByNodeIdHelper(const std::vector &colorVec) +{ + pcMatBinding->value = SoMaterialBinding::PER_VERTEX_INDEXED; + // resizing and writing the color vector: pcShapeMaterial->diffuseColor.setNum(vNodeElementIdx.size()); SbColor* colors = pcShapeMaterial->diffuseColor.startEditing(); - //int i=0; - //for(std::vector::const_iterator it=vNodeElementIdx.begin() - // ;it!=vNodeElementIdx.end() - // ;++it,i++){ - // const std::map::const_iterator pos = NodeColorMap.find(*it); - // if(pos == NodeColorMap.end()) - // colors[i] = SbColor(0,1,0); - // else - // colors[i] = SbColor(pos->second.r,pos->second.g,pos->second.b); - //} - - i=0; + long i=0; for(std::vector::const_iterator it=vNodeElementIdx.begin() ;it!=vNodeElementIdx.end() ;++it,i++) @@ -578,18 +548,38 @@ void ViewProviderFemMesh::resetColorByNodeId(void) } void ViewProviderFemMesh::setDisplacementByNodeId(const std::map &NodeDispMap) +{ + long startId = NodeDispMap.begin()->first; + long endId = (--NodeDispMap.end())->first; + + std::vector vecVec(endId-startId+2,Base::Vector3d()); + + for(std::map::const_iterator it=NodeDispMap.begin();it!=NodeDispMap.end();++it) + vecVec[it->first-startId] = it->second; + + setDisplacementByNodeIdHelper(vecVec,startId); +} + +void ViewProviderFemMesh::setDisplacementByNodeId(const std::vector &NodeIds,const std::vector &NodeDisps) +{ + long startId = *(std::min_element(NodeIds.begin(), NodeIds.end())); + long endId = *(std::max_element(NodeIds.begin(), NodeIds.end())); + + std::vector vecVec(endId-startId+2,Base::Vector3d()); + + long i=0; + for(std::vector::const_iterator it=NodeIds.begin();it!=NodeIds.end();++it,i++) + vecVec[*it-startId] = NodeDisps[i]; + + setDisplacementByNodeIdHelper(vecVec,startId); +} + +void ViewProviderFemMesh::setDisplacementByNodeIdHelper(const std::vector& DispVector,long startId) { DisplacementVector.resize(vNodeElementIdx.size()); int i=0; - for(std::vector::const_iterator it=vNodeElementIdx.begin() - ;it!=vNodeElementIdx.end() - ;++it,i++){ - const std::map::const_iterator pos = NodeDispMap.find(*it); - if(pos == NodeDispMap.end()) - DisplacementVector[i] = Base::Vector3d(0.0,0.0,0.0); - else - DisplacementVector[i] = pos->second; - } + for(std::vector::const_iterator it=vNodeElementIdx.begin();it!=vNodeElementIdx.end();++it,i++) + DisplacementVector[i] = DispVector[*it-startId]; animateNodes(1.0); } @@ -602,6 +592,9 @@ void ViewProviderFemMesh::resetDisplacementByNodeId(void) /// reaply the node displacement with a certain factor and do a redraw void ViewProviderFemMesh::animateNodes(double factor) { + if(DisplacementVector.size() == 0) + return; + float x,y,z; // set the point coordinates long sz = pcCoords->point.getNum(); diff --git a/src/Mod/Fem/Gui/ViewProviderFemMesh.h b/src/Mod/Fem/Gui/ViewProviderFemMesh.h index 16e6effb0..174591685 100755 --- a/src/Mod/Fem/Gui/ViewProviderFemMesh.h +++ b/src/Mod/Fem/Gui/ViewProviderFemMesh.h @@ -111,6 +111,7 @@ public: void resetColorByNodeId(void); /// set the displacement for each node void setDisplacementByNodeId(const std::map &NodeDispMap); + void setDisplacementByNodeId(const std::vector &NodeIds,const std::vector &NodeDisps); /// reset the view of the node displacement void resetDisplacementByNodeId(void); /// reaply the node displacement with a certain factor and do a redraw @@ -136,6 +137,8 @@ protected: /// get called by the container whenever a property has been changed virtual void onChanged(const App::Property* prop); + void setColorByNodeIdHelper(const std::vector &); + void setDisplacementByNodeIdHelper(const std::vector& DispVector,long startId); /// index of elements to their triangles std::vector vFaceElementIdx; std::vector vNodeElementIdx; diff --git a/src/Mod/Fem/Gui/ViewProviderFemMeshPy.xml b/src/Mod/Fem/Gui/ViewProviderFemMeshPy.xml index 2af3aacdf..d120bfd11 100644 --- a/src/Mod/Fem/Gui/ViewProviderFemMeshPy.xml +++ b/src/Mod/Fem/Gui/ViewProviderFemMeshPy.xml @@ -20,12 +20,17 @@ - - - - - - + + + + + + + + + + + Postprocessing color of the nodes. The faces between the nodes gets interpolated. diff --git a/src/Mod/Fem/Gui/ViewProviderFemMeshPyImp.cpp b/src/Mod/Fem/Gui/ViewProviderFemMeshPyImp.cpp index cbea69e5f..a24a843af 100644 --- a/src/Mod/Fem/Gui/ViewProviderFemMeshPyImp.cpp +++ b/src/Mod/Fem/Gui/ViewProviderFemMeshPyImp.cpp @@ -35,6 +35,19 @@ PyObject* ViewProviderFemMeshPy::animate(PyObject * args) Py_Return; } +App::Color calcColor(double value,double min, double max) +{ + if (value < min) + return App::Color (0.0,1.0,0.0); + if (value > max) + return App::Color (1.0,0.0,0.0); + if ( value < (min + (max-min)/2.0 )) + return App::Color ((value-min) / ((max-min)/2.0),1.0,0.0) ; + else + return App::Color (1.0,1-((value-min-((max-min)/2.0)) / ((max-min)/2.0)),0.0); +} + + PyObject* ViewProviderFemMeshPy::setNodeColorByResult(PyObject *args) { PyObject *object=0; @@ -42,6 +55,23 @@ PyObject* ViewProviderFemMeshPy::setNodeColorByResult(PyObject *args) App::DocumentObject* obj = static_cast(object)->getDocumentObjectPtr(); if (obj && obj->getTypeId().isDerivedFrom(Fem::FemResultValue::getClassTypeId())){ Fem::FemResultValue *result = static_cast(obj); + const std::vector & Ids = result->ElementNumbers.getValues() ; + const std::vector & Vals = result->Values.getValues() ; + std::vector NodeColors(Vals.size()); + float max = 0.0; + for(std::vector::const_iterator it= Vals.begin();it!=Vals.end();++it) + if(*it > max) + max = *it; + + // fill up color vector + long i=0; + for(std::vector::const_iterator it= Vals.begin();it!=Vals.end();++it,i++) + NodeColors[i] = calcColor(*it,0.0,max); + + // set the color to the view-provider + this->getViewProviderFemMeshPtr()->setColorByNodeId(Ids,NodeColors); + + }else if (obj && obj->getTypeId().isDerivedFrom(Fem::FemResultVector::getClassTypeId())){ Fem::FemResultVector *result = static_cast(obj); const std::vector & Ids = result->ElementNumbers.getValues() ; @@ -51,22 +81,13 @@ PyObject* ViewProviderFemMeshPy::setNodeColorByResult(PyObject *args) for(std::vector::const_iterator it= Vecs.begin();it!=Vecs.end();++it) if(it->Length() > max) max = it->Length(); + + // fill up color vector long i=0; - for(std::vector::const_iterator it= Vecs.begin();it!=Vecs.end();++it,i++){ - double value = it->Length(); - double min = 0.0; - - if (value < min) - NodeColors[i] = App::Color (0.0,1.0,0.0); - else if (value > max) - NodeColors[i] = App::Color (1.0,0.0,0.0); - else if ( value < (min + (max-min)/2.0 )) - NodeColors[i] = App::Color ((value-min) / ((max-min)/2.0),1.0,0.0) ; - else - NodeColors[i] = App::Color (1.0,1-((value-min-((max-min)/2.0)) / ((max-min)/2.0)),0.0); - - } - + for(std::vector::const_iterator it= Vecs.begin();it!=Vecs.end();++it,i++) + NodeColors[i] = calcColor(it->Length(),0.0,max); + + // set the color to the view-provider this->getViewProviderFemMeshPtr()->setColorByNodeId(Ids,NodeColors); @@ -80,7 +101,28 @@ PyObject* ViewProviderFemMeshPy::setNodeColorByResult(PyObject *args) } +PyObject* ViewProviderFemMeshPy::setNodeDisplacementByResult(PyObject *args) +{ + PyObject *object=0; + if (PyArg_ParseTuple(args,"O!",&(App::DocumentObjectPy::Type), &object)) { + App::DocumentObject* obj = static_cast(object)->getDocumentObjectPtr(); + if (obj && obj->getTypeId().isDerivedFrom(Fem::FemResultVector::getClassTypeId())){ + Fem::FemResultVector *result = static_cast(obj); + const std::vector & Ids = result->ElementNumbers.getValues() ; + const std::vector & Vecs = result->Values.getValues() ; + // set the displacement to the view-provider + this->getViewProviderFemMeshPtr()->setDisplacementByNodeId(Ids,Vecs); + + }else{ + PyErr_SetString(PyExc_Exception, "Argument has to be a ResultVector!"); + return 0; + } + } + + Py_Return; + +} Py::Dict ViewProviderFemMeshPy::getNodeColor(void) const { //return Py::List(); diff --git a/src/Mod/Fem/MechanicalAnalysis.py b/src/Mod/Fem/MechanicalAnalysis.py index 8a3c1caf1..2dc0cb98c 100644 --- a/src/Mod/Fem/MechanicalAnalysis.py +++ b/src/Mod/Fem/MechanicalAnalysis.py @@ -380,25 +380,20 @@ class _ResultControlTaskPanel: self.formUi.lineEdit_Max.setText(str(maxL)) self.formUi.doubleSpinBox_MinValueColor.setValue(maxL) - colors = [] - for i in values: - colors.append( FemLib.colorValue(i.Length,0.0,maxL) ) - self.MeshObject.ViewObject.NodeColor = dict(zip( self.DisplacementObject.ElementNumbers,colors)) + self.MeshObject.ViewObject.setNodeColorByResult(self.DisplacementObject) + def setDisplacement(self): if self.DisplacementObject: - values = self.DisplacementObject.Values - self.MeshObject.ViewObject.NodeDisplacement = dict(zip( self.DisplacementObject.ElementNumbers,values)) + self.MeshObject.ViewObject.setNodeDisplacementByResult(self.DisplacementObject) def setColorStress(self): if self.StressObject: values = self.StressObject.Values maxVal = max(values) self.formUi.doubleSpinBox_MinValueColor.setValue(maxVal) - colors = [] - for i in values: - colors.append( FemLib.colorValue(i,0.0,maxVal) ) - self.MeshObject.ViewObject.ElementColor = dict(zip(self.StressObject.ElementNumbers,colors)) - + + self.MeshObject.ViewObject.setNodeColorByResult(self.StressObject) + def update(self): 'fills the widgets'