From: rnv Date: Sat, 13 Nov 2010 11:14:11 +0000 (+0000) Subject: Implementation point 1 of the "20948: EDF 1468 SMESH: Histogram of the quality contro... X-Git-Url: http://git.salome-platform.org/gitweb/?a=commitdiff_plain;h=80ccf6a58da57077a0f489e50a95e27c9e033f67;p=modules%2Fsmesh.git Implementation point 1 of the "20948: EDF 1468 SMESH: Histogram of the quality controls" feature. --- diff --git a/resources/SalomeApp.xml b/resources/SalomeApp.xml index 7f3b9d7e4..7af58b731 100644 --- a/resources/SalomeApp.xml +++ b/resources/SalomeApp.xml @@ -65,6 +65,9 @@ + + + diff --git a/src/OBJECT/Makefile.am b/src/OBJECT/Makefile.am index 0e8cdabd9..219350562 100644 --- a/src/OBJECT/Makefile.am +++ b/src/OBJECT/Makefile.am @@ -34,7 +34,9 @@ salomeinclude_HEADERS = \ SMESH_DeviceActor.h \ SMESH_PreviewActorsCollection.h \ SMESH_ExtractGeometry.h \ - SMESH_FaceOrientationFilter.h + SMESH_FaceOrientationFilter.h \ + SMESH_ScalarBarActor.h + # Libraries targets @@ -46,7 +48,8 @@ dist_libSMESHObject_la_SOURCES = \ SMESH_PreviewActorsCollection.cxx \ SMESH_ExtractGeometry.cxx \ SMESH_ActorUtils.cxx \ - SMESH_FaceOrientationFilter.cxx + SMESH_FaceOrientationFilter.cxx \ + SMESH_ScalarBarActor.cxx libSMESHObject_la_CPPFLAGS = \ $(QT_INCLUDES) \ diff --git a/src/OBJECT/SMESH_Actor.cxx b/src/OBJECT/SMESH_Actor.cxx index 8386faf3a..4afc7f4ca 100644 --- a/src/OBJECT/SMESH_Actor.cxx +++ b/src/OBJECT/SMESH_Actor.cxx @@ -30,6 +30,7 @@ #include "SMESH_DeviceActor.h" #include "SMESH_ObjectDef.h" #include "SMESH_ControlsDef.hxx" +#include "SMESH_ScalarBarActor.h" #include "VTKViewer_CellCenters.h" #include "VTKViewer_ExtractUnstructuredGrid.h" #include "VTKViewer_FramedTextActor.h" @@ -64,7 +65,6 @@ #include #include -#include #include #include @@ -371,7 +371,7 @@ SMESH_ActorDef::SMESH_ActorDef() //Controls - Aspect Ratio: incorrect colors of the best and worst values myLookupTable->SetHueRange(0.667,0.0); - myScalarBarActor = vtkScalarBarActor::New(); + myScalarBarActor = SMESH_ScalarBarActor::New(); myScalarBarActor->SetVisibility(false); myScalarBarActor->SetLookupTable(myLookupTable); @@ -1939,6 +1939,21 @@ void SMESH_ActorDef::UpdateScalarBar() if( mgr->hasValue( "SMESH", "scalar_bar_num_colors" ) ) anIntVal = mgr->integerValue( "SMESH", "scalar_bar_num_colors", anIntVal ); myScalarBarActor->SetMaximumNumberOfColors( anIntVal == 0 ? 64 : anIntVal ); + + bool distributionVisibility = mgr->booleanValue("SMESH","distribution_visibility"); + myScalarBarActor->SetDistributionVisibility(distributionVisibility); + + int coloringType = mgr->integerValue("SMESH", "distribution_coloring_type", 0); + myScalarBarActor->SetDistributionColoringType(coloringType); + + QColor distributionColor = mgr->colorValue("SMESH", "distribution_color", + QColor(255, 255, 255)); + double rgb[3]; + rgb[0]= distributionColor.red()/255.; + rgb[1]= distributionColor.green()/255.; + rgb[2]= distributionColor.blue()/255.; + myScalarBarActor->SetDistributionColor(rgb); + } diff --git a/src/OBJECT/SMESH_Actor.h b/src/OBJECT/SMESH_Actor.h index c2d46098a..24a57a00a 100644 --- a/src/OBJECT/SMESH_Actor.h +++ b/src/OBJECT/SMESH_Actor.h @@ -35,7 +35,7 @@ class vtkUnstructuredGrid; -class vtkScalarBarActor; +class SMESH_ScalarBarActor; class vtkPlane; class vtkImplicitBoolean; @@ -128,7 +128,7 @@ class SMESHOBJECT_EXPORT SMESH_Actor: public SALOME_Actor virtual eControl GetControlMode() = 0; virtual SMESH::Controls::FunctorPtr GetFunctor() = 0; - virtual vtkScalarBarActor* GetScalarBarActor() = 0; + virtual SMESH_ScalarBarActor* GetScalarBarActor() = 0; virtual void RemoveAllClippingPlanes() = 0; virtual vtkIdType GetNumberOfClippingPlanes() = 0; diff --git a/src/OBJECT/SMESH_ActorDef.h b/src/OBJECT/SMESH_ActorDef.h index 9b1c4df1d..09b2232f0 100644 --- a/src/OBJECT/SMESH_ActorDef.h +++ b/src/OBJECT/SMESH_ActorDef.h @@ -59,24 +59,20 @@ class vtkPolyDataMapper; class vtkUnstructuredGrid; class vtkMergeFilter; class vtkPolyData; - class vtkMapper; class vtkActor2D; class vtkMaskPoints; class vtkLabeledDataMapper; class vtkSelectVisiblePoints; - -class vtkScalarBarActor; class vtkLookupTable; - class vtkPlane; class vtkImplicitBoolean; - class vtkTimeStamp; class VTKViewer_CellCenters; class SMESH_DeviceActor; +class SMESH_ScalarBarActor; class SMESH_ActorDef : public SMESH_Actor @@ -187,7 +183,7 @@ class SMESH_ActorDef : public SMESH_Actor virtual eControl GetControlMode(){ return myControlMode;} virtual SMESH::Controls::FunctorPtr GetFunctor() { return myFunctor; } - virtual vtkScalarBarActor* GetScalarBarActor(){ return myScalarBarActor;} + virtual SMESH_ScalarBarActor* GetScalarBarActor(){ return myScalarBarActor;} virtual void RemoveAllClippingPlanes(); virtual vtkIdType GetNumberOfClippingPlanes(); @@ -216,7 +212,7 @@ class SMESH_ActorDef : public SMESH_Actor TVisualObjPtr myVisualObj; vtkTimeStamp* myTimeStamp; - vtkScalarBarActor* myScalarBarActor; + SMESH_ScalarBarActor* myScalarBarActor; vtkLookupTable* myLookupTable; vtkProperty* mySurfaceProp; diff --git a/src/OBJECT/SMESH_DeviceActor.cxx b/src/OBJECT/SMESH_DeviceActor.cxx index 4be8cadec..600a4987c 100644 --- a/src/OBJECT/SMESH_DeviceActor.cxx +++ b/src/OBJECT/SMESH_DeviceActor.cxx @@ -26,6 +26,7 @@ // Module : SMESH // #include "SMESH_DeviceActor.h" +#include "SMESH_ScalarBarActor.h" #include "SMESH_ExtractGeometry.h" #include "SMESH_ControlsDef.hxx" #include "SMESH_ActorUtils.h" @@ -48,7 +49,6 @@ #include #include -#include #include #include #include @@ -282,7 +282,7 @@ SMESH_DeviceActor void SMESH_DeviceActor ::SetControlMode(SMESH::Controls::FunctorPtr theFunctor, - vtkScalarBarActor* theScalarBarActor, + SMESH_ScalarBarActor* theScalarBarActor, vtkLookupTable* theLookupTable) { bool anIsInitialized = theFunctor; @@ -310,6 +310,12 @@ SMESH_DeviceActor double aValue = aNumericalFunctor->GetValue(anObjId); aScalars->SetValue(i,aValue); } + int nbIntervals = theScalarBarActor->GetMaximumNumberOfColors(); + std::vector nbEvents; + std::vector funValues; + aNumericalFunctor->GetHistogram(nbIntervals, nbEvents, funValues); + theScalarBarActor->SetDistribution(nbEvents); + }else if(Predicate* aPredicate = dynamic_cast(theFunctor.get())){ for(vtkIdType i = 0; i < aNbCells; i++){ vtkIdType anId = myExtractUnstructuredGrid->GetInputId(i); @@ -336,7 +342,7 @@ SMESH_DeviceActor void SMESH_DeviceActor ::SetExtControlMode(SMESH::Controls::FunctorPtr theFunctor, - vtkScalarBarActor* theScalarBarActor, + SMESH_ScalarBarActor* theScalarBarActor, vtkLookupTable* theLookupTable) { bool anIsInitialized = theFunctor; @@ -469,6 +475,16 @@ SMESH_DeviceActor myMergeFilter->SetScalars(aDataSet); aDataSet->Delete(); } + + //Set Distribution + if(NumericalFunctor* aNumericalFunctor = dynamic_cast(theFunctor.get())){ + int nbIntervals = theScalarBarActor->GetMaximumNumberOfColors(); + std::vector nbEvents; + std::vector funValues; + aNumericalFunctor->GetHistogram(nbIntervals, nbEvents, funValues); + theScalarBarActor->SetDistribution(nbEvents); + } + } GetMapper()->SetScalarVisibility(anIsInitialized); theScalarBarActor->SetVisibility(anIsInitialized); diff --git a/src/OBJECT/SMESH_DeviceActor.h b/src/OBJECT/SMESH_DeviceActor.h index 7c506bd38..1e598fa84 100644 --- a/src/OBJECT/SMESH_DeviceActor.h +++ b/src/OBJECT/SMESH_DeviceActor.h @@ -42,7 +42,6 @@ class vtkProperty; class vtkMergeFilter; class vtkShrinkFilter; class vtkUnstructuredGrid; -class vtkScalarBarActor; class vtkLookupTable; class vtkImplicitBoolean; class vtkPassThroughFilter; @@ -54,6 +53,7 @@ class VTKViewer_PolyDataMapper; class SMESH_ExtractGeometry; class SMESH_FaceOrientationFilter; +class SMESH_ScalarBarActor; class SMESHOBJECT_EXPORT SMESH_DeviceActor: public vtkLODActor{ @@ -120,10 +120,10 @@ class SMESHOBJECT_EXPORT SMESH_DeviceActor: public vtkLODActor{ vtkUnstructuredGrid* GetUnstructuredGrid(); void SetControlMode(SMESH::Controls::FunctorPtr theFunctor, - vtkScalarBarActor* theScalarBarActor, + SMESH_ScalarBarActor* theScalarBarActor, vtkLookupTable* theLookupTable); void SetExtControlMode(SMESH::Controls::FunctorPtr theFunctor, - vtkScalarBarActor* theScalarBarActor, + SMESH_ScalarBarActor* theScalarBarActor, vtkLookupTable* theLookupTable); void SetExtControlMode(SMESH::Controls::FunctorPtr theFunctor); diff --git a/src/OBJECT/SMESH_PreviewActorsCollection.cxx b/src/OBJECT/SMESH_PreviewActorsCollection.cxx index d014af78c..059edd927 100644 --- a/src/OBJECT/SMESH_PreviewActorsCollection.cxx +++ b/src/OBJECT/SMESH_PreviewActorsCollection.cxx @@ -35,7 +35,6 @@ // VTK includes #include -#include #include #include #include diff --git a/src/OBJECT/SMESH_ScalarBarActor.cxx b/src/OBJECT/SMESH_ScalarBarActor.cxx new file mode 100644 index 000000000..3f7622672 --- /dev/null +++ b/src/OBJECT/SMESH_ScalarBarActor.cxx @@ -0,0 +1,923 @@ +// Copyright (C) 2007-2010 CEA/DEN, EDF R&D, OPEN CASCADE +// +// Copyright (C) 2003-2007 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN, +// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS +// +// This library is free software; you can redistribute it and/or +// modify it under the terms of the GNU Lesser General Public +// License as published by the Free Software Foundation; either +// version 2.1 of the License. +// +// 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 +// Lesser General Public License for more details. +// +// You should have received a copy of the GNU Lesser General Public +// License along with this library; if not, write to the Free Software +// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +// +// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +// +// File : SMESH_ScalarBarActor.cxx +// Author : Roman NIKOLAEV +// Module : SMESH +// + +#include "SMESH_ScalarBarActor.h" + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define SHRINK_COEF 0.08; + +vtkStandardNewMacro(SMESH_ScalarBarActor); + +vtkCxxSetObjectMacro(SMESH_ScalarBarActor,LookupTable,vtkScalarsToColors); +vtkCxxSetObjectMacro(SMESH_ScalarBarActor,LabelTextProperty,vtkTextProperty); +vtkCxxSetObjectMacro(SMESH_ScalarBarActor,TitleTextProperty,vtkTextProperty); + +//---------------------------------------------------------------------------- +// Instantiate object with 64 maximum colors; 5 labels; %%-#6.3g label +// format, no title, and vertical orientation. The initial scalar bar +// size is (0.05 x 0.8) of the viewport size. +SMESH_ScalarBarActor::SMESH_ScalarBarActor() { + this->LookupTable = NULL; + this->Position2Coordinate->SetValue(0.17, 0.8); + + this->PositionCoordinate->SetCoordinateSystemToNormalizedViewport(); + this->PositionCoordinate->SetValue(0.82,0.1); + + this->MaximumNumberOfColors = 64; + this->NumberOfLabels = 5; + this->NumberOfLabelsBuilt = 0; + this->Orientation = VTK_ORIENT_VERTICAL; + this->Title = NULL; + + this->LabelTextProperty = vtkTextProperty::New(); + this->LabelTextProperty->SetFontSize(12); + this->LabelTextProperty->SetBold(1); + this->LabelTextProperty->SetItalic(1); + this->LabelTextProperty->SetShadow(1); + this->LabelTextProperty->SetFontFamilyToArial(); + + this->TitleTextProperty = vtkTextProperty::New(); + this->TitleTextProperty->ShallowCopy(this->LabelTextProperty); + + this->LabelFormat = new char[8]; + sprintf(this->LabelFormat,"%s","%-#6.3g"); + + this->TitleMapper = vtkTextMapper::New(); + this->TitleActor = vtkActor2D::New(); + this->TitleActor->SetMapper(this->TitleMapper); + this->TitleActor->GetPositionCoordinate()-> + SetReferenceCoordinate(this->PositionCoordinate); + + this->TextMappers = NULL; + this->TextActors = NULL; + + this->ScalarBar = vtkPolyData::New(); + this->ScalarBarMapper = vtkPolyDataMapper2D::New(); + this->ScalarBarMapper->SetInput(this->ScalarBar); + this->ScalarBarActor = vtkActor2D::New(); + this->ScalarBarActor->SetMapper(this->ScalarBarMapper); + this->ScalarBarActor->GetPositionCoordinate()-> + SetReferenceCoordinate(this->PositionCoordinate); + this->LastOrigin[0] = 0; + this->LastOrigin[1] = 0; + this->LastSize[0] = 0; + this->LastSize[1] = 0; + + + // rnv begin + // Customization of the vtkScalarBarActor to show distribution histogram. + myDistribution = vtkPolyData::New(); + myDistributionMapper = vtkPolyDataMapper2D::New(); + myDistributionMapper->SetInput(this->myDistribution); + + myDistributionActor = vtkActor2D::New(); + myDistributionActor->SetMapper(this->myDistributionMapper); + myDistributionActor->GetPositionCoordinate()-> + SetReferenceCoordinate(this->PositionCoordinate); + + // By default distribution histogram is invisible + myDistributionActor->SetVisibility(0); + + // By default monocolor + myDistributionColoringType = SMESH_MONOCOLOR_TYPE; + // rnv end +} + +//---------------------------------------------------------------------------- +// Release any graphics resources that are being consumed by this actor. +// The parameter window could be used to determine which graphic +// resources to release. +void SMESH_ScalarBarActor::ReleaseGraphicsResources(vtkWindow *win) +{ + this->TitleActor->ReleaseGraphicsResources(win); + if (this->TextMappers != NULL ) + { + for (int i=0; i < this->NumberOfLabelsBuilt; i++) + { + this->TextActors[i]->ReleaseGraphicsResources(win); + } + } + this->ScalarBarActor->ReleaseGraphicsResources(win); + // rnv begin + // Customization of the vtkScalarBarActor to show distribution histogram. + myDistributionActor->ReleaseGraphicsResources(win); +} + + +/*--------------------------------------------------------------------------*/ +SMESH_ScalarBarActor::~SMESH_ScalarBarActor() { + if (this->LabelFormat) + { + delete [] this->LabelFormat; + this->LabelFormat = NULL; + } + + this->TitleMapper->Delete(); + this->TitleActor->Delete(); + + if (this->TextMappers != NULL ) + { + for (int i=0; i < this->NumberOfLabelsBuilt; i++) + { + this->TextMappers[i]->Delete(); + this->TextActors[i]->Delete(); + } + delete [] this->TextMappers; + delete [] this->TextActors; + } + + this->ScalarBar->Delete(); + this->ScalarBarMapper->Delete(); + this->ScalarBarActor->Delete(); + + if (this->Title) + { + delete [] this->Title; + this->Title = NULL; + } + + this->SetLookupTable(NULL); + this->SetLabelTextProperty(NULL); + this->SetTitleTextProperty(NULL); + + // rnv begin + // Customization of the vtkScalarBarActor to show distribution histogram: + myDistribution->Delete(); + myDistributionMapper->Delete(); + myDistributionActor->Delete(); + // rnv end +} + +//---------------------------------------------------------------------------- +int SMESH_ScalarBarActor::RenderOverlay(vtkViewport *viewport) +{ + int renderedSomething = 0; + int i; + + // Everything is built, just have to render + if (this->Title != NULL) + { + renderedSomething += this->TitleActor->RenderOverlay(viewport); + } + this->ScalarBarActor->RenderOverlay(viewport); + this->myDistributionActor->RenderOverlay(viewport); + if( this->TextActors == NULL) + { + vtkWarningMacro(<<"Need a mapper to render a scalar bar"); + return renderedSomething; + } + + for (i=0; iNumberOfLabels; i++) + { + renderedSomething += this->TextActors[i]->RenderOverlay(viewport); + } + + renderedSomething = (renderedSomething > 0)?(1):(0); + + return renderedSomething; +} + + +//---------------------------------------------------------------------------- +int SMESH_ScalarBarActor::RenderOpaqueGeometry(vtkViewport *viewport) +{ + int renderedSomething = 0; + int i; + int size[2]; + + if (!this->LookupTable) + { + vtkWarningMacro(<<"Need a mapper to render a scalar bar"); + return 0; + } + + if (!this->TitleTextProperty) + { + vtkErrorMacro(<<"Need title text property to render a scalar bar"); + return 0; + } + + if (!this->LabelTextProperty) + { + vtkErrorMacro(<<"Need label text property to render a scalar bar"); + return 0; + } + + // Check to see whether we have to rebuild everything + int positionsHaveChanged = 0; + if (viewport->GetMTime() > this->BuildTime || + (viewport->GetVTKWindow() && + viewport->GetVTKWindow()->GetMTime() > this->BuildTime)) + { + // if the viewport has changed we may - or may not need + // to rebuild, it depends on if the projected coords chage + int *barOrigin; + barOrigin = this->PositionCoordinate->GetComputedViewportValue(viewport); + size[0] = + this->Position2Coordinate->GetComputedViewportValue(viewport)[0] - + barOrigin[0]; + size[1] = + this->Position2Coordinate->GetComputedViewportValue(viewport)[1] - + barOrigin[1]; + if (this->LastSize[0] != size[0] || + this->LastSize[1] != size[1] || + this->LastOrigin[0] != barOrigin[0] || + this->LastOrigin[1] != barOrigin[1]) + { + positionsHaveChanged = 1; + } + } + + // Check to see whether we have to rebuild everything + if (positionsHaveChanged || + this->GetMTime() > this->BuildTime || + this->LookupTable->GetMTime() > this->BuildTime || + this->LabelTextProperty->GetMTime() > this->BuildTime || + this->TitleTextProperty->GetMTime() > this->BuildTime) + { + vtkDebugMacro(<<"Rebuilding subobjects"); + + // Delete previously constructed objects + // + if (this->TextMappers != NULL ) + { + for (i=0; i < this->NumberOfLabelsBuilt; i++) + { + this->TextMappers[i]->Delete(); + this->TextActors[i]->Delete(); + } + delete [] this->TextMappers; + delete [] this->TextActors; + } + + // Build scalar bar object; determine its type + // + // is this a vtkLookupTable or a subclass of vtkLookupTable + // with its scale set to log + // NOTE: it's possible we could to without the 'lut' variable + // later in the code, but if the vtkLookupTableSafeDownCast operation + // fails for some reason, this code will break in new ways. So, the 'LUT' + // variable is used for this operation only + vtkLookupTable *LUT = vtkLookupTable::SafeDownCast( this->LookupTable ); + int isLogTable = 0; + if ( LUT ) + { + if ( LUT->GetScale() == VTK_SCALE_LOG10 ) + { + isLogTable = 1; + } + } + + // we hard code how many steps to display + vtkScalarsToColors *lut = this->LookupTable; + int numColors = this->MaximumNumberOfColors; + double *range = lut->GetRange(); + + int numPts = 2*(numColors + 1); + vtkPoints *pts = vtkPoints::New(); + pts->SetNumberOfPoints(numPts); + vtkCellArray *polys = vtkCellArray::New(); + polys->Allocate(polys->EstimateSize(numColors,4)); + vtkUnsignedCharArray *colors = vtkUnsignedCharArray::New(); + colors->SetNumberOfComponents(3); + colors->SetNumberOfTuples(numColors); + + + // rnv begin + // Customization of the vtkScalarBarActor to show distribution histogram. + bool distrVisibility = (numColors == this->myNbValues.size()); + vtkPoints *distrPts; + vtkCellArray *distrPolys; + vtkUnsignedCharArray *distColors = 0; + int numDistrPts = 0, numPositiveVal=0, maxValue=0; + if(!distrVisibility) + vtkDebugMacro(<<" Distribution invisible, because numColors == this->myNbValues.size()"); + + if (distrVisibility && GetDistributionVisibility()) { + for( i=0 ;iSetNumberOfPoints(numDistrPts); + distrPolys->Allocate(distrPolys->EstimateSize(numPositiveVal,4)); + this->myDistribution->Initialize(); + this->myDistribution->SetPoints(distrPts); + this->myDistribution->SetPolys(distrPolys); + distrPts->Delete(); + distrPolys->Delete(); + if ( myDistributionColoringType == SMESH_MULTICOLOR_TYPE ) { + distColors = vtkUnsignedCharArray::New(); + distColors->SetNumberOfComponents(3); + distColors->SetNumberOfTuples(numPositiveVal); + this->myDistribution->GetCellData()->SetScalars(distColors); + distColors->Delete(); + } else if( myDistributionColoringType == SMESH_MONOCOLOR_TYPE ){ + this->myDistribution->GetCellData()->SetScalars(NULL); + } + } else { + myDistribution->Reset(); + } + // rnv end + + this->ScalarBarActor->SetProperty(this->GetProperty()); + this->ScalarBar->Initialize(); + this->ScalarBar->SetPoints(pts); + this->ScalarBar->SetPolys(polys); + this->ScalarBar->GetCellData()->SetScalars(colors); + pts->Delete(); polys->Delete(); colors->Delete(); + + // get the viewport size in display coordinates + int *barOrigin, barWidth, barHeight, distrHeight; + barOrigin = this->PositionCoordinate->GetComputedViewportValue(viewport); + size[0] = + this->Position2Coordinate->GetComputedViewportValue(viewport)[0] - + barOrigin[0]; + size[1] = + this->Position2Coordinate->GetComputedViewportValue(viewport)[1] - + barOrigin[1]; + this->LastOrigin[0] = barOrigin[0]; + this->LastOrigin[1] = barOrigin[1]; + this->LastSize[0] = size[0]; + this->LastSize[1] = size[1]; + + // Update all the composing objects + this->TitleActor->SetProperty(this->GetProperty()); + this->TitleMapper->SetInput(this->Title); + if (this->TitleTextProperty->GetMTime() > this->BuildTime) + { + // Shallow copy here so that the size of the title prop is not affected + // by the automatic adjustment of its text mapper's size (i.e. its + // mapper's text property is identical except for the font size + // which will be modified later). This allows text actors to + // share the same text property, and in that case specifically allows + // the title and label text prop to be the same. + this->TitleMapper->GetTextProperty()->ShallowCopy(this->TitleTextProperty); + this->TitleMapper->GetTextProperty()->SetJustificationToCentered(); + } + + // find the best size for the title font + int titleSize[2]; + this->SizeTitle(titleSize, size, viewport); + + // find the best size for the ticks + int labelSize[2]; + this->AllocateAndSizeLabels(labelSize, size, viewport,range); + this->NumberOfLabelsBuilt = this->NumberOfLabels; + + // generate points + double x[3]; x[2] = 0.0; + double delta, itemH, shrink; + if ( this->Orientation == VTK_ORIENT_VERTICAL ) { + // rnv begin + // Customization of the vtkScalarBarActor to show distribution histogram. + double delimeter=0.0; + if(GetDistributionVisibility() && distrVisibility) { + delimeter=0.01*size[0]; //1 % from horizontal size of the full presentation size. + barWidth = size[0] - 4 - labelSize[0]; + distrHeight = barWidth/2; + } else { + barWidth = size[0] - 4 - labelSize[0]; + distrHeight = 0; + } + + barHeight = (int)(0.86*size[1]); + delta=(double)barHeight/numColors; + + for ( i=0; iSetPoint(2*i,x); + x[0] = barWidth; + pts->SetPoint(2*i+1,x); + } + + if(GetDistributionVisibility() && distrVisibility) { + // Distribution points + shrink = delta*SHRINK_COEF; + vtkIdType distPtsId=0; + vtkIdType distPtsIds[4]; + for(i=0; iSetPoint(distPtsId++,x); + + // second point of polygon (quadrangle) + x[0] = itemH; + distPtsIds[1] = distPtsId; + distrPts->SetPoint(distPtsId++,x); + + x[1] = i*delta+delta-shrink; + + // third point of polygon (quadrangle) + x[0] = 0; + distPtsIds[3] = distPtsId; + distrPts->SetPoint(distPtsId++,x); + + // fourth point of polygon (quadrangle) + x[0] = itemH; + distPtsIds[2] = distPtsId; + distrPts->SetPoint(distPtsId++,x); + + //Inser Quadrangle + distrPolys->InsertNextCell(4,distPtsIds); + } + } + } + } + // rnv end + else { + barWidth = size[0]; + + // rnv begin + // Customization of the vtkScalarBarActor to show distribution histogram. + double coef1, delimeter=0.0; + if(GetDistributionVisibility() && distrVisibility) { + coef1=0.62; + distrHeight = (int)((coef1/2)*size[1]); + //delimeter between distribution diagram and scalar bar + delimeter=0.02*size[1]; + } + else { + coef1=0.4; + barHeight = (int)(coef1*size[1]); + distrHeight = 0; + } + + barHeight = (int)(coef1*size[1]); + + delta=(double)barWidth/numColors; + for (i=0; iSetPoint(2*i,x); + x[1] = distrHeight + delimeter; + pts->SetPoint(2*i+1,x); + } + + if(GetDistributionVisibility() && distrVisibility) { + // Distribution points + shrink = delta*SHRINK_COEF; + vtkIdType distPtsId=0; + vtkIdType distPtsIds[4]; + for(i=0; iSetPoint(distPtsId++,x); + + // second point of polygon (quadrangle) + x[0] = i*delta+shrink; + x[1] = itemH; + distPtsIds[3] = distPtsId; + distrPts->SetPoint(distPtsId++,x); + + // third point of polygon (quadrangle) + x[0] = i*delta+delta-shrink; + x[1] = 0; + distPtsIds[1] = distPtsId; + distrPts->SetPoint(distPtsId++,x); + + // fourth point of polygon (quadrangle) + x[0] = i*delta+delta-shrink; + x[1] = itemH; + distPtsIds[2] = distPtsId; + distrPts->SetPoint(distPtsId++,x); + + // Add polygon into poly data + distrPolys->InsertNextCell(4,distPtsIds); + } + } + } + // rnv end + } + + //polygons & cell colors + unsigned char *rgba, *rgb; + vtkIdType ptIds[4], dcCount=0; + for (i=0; iInsertNextCell(4,ptIds); + + if ( isLogTable ) + { + double rgbval = log10(range[0]) + + i*(log10(range[1])-log10(range[0]))/(numColors -1); + rgba = lut->MapValue(pow(10.0,rgbval)); + } + else + { + rgba = lut->MapValue(range[0] + (range[1] - range[0])* + ((double)i /(numColors-1.0))); + } + + rgb = colors->GetPointer(3*i); //write into array directly + rgb[0] = rgba[0]; + rgb[1] = rgba[1]; + rgb[2] = rgba[2]; + + // rnv begin + // Customization of the vtkScalarBarActor to show distribution histogram. + if(myNbValues[i] && myDistributionColoringType == SMESH_MULTICOLOR_TYPE && GetDistributionVisibility() && distrVisibility) + { + rgb = distColors->GetPointer(3*dcCount); //write into array directly + rgb[0] = rgba[0]; + rgb[1] = rgba[1]; + rgb[2] = rgba[2]; + dcCount++; + } + } + + // Now position everything properly + // + double val; + if (this->Orientation == VTK_ORIENT_VERTICAL) + { + int sizeTextData[2]; + + // center the title + this->TitleActor->SetPosition(size[0]/2, 0.9*size[1]); + + for (i=0; i < this->NumberOfLabels; i++) + { + if (this->NumberOfLabels > 1) + { + val = (double)i/(this->NumberOfLabels-1) *barHeight; + } + else + { + val = 0.5*barHeight; + } + this->TextMappers[i]->GetSize(viewport,sizeTextData); + this->TextMappers[i]->GetTextProperty()->SetJustificationToLeft(); + this->TextActors[i]->SetPosition(barWidth+3, + val - sizeTextData[1]/2); + } + } + else + { + this->TitleActor->SetPosition(size[0]/2, + barHeight + labelSize[1] + 0.1*size[1]); + for (i=0; i < this->NumberOfLabels; i++) + { + this->TextMappers[i]->GetTextProperty()->SetJustificationToCentered(); + if (this->NumberOfLabels > 1) + { + val = (double)i/(this->NumberOfLabels-1) * barWidth; + } + else + { + val = 0.5*barWidth; + } + this->TextActors[i]->SetPosition(val, barHeight + 0.05*size[1]); + } + } + + this->BuildTime.Modified(); + } + + // Everything is built, just have to render + if (this->Title != NULL) + { + renderedSomething += this->TitleActor->RenderOpaqueGeometry(viewport); + } + this->ScalarBarActor->RenderOpaqueGeometry(viewport); + this->myDistributionActor->RenderOpaqueGeometry(viewport); + for (i=0; iNumberOfLabels; i++) + { + renderedSomething += this->TextActors[i]->RenderOpaqueGeometry(viewport); + } + + renderedSomething = (renderedSomething > 0)?(1):(0); + + return renderedSomething; +} + +//---------------------------------------------------------------------------- +void SMESH_ScalarBarActor::PrintSelf(ostream& os, vtkIndent indent) +{ + this->Superclass::PrintSelf(os,indent); + + if ( this->LookupTable ) + { + os << indent << "Lookup Table:\n"; + this->LookupTable->PrintSelf(os,indent.GetNextIndent()); + } + else + { + os << indent << "Lookup Table: (none)\n"; + } + + if (this->TitleTextProperty) + { + os << indent << "Title Text Property:\n"; + this->TitleTextProperty->PrintSelf(os,indent.GetNextIndent()); + } + else + { + os << indent << "Title Text Property: (none)\n"; + } + + if (this->LabelTextProperty) + { + os << indent << "Label Text Property:\n"; + this->LabelTextProperty->PrintSelf(os,indent.GetNextIndent()); + } + else + { + os << indent << "Label Text Property: (none)\n"; + } + + os << indent << "Title: " << (this->Title ? this->Title : "(none)") << "\n"; + os << indent << "Maximum Number Of Colors: " + << this->MaximumNumberOfColors << "\n"; + os << indent << "Number Of Labels: " << this->NumberOfLabels << "\n"; + os << indent << "Number Of Labels Built: " << this->NumberOfLabelsBuilt << "\n"; + + os << indent << "Orientation: "; + if ( this->Orientation == VTK_ORIENT_HORIZONTAL ) + { + os << "Horizontal\n"; + } + else + { + os << "Vertical\n"; + } + + os << indent << "Label Format: " << this->LabelFormat << "\n"; +} + +//---------------------------------------------------------------------------- +void SMESH_ScalarBarActor::ShallowCopy(vtkProp *prop) +{ + SMESH_ScalarBarActor *a = SMESH_ScalarBarActor::SafeDownCast(prop); + if ( a != NULL ) + { + this->SetPosition2(a->GetPosition2()); + this->SetLookupTable(a->GetLookupTable()); + this->SetMaximumNumberOfColors(a->GetMaximumNumberOfColors()); + this->SetOrientation(a->GetOrientation()); + this->SetLabelTextProperty(a->GetLabelTextProperty()); + this->SetTitleTextProperty(a->GetTitleTextProperty()); + this->SetLabelFormat(a->GetLabelFormat()); + this->SetTitle(a->GetTitle()); + this->GetPositionCoordinate()->SetCoordinateSystem( + a->GetPositionCoordinate()->GetCoordinateSystem()); + this->GetPositionCoordinate()->SetValue( + a->GetPositionCoordinate()->GetValue()); + this->GetPosition2Coordinate()->SetCoordinateSystem( + a->GetPosition2Coordinate()->GetCoordinateSystem()); + this->GetPosition2Coordinate()->SetValue( + a->GetPosition2Coordinate()->GetValue()); + } + + // Now do superclass + this->vtkActor2D::ShallowCopy(prop); +} + +//---------------------------------------------------------------------------- +void SMESH_ScalarBarActor::AllocateAndSizeLabels(int *labelSize, + int *size, + vtkViewport *viewport, + double *range) +{ + labelSize[0] = labelSize[1] = 0; + + this->TextMappers = new vtkTextMapper * [this->NumberOfLabels]; + this->TextActors = new vtkActor2D * [this->NumberOfLabels]; + + char string[512]; + + double val; + int i; + + // TODO: this should be optimized, maybe by keeping a list of + // allocated mappers, in order to avoid creation/destruction of + // their underlying text properties (i.e. each time a mapper is + // created, text properties are created and shallow-assigned a font size + // which value might be "far" from the target font size). + + // is this a vtkLookupTable or a subclass of vtkLookupTable + // with its scale set to log + vtkLookupTable *LUT = vtkLookupTable::SafeDownCast( this->LookupTable ); + int isLogTable = 0; + if ( LUT ) + { + if ( LUT->GetScale() == VTK_SCALE_LOG10 ) + { + isLogTable = 1; + } + } + + for (i=0; i < this->NumberOfLabels; i++) + { + this->TextMappers[i] = vtkTextMapper::New(); + + if ( isLogTable ) + { + double lval; + if (this->NumberOfLabels > 1) + { + lval = log10(range[0]) + (double)i/(this->NumberOfLabels-1) * + (log10(range[1])-log10(range[0])); + } + else + { + lval = log10(range[0]) + 0.5*(log10(range[1])-log10(range[0])); + } + val = pow(10.0,lval); + } + else + { + if (this->NumberOfLabels > 1) + { + val = range[0] + + (double)i/(this->NumberOfLabels-1) * (range[1]-range[0]); + } + else + { + val = range[0] + 0.5*(range[1]-range[0]); + } + } + + sprintf(string, this->LabelFormat, val); + this->TextMappers[i]->SetInput(string); + + // Shallow copy here so that the size of the label prop is not affected + // by the automatic adjustment of its text mapper's size (i.e. its + // mapper's text property is identical except for the font size + // which will be modified later). This allows text actors to + // share the same text property, and in that case specifically allows + // the title and label text prop to be the same. + this->TextMappers[i]->GetTextProperty()->ShallowCopy( + this->LabelTextProperty); + + this->TextActors[i] = vtkActor2D::New(); + this->TextActors[i]->SetMapper(this->TextMappers[i]); + this->TextActors[i]->SetProperty(this->GetProperty()); + this->TextActors[i]->GetPositionCoordinate()-> + SetReferenceCoordinate(this->PositionCoordinate); + } + + if (this->NumberOfLabels) + { + int targetWidth, targetHeight; + // rnv begin + // Customization of the vtkScalarBarActor to show distribution histogram. + bool distrVisibility = this->MaximumNumberOfColors == this->myNbValues.size(); + double coef; + if( GetDistributionVisibility() && distrVisibility ) + if(this->Orientation == VTK_ORIENT_VERTICAL) + coef = 0.4; + else + coef = 0.18; + else + if(this->Orientation == VTK_ORIENT_VERTICAL) + coef = 0.6; + else + coef=0.25; + + + if ( this->Orientation == VTK_ORIENT_VERTICAL ) + { + targetWidth = (int)(coef*size[0]); + targetHeight = (int)(0.86*size[1]/this->NumberOfLabels); + } + else + { + targetWidth = (int)(size[0]*0.8/this->NumberOfLabels); + targetHeight = (int)(coef*size[1]); + } + // rnv end + + vtkTextMapper::SetMultipleConstrainedFontSize(viewport, + targetWidth, + targetHeight, + this->TextMappers, + this->NumberOfLabels, + labelSize); + } +} + +//---------------------------------------------------------------------------- +void SMESH_ScalarBarActor::SizeTitle(int *titleSize, + int *size, + vtkViewport *viewport) +{ + titleSize[0] = titleSize[1] = 0; + + if (this->Title == NULL || !strlen(this->Title)) + { + return; + } + + int targetWidth, targetHeight; + + targetWidth = size[0]; + // rnv begin + // Customization of the vtkScalarBarActor to show distribution histogram. + bool distrVisibility = this->MaximumNumberOfColors == this->myNbValues.size(); + double coef; + if( GetDistributionVisibility() && distrVisibility ) + coef=0.18; + else + coef=0.25; + + if ( this->Orientation == VTK_ORIENT_VERTICAL ) + { + targetHeight = (int)(0.1*size[1]); + } + else + { + targetHeight = (int)(coef*size[1]); + } + + this->TitleMapper->SetConstrainedFontSize( + viewport, targetWidth, targetHeight); + + this->TitleMapper->GetSize(viewport, titleSize); +} + + +/*--------------------------------------------------------------------------*/ +void SMESH_ScalarBarActor::SetDistributionVisibility(int flag) { + myDistributionActor->SetVisibility(flag); + Modified(); +} + + +/*--------------------------------------------------------------------------*/ +int SMESH_ScalarBarActor::GetDistributionVisibility() { + return myDistributionActor->GetVisibility(); +} + + +void SMESH_ScalarBarActor::SetDistribution(std::vector theNbValues) { + myNbValues = theNbValues; +} + + +void SMESH_ScalarBarActor::SetDistributionColor (double rgb[3]) { + myDistributionActor->GetProperty()->SetColor(rgb); + Modified(); +} + +void SMESH_ScalarBarActor::GetDistributionColor (double rgb[3]) { + myDistributionActor->GetProperty()->GetColor(rgb); +} diff --git a/src/OBJECT/SMESH_ScalarBarActor.h b/src/OBJECT/SMESH_ScalarBarActor.h new file mode 100644 index 000000000..0f895cd57 --- /dev/null +++ b/src/OBJECT/SMESH_ScalarBarActor.h @@ -0,0 +1,246 @@ +// Copyright (C) 2007-2010 CEA/DEN, EDF R&D, OPEN CASCADE +// +// Copyright (C) 2003-2007 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN, +// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS +// +// This library is free software; you can redistribute it and/or +// modify it under the terms of the GNU Lesser General Public +// License as published by the Free Software Foundation; either +// version 2.1 of the License. +// +// 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 +// Lesser General Public License for more details. +// +// You should have received a copy of the GNU Lesser General Public +// License along with this library; if not, write to the Free Software +// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +// +// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com +// + +// SMESH SCALAR BAR : 2D Actor for the visualization scalar bar with the distribution diagram +// it is customized vtkScalarBarActor. +// File : SMESH_ScalarBarActor.h +// Author : Roman NIKOLAEV +// Module : SMESH + + +// .NAME vtkScalarBarActor - Create a scalar bar with labels +// .SECTION Description +// vtkScalarBarActor creates a scalar bar with annotation text. A scalar +// bar is a legend that indicates to the viewer the correspondence between +// color value and data value. The legend consists of a rectangular bar +// made of rectangular pieces each colored a constant value. Since +// vtkScalarBarActor is a subclass of vtkActor2D, it is drawn in the image +// plane (i.e., in the renderer's viewport) on top of the 3D graphics window. +// +// To use vtkScalarBarActor you must associate a vtkScalarsToColors (or +// subclass) with it. The lookup table defines the colors and the +// range of scalar values used to map scalar data. Typically, the +// number of colors shown in the scalar bar is not equal to the number +// of colors in the lookup table, in which case sampling of +// the lookup table is performed. +// +// Other optional capabilities include specifying the fraction of the +// viewport size (both x and y directions) which will control the size +// of the scalar bar and the number of annotation labels. The actual position +// of the scalar bar on the screen is controlled by using the +// vtkActor2D::SetPosition() method (by default the scalar bar is +// centered in the viewport). Other features include the ability to +// orient the scalar bar horizontally of vertically and controlling +// the format (printf style) with which to print the labels on the +// scalar bar. Also, the vtkScalarBarActor's property is applied to +// the scalar bar and annotation (including layer, and +// compositing operator). +// +// Set the text property/attributes of the title and the labels through the +// vtkTextProperty objects associated to this actor. +// +// .SECTION Caveats +// If a vtkLogLookupTable is specified as the lookup table to use, then the +// labels are created using a logarithmic scale. +// +// .SECTION See Also +// vtkActor2D vtkTextProperty vtkTextMapper vtkPolyDataMapper2D + +#ifndef SMESH_SCALAR_BAR_ACTOR_H +#define SMESH_SCALAR_BAR_ACTOR_H + +#include + +#include + +#include + +class vtkPolyData; +class vtkPolyDataMapper2D; +class vtkScalarsToColors; +class vtkTextMapper; +class vtkTextProperty; + +#define VTK_ORIENT_HORIZONTAL 0 +#define VTK_ORIENT_VERTICAL 1 + +#define SMESH_MONOCOLOR_TYPE 0 +#define SMESH_MULTICOLOR_TYPE 1 + + +class SMESHOBJECT_EXPORT SMESH_ScalarBarActor: public vtkActor2D { + public: + void PrintSelf(ostream& os, vtkIndent indent); + + vtkTypeMacro(SMESH_ScalarBarActor,vtkActor2D); + + // Description: + // Instantiate object with 64 maximum colors; 5 labels; %%-#6.3g label + // format, no title, and vertical orientation. The initial scalar bar + // size is (0.05 x 0.8) of the viewport size. + static SMESH_ScalarBarActor *New(); + + // Description: + // Draw the scalar bar and annotation text to the screen. + int RenderOpaqueGeometry(vtkViewport* viewport); + int RenderTranslucentGeometry(vtkViewport*) { return 0; }; + int RenderOverlay(vtkViewport* viewport); + + // Description: + // Release any graphics resources that are being consumed by this actor. + // The parameter window could be used to determine which graphic + // resources to release. + virtual void ReleaseGraphicsResources(vtkWindow *); + + // Description: + // Set/Get the vtkLookupTable to use. The lookup table specifies the number + // of colors to use in the table (if not overridden), as well as the scalar + // range. + virtual void SetLookupTable(vtkScalarsToColors*); + vtkGetObjectMacro(LookupTable,vtkScalarsToColors); + + // Description: + // Set/Get the maximum number of scalar bar segments to show. This may + // differ from the number of colors in the lookup table, in which case + // the colors are samples from the lookup table. + vtkSetClampMacro(MaximumNumberOfColors, int, 2, VTK_LARGE_INTEGER); + vtkGetMacro(MaximumNumberOfColors, int); + + // Description: + // Set/Get the number of annotation labels to show. + vtkSetClampMacro(NumberOfLabels, int, 0, 64); + vtkGetMacro(NumberOfLabels, int); + + // Description: + // Control the orientation of the scalar bar. + vtkSetClampMacro(Orientation,int,VTK_ORIENT_HORIZONTAL, VTK_ORIENT_VERTICAL); + vtkGetMacro(Orientation, int); + void SetOrientationToHorizontal() + {this->SetOrientation(VTK_ORIENT_HORIZONTAL);}; + void SetOrientationToVertical() {this->SetOrientation(VTK_ORIENT_VERTICAL);}; + + // Description: + // Set/Get the title text property. + virtual void SetTitleTextProperty(vtkTextProperty *p); + vtkGetObjectMacro(TitleTextProperty,vtkTextProperty); + + // Description: + // Set/Get the labels text property. + virtual void SetLabelTextProperty(vtkTextProperty *p); + vtkGetObjectMacro(LabelTextProperty,vtkTextProperty); + + // Description: + // Set/Get the format with which to print the labels on the scalar + // bar. + vtkSetStringMacro(LabelFormat); + vtkGetStringMacro(LabelFormat); + + // Description: + // Set/Get the title of the scalar bar actor, + vtkSetStringMacro(Title); + vtkGetStringMacro(Title); + + // Description: + // Shallow copy of a scalar bar actor. Overloads the virtual vtkProp method. + void ShallowCopy(vtkProp *prop); + + // Description: + // Set visibility of the distribution histogram + // rnv: Customization of the vtkScalarBarActor to show distribution histogram: + virtual void SetDistributionVisibility(int flag); + + // Description: + // Set visibility of the distribution histogram + // rnv: Customization of the vtkScalarBarActor to show distribution histogram: + virtual int GetDistributionVisibility(); + // Description: + // Set distribution + virtual void SetDistribution(std::vector theNbValues); + + // Description: + // Set distribution coloring type (SMESH_MONOCOLOR_TYPE or SMESH_MULTICOLOR_TYPE) + void SetDistributionColoringType(int theDistributionColoringType) {myDistributionColoringType = theDistributionColoringType;Modified();} + + // Description: + // Get distribution coloring type ((SMESH_MONOCOLOR_TYPE or SMESH_MULTICOLOR_TYPE)) + int GetDistributionColoringType() {return myDistributionColoringType;} + + // Description: + // Set Distribution Color + void SetDistributionColor (double rgb[3]); + + // Description: + // Get Distribution Color + void GetDistributionColor (double rgb[3]); + + + + protected: + SMESH_ScalarBarActor(); + ~SMESH_ScalarBarActor(); + + vtkScalarsToColors *LookupTable; + vtkTextProperty *TitleTextProperty; + vtkTextProperty *LabelTextProperty; + + int MaximumNumberOfColors; + int NumberOfLabels; + int NumberOfLabelsBuilt; + int Orientation; + char *Title; + char *LabelFormat; + + vtkTextMapper **TextMappers; + virtual void AllocateAndSizeLabels(int *labelSize, int *size, + vtkViewport *viewport, double *range); + + + + private: + vtkTextMapper *TitleMapper; + vtkActor2D *TitleActor; + + vtkActor2D **TextActors; + + vtkPolyData *ScalarBar; + vtkPolyDataMapper2D *ScalarBarMapper; + vtkActor2D *ScalarBarActor; + + vtkTimeStamp BuildTime; + int LastSize[2]; + int LastOrigin[2]; + + void SizeTitle(int *titleSize, int *size, vtkViewport *viewport); + + // rnv: Customization of the vtkScalarBarActor to show distribution histogram: + vtkPolyData* myDistribution; //Distribution polygonal data + vtkActor2D* myDistributionActor; //Distribution actor + vtkPolyDataMapper2D* myDistributionMapper; //Distribution mapper + std::vector myNbValues; //Nb values for the range + int myDistributionColoringType; //Distribution color type (monocolor or multicolor) + + private: + SMESH_ScalarBarActor(const SMESH_ScalarBarActor&); // Not implemented. + void operator=(const SMESH_ScalarBarActor&); // Not implemented. +}; + +#endif //SMESH_SCALAR_BAR_ACTOR_H diff --git a/src/SMESHGUI/SMESHGUI.cxx b/src/SMESHGUI/SMESHGUI.cxx index d4defd2dc..46876d3d7 100644 --- a/src/SMESHGUI/SMESHGUI.cxx +++ b/src/SMESHGUI/SMESHGUI.cxx @@ -85,6 +85,7 @@ #include #include +#include #include #include "SMESH_ControlsDef.hxx" @@ -134,7 +135,6 @@ #include // VTK includes -#include #include #include #include @@ -772,7 +772,7 @@ if ( anIO->hasEntry() ) { SMESH_Actor* anActor = SMESH::FindActorByEntry( anIO->getEntry() ); if ( anActor && anActor->GetScalarBarActor() && anActor->GetControlMode() != SMESH_Actor::eNone ) { - vtkScalarBarActor* aScalarBarActor = anActor->GetScalarBarActor(); + SMESH_ScalarBarActor* aScalarBarActor = anActor->GetScalarBarActor(); SMESH::Controls::FunctorPtr aFunctor = anActor->GetFunctor(); if ( aScalarBarActor && aFunctor ) { SMESH::Controls::NumericalFunctor* aNumFun = dynamic_cast( aFunctor.get() ); @@ -815,6 +815,24 @@ } } + void ShowDistribution() { + LightApp_SelectionMgr* aSel = SMESHGUI::selectionMgr(); + SALOME_ListIO selected; + if ( aSel ) + aSel->selectedObjects( selected ); + + if ( selected.Extent() == 1 ) { + Handle(SALOME_InteractiveObject) anIO = selected.First(); + if ( anIO->hasEntry() ) { + SMESH_Actor* anActor = SMESH::FindActorByEntry( anIO->getEntry() ); + if ( anActor && anActor->GetScalarBarActor() && anActor->GetControlMode() != SMESH_Actor::eNone ) { + SMESH_ScalarBarActor *aScalarBarActor = anActor->GetScalarBarActor(); + aScalarBarActor->SetDistributionVisibility(!aScalarBarActor->GetDistributionVisibility()); + } + } + } + } + void DisableAutoColor(){ LightApp_SelectionMgr *aSel = SMESHGUI::selectionMgr(); SALOME_ListIO selected; @@ -1798,6 +1816,13 @@ bool SMESHGUI::OnGUIEvent( int theCommandID ) break; } + case 203: + { + // show/ distribution + ::ShowDistribution(); + break; + } + // Auto-color case 1136: ::AutoColor(); @@ -3219,6 +3244,7 @@ void SMESHGUI::initialize( CAM_Application* app ) createSMESHAction( 200, "RESET" ); createSMESHAction( 201, "SCALAR_BAR_PROP" ); createSMESHAction( 202, "SAVE_DISTRIBUTION" ); + createSMESHAction( 203, "SHOW_DISTRIBUTION","",0, true ); createSMESHAction( 211, "WIRE", "ICON_WIRE", 0, true ); createSMESHAction( 212, "SHADE", "ICON_SHADE", 0, true ); createSMESHAction( 213, "SHRINK", "ICON_SHRINK", 0, true ); @@ -3822,6 +3848,11 @@ void SMESHGUI::initialize( CAM_Application* app ) popupMgr()->insert( action( 202 ), anId, -1 ); // SAVE_DISTRIBUTION popupMgr()->setRule( action( 202 ), aMeshInVTK + "&& isNumFunctor", QtxPopupMgr::VisibleRule ); + popupMgr()->insert( action( 203 ), anId, -1 ); // SHOW_DISTRIBUTION + popupMgr()->setRule( action( 203 ), aMeshInVTK + "&& isNumFunctor", QtxPopupMgr::VisibleRule ); + popupMgr()->setRule( action( 203 ), aMeshInVTK + "&& isNumFunctor && isDistributionVisible", QtxPopupMgr::ToggleRule); + + popupMgr()->insert( separator(), -1, -1 ); //------------------------------------------------- @@ -4353,6 +4384,18 @@ void SMESHGUI::createPreferences() setPreferenceProperty( hh, "min", 0.0 ); setPreferenceProperty( hh, "max", 1.0 ); setPreferenceProperty( hh, "step", 0.1 ); + + int distributionGr = addPreference( tr( "SMESH_DISTRIBUTION_SCALARBAR" ), sbarTab, LightApp_Preferences::Auto, "SMESH", "distribution_visibility" ); + int coloringType = addPreference( tr( "SMESH_DISTRIBUTION_COLORING_TYPE" ), distributionGr, LightApp_Preferences::Selector, "SMESH", "distribution_coloring_type" ); + setPreferenceProperty( distributionGr, "columns", 3 ); + QStringList types; + types.append( tr( "SMESH_MONOCOLOR" ) ); + types.append( tr( "SMESH_MULTICOLOR" ) ); + indices.clear(); indices.append( 0 ); indices.append( 1 ); + setPreferenceProperty( coloringType, "strings", types ); + setPreferenceProperty( coloringType, "indexes", indices ); + addPreference( tr( "SMESH_DISTRIBUTION_COLOR" ), distributionGr, LightApp_Preferences::Color, "SMESH", "distribution_color" ); + } void SMESHGUI::preferencesChanged( const QString& sect, const QString& name ) diff --git a/src/SMESHGUI/SMESHGUI_Preferences_ScalarBarDlg.cxx b/src/SMESHGUI/SMESHGUI_Preferences_ScalarBarDlg.cxx index ec3a4d14f..43640501e 100644 --- a/src/SMESHGUI/SMESHGUI_Preferences_ScalarBarDlg.cxx +++ b/src/SMESHGUI/SMESHGUI_Preferences_ScalarBarDlg.cxx @@ -33,6 +33,8 @@ #include "SMESHGUI_Utils.h" #include +#include +#include // SALOME GUI includes #include @@ -63,7 +65,6 @@ // VTK includes #include -#include #include #define MINIMUM_WIDTH 70 @@ -279,8 +280,35 @@ SMESHGUI_Preferences_ScalarBarDlg::SMESHGUI_Preferences_ScalarBarDlg( SMESHGUI* myOriginDimGrpLayout->addWidget( myHeightSpin, 1, 3 ); aTopLayout->addWidget( myOriginDimGrp ); + /******************************************************************************/ - /***************************************************************/ + // Destribution + myDistributionGrp = new QGroupBox ( tr( "SMESH_DISTRIBUTION_SCALARBAR" ), this ); + myDistributionGrp->setCheckable(true); + QHBoxLayout* aDistributionGrpLayout = new QHBoxLayout( myDistributionGrp ); + aDistributionGrpLayout->setSpacing( SPACING_SIZE ); aDistributionGrpLayout->setMargin( MARGIN_SIZE ); + + myDistribColorGrp = new QButtonGroup( this ); + + myDMonoColor = new QRadioButton( tr( "SMESH_MONOCOLOR" ) , myDistributionGrp ); + myDMultiColor = new QRadioButton( tr( "SMESH_MULTICOLOR" ), myDistributionGrp ); + myDMonoColor->setChecked( true ); + + myDistribColorGrp->addButton(myDMonoColor);myDistribColorGrp->setId(myDMonoColor,1); + myDistribColorGrp->addButton(myDMultiColor);myDistribColorGrp->setId(myDMultiColor,2); + + aDistributionGrpLayout->addWidget( myDMultiColor ); + aDistributionGrpLayout->addWidget( myDMonoColor ); + + //Color of the Distribution in monocolor case: + myDistributionColorLbl = new QLabel( tr( "SMESH_DISTRIBUTION_COLOR" ), myDistributionGrp ); + aDistributionGrpLayout->addWidget( myDistributionColorLbl ); + myMonoColorBtn = new QtxColorButton( myDistributionGrp ); + aDistributionGrpLayout->addWidget(myMonoColorBtn); + + aTopLayout->addWidget(myDistributionGrp); + + /******************************************************************************/ // Common buttons myButtonGrp = new QGroupBox( this ); QHBoxLayout* myButtonGrpLayout = new QHBoxLayout( myButtonGrp ); @@ -376,6 +404,25 @@ SMESHGUI_Preferences_ScalarBarDlg::SMESHGUI_Preferences_ScalarBarDlg( SMESHGUI* setOriginAndSize(myIniX, myIniY, myIniW, myIniH); + + bool distributionVisibility = mgr->booleanValue("SMESH","distribution_visibility"); + myDistributionGrp->setChecked(distributionVisibility); + + int coloringType = mgr->integerValue("SMESH", "distribution_coloring_type", 0); + if( coloringType == SMESH_MONOCOLOR_TYPE ) { + myDMultiColor->setChecked(true); + onDistributionChanged(myDistribColorGrp->id(myDMultiColor)); + } else { + myDMonoColor->setChecked(true); + onDistributionChanged(myDistribColorGrp->id(myDMonoColor)); + } + + QColor distributionColor = mgr->colorValue("SMESH", "distribution_color", + QColor(255, 255, 255)); + myMonoColorBtn->setColor(distributionColor); + + + // --> then init from selection if necessary onSelectionChanged(); @@ -388,10 +435,11 @@ SMESHGUI_Preferences_ScalarBarDlg::SMESHGUI_Preferences_ScalarBarDlg( SMESHGUI* connect( myXSpin, SIGNAL( valueChanged( double ) ), this, SLOT( onXYChanged() ) ); connect( myYSpin, SIGNAL( valueChanged( double ) ), this, SLOT( onXYChanged() ) ); connect( aOrientationGrp, SIGNAL( buttonClicked( int ) ), this, SLOT( onOrientationChanged() ) ); + connect( myDistribColorGrp, SIGNAL( buttonClicked( int ) ), this, SLOT( onDistributionChanged( int ) ) ); connect( mySelectionMgr, SIGNAL( currentSelectionChanged() ), this, SLOT( onSelectionChanged() ) ); connect( mySMESHGUI, SIGNAL( SignalCloseAllDialogs() ), this, SLOT( onCancel() ) ); - myHelpFileName = "about_quality_controls_page.html"; + myHelpFileName = "quality_page.html"; } //================================================================================================= @@ -430,7 +478,7 @@ bool SMESHGUI_Preferences_ScalarBarDlg::onApply() // Scalar Bar properties if (!myActor) return false; - vtkScalarBarActor* myScalarBarActor = myActor->GetScalarBarActor(); + SMESH_ScalarBarActor* myScalarBarActor = myActor->GetScalarBarActor(); vtkTextProperty* aTitleTextPrp = myScalarBarActor->GetTitleTextProperty(); QColor aTColor = myTitleColorBtn->color(); @@ -461,7 +509,18 @@ bool SMESHGUI_Preferences_ScalarBarDlg::onApply() myScalarBarActor->SetLabelTextProperty( aLabelsTextPrp ); myScalarBarActor->SetNumberOfLabels( myLabelsSpin->value() ); - myScalarBarActor->SetMaximumNumberOfColors( myColorsSpin->value() ); + if( myColorsSpin->value() != myScalarBarActor->GetMaximumNumberOfColors() ) { + myScalarBarActor->SetMaximumNumberOfColors( myColorsSpin->value() ); + SMESH::Controls::FunctorPtr fn = myActor->GetFunctor(); + SMESH::Controls::NumericalFunctor* aNumericalFunctor = dynamic_cast(fn.get()); + if( aNumericalFunctor ) { + int nbIntervals = myColorsSpin->value(); + std::vector nbEvents; + std::vector funValues; + aNumericalFunctor->GetHistogram(nbIntervals, nbEvents, funValues); + myScalarBarActor->SetDistribution(nbEvents); + } + } if ( myHorizRadioBtn->isChecked() ) myScalarBarActor->SetOrientationToHorizontal(); @@ -472,6 +531,21 @@ bool SMESHGUI_Preferences_ScalarBarDlg::onApply() myScalarBarActor->SetWidth( myWidthSpin->value() ); myScalarBarActor->SetHeight( myHeightSpin->value() ); + // Distribution + myScalarBarActor->SetDistributionVisibility((int)myDistributionGrp->isChecked()); + if( myDistributionGrp->isChecked() ) { + int ColoringType = myDMultiColor->isChecked() ? SMESH_MULTICOLOR_TYPE : SMESH_MONOCOLOR_TYPE; + myScalarBarActor->SetDistributionColoringType(ColoringType); + if( !myDMultiColor->isChecked() ) { + QColor aTColor = myMonoColorBtn->color(); + double rgb[3]; + rgb [0] = aTColor.red()/255.; + rgb [1] = aTColor.green()/255.; + rgb [2] = aTColor.blue()/255.; + myScalarBarActor->SetDistributionColor(rgb); + } + } + double aMin = myMinEdit->text().toDouble(); double aMax = myMaxEdit->text().toDouble(); vtkLookupTable* myLookupTable = @@ -540,7 +614,7 @@ void SMESHGUI_Preferences_ScalarBarDlg::onSelectionChanged() SMESH_Actor* anActor = SMESH::FindActorByEntry(anIO->getEntry()); if ( anActor && anActor->GetScalarBarActor() && anActor->GetControlMode() != SMESH_Actor::eNone ) { myActor = anActor; - vtkScalarBarActor* myScalarBarActor = myActor->GetScalarBarActor(); + SMESH_ScalarBarActor* myScalarBarActor = myActor->GetScalarBarActor(); if ( myScalarBarActor->GetLookupTable() ) { vtkFloatingPointType *range = myScalarBarActor->GetLookupTable()->GetRange(); @@ -581,6 +655,17 @@ void SMESHGUI_Preferences_ScalarBarDlg::onSelectionChanged() myIniH = myScalarBarActor->GetHeight(); setOriginAndSize( myIniX, myIniY, myIniW, myIniH ); + myDistributionGrp->setChecked((bool)myScalarBarActor->GetDistributionVisibility()); + int coloringType = myScalarBarActor->GetDistributionColoringType(); + myScalarBarActor->GetDistributionColor( aTColor ); + myMonoColorBtn->setColor( QColor( (int)( aTColor[0]*255 ), (int)( aTColor[1]*255 ), (int)( aTColor[2]*255 ) ) ); + if ( coloringType == SMESH_MONOCOLOR_TYPE ) { + myDMonoColor->setChecked(true); + onDistributionChanged(myDistribColorGrp->id(myDMonoColor)); + } else { + myDMultiColor->setChecked(true); + onDistributionChanged(myDistribColorGrp->id(myDMultiColor)); + } myRangeGrp->setEnabled( true ); myFontGrp->setEnabled( true ); myLabColorGrp->setEnabled( true ); @@ -651,6 +736,19 @@ void SMESHGUI_Preferences_ScalarBarDlg::setOriginAndSize( const double x, onXYChanged(); } + +//================================================================================================= +/*! + * SMESHGUI_Preferences_ScalarBarDlg::onDistributionChanged + * + * Called when coloring type of the distribution is changed + */ +//================================================================================================= +void SMESHGUI_Preferences_ScalarBarDlg::onDistributionChanged( int id ) { + myMonoColorBtn->setEnabled(myDistribColorGrp->id(myDMonoColor) == id); + myDistributionColorLbl->setEnabled(myDistribColorGrp->id(myDMonoColor) == id); +} + //================================================================================================= /*! * SMESHGUI_Preferences_ScalarBarDlg::onOrientationChanged diff --git a/src/SMESHGUI/SMESHGUI_Preferences_ScalarBarDlg.h b/src/SMESHGUI/SMESHGUI_Preferences_ScalarBarDlg.h index c71c43cda..42058ee2b 100644 --- a/src/SMESHGUI/SMESHGUI_Preferences_ScalarBarDlg.h +++ b/src/SMESHGUI/SMESHGUI_Preferences_ScalarBarDlg.h @@ -40,6 +40,8 @@ class QLineEdit; class QPushButton; class QToolButton; class QRadioButton; +class QButtonGroup; +class QLabel; class SMESHGUI; class SMESH_Actor; @@ -77,6 +79,7 @@ protected slots: void onSelectionChanged(); void onXYChanged(); void onOrientationChanged(); + void onDistributionChanged( int ); private: SMESHGUI* mySMESHGUI; @@ -117,7 +120,14 @@ private: SMESHGUI_SpinBox* myWidthSpin; SMESHGUI_SpinBox* myHeightSpin; + QGroupBox* myDistributionGrp; + QRadioButton* myDMonoColor; + QRadioButton* myDMultiColor; + QtxColorButton* myMonoColorBtn; + QLabel* myDistributionColorLbl; + QGroupBox* myButtonGrp; + QButtonGroup* myDistribColorGrp; QPushButton* myOkBtn; QPushButton* myApplyBtn; QPushButton* myCancelBtn; diff --git a/src/SMESHGUI/SMESHGUI_Selection.cxx b/src/SMESHGUI/SMESHGUI_Selection.cxx index 2d923a91d..df7c9c1c6 100644 --- a/src/SMESHGUI/SMESHGUI_Selection.cxx +++ b/src/SMESHGUI/SMESHGUI_Selection.cxx @@ -34,6 +34,7 @@ #include #include +#include // SALOME GUI includes #include @@ -123,6 +124,7 @@ QVariant SMESHGUI_Selection::parameter( const int ind, const QString& p ) const else if ( p=="facesOrientationMode" ) val = QVariant( facesOrientationMode( ind ) ); else if ( p=="groupType" ) val = QVariant( groupType( ind ) ); else if ( p=="quadratic2DMode") val = QVariant(quadratic2DMode(ind)); + else if ( p=="isDistributionVisible") val = QVariant(isDistributionVisible(ind)); if( val.isValid() ) return val; @@ -217,6 +219,16 @@ QString SMESHGUI_Selection::quadratic2DMode( int ind ) const return "Unknown"; } +//======================================================================= +//function : isDistributionVisible +//purpose : Visible/Invisible distribution of the ScalarBar Actor +//======================================================================= + +bool SMESHGUI_Selection::isDistributionVisible(int ind) const { + SMESH_Actor* actor = getActor( ind ); + return (actor && actor->GetScalarBarActor() && actor->GetScalarBarActor()->GetDistributionVisibility()); +} + //======================================================================= //function : shrinkMode //purpose : return either 'IsSrunk', 'IsNotShrunk' or 'IsNotShrinkable' @@ -622,4 +634,3 @@ QString SMESHGUI_Selection::groupType( int ind ) const } return type; } - diff --git a/src/SMESHGUI/SMESHGUI_Selection.h b/src/SMESHGUI/SMESHGUI_Selection.h index 2ad94150f..2ad545d98 100644 --- a/src/SMESHGUI/SMESHGUI_Selection.h +++ b/src/SMESHGUI/SMESHGUI_Selection.h @@ -61,6 +61,8 @@ public: virtual QString quadratic2DMode(int ) const; + virtual bool isDistributionVisible(int ) const; + // parameters got from actor return nothing if an actor is not visible virtual QList elemTypes( int ) const; virtual QList labeledTypes( int ) const; diff --git a/src/SMESHGUI/SMESH_msg_en.ts b/src/SMESHGUI/SMESH_msg_en.ts index c5183a84e..189c5c1b3 100644 --- a/src/SMESHGUI/SMESH_msg_en.ts +++ b/src/SMESHGUI/SMESH_msg_en.ts @@ -635,6 +635,10 @@ MEN_SAVE_DISTRIBUTION Export Distribution... + + MEN_SHOW_DISTRIBUTION + Show Distribution + MEN_REVOLUTION Revolution @@ -1841,6 +1845,14 @@ add the exported data to its contents? SMESH_POSITION_SIZE_SCALARBAR Origin && Size + + SMESH_DISTRIBUTION_SCALARBAR + Distribution + + + SMESH_SHOW_DISTRIBUTION_SCALARBAR + Show Distribution + SMESH_PRECISION Precision @@ -2085,6 +2097,22 @@ add the exported data to its contents? SMESH_VERTICAL Vertical + + + SMESH_DISTRIBUTION_COLORING_TYPE + Coloring Type + + + SMESH_MONOCOLOR + Monocolor + + + SMESH_DISTRIBUTION_COLOR + Distribution color: + + + SMESH_MULTICOLOR + Multicolor SMESH_VISU_PROBLEM @@ -2575,6 +2603,10 @@ Consider saving your work before application crash STB_SAVE_DISTRIBUTION Save distribution to the file + + + STB_SHOW_DISTRIBUTION + Show Distribution STB_REVOLUTION @@ -3108,6 +3140,10 @@ Consider saving your work before application crash TOP_SAVE_DISTRIBUTION Export distribution + + TOP_SHOW_DISTRIBUTION + Show Distribution + TOP_REVOLUTION Revolution