Salome HOME
Bug IPAL22927: TC6.5.0: bounding box is not updated for Point Map 3D
[modules/visu.git] / src / PIPELINE / VISU_ScalarBarActor.cxx
1 // Copyright (C) 2007-2012  CEA/DEN, EDF R&D, OPEN CASCADE
2 //
3 // Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
5 //
6 // This library is free software; you can redistribute it and/or
7 // modify it under the terms of the GNU Lesser General Public
8 // License as published by the Free Software Foundation; either
9 // version 2.1 of the License.
10 //
11 // This library is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14 // Lesser General Public License for more details.
15 //
16 // You should have received a copy of the GNU Lesser General Public
17 // License along with this library; if not, write to the Free Software
18 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
19 //
20 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
21 //
22
23 //  VISU OBJECT : interactive object for VISU entities implementation
24 // File:    VISU_PipeLine.hxx
25 // Author:  Alexey PETROV
26 // Module : VISU
27 //
28 #include "VISU_ScalarBarActor.hxx"
29
30 #include <vtkPolyDataMapper2D.h>
31 #include <vtkCellArray.h>
32 #include <vtkCellData.h>
33 #include <vtkObjectFactory.h>
34 #include <vtkPolyData.h>
35 #include <vtkPolyDataMapper2D.h>
36 #include <vtkScalarsToColors.h>
37 #include <vtkTextMapper.h>
38 #include <vtkTextProperty.h>
39 #include <vtkViewport.h>
40 #include <vtkWindow.h>
41 #include <vtkLogLookupTable.h>
42 #include <vtkProperty2D.h> // RKV
43 #include <vtkAxisActor2D.h> // RKV
44
45 using namespace std;
46
47 vtkCxxRevisionMacro(VISU_ScalarBarActor, "$Revision$");
48
49 vtkCxxSetObjectMacro(VISU_ScalarBarActor,LookupTable,VISU_LookupTable);
50 vtkCxxSetObjectMacro(VISU_ScalarBarActor,LabelTextProperty,vtkTextProperty);
51 vtkCxxSetObjectMacro(VISU_ScalarBarActor,TitleTextProperty,vtkTextProperty);
52
53 //------------------------------------------------------------------------------
54 VISU_ScalarBarActor* VISU_ScalarBarActor::New(){
55   vtkObject* ret = vtkObjectFactory::CreateInstance("VISU_ScalarBarActor");
56   if(ret)
57     return (VISU_ScalarBarActor*)ret;
58   return new VISU_ScalarBarActor;
59 }
60
61 VISU_ScalarBarActor::VISU_ScalarBarActor()
62 {
63   this->LookupTable = NULL;
64   this->Position2Coordinate->SetValue(0.17, 0.8);
65   
66   this->PositionCoordinate->SetCoordinateSystemToNormalizedViewport();
67   this->PositionCoordinate->SetValue(0.82,0.1);
68   
69   this->MaximumNumberOfColors = 64;
70   this->NumberOfLabels = 5;
71   this->NumberOfLabelsBuilt = 0;
72   this->Orientation = VTK_ORIENT_VERTICAL;
73   this->Title = NULL;
74
75   this->LabelTextProperty = vtkTextProperty::New();
76   this->LabelTextProperty->SetFontSize(12);
77   this->LabelTextProperty->SetBold(1);
78   this->LabelTextProperty->SetItalic(1);
79   this->LabelTextProperty->SetShadow(1);
80   this->LabelTextProperty->SetFontFamilyToArial();
81
82   this->TitleTextProperty = vtkTextProperty::New();
83   this->TitleTextProperty->ShallowCopy(this->LabelTextProperty);
84
85   this->LabelFormat = new char[8]; 
86   sprintf(this->LabelFormat,"%s","%-#6.3g");
87
88   this->TitleMapper = vtkTextMapper::New();
89   this->TitleActor = vtkActor2D::New();
90   this->TitleActor->SetMapper(this->TitleMapper);
91   this->TitleActor->GetPositionCoordinate()->
92     SetReferenceCoordinate(this->PositionCoordinate);
93   
94   this->TextMappers = NULL;
95   this->TextActors = NULL;
96
97   this->ScalarBar = vtkPolyData::New();
98   this->ScalarBarMapper = vtkPolyDataMapper2D::New();
99   this->ScalarBarMapper->SetInput(this->ScalarBar);
100   this->ScalarBarActor = vtkActor2D::New();
101   this->ScalarBarActor->SetMapper(this->ScalarBarMapper);
102   this->ScalarBarActor->GetPositionCoordinate()->
103     SetReferenceCoordinate(this->PositionCoordinate);
104   this->LastOrigin[0] = 0;
105   this->LastOrigin[1] = 0;
106   this->LastSize[0] = 0;
107   this->LastSize[1] = 0;
108
109   this->TitleRatioSize = 0;
110   this->LabelRatioWidth = 0;
111   this->BarRatioWidth = 0;
112   this->BarRatioHeight = 0;
113   
114   // RKV : Begin
115   this->Distribution = vtkDoubleArray::New();
116   this->DistributionObj = vtkDataObject::New();
117   this->DistributionActor = VISU_XYPlotActor::New();
118   this->DistributionActor->SetTitle("");
119   this->DistributionActor->SetXTitle("");
120   this->DistributionActor->SetYTitle("");
121   this->DistributionActor->GetXAxisActor2D()->LabelVisibilityOff();
122   this->DistributionActor->GetXAxisActor2D()->TitleVisibilityOff();
123   this->DistributionActor->GetXAxisActor2D()->TickVisibilityOff();
124 //  this->DistributionActor->GetXAxisActor2D()->SetFontFactor(0.);
125   this->DistributionActor->SetNumberOfYLabels(1);
126 //  this->DistributionActor->SetNumberOfXLabels(2);
127   this->DistributionActor->GetXAxisActor2D()->AdjustLabelsOff();
128   this->DistributionActor->GetYAxisActor2D()->AdjustLabelsOff();
129   this->DistributionActor->LegendOff();
130   this->DistributionActor->SetLabelFormat("%4.3f");
131   this->DistributionActor->SetXValuesToIndex();
132 //  this->DistributionActor->GetPositionCoordinate()->SetValue(0.0, 0.67, 0);
133 //  this->DistributionActor->GetPosition2Coordinate()->SetValue(1.0, 0.33, 0); // #relative to Position
134   this->DistributionActor->GetPositionCoordinate()->
135     SetReferenceCoordinate(this->PositionCoordinate);
136   this->DistributionVisibilityOff(); // Don't show the distribution curve by default
137   
138   // RKV : End
139 }
140
141 void VISU_ScalarBarActor::ReleaseGraphicsResources(vtkWindow *win)
142 {
143   this->TitleActor->ReleaseGraphicsResources(win);
144   if (this->TextMappers != NULL )
145     {
146     for (int i=0; i < this->NumberOfLabelsBuilt; i++)
147       {
148       this->TextActors[i]->ReleaseGraphicsResources(win);
149       }
150     }
151   this->ScalarBarActor->ReleaseGraphicsResources(win);
152   this->DistributionActor->ReleaseGraphicsResources(win); // RKV
153 }
154
155 VISU_ScalarBarActor::~VISU_ScalarBarActor()
156 {
157   if (this->LabelFormat) 
158     {
159     delete [] this->LabelFormat;
160     this->LabelFormat = NULL;
161     }
162
163   this->TitleMapper->Delete();
164   this->TitleActor->Delete();
165
166   if (this->TextMappers != NULL )
167     {
168     for (int i=0; i < this->NumberOfLabelsBuilt; i++)
169       {
170       this->TextMappers[i]->Delete();
171       this->TextActors[i]->Delete();
172       }
173     delete [] this->TextMappers;
174     delete [] this->TextActors;
175     }
176
177   // RKV : Begin
178   this->DistributionActor->Delete();
179   this->DistributionObj->Delete();
180   this->SetDistribution(NULL);
181   // RKV : End
182
183   this->ScalarBar->Delete();
184   this->ScalarBarMapper->Delete();
185   this->ScalarBarActor->Delete();
186   
187   if (this->Title)
188     {
189     delete [] this->Title;
190     this->Title = NULL;
191     }
192   
193   this->SetLookupTable(NULL);
194   this->SetLabelTextProperty(NULL);
195   this->SetTitleTextProperty(NULL);
196 }
197
198 int VISU_ScalarBarActor::RenderOverlay(vtkViewport *viewport)
199 {
200   int renderedSomething = 0;
201   int i;
202   
203   // Everything is built, just have to render
204   if (this->Title != NULL)
205     {
206     renderedSomething += this->TitleActor->RenderOverlay(viewport);
207     }
208   this->ScalarBarActor->RenderOverlay(viewport);
209   // RKV : Begin
210   if (this->DistributionVisibility)
211     this->DistributionActor->RenderOverlay(viewport);
212   // RKV : End
213   if( this->TextActors == NULL)
214     {
215      vtkWarningMacro(<<"Need a mapper to render a scalar bar");
216      return renderedSomething;
217     }
218   
219   for (i=0; i<this->NumberOfLabels; i++)
220     {
221     renderedSomething += this->TextActors[i]->RenderOverlay(viewport);
222     }
223
224   renderedSomething = (renderedSomething > 0)?(1):(0);
225
226   return renderedSomething;
227 }
228
229 int VISU_ScalarBarActor::RenderOpaqueGeometry(vtkViewport *viewport)
230 {
231   int renderedSomething = 0;
232   int i;
233   int size[2];
234   
235   if (!this->LookupTable)
236     {
237     vtkWarningMacro(<<"Need a mapper to render a scalar bar");
238     return 0;
239     }
240
241   if (!this->TitleTextProperty)
242     {
243     vtkErrorMacro(<<"Need title text property to render a scalar bar");
244     return 0;
245     }
246
247   if (!this->LabelTextProperty)
248     {
249     vtkErrorMacro(<<"Need label text property to render a scalar bar");
250     return 0;
251     }
252
253   // Check to see whether we have to rebuild everything
254   int positionsHaveChanged = 0;
255   if (viewport->GetMTime() > this->BuildTime || 
256       (viewport->GetVTKWindow() && 
257        viewport->GetVTKWindow()->GetMTime() > this->BuildTime))
258     {
259     // if the viewport has changed we may - or may not need
260     // to rebuild, it depends on if the projected coords chage
261     int *barOrigin;
262     barOrigin = this->PositionCoordinate->GetComputedViewportValue(viewport);
263     size[0] = 
264       this->Position2Coordinate->GetComputedViewportValue(viewport)[0] -
265       barOrigin[0];
266     size[1] = 
267       this->Position2Coordinate->GetComputedViewportValue(viewport)[1] -
268       barOrigin[1];
269     if (this->LastSize[0] != size[0] || 
270         this->LastSize[1] != size[1] ||
271         this->LastOrigin[0] != barOrigin[0] || 
272         this->LastOrigin[1] != barOrigin[1])
273       {
274       positionsHaveChanged = 1;
275       }
276     }
277   
278   // Check to see whether we have to rebuild everything
279   // RKV : Begin
280   if (positionsHaveChanged ||
281       this->GetMTime() > this->BuildTime || 
282       this->LookupTable->GetMTime() > this->BuildTime ||
283       this->LabelTextProperty->GetMTime() > this->BuildTime ||
284       this->TitleTextProperty->GetMTime() > this->BuildTime ||
285       this->Distribution->GetMTime() > this->BuildTime)
286   // RKV : End
287 /* RKV  if (positionsHaveChanged ||
288       this->GetMTime() > this->BuildTime || 
289       this->LookupTable->GetMTime() > this->BuildTime ||
290       this->LabelTextProperty->GetMTime() > this->BuildTime ||
291       this->TitleTextProperty->GetMTime() > this->BuildTime)*/
292     {
293
294     // Delete previously constructed objects
295     //
296     if (this->TextMappers != NULL )
297       {
298       for (i=0; i < this->NumberOfLabelsBuilt; i++)
299         {
300         this->TextMappers[i]->Delete();
301         this->TextActors[i]->Delete();
302         }
303       delete [] this->TextMappers;
304       delete [] this->TextActors;
305       }
306
307     // Build scalar bar object; determine its type
308     //
309     VISU_LookupTable *lut = this->LookupTable; //SALOME specific
310     int isLogTable = lut->GetScale() == VTK_SCALE_LOG10;
311     
312     // we hard code how many steps to display
313     int numColors = this->MaximumNumberOfColors;
314     vtkFloatingPointType *range = lut->GetRange();
315
316     int numPts = 2*(numColors + 1);
317     vtkPoints *pts = vtkPoints::New();
318     pts->SetNumberOfPoints(numPts);
319     vtkCellArray *polys = vtkCellArray::New();
320     polys->Allocate(polys->EstimateSize(numColors,4));
321     vtkUnsignedCharArray *colors = vtkUnsignedCharArray::New();
322     colors->SetNumberOfComponents(3);
323     colors->SetNumberOfTuples(numColors);
324
325 // RKV : Begin
326     // If the distribution is changed then recalculate the total
327     if (this->Distribution->GetMTime() > this->BuildTime) {
328           int aNbVals = this->Distribution->GetNumberOfTuples();
329       double range[2];
330       this->Distribution->GetRange(range);
331       this->DistributionActor->SetYRange(0, range[1]);
332 /*        int total = 0;
333           for(vtkIdType aValId = 0; aValId < aNbVals; aValId++){
334                 total += this->Distribution->GetValue(aValId);
335           }
336           this->DistributionActor->SetYRange(0, total);
337 */
338       }
339   
340     this->DistributionActor->SetProperty(this->GetProperty());
341     this->DistributionActor->GetProperty()->SetColor(1, 1, 1);
342     this->DistributionActor->GetProperty()->SetLineWidth(2);
343     this->DistributionActor->GetProperty()->SetDisplayLocationToForeground();
344     vtkTextProperty* tprop;
345     tprop = this->DistributionActor->GetTitleTextProperty();
346     tprop->SetColor(this->DistributionActor->GetProperty()->GetColor());
347 //  this->DistributionActor->SetAxisTitleTextProperty(tprop);
348 //  this->DistributionActor->SetAxisLabelTextProperty(tprop);
349     
350 // RKV : End
351     this->ScalarBarActor->SetProperty(this->GetProperty());
352     this->ScalarBar->Initialize();
353     this->ScalarBar->SetPoints(pts);
354     this->ScalarBar->SetPolys(polys);
355     this->ScalarBar->GetCellData()->SetScalars(colors);
356     pts->Delete(); polys->Delete(); colors->Delete();
357
358     // get the viewport size in display coordinates
359     int *barOrigin, barWidth, barHeight;
360     barOrigin = this->PositionCoordinate->GetComputedViewportValue(viewport);
361     size[0] = 
362       this->Position2Coordinate->GetComputedViewportValue(viewport)[0] -
363       barOrigin[0];
364     size[1] = 
365       this->Position2Coordinate->GetComputedViewportValue(viewport)[1] -
366       barOrigin[1];
367     this->LastOrigin[0] = barOrigin[0];
368     this->LastOrigin[1] = barOrigin[1];
369     this->LastSize[0] = size[0];
370     this->LastSize[1] = size[1];
371     
372     // Update all the composing objects
373     this->TitleActor->SetProperty(this->GetProperty());
374     this->TitleMapper->SetInput(this->Title);
375     if (this->TitleTextProperty->GetMTime() > this->BuildTime)
376       {
377       // Shallow copy here so that the size of the title prop is not affected
378       // by the automatic adjustment of its text mapper's size (i.e. its
379       // mapper's text property is identical except for the font size
380       // which will be modified later). This allows text actors to
381       // share the same text property, and in that case specifically allows
382       // the title and label text prop to be the same.
383       this->TitleMapper->GetTextProperty()->ShallowCopy(this->TitleTextProperty);
384       this->TitleMapper->GetTextProperty()->SetJustificationToCentered();
385       }
386     
387     // find the best size for the title font
388     int titleSize[2];
389     this->SizeTitle(titleSize, size, viewport);
390     
391     // find the best size for the ticks
392     int labelSize[2];
393     this->AllocateAndSizeLabels(labelSize, size, viewport, range);
394     this->NumberOfLabelsBuilt = this->NumberOfLabels;
395     
396     this->SizeBar(barWidth, barHeight, size, viewport, range);
397
398     // generate points
399     vtkFloatingPointType x[3]; x[2] = 0.0;
400     vtkFloatingPointType delta, val;
401     if ( this->Orientation == VTK_ORIENT_VERTICAL )
402       {
403       delta=(vtkFloatingPointType)barHeight/numColors;
404       for (i=0; i<numPts/2; i++)
405         {
406         x[0] = 0;
407         x[1] = i*delta;
408         pts->SetPoint(2*i,x);
409         x[0] = barWidth;
410         pts->SetPoint(2*i+1,x);
411         }
412       }
413     else
414       {
415       delta=(vtkFloatingPointType)barWidth/numColors;
416       for (i=0; i<numPts/2; i++)
417         {
418         x[0] = i*delta;
419         x[1] = barHeight;
420         pts->SetPoint(2*i,x);
421         x[1] = 0;
422         pts->SetPoint(2*i+1,x);
423         }
424       }
425
426     //polygons & cell colors
427     unsigned char *rgba, *rgb;
428     vtkIdType ptIds[4];
429     for (i=0; i<numColors; i++)
430       {
431       ptIds[0] = 2*i;
432       ptIds[1] = ptIds[0] + 1;
433       ptIds[2] = ptIds[1] + 2;
434       ptIds[3] = ptIds[0] + 2;
435       polys->InsertNextCell(4,ptIds);
436
437       if ( isLogTable ){ //SALOME specific
438         vtkFloatingPointType rgbval = log10(range[0]) + 
439           i*(log10(range[1])-log10(range[0]))/(numColors -1);
440         rgba = lut->MapValue(rgbval);
441       }else{
442         rgba = lut->MapValue(range[0] + (range[1] - range[0])*
443                              ((vtkFloatingPointType)i /(numColors-1.0)));
444       }
445
446       rgb = colors->GetPointer(3*i); //write into array directly
447       rgb[0] = rgba[0];
448       rgb[1] = rgba[1];
449       rgb[2] = rgba[2];
450     }
451
452     // Now position everything properly
453     //
454     if (this->Orientation == VTK_ORIENT_VERTICAL)
455       {
456       int sizeTextData[2];
457       
458       // center the title
459       this->TitleActor->SetPosition(size[0]/2, 0.9*size[1]);
460       
461       for (i=0; i < this->NumberOfLabels; i++)
462         {
463         val = (vtkFloatingPointType)i/(this->NumberOfLabels-1) *barHeight;
464         this->TextMappers[i]->GetSize(viewport,sizeTextData);
465         this->TextMappers[i]->GetTextProperty()->SetJustificationToLeft();
466         this->TextActors[i]->SetPosition(barWidth+3,
467                                          val - sizeTextData[1]/2);
468         }
469         
470       }
471     else
472       {
473       this->TitleActor->SetPosition(size[0]/2, 
474                                     barHeight + labelSize[1] + 0.1*size[1]);
475       for (i=0; i < this->NumberOfLabels; i++)
476         {
477         this->TextMappers[i]->GetTextProperty()->SetJustificationToCentered();
478         val = (vtkFloatingPointType)i/(this->NumberOfLabels-1) * barWidth;
479         this->TextActors[i]->SetPosition(val, barHeight + 0.05*size[1]);
480         }
481         
482       }
483       
484     // Compute the position of the distribution curve
485     this->PlaceDistribution(viewport, barWidth, barHeight); // RKV
486
487     this->BuildTime.Modified();
488     }
489
490   // Everything is built, just have to render
491   if (this->Title != NULL)
492     {
493     renderedSomething += this->TitleActor->RenderOpaqueGeometry(viewport);
494     }
495   this->ScalarBarActor->RenderOpaqueGeometry(viewport);
496   // RKV : Begin
497   if (this->DistributionVisibility)
498     this->DistributionActor->RenderOpaqueGeometry(viewport);
499   // RKV : End
500   for (i=0; i<this->NumberOfLabels; i++)
501     {
502     renderedSomething += this->TextActors[i]->RenderOpaqueGeometry(viewport);
503     }
504
505   renderedSomething = (renderedSomething > 0)?(1):(0);
506
507   return renderedSomething;
508 }
509
510 void VISU_ScalarBarActor::PrintSelf(ostream& os, vtkIndent indent)
511 {
512   this->Superclass::PrintSelf(os,indent);
513
514   if ( this->LookupTable )
515     {
516     os << indent << "Lookup Table:\n";
517     this->LookupTable->PrintSelf(os,indent.GetNextIndent());
518     }
519   else
520     {
521     os << indent << "Lookup Table: (none)\n";
522     }
523
524   if (this->TitleTextProperty)
525     {
526     os << indent << "Title Text Property:\n";
527     this->TitleTextProperty->PrintSelf(os,indent.GetNextIndent());
528     }
529   else
530     {
531     os << indent << "Title Text Property: (none)\n";
532     }
533
534   if (this->LabelTextProperty)
535     {
536     os << indent << "Label Text Property:\n";
537     this->LabelTextProperty->PrintSelf(os,indent.GetNextIndent());
538     }
539   else
540     {
541     os << indent << "Label Text Property: (none)\n";
542     }
543
544   os << indent << "Title: " << (this->Title ? this->Title : "(none)") << "\n";
545   os << indent << "Maximum Number Of Colors: " 
546      << this->MaximumNumberOfColors << "\n";
547   os << indent << "Number Of Labels: " << this->NumberOfLabels << "\n";
548   os << indent << "Number Of Labels Built: " << this->NumberOfLabelsBuilt << "\n";
549
550   os << indent << "Orientation: ";
551   if ( this->Orientation == VTK_ORIENT_HORIZONTAL )
552     {
553     os << "Horizontal\n";
554     }
555   else
556     {
557     os << "Vertical\n";
558     }
559
560   os << indent << "Label Format: " << this->LabelFormat << "\n";
561 }
562
563 void VISU_ScalarBarActor::ShallowCopy(vtkProp *prop)
564 {
565   VISU_ScalarBarActor *a = VISU_ScalarBarActor::SafeDownCast(prop);
566   if ( a != NULL )
567     {
568     this->SetPosition2(a->GetPosition2());
569     this->SetLookupTable(a->GetLookupTable());
570     this->SetMaximumNumberOfColors(a->GetMaximumNumberOfColors());
571     this->SetOrientation(a->GetOrientation());
572     this->SetLabelTextProperty(a->GetLabelTextProperty());
573     this->SetTitleTextProperty(a->GetTitleTextProperty());
574     this->SetLabelFormat(a->GetLabelFormat());
575     this->SetTitle(a->GetTitle());
576     this->GetPositionCoordinate()->SetCoordinateSystem(
577       a->GetPositionCoordinate()->GetCoordinateSystem());    
578     this->GetPositionCoordinate()->SetValue(
579       a->GetPositionCoordinate()->GetValue());
580     this->GetPosition2Coordinate()->SetCoordinateSystem(
581       a->GetPosition2Coordinate()->GetCoordinateSystem());    
582     this->GetPosition2Coordinate()->SetValue(
583       a->GetPosition2Coordinate()->GetValue());
584     }
585
586   // Now do superclass
587   this->vtkActor2D::ShallowCopy(prop);
588 }
589
590 void VISU_ScalarBarActor::AllocateAndSizeLabels(int *labelSize, int *size,
591                                               vtkViewport *viewport,
592                                               vtkFloatingPointType *range)
593 {
594   labelSize[0] = labelSize[1] = 0;
595
596   this->TextMappers = new vtkTextMapper * [this->NumberOfLabels];
597   this->TextActors = new vtkActor2D * [this->NumberOfLabels];
598
599   char string[512];
600
601   vtkFloatingPointType val;
602   int i;
603   
604   // TODO: this should be optimized, maybe by keeping a list of
605   // allocated mappers, in order to avoid creation/destruction of
606   // their underlying text properties (i.e. each time a mapper is
607   // created, text properties are created and shallow-assigned a font size
608   // which value might be "far" from the target font size).
609
610   VISU_LookupTable *lut = this->LookupTable; //SALOME specific
611   int isLogTable = lut->GetScale() == VTK_SCALE_LOG10;
612
613   for (i=0; i < this->NumberOfLabels; i++)
614     {
615     this->TextMappers[i] = vtkTextMapper::New();
616
617     if(isLogTable && 0 < i && i < this->NumberOfLabels - 1){ // SALOME specific
618       vtkFloatingPointType lval = log10(range[0]) + (vtkFloatingPointType)i/(this->NumberOfLabels-1) *
619         (log10(range[1])-log10(range[0]));
620       val = pow((double)10,(double)lval);
621     }else{
622       val = range[0] + (vtkFloatingPointType)i/(this->NumberOfLabels-1) * (range[1]-range[0]);
623     }
624     sprintf(string, this->LabelFormat, val);
625     this->TextMappers[i]->SetInput(string);
626
627     // Shallow copy here so that the size of the label prop is not affected
628     // by the automatic adjustment of its text mapper's size (i.e. its
629     // mapper's text property is identical except for the font size
630     // which will be modified later). This allows text actors to
631     // share the same text property, and in that case specifically allows
632     // the title and label text prop to be the same.
633     this->TextMappers[i]->GetTextProperty()->ShallowCopy(
634       this->LabelTextProperty);
635
636     this->TextActors[i] = vtkActor2D::New();
637     this->TextActors[i]->SetMapper(this->TextMappers[i]);
638     this->TextActors[i]->SetProperty(this->GetProperty());
639     this->TextActors[i]->GetPositionCoordinate()->
640       SetReferenceCoordinate(this->PositionCoordinate);
641     }
642
643   if (this->NumberOfLabels)
644     {
645     int targetWidth, targetHeight;
646
647     if(LabelRatioWidth == 0)
648       if ( this->Orientation == VTK_ORIENT_VERTICAL )
649           targetWidth = (int)(0.6*size[0]);
650         else
651           targetWidth = (int)(size[0]*0.8/this->NumberOfLabels);
652     else
653       targetWidth = (int)(0.01*LabelRatioWidth*size[0]);
654
655     if ( this->Orientation == VTK_ORIENT_VERTICAL )
656       targetHeight = (int)(0.86*size[1]/this->NumberOfLabels);
657     else
658       targetHeight = (int)(0.25*size[1]);
659
660     vtkTextMapper::SetMultipleConstrainedFontSize(viewport, 
661                                                   targetWidth, 
662                                                   targetHeight,
663                                                   this->TextMappers,
664                                                   this->NumberOfLabels,
665                                                   labelSize);
666     }
667 }
668
669 void VISU_ScalarBarActor::SizeTitle(int *titleSize, int *size, 
670                                   vtkViewport *viewport)
671 {
672   titleSize[0] = titleSize[1] = 0;
673
674   if (this->Title == NULL || !strlen(this->Title))
675     {
676     return;
677     }
678
679   int targetWidth, targetHeight;
680   
681   if(TitleRatioSize == 0)
682     targetWidth = size[0];
683   else
684     targetWidth = (int)(0.01*TitleRatioSize*size[0]);
685
686   if ( this->Orientation == VTK_ORIENT_VERTICAL )
687     targetHeight = (int)(0.1*size[1]);
688   else
689     targetHeight = (int)(0.25*size[1]);
690
691   this->TitleMapper->SetConstrainedFontSize(
692     viewport, targetWidth, targetHeight);
693
694   this->TitleMapper->GetSize(viewport, titleSize);
695 }
696
697 // RKV : Begin
698 void VISU_ScalarBarActor::SetDistributionVisibility(int v) 
699 {
700   this->DistributionVisibility = v;
701   if (v) {
702         this->DistributionActor->VisibilityOn();
703   } else {
704         this->DistributionActor->VisibilityOff();
705   }
706 }
707
708 void VISU_ScalarBarActor::SetDistribution(vtkDoubleArray *distr) 
709 {
710   this->Distribution = distr;
711   if (distr == NULL) return;
712   
713   this->DistributionObj->Initialize();
714   this->DistributionObj->GetFieldData()->AddArray(this->Distribution);
715   this->DistributionActor->AddDataObjectInput(this->DistributionObj);
716   // Set ranges of axes for the distribution curve
717   this->DistributionActor->SetXRange(0, this->Distribution->GetNumberOfTuples()-1);
718   double range[2];
719   this->Distribution->GetRange(range);
720   int aNbVals = this->Distribution->GetNumberOfTuples();
721 //  int total = 0;
722   if (this->GetDebug()) {
723   for(vtkIdType aValId = 0; aValId < aNbVals; aValId++){
724 //      if (this->GetDebug()) {
725                 if (this->Distribution->GetValue(aValId) > 0)
726               vtkDebugMacro(<< "D(" << aValId << ") = " << this->Distribution->GetValue(aValId));
727 //      }
728 //      total += this->Distribution->GetValue(aValId);
729   }
730   }
731 //  this->DistributionActor->SetYRange(0, total);
732   this->DistributionActor->SetYRange(0, range[1]);
733   vtkDebugMacro(<< "max X = " << this->Distribution->GetNumberOfTuples());
734   vtkDebugMacro(<< "Y = (" << range[0] << ", " << range[1] << ")");
735 //  vtkDebugMacro(<< "total = " << total);
736 }
737
738 void VISU_ScalarBarActor::DebugOn() {
739         this->DistributionActor->DebugOn();
740         Superclass::DebugOn();
741
742
743 void VISU_ScalarBarActor::DebugOff() {
744         this->DistributionActor->DebugOff();
745         Superclass::DebugOff();
746
747 // RKV : End
748
749 void VISU_ScalarBarActor::SetRatios(int titleRatioSize, int labelRatioWidth, 
750                                     int barRatioWidth, int barRatioHeight)
751 {
752   TitleRatioSize=titleRatioSize;
753   if(TitleRatioSize>100)
754     TitleRatioSize=100;
755   else if(TitleRatioSize<0)
756     TitleRatioSize=0;
757
758   LabelRatioWidth=labelRatioWidth;
759   if(LabelRatioWidth>100)
760     LabelRatioWidth=100;
761   else if(LabelRatioWidth<0)
762     LabelRatioWidth=0;
763
764   BarRatioWidth=barRatioWidth;
765   if(BarRatioWidth>100)
766     BarRatioWidth=100;
767   else if(BarRatioWidth<0)
768     BarRatioWidth=0;
769
770   BarRatioHeight=barRatioHeight;
771   if(BarRatioHeight>100)
772     BarRatioHeight=100;
773   else if(BarRatioHeight<0)
774     BarRatioHeight=0;
775 }
776
777 void VISU_ScalarBarActor::GetRatios(int& titleRatioSize, int& labelRatioWidth, 
778                                     int& barRatioWidth, int& barRatioHeight)
779 {
780   titleRatioSize=TitleRatioSize;
781   labelRatioWidth=LabelRatioWidth;
782   barRatioWidth=BarRatioWidth;
783   barRatioHeight=BarRatioHeight;
784 }
785
786 void VISU_ScalarBarActor::SizeBar(int& barSizeWidth, int& barSizeHeight, int *size,
787                                   vtkViewport *viewport, vtkFloatingPointType *range)
788 {
789   if(BarRatioWidth == 0)
790     if ( this->Orientation == VTK_ORIENT_VERTICAL )
791       {
792         int labelSize[2];
793         this->AllocateAndSizeLabels(labelSize, size, viewport,range);
794         barSizeWidth = size[0] - 4 - labelSize[0];
795       } else
796         barSizeWidth = size[0];
797   else
798     barSizeWidth = (int)(0.01*BarRatioWidth*size[0]);
799
800   if(BarRatioHeight == 0)
801     if ( this->Orientation == VTK_ORIENT_VERTICAL )
802       barSizeHeight = (int)(0.86*size[1]);
803     else
804       barSizeHeight = (int)(0.4*size[1]);
805   else
806     barSizeHeight = (int)(0.01*BarRatioHeight*size[1]);
807 }
808 // RKV : Begin
809 //------------------------------------------------------------------------------
810 /** Place the distribution plot actor in the viewport according to the 
811  * scalar bar location and orientation */
812 void VISU_ScalarBarActor::PlaceDistribution(vtkViewport *viewport, const int barWidth, const int barHeight) {
813     vtkDebugMacro(<< "barOrigin[0]=" << this->LastOrigin[0] << "; barOrigin[1]=" << this->LastOrigin[1]);
814     // Detect the side of the viewport where the curve should be placed by the bar origin.
815     double u = (double)(this->LastOrigin[0]), v = (double)(this->LastOrigin[1]), z=0;
816     viewport->ViewportToNormalizedViewport(u, v);
817     
818     if ( this->Orientation == VTK_ORIENT_VERTICAL ) {
819       // Position the distribution curve vertically
820       if (u > 0.5) {
821         // X - UP, Y - TO THE LEFT
822         this->DistributionActor->SetPlotLocation(VISU_XYPLOT_RIGHT);
823         // Curve to be placed on the left side of the bar
824         vtkDebugMacro(<< "Curve to be placed on the left side of the bar");
825         // relative to the bar origin
826         u = 0;
827         v = 0;
828         viewport->ViewportToNormalizedViewport(u, v);
829         vtkDebugMacro(<< "u=" << u << "; v=" << v);
830         this->DistributionActor->GetPositionCoordinate()->SetValue(u, v, 0);
831         // relative to Position
832         u = - barWidth;
833         v = barHeight;
834         viewport->ViewportToNormalizedViewport(u, v);
835         vtkDebugMacro("u2=" << u << "; v2=" << v);
836         this->DistributionActor->GetPosition2Coordinate()->SetValue(u, v, 0);
837       } else {
838         // X - UP, Y - TO THE RIGHT
839         this->DistributionActor->SetPlotLocation(VISU_XYPLOT_LEFT);
840         // Curve to be placed on the right side of the bar
841         vtkDebugMacro(<< "Curve to be placed on the right side of the bar");
842         // relative to the bar origin
843         u = barWidth;
844         v = 0;
845         viewport->ViewportToNormalizedViewport(u, v);
846         vtkDebugMacro(<< "u=" << u << "; v=" << v);
847         this->DistributionActor->GetPositionCoordinate()->SetValue(u, v, 0);
848         // relative to Position
849         u = barWidth;
850         v = barHeight;
851         viewport->ViewportToNormalizedViewport(u, v);
852         vtkDebugMacro("u2=" << u << "; v2=" << v);
853         this->DistributionActor->GetPosition2Coordinate()->SetValue(u, v, 0);
854       }
855     } else {
856       // Position the distribution curve horizontally
857       if (v > 0.5) {
858         // X - TO THE LEFT, Y - DOWN
859         this->DistributionActor->SetPlotLocation(VISU_XYPLOT_TOP);
860         // Curve to be placed below the bar
861         vtkDebugMacro(<< "Curve to be placed below the bar");
862         // relative to the bar origin
863         u = 0;
864         v = 0;
865         viewport->ViewportToNormalizedViewport(u, v);
866         vtkDebugMacro(<< "u=" << u << "; v=" << v);
867         this->DistributionActor->GetPositionCoordinate()->SetValue(u, v, 0);
868         // relative to Position
869         u = barWidth;
870         v = - barHeight;
871         viewport->ViewportToNormalizedViewport(u, v);
872         vtkDebugMacro("u2=" << u << "; v2=" << v);
873         this->DistributionActor->GetPosition2Coordinate()->SetValue(u, v, 0);
874       } else {
875         // X - TO THE RIGHT, Y - UP
876         this->DistributionActor->SetPlotLocation(VISU_XYPLOT_BOTTOM);
877         // Curve to be placed on the top of the bar
878         vtkDebugMacro(<< "Curve to be placed on the top of the bar");
879         // relative to the bar origin
880         u = 0;
881         v = barHeight;
882         viewport->ViewportToNormalizedViewport(u, v);
883         vtkDebugMacro(<< "u=" << u << "; v=" << v);
884         this->DistributionActor->GetPositionCoordinate()->SetValue(u, v, 0);
885         // relative to Position
886         u = barWidth;
887         v = barHeight;
888         viewport->ViewportToNormalizedViewport(u, v);
889         vtkDebugMacro("u2=" << u << "; v2=" << v);
890         this->DistributionActor->GetPosition2Coordinate()->SetValue(u, v, 0);
891       }
892     }
893 }
894 // RKV : End
895