1 /*=========================================================================
2 
3   Program:   Visualization Toolkit
4 
5   Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen
6   All rights reserved.
7   See Copyright.txt or http://www.kitware.com/Copyright.htm for details.
8 
9      This software is distributed WITHOUT ANY WARRANTY; without even
10      the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
11      PURPOSE.  See the above copyright notice for more information.
12 
13 =========================================================================*/
14 #include "vtkSurfaceLICInterface.h"
15 
16 #include "vtkFloatArray.h"
17 #include "vtkImageData.h"
18 #include "vtkLineIntegralConvolution2D.h"
19 #include "vtkObjectFactory.h"
20 #include "vtkOpenGLError.h"
21 #include "vtkOpenGLFramebufferObject.h"
22 #include "vtkOpenGLRenderWindow.h"
23 #include "vtkOpenGLShaderCache.h"
24 #include "vtkOpenGLState.h"
25 #include "vtkPainterCommunicator.h"
26 #include "vtkPixelBufferObject.h"
27 #include "vtkPointData.h"
28 #include "vtkPolyData.h"
29 #include "vtkProperty.h"
30 #include "vtkRenderer.h"
31 #include "vtkScalarsToColors.h"
32 #include "vtkShaderProgram.h"
33 #include "vtkSurfaceLICComposite.h"
34 #include "vtkTextureObjectVS.h"
35 
36 #include "vtkOpenGLIndexBufferObject.h"
37 #include "vtkOpenGLVertexArrayObject.h"
38 #include "vtkOpenGLVertexBufferObject.h"
39 
40 #include "vtkLICNoiseHelper.h"
41 #include "vtkSurfaceLICHelper.h"
42 
43 #include <algorithm>
44 #include <cmath>
45 #include <cstdlib>
46 #include <cstring>
47 #include <deque>
48 #include <limits>
49 #include <vector>
50 
51 #include "vtkSurfaceLICInterface_CE.h"
52 #include "vtkSurfaceLICInterface_DCpy.h"
53 #include "vtkSurfaceLICInterface_SC.h"
54 #include "vtkTextureObjectVS.h"
55 
56 typedef vtkLineIntegralConvolution2D vtkLIC2D;
57 
58 // write intermediate results to disk for debugging
59 #define vtkSurfaceLICInterfaceDEBUG 0
60 #if vtkSurfaceLICInterfaceDEBUG >= 2
61 #include "vtkTextureIO.h"
62 #include <sstream>
63 using std::ostringstream;
64 //------------------------------------------------------------------------------
mpifn(vtkPainterCommunicator * comm,const char * fn)65 static std::string mpifn(vtkPainterCommunicator* comm, const char* fn)
66 {
67   ostringstream oss;
68   oss << comm->GetRank() << "_" << fn;
69   return oss.str();
70 }
71 #endif
72 
73 vtkObjectFactoryNewMacro(vtkSurfaceLICInterface);
74 
75 //------------------------------------------------------------------------------
vtkSurfaceLICInterface()76 vtkSurfaceLICInterface::vtkSurfaceLICInterface()
77 {
78   this->Internals = new vtkSurfaceLICHelper();
79 
80   this->Enable = 1;
81   this->AlwaysUpdate = 0;
82 
83   this->StepSize = 1;
84   this->NumberOfSteps = 20;
85   this->NormalizeVectors = 1;
86 
87   this->EnhancedLIC = 1;
88 
89   this->EnhanceContrast = 0;
90   this->LowLICContrastEnhancementFactor = 0.0;
91   this->HighLICContrastEnhancementFactor = 0.0;
92   this->LowColorContrastEnhancementFactor = 0.0;
93   this->HighColorContrastEnhancementFactor = 0.0;
94   this->AntiAlias = 0;
95   this->ColorMode = COLOR_MODE_BLEND;
96   this->LICIntensity = 0.8;
97   this->MapModeBias = 0.0;
98 
99   this->GenerateNoiseTexture = 0;
100   this->NoiseType = NOISE_TYPE_GAUSSIAN;
101   this->NoiseTextureSize = 200;
102   this->MinNoiseValue = 0.0;
103   this->MaxNoiseValue = 0.8;
104   this->NoiseGrainSize = 1;
105   this->NumberOfNoiseLevels = 256;
106   this->ImpulseNoiseProbability = 1.0;
107   this->ImpulseNoiseBackgroundValue = 0.0;
108   this->NoiseGeneratorSeed = 1;
109 
110   this->MaskOnSurface = 0;
111   this->MaskThreshold = 0.0;
112   this->MaskIntensity = 0.0;
113   this->MaskColor[0] = 0.5;
114   this->MaskColor[1] = 0.5;
115   this->MaskColor[2] = 0.5;
116 
117   this->CompositeStrategy = COMPOSITE_AUTO;
118 }
119 
120 //------------------------------------------------------------------------------
~vtkSurfaceLICInterface()121 vtkSurfaceLICInterface::~vtkSurfaceLICInterface()
122 {
123 #if vtkSurfaceLICInterfaceDEBUG >= 1
124   cerr << "=====vtkSurfaceLICInterface::~vtkSurfaceLICInterface" << endl;
125 #endif
126   this->ReleaseGraphicsResources(this->Internals->Context);
127   delete this->Internals;
128 }
129 
ShallowCopy(vtkSurfaceLICInterface * m)130 void vtkSurfaceLICInterface::ShallowCopy(vtkSurfaceLICInterface* m)
131 {
132   this->SetNumberOfSteps(m->GetNumberOfSteps());
133   this->SetStepSize(m->GetStepSize());
134   this->SetEnhancedLIC(m->GetEnhancedLIC());
135   this->SetGenerateNoiseTexture(m->GetGenerateNoiseTexture());
136   this->SetNoiseType(m->GetNoiseType());
137   this->SetNormalizeVectors(m->GetNormalizeVectors());
138   this->SetNoiseTextureSize(m->GetNoiseTextureSize());
139   this->SetNoiseGrainSize(m->GetNoiseGrainSize());
140   this->SetMinNoiseValue(m->GetMinNoiseValue());
141   this->SetMaxNoiseValue(m->GetMaxNoiseValue());
142   this->SetNumberOfNoiseLevels(m->GetNumberOfNoiseLevels());
143   this->SetImpulseNoiseProbability(m->GetImpulseNoiseProbability());
144   this->SetImpulseNoiseBackgroundValue(m->GetImpulseNoiseBackgroundValue());
145   this->SetNoiseGeneratorSeed(m->GetNoiseGeneratorSeed());
146   this->SetEnhanceContrast(m->GetEnhanceContrast());
147   this->SetLowLICContrastEnhancementFactor(m->GetLowLICContrastEnhancementFactor());
148   this->SetHighLICContrastEnhancementFactor(m->GetHighLICContrastEnhancementFactor());
149   this->SetLowColorContrastEnhancementFactor(m->GetLowColorContrastEnhancementFactor());
150   this->SetHighColorContrastEnhancementFactor(m->GetHighColorContrastEnhancementFactor());
151   this->SetAntiAlias(m->GetAntiAlias());
152   this->SetColorMode(m->GetColorMode());
153   this->SetLICIntensity(m->GetLICIntensity());
154   this->SetMapModeBias(m->GetMapModeBias());
155   this->SetMaskOnSurface(m->GetMaskOnSurface());
156   this->SetMaskThreshold(m->GetMaskThreshold());
157   this->SetMaskIntensity(m->GetMaskIntensity());
158   this->SetMaskColor(m->GetMaskColor());
159   this->SetEnable(m->GetEnable());
160 }
161 
UpdateCommunicator(vtkRenderer * renderer,vtkActor * actor,vtkDataObject * input)162 void vtkSurfaceLICInterface::UpdateCommunicator(
163   vtkRenderer* renderer, vtkActor* actor, vtkDataObject* input)
164 {
165   // commented out as camera and data changes also
166   // require a communicator update, currently the
167   // test does not include these
168   //  if (this->NeedToUpdateCommunicator())
169   {
170     // create a communicator that contains only ranks
171     // that have visible data. In parallel this is a
172     // collective operation across all ranks. In
173     // serial this is a no-op.
174     this->CreateCommunicator(renderer, actor, input);
175   }
176 }
177 
PrepareForGeometry()178 void vtkSurfaceLICInterface::PrepareForGeometry()
179 {
180   vtkOpenGLState* ostate = this->Internals->Context->GetState();
181 
182   // save the active fbo and its draw buffer
183   ostate->PushFramebufferBindings();
184 
185   // ------------------------------------------- render geometry, project vectors onto screen, etc
186   // setup our fbo
187   vtkOpenGLFramebufferObject* fbo = this->Internals->FBO;
188   fbo->Bind();
189   fbo->AddDepthAttachment(this->Internals->DepthImage);
190   fbo->AddColorAttachment(0U, this->Internals->GeometryImage);
191   fbo->AddColorAttachment(1U, this->Internals->VectorImage);
192   fbo->AddColorAttachment(2U, this->Internals->MaskVectorImage);
193   fbo->ActivateDrawBuffers(3);
194   vtkCheckFrameBufferStatusMacro(GL_FRAMEBUFFER);
195 
196   // clear internal color and depth buffers
197   // the LIC'er requires *all* fragments in the vector
198   // texture to be initialized to 0
199   ostate->vtkglDisable(GL_BLEND);
200   ostate->vtkglEnable(GL_DEPTH_TEST);
201   ostate->vtkglDisable(GL_SCISSOR_TEST);
202   ostate->vtkglClearColor(0.0, 0.0, 0.0, 0.0);
203   ostate->vtkglClear(GL_DEPTH_BUFFER_BIT | GL_COLOR_BUFFER_BIT);
204 }
205 
CompletedGeometry()206 void vtkSurfaceLICInterface::CompletedGeometry()
207 {
208   vtkOpenGLFramebufferObject* fbo = this->Internals->FBO;
209   fbo->RemoveDepthAttachment();
210   fbo->RemoveColorAttachment(0U);
211   fbo->RemoveColorAttachment(1U);
212   fbo->RemoveColorAttachment(2U);
213   fbo->DeactivateDrawBuffers();
214 
215 #if vtkSurfaceLICInterfaceDEBUG >= 2
216   vtkPainterCommunicator* comm = this->GetCommunicator();
217 
218   vtkTextureIO::Write(mpifn(comm, "slicp_geometry_image.vtm"), this->Internals->GeometryImage,
219     this->Internals->BlockExts);
220   vtkTextureIO::Write(mpifn(comm, "slicp_vector_image.vtm"), this->Internals->VectorImage,
221     this->Internals->BlockExts);
222   vtkTextureIO::Write(mpifn(comm, "slicp_mask_vector_image.vtm"), this->Internals->MaskVectorImage,
223     this->Internals->BlockExts);
224   vtkTextureIO::Write(
225     mpifn(comm, "slicp_depth_image.vtm"), this->Internals->DepthImage, this->Internals->BlockExts);
226 #endif
227 }
228 
GatherVectors()229 void vtkSurfaceLICInterface::GatherVectors()
230 {
231   vtkPixelExtent viewExt(this->Internals->Viewsize[0], this->Internals->Viewsize[1]);
232 
233   vtkPainterCommunicator* comm = this->GetCommunicator();
234 
235   // get tight screen space bounds to reduce communication/computation
236   vtkPixelBufferObject* vecPBO = this->Internals->VectorImage->Download();
237   void* pVecPBO = vecPBO->MapPackedBuffer();
238 
239   this->Internals->GetPixelBounds(
240     (float*)pVecPBO, this->Internals->Viewsize[0], this->Internals->BlockExts);
241 
242   // initialize compositor
243   this->Internals->Compositor->Initialize(viewExt, this->Internals->BlockExts,
244     this->CompositeStrategy, this->StepSize, this->NumberOfSteps, this->NormalizeVectors,
245     this->EnhancedLIC, this->AntiAlias);
246 
247   if (comm->GetMPIInitialized())
248   {
249     // parallel run
250     // need to use the communicator provided by the rendering engine
251     this->Internals->Compositor->SetCommunicator(comm);
252 
253     // build compositing program and set up the screen space decomp
254     // with guard pixels
255     int iErr = 0;
256     iErr = this->Internals->Compositor->BuildProgram((float*)pVecPBO);
257     if (iErr)
258     {
259       vtkErrorMacro("Failed to construct program, reason " << iErr);
260     }
261 
262     // composite vectors
263     vtkTextureObject* compositeVectors = this->Internals->CompositeVectorImage;
264     iErr = this->Internals->Compositor->Gather(pVecPBO, VTK_FLOAT, 4, compositeVectors);
265     if (iErr)
266     {
267       vtkErrorMacro("Failed to composite vectors, reason  " << iErr);
268     }
269 
270     // composite mask vectors
271     vtkTextureObject* compositeMaskVectors = this->Internals->CompositeMaskVectorImage;
272     vtkPixelBufferObject* maskVecPBO = this->Internals->MaskVectorImage->Download();
273     void* pMaskVecPBO = maskVecPBO->MapPackedBuffer();
274     iErr = this->Internals->Compositor->Gather(pMaskVecPBO, VTK_FLOAT, 4, compositeMaskVectors);
275     if (iErr)
276     {
277       vtkErrorMacro("Failed to composite mask vectors, reason " << iErr);
278     }
279     maskVecPBO->UnmapPackedBuffer();
280     maskVecPBO->Delete();
281 
282     // restore the default communicator
283     this->Internals->Compositor->RestoreDefaultCommunicator();
284 
285 #if vtkSurfaceLICInterfaceDEBUG >= 2
286     vtkTextureIO::Write(mpifn(comm, "slicp_new_vector_image.vtm"),
287       this->Internals->CompositeVectorImage,
288       this->Internals->Compositor->GetDisjointGuardExtents());
289 
290     vtkTextureIO::Write(mpifn(comm, "slicp_new_mask_vector_image.vtm"),
291       this->Internals->CompositeMaskVectorImage,
292       this->Internals->Compositor->GetDisjointGuardExtents());
293 #endif
294   }
295   else
296   {
297     // serial run
298     // make the decomposition disjoint and add guard pixels
299     this->Internals->Compositor->InitializeCompositeExtents((float*)pVecPBO);
300 
301     // use the lic decomp from here on out, in serial we have this
302     // flexibility because we don't need to worry about ordered compositing
303     // or IceT's scissor boxes
304     this->Internals->BlockExts = this->Internals->Compositor->GetCompositeExtents();
305 
306     // pass through without compositing
307     this->Internals->CompositeVectorImage = this->Internals->VectorImage;
308     this->Internals->CompositeMaskVectorImage = this->Internals->MaskVectorImage;
309   }
310 
311   vecPBO->UnmapPackedBuffer();
312   vecPBO->Delete();
313 }
314 
ApplyLIC()315 void vtkSurfaceLICInterface::ApplyLIC()
316 {
317   vtkPainterCommunicator* comm = this->GetCommunicator();
318 
319   vtkPixelExtent viewExt(this->Internals->Viewsize[0], this->Internals->Viewsize[1]);
320 
321 #if vtkSurfaceLICInterfaceDEBUG >= 2
322   ostringstream oss;
323   if (this->GenerateNoiseTexture)
324   {
325     const char* noiseType[3] = { "unif", "gauss", "perl" };
326     oss << "slicp_noise_" << noiseType[this->NoiseType] << "_size_" << this->NoiseTextureSize
327         << "_grain_" << this->NoiseGrainSize << "_minval_" << this->MinNoiseValue << "_maxval_"
328         << this->MaxNoiseValue << "_nlevels_" << this->NumberOfNoiseLevels << "_impulseprob_"
329         << this->ImpulseNoiseProbability << "_impulseprob_" << this->ImpulseNoiseBackgroundValue
330         << ".vtk";
331   }
332   else
333   {
334     oss << "slicp_noise_default.vtk";
335   }
336   vtkTextureIO::Write(mpifn(comm, oss.str().c_str()), this->Internals->NoiseImage);
337 #endif
338 
339   // TODO -- this means that the steps size is a function
340   // of aspect ratio which is pretty insane...
341   // convert from window units to texture units
342   // this isn't correct since there's no way to account
343   // for anisotropy in the trasnform to texture space
344   double tcScale[2] = { 1.0 / this->Internals->Viewsize[0], 1.0 / this->Internals->Viewsize[1] };
345 
346   double stepSize = this->StepSize * sqrt(tcScale[0] * tcScale[0] + tcScale[1] * tcScale[1]);
347 
348   stepSize = stepSize <= 0.0 ? 1.0e-10 : stepSize;
349 
350   // configure image lic
351   vtkLineIntegralConvolution2D* LICer = this->Internals->LICer;
352 
353   LICer->SetStepSize(stepSize);
354   LICer->SetNumberOfSteps(this->NumberOfSteps);
355   LICer->SetEnhancedLIC(this->EnhancedLIC);
356   switch (this->EnhanceContrast)
357   {
358     case ENHANCE_CONTRAST_LIC:
359     case ENHANCE_CONTRAST_BOTH:
360       LICer->SetEnhanceContrast(vtkLIC2D::ENHANCE_CONTRAST_ON);
361       break;
362     default:
363       LICer->SetEnhanceContrast(vtkLIC2D::ENHANCE_CONTRAST_OFF);
364   }
365   LICer->SetLowContrastEnhancementFactor(this->LowLICContrastEnhancementFactor);
366   LICer->SetHighContrastEnhancementFactor(this->HighLICContrastEnhancementFactor);
367   LICer->SetAntiAlias(this->AntiAlias);
368   LICer->SetComponentIds(0, 1);
369   LICer->SetNormalizeVectors(this->NormalizeVectors);
370   LICer->SetMaskThreshold(this->MaskThreshold);
371   LICer->SetCommunicator(comm);
372 
373   // loop over composited extents
374   const std::deque<vtkPixelExtent>& compositeExts =
375     this->Internals->Compositor->GetCompositeExtents();
376 
377   const std::deque<vtkPixelExtent>& disjointGuardExts =
378     this->Internals->Compositor->GetDisjointGuardExtents();
379 
380   this->Internals->LICImage.TakeReference(LICer->Execute(viewExt, // screen extent
381     disjointGuardExts, // disjoint extent of valid vectors
382     compositeExts,     // disjoint extent where lic is needed
383     this->Internals->CompositeVectorImage, this->Internals->CompositeMaskVectorImage,
384     this->Internals->NoiseImage));
385 
386   if (!this->Internals->LICImage)
387   {
388     vtkErrorMacro("Failed to compute image LIC");
389     return;
390   }
391 
392 #if vtkSurfaceLICInterfaceDEBUG >= 2
393   vtkTextureIO::Write(mpifn(comm, "slicp_lic.vtm"), this->Internals->LICImage, compositeExts);
394 #endif
395 
396   // ------------------------------------------- move from LIC decomp back to geometry decomp
397   if (comm->GetMPIInitialized() &&
398     (this->Internals->Compositor->GetStrategy() != COMPOSITE_INPLACE))
399   {
400 #ifdef vtkSurfaceLICMapperTIME
401     this->StartTimerEvent("vtkSurfaceLICMapper::ScatterLIC");
402 #endif
403 
404     // parallel run
405     // need to use the communicator provided by the rendering engine
406     this->Internals->Compositor->SetCommunicator(comm);
407 
408     vtkPixelBufferObject* licPBO = this->Internals->LICImage->Download();
409     void* pLicPBO = licPBO->MapPackedBuffer();
410     vtkTextureObject* newLicImage = nullptr;
411     int iErr = this->Internals->Compositor->Scatter(pLicPBO, VTK_FLOAT, 4, newLicImage);
412     if (iErr)
413     {
414       vtkErrorMacro("Failed to scatter lic");
415     }
416     licPBO->UnmapPackedBuffer();
417     licPBO->Delete();
418     this->Internals->LICImage = nullptr;
419     this->Internals->LICImage = newLicImage;
420     newLicImage->Delete();
421 
422     // restore the default communicator
423     this->Internals->Compositor->RestoreDefaultCommunicator();
424 
425 #ifdef vtkSurfaceLICMapperTIME
426     this->EndTimerEvent("vtkSurfaceLICMapper::ScatterLIC");
427 #endif
428 #if vtkSurfaceLICInterfaceDEBUG >= 2
429     vtkTextureIO::Write(
430       mpifn(comm, "slicp_new_lic.vtm"), this->Internals->LICImage, this->Internals->BlockExts);
431 #endif
432   }
433 }
434 
CombineColorsAndLIC()435 void vtkSurfaceLICInterface::CombineColorsAndLIC()
436 {
437   vtkOpenGLRenderWindow* renWin = this->Internals->Context;
438   vtkOpenGLState* ostate = renWin->GetState();
439 
440   vtkPainterCommunicator* comm = this->GetCommunicator();
441 
442   vtkPixelExtent viewExt(this->Internals->Viewsize[0], this->Internals->Viewsize[1]);
443 
444   vtkOpenGLFramebufferObject* fbo = this->Internals->FBO;
445   ostate->PushFramebufferBindings();
446   fbo->Bind();
447   fbo->InitializeViewport(this->Internals->Viewsize[0], this->Internals->Viewsize[1]);
448   fbo->AddColorAttachment(0, this->Internals->RGBColorImage);
449   fbo->AddColorAttachment(1, this->Internals->HSLColorImage);
450   fbo->ActivateDrawBuffers(2);
451   vtkCheckFrameBufferStatusMacro(GL_FRAMEBUFFER);
452 
453   // clear the parts of the screen which we will modify
454   ostate->vtkglEnable(GL_SCISSOR_TEST);
455   ostate->vtkglClearColor(0.0, 0.0, 0.0, 0.0);
456   size_t nBlocks = this->Internals->BlockExts.size();
457   for (size_t e = 0; e < nBlocks; ++e)
458   {
459     vtkPixelExtent ext = this->Internals->BlockExts[e];
460     ext.Grow(2); // halo for linear filtering
461     ext &= viewExt;
462 
463     unsigned int extSize[2];
464     ext.Size(extSize);
465 
466     ostate->vtkglScissor(ext[0], ext[2], extSize[0], extSize[1]);
467     ostate->vtkglClear(GL_COLOR_BUFFER_BIT);
468   }
469   ostate->vtkglDisable(GL_SCISSOR_TEST);
470 
471   this->Internals->VectorImage->Activate();
472   this->Internals->GeometryImage->Activate();
473   this->Internals->LICImage->Activate();
474 
475   if (!this->Internals->ColorPass->Program)
476   {
477     this->InitializeResources();
478   }
479   vtkShaderProgram* colorPass = this->Internals->ColorPass->Program;
480   renWin->GetShaderCache()->ReadyShaderProgram(colorPass);
481 
482   colorPass->SetUniformi("texVectors", this->Internals->VectorImage->GetTextureUnit());
483   colorPass->SetUniformi("texGeomColors", this->Internals->GeometryImage->GetTextureUnit());
484   colorPass->SetUniformi("texLIC", this->Internals->LICImage->GetTextureUnit());
485   colorPass->SetUniformi("uScalarColorMode", this->ColorMode);
486   colorPass->SetUniformf("uLICIntensity", this->LICIntensity);
487   colorPass->SetUniformf("uMapBias", this->MapModeBias);
488   colorPass->SetUniformf("uMaskIntensity", this->MaskIntensity);
489   float fMaskColor[3];
490   fMaskColor[0] = this->MaskColor[0];
491   fMaskColor[1] = this->MaskColor[1];
492   fMaskColor[2] = this->MaskColor[2];
493   colorPass->SetUniform3f("uMaskColor", fMaskColor);
494 
495   for (size_t e = 0; e < nBlocks; ++e)
496   {
497     this->Internals->RenderQuad(viewExt, this->Internals->BlockExts[e], this->Internals->ColorPass);
498   }
499 
500   this->Internals->VectorImage->Deactivate();
501   this->Internals->GeometryImage->Deactivate();
502   this->Internals->LICImage->Deactivate();
503 
504   // --------------------------------------------- color contrast enhance
505   if ((this->EnhanceContrast == ENHANCE_CONTRAST_COLOR) ||
506     (this->EnhanceContrast == ENHANCE_CONTRAST_BOTH))
507   {
508 #if vtkSurfaceLICInterfaceDEBUG >= 2
509     vtkTextureIO::Write(mpifn(comm, "slic_color_rgb_in.vtm"), this->Internals->RGBColorImage,
510       this->Internals->BlockExts);
511     vtkTextureIO::Write(mpifn(comm, "slic_color_hsl_in.vtm"), this->Internals->HSLColorImage,
512       this->Internals->BlockExts);
513 #endif
514 
515     // find min/max lighness value for color contrast enhancement.
516     float LMin = VTK_FLOAT_MAX;
517     float LMax = -VTK_FLOAT_MAX;
518     float LMaxMinDiff = VTK_FLOAT_MAX;
519 
520     vtkSurfaceLICHelper::StreamingFindMinMax(fbo, this->Internals->BlockExts, LMin, LMax);
521 
522     if (!this->Internals->BlockExts.empty() && ((LMax <= LMin) || (LMin < 0.0f) || (LMax > 1.0f)))
523     {
524       vtkErrorMacro(<< comm->GetRank() << ": Invalid range " << LMin << ", " << LMax
525                     << " for color contrast enhancement");
526       LMin = 0.0;
527       LMax = 1.0;
528       LMaxMinDiff = 1.0;
529     }
530 
531     // global collective reduction for parallel operation
532     this->GetGlobalMinMax(comm, LMin, LMax);
533 
534     // set M and m as a fraction of the range.
535     LMaxMinDiff = LMax - LMin;
536     LMin += LMaxMinDiff * this->LowColorContrastEnhancementFactor;
537     LMax -= LMaxMinDiff * this->HighColorContrastEnhancementFactor;
538     LMaxMinDiff = LMax - LMin;
539 
540     // normalize shader
541     fbo->AddColorAttachment(0U, this->Internals->RGBColorImage);
542     fbo->ActivateDrawBuffer(0U);
543     vtkCheckFrameBufferStatusMacro(GL_DRAW_FRAMEBUFFER);
544 
545     this->Internals->GeometryImage->Activate();
546     this->Internals->HSLColorImage->Activate();
547     this->Internals->LICImage->Activate();
548 
549     if (!this->Internals->ColorEnhancePass->Program)
550     {
551       this->InitializeResources();
552     }
553     vtkShaderProgram* colorEnhancePass = this->Internals->ColorEnhancePass->Program;
554     renWin->GetShaderCache()->ReadyShaderProgram(colorEnhancePass);
555     colorEnhancePass->SetUniformi(
556       "texGeomColors", this->Internals->GeometryImage->GetTextureUnit());
557     colorEnhancePass->SetUniformi("texHSLColors", this->Internals->HSLColorImage->GetTextureUnit());
558     colorEnhancePass->SetUniformi("texLIC", this->Internals->LICImage->GetTextureUnit());
559     colorEnhancePass->SetUniformf("uLMin", LMin);
560     colorEnhancePass->SetUniformf("uLMaxMinDiff", LMaxMinDiff);
561 
562     for (size_t e = 0; e < nBlocks; ++e)
563     {
564       this->Internals->RenderQuad(
565         viewExt, this->Internals->BlockExts[e], this->Internals->ColorEnhancePass);
566     }
567 
568     this->Internals->GeometryImage->Deactivate();
569     this->Internals->HSLColorImage->Deactivate();
570     this->Internals->LICImage->Deactivate();
571 
572     fbo->RemoveColorAttachment(0U);
573     fbo->DeactivateDrawBuffers();
574   }
575   else
576   {
577     fbo->RemoveColorAttachment(0U);
578     fbo->RemoveColorAttachment(1U);
579     fbo->DeactivateDrawBuffers();
580   }
581 
582   ostate->PopFramebufferBindings();
583 
584 #if vtkSurfaceLICInterfaceDEBUG >= 2
585   vtkTextureIO::Write(
586     mpifn(comm, "slicp_new_rgb.vtm"), this->Internals->RGBColorImage, this->Internals->BlockExts);
587 #endif
588 }
589 
CopyToScreen()590 void vtkSurfaceLICInterface::CopyToScreen()
591 {
592   vtkOpenGLRenderWindow* renWin = this->Internals->Context;
593   vtkOpenGLState* ostate = renWin->GetState();
594 
595   vtkPixelExtent viewExt(this->Internals->Viewsize[0], this->Internals->Viewsize[1]);
596 
597   ostate->PopFramebufferBindings();
598 
599   ostate->vtkglDisable(GL_BLEND);
600   ostate->vtkglDisable(GL_SCISSOR_TEST);
601   ostate->vtkglEnable(GL_DEPTH_TEST);
602 
603   // Viewport transformation for 1:1 'pixel=texel=data' mapping.
604   // Note this is not enough for 1:1 mapping, because depending on the
605   // primitive displayed (point,line,polygon), the rasterization rules
606   // are different.
607   ostate->vtkglViewport(0, 0, this->Internals->Viewsize[0], this->Internals->Viewsize[1]);
608 
609   this->Internals->DepthImage->Activate();
610   this->Internals->RGBColorImage->Activate();
611 
612   if (!this->Internals->CopyPass->Program)
613   {
614     this->InitializeResources();
615   }
616   vtkShaderProgram* copyPass = this->Internals->CopyPass->Program;
617   renWin->GetShaderCache()->ReadyShaderProgram(copyPass);
618   copyPass->SetUniformi("texDepth", this->Internals->DepthImage->GetTextureUnit());
619   copyPass->SetUniformi("texRGBColors", this->Internals->RGBColorImage->GetTextureUnit());
620 
621   size_t nBlocks = this->Internals->BlockExts.size();
622   for (size_t e = 0; e < nBlocks; ++e)
623   {
624     this->Internals->RenderQuad(viewExt, this->Internals->BlockExts[e], this->Internals->CopyPass);
625   }
626 
627   this->Internals->DepthImage->Deactivate();
628   this->Internals->RGBColorImage->Deactivate();
629 
630 #ifdef vtkSurfaceLICMapperTIME
631   this->EndTimerEvent("vtkSurfaceLICMapper::DepthCopy");
632 #endif
633 
634   //
635   this->Internals->Updated();
636 }
637 
638 //------------------------------------------------------------------------------
ReleaseGraphicsResources(vtkWindow * win)639 void vtkSurfaceLICInterface::ReleaseGraphicsResources(vtkWindow* win)
640 {
641   this->Internals->ReleaseGraphicsResources(win);
642   this->Internals->Context = nullptr;
643 }
644 
645 //------------------------------------------------------------------------------
646 #define vtkSetMonitoredParameterMacro(_name, _type, _code)                                         \
647   void vtkSurfaceLICInterface::Set##_name(_type val)                                               \
648   {                                                                                                \
649     if (val == this->_name)                                                                        \
650     {                                                                                              \
651       return;                                                                                      \
652     }                                                                                              \
653     _code this->_name = val;                                                                       \
654     this->Modified();                                                                              \
655   }
656 // lic
657 vtkSetMonitoredParameterMacro(GenerateNoiseTexture, int, this->Internals->Noise = nullptr;
658                               this->Internals->NoiseImage = nullptr;);
659 
660 vtkSetMonitoredParameterMacro(NoiseType, int, this->Internals->Noise = nullptr;
661                               this->Internals->NoiseImage = nullptr;);
662 
663 vtkSetMonitoredParameterMacro(NoiseTextureSize, int, this->Internals->Noise = nullptr;
664                               this->Internals->NoiseImage = nullptr;);
665 
666 vtkSetMonitoredParameterMacro(NoiseGrainSize, int, this->Internals->Noise = nullptr;
667                               this->Internals->NoiseImage = nullptr;);
668 
669 vtkSetMonitoredParameterMacro(MinNoiseValue, double, val = val < 0.0 ? 0.0 : val;
670                               val = val > 1.0 ? 1.0 : val; this->Internals->Noise = nullptr;
671                               this->Internals->NoiseImage = nullptr;);
672 
673 vtkSetMonitoredParameterMacro(MaxNoiseValue, double, val = val < 0.0 ? 0.0 : val;
674                               val = val > 1.0 ? 1.0 : val; this->Internals->Noise = nullptr;
675                               this->Internals->NoiseImage = nullptr;);
676 
677 vtkSetMonitoredParameterMacro(NumberOfNoiseLevels, int, this->Internals->Noise = nullptr;
678                               this->Internals->NoiseImage = nullptr;);
679 
680 vtkSetMonitoredParameterMacro(ImpulseNoiseProbability, double, val = val < 0.0 ? 0.0 : val;
681                               val = val > 1.0 ? 1.0 : val; this->Internals->Noise = nullptr;
682                               this->Internals->NoiseImage = nullptr;);
683 
684 vtkSetMonitoredParameterMacro(ImpulseNoiseBackgroundValue, double, val = val < 0.0 ? 0.0 : val;
685                               val = val > 1.0 ? 1.0 : val; this->Internals->Noise = nullptr;
686                               this->Internals->NoiseImage = nullptr;);
687 
688 vtkSetMonitoredParameterMacro(NoiseGeneratorSeed, int, this->Internals->Noise = nullptr;
689                               this->Internals->NoiseImage = nullptr;);
690 
691 // compositor
692 vtkSetMonitoredParameterMacro(CompositeStrategy, int, );
693 
694 // lic/compositor
695 vtkSetMonitoredParameterMacro(NumberOfSteps, int, );
696 
697 vtkSetMonitoredParameterMacro(StepSize, double, );
698 
699 vtkSetMonitoredParameterMacro(NormalizeVectors, int, val = val < 0 ? 0 : val;
700                               val = val > 1 ? 1 : val;);
701 
702 vtkSetMonitoredParameterMacro(MaskThreshold, double, );
703 
704 vtkSetMonitoredParameterMacro(EnhancedLIC, int, );
705 
706 // lic
707 vtkSetMonitoredParameterMacro(LowLICContrastEnhancementFactor, double, val = val < 0.0 ? 0.0 : val;
708                               val = val > 1.0 ? 1.0 : val;);
709 
710 vtkSetMonitoredParameterMacro(HighLICContrastEnhancementFactor, double, val = val < 0.0 ? 0.0 : val;
711                               val = val > 1.0 ? 1.0 : val;);
712 
713 vtkSetMonitoredParameterMacro(AntiAlias, int, val = val < 0 ? 0 : val;);
714 
715 // geometry
716 vtkSetMonitoredParameterMacro(MaskOnSurface, int, val = val < 0 ? 0 : val;
717                               val = val > 1 ? 1 : val;);
718 
719 // colors
720 vtkSetMonitoredParameterMacro(ColorMode, int, );
721 
722 vtkSetMonitoredParameterMacro(LICIntensity, double, val = val < 0.0 ? 0.0 : val;
723                               val = val > 1.0 ? 1.0 : val;);
724 
725 vtkSetMonitoredParameterMacro(MaskIntensity, double, val = val < 0.0 ? 0.0 : val;
726                               val = val > 1.0 ? 1.0 : val;);
727 
728 vtkSetMonitoredParameterMacro(MapModeBias, double, val = val < -1.0 ? -1.0 : val;
729                               val = val > 1.0 ? 1.0 : val;);
730 
731 vtkSetMonitoredParameterMacro(
732   LowColorContrastEnhancementFactor, double, val = val < 0.0 ? 0.0 : val;
733   val = val > 1.0 ? 1.0 : val;);
734 
735 vtkSetMonitoredParameterMacro(
736   HighColorContrastEnhancementFactor, double, val = val < 0.0 ? 0.0 : val;
737   val = val > 1.0 ? 1.0 : val;);
738 
739 //------------------------------------------------------------------------------
SetMaskColor(double * val)740 void vtkSurfaceLICInterface::SetMaskColor(double* val)
741 {
742   double rgb[3];
743   for (int q = 0; q < 3; ++q)
744   {
745     rgb[q] = val[q];
746     rgb[q] = rgb[q] < 0.0 ? 0.0 : rgb[q];
747     rgb[q] = rgb[q] > 1.0 ? 1.0 : rgb[q];
748   }
749   if ((rgb[0] == this->MaskColor[0]) && (rgb[1] == this->MaskColor[1]) &&
750     (rgb[2] == this->MaskColor[2]))
751   {
752     return;
753   }
754   for (int q = 0; q < 3; ++q)
755   {
756     this->MaskColor[q] = rgb[q];
757   }
758   this->Modified();
759 }
760 
761 //------------------------------------------------------------------------------
SetEnhanceContrast(int val)762 void vtkSurfaceLICInterface::SetEnhanceContrast(int val)
763 {
764   val = val < ENHANCE_CONTRAST_OFF ? ENHANCE_CONTRAST_OFF : val;
765   val = val > ENHANCE_CONTRAST_BOTH ? ENHANCE_CONTRAST_BOTH : val;
766   if (val == this->EnhanceContrast)
767   {
768     return;
769   }
770 
771   this->EnhanceContrast = val;
772   this->Modified();
773 }
774 
775 //------------------------------------------------------------------------------
SetNoiseDataSet(vtkImageData * data)776 void vtkSurfaceLICInterface::SetNoiseDataSet(vtkImageData* data)
777 {
778   if (data == this->Internals->Noise)
779   {
780     return;
781   }
782   this->Internals->Noise = data;
783   this->Internals->NoiseImage = nullptr;
784   this->Modified();
785 }
786 
787 //------------------------------------------------------------------------------
GetNoiseDataSet()788 vtkImageData* vtkSurfaceLICInterface::GetNoiseDataSet()
789 {
790   if (this->Internals->Noise == nullptr)
791   {
792     vtkImageData* noise = nullptr;
793     if (this->GenerateNoiseTexture)
794     {
795       // report potential issues
796       if (this->NoiseGrainSize >= this->NoiseTextureSize)
797       {
798         vtkErrorMacro("NoiseGrainSize must be smaller than NoiseTextureSize");
799       }
800       if (this->MinNoiseValue >= this->MaxNoiseValue)
801       {
802         vtkErrorMacro("MinNoiseValue must be smaller than MaxNoiseValue");
803       }
804       if ((this->ImpulseNoiseProbability == 1.0) && (this->NumberOfNoiseLevels < 2))
805       {
806         vtkErrorMacro("NumberOfNoiseLevels must be greater than 1 "
807                       "when not generating impulse noise");
808       }
809 
810       // generate a custom noise texture based on the
811       // current settings.
812       int noiseTextureSize = this->NoiseTextureSize;
813       int noiseGrainSize = this->NoiseGrainSize;
814       vtkLICRandomNoise2D noiseGen;
815       float* noiseValues = noiseGen.Generate(this->NoiseType, noiseTextureSize, noiseGrainSize,
816         static_cast<float>(this->MinNoiseValue), static_cast<float>(this->MaxNoiseValue),
817         this->NumberOfNoiseLevels, this->ImpulseNoiseProbability,
818         static_cast<float>(this->ImpulseNoiseBackgroundValue), this->NoiseGeneratorSeed);
819       if (noiseValues == nullptr)
820       {
821         vtkErrorMacro("Failed to generate noise.");
822       }
823 
824       vtkFloatArray* noiseArray = vtkFloatArray::New();
825       noiseArray->SetNumberOfComponents(2);
826       noiseArray->SetName("noise");
827       vtkIdType arraySize = 2 * noiseTextureSize * noiseTextureSize;
828       noiseArray->SetArray(noiseValues, arraySize, 0);
829 
830       noise = vtkImageData::New();
831       noise->SetSpacing(1.0, 1.0, 1.0);
832       noise->SetOrigin(0.0, 0.0, 0.0);
833       noise->SetDimensions(noiseTextureSize, noiseTextureSize, 1);
834       noise->GetPointData()->SetScalars(noiseArray);
835 
836       noiseArray->Delete();
837     }
838     else
839     {
840       // load a predefined noise texture.
841       noise = vtkLICRandomNoise2D::GetNoiseResource();
842     }
843 
844     this->Internals->Noise = noise;
845     this->Internals->NoiseImage = nullptr;
846     noise->Delete();
847     noise = nullptr;
848   }
849 
850   return this->Internals->Noise;
851 }
852 
853 //------------------------------------------------------------------------------
UpdateNoiseImage(vtkRenderWindow * renWin)854 void vtkSurfaceLICInterface::UpdateNoiseImage(vtkRenderWindow* renWin)
855 {
856   vtkOpenGLRenderWindow* rw = vtkOpenGLRenderWindow::SafeDownCast(renWin);
857   vtkImageData* noiseDataSet = this->GetNoiseDataSet();
858 
859   int ext[6];
860   noiseDataSet->GetExtent(ext);
861   unsigned int dataWidth = ext[1] - ext[0] + 1;
862   unsigned int dataHeight = ext[3] - ext[2] + 1;
863 
864   vtkDataArray* noiseArray = noiseDataSet->GetPointData()->GetScalars();
865   int dataType = noiseArray->GetDataType();
866   void* data = noiseArray->GetVoidPointer(0);
867   int dataComps = noiseArray->GetNumberOfComponents();
868   unsigned int dataSize = noiseArray->GetNumberOfTuples() * dataComps;
869 
870   vtkPixelBufferObject* pbo = vtkPixelBufferObject::New();
871   pbo->SetContext(renWin);
872   pbo->Upload1D(dataType, data, dataSize, 1, 0);
873 
874   vtkTextureObject* tex = vtkTextureObject::New();
875   tex->SetContext(rw);
876   tex->SetBaseLevel(0);
877   tex->SetMaxLevel(0);
878   tex->SetWrapS(vtkTextureObject::Repeat);
879   tex->SetWrapT(vtkTextureObject::Repeat);
880   tex->SetMinificationFilter(vtkTextureObject::Nearest);
881   tex->SetMagnificationFilter(vtkTextureObject::Nearest);
882   tex->Create2D(dataWidth, dataHeight, dataComps, pbo, false);
883   tex->SetAutoParameters(0);
884   pbo->Delete();
885 
886   this->Internals->NoiseImage = tex;
887   tex->Delete();
888 }
889 
890 //------------------------------------------------------------------------------
IsSupported(vtkRenderWindow * renWin)891 bool vtkSurfaceLICInterface::IsSupported(vtkRenderWindow* renWin)
892 {
893   vtkOpenGLRenderWindow* context = vtkOpenGLRenderWindow::SafeDownCast(renWin);
894 
895   return vtkSurfaceLICHelper::IsSupported(context);
896 }
897 
898 //------------------------------------------------------------------------------
CanRenderSurfaceLIC(vtkActor * actor)899 bool vtkSurfaceLICInterface::CanRenderSurfaceLIC(vtkActor* actor)
900 {
901   // check the render context for GL feature support
902   // note this also handles non-opengl render window
903   if (this->Internals->ContextNeedsUpdate &&
904     !vtkSurfaceLICInterface::IsSupported(this->Internals->Context))
905   {
906     vtkErrorMacro("SurfaceLIC is not supported");
907     return false;
908   }
909 
910   bool canRender = false;
911 
912   int rep = actor->GetProperty()->GetRepresentation();
913 
914   if (this->Enable && this->Internals->HasVectors && (rep == VTK_SURFACE))
915   {
916     canRender = true;
917   }
918 
919 #if vtkSurfaceLICInterfaceDEBUG >= 1
920   cerr << this->Internals->Communicator->GetWorldRank() << " CanRender " << canRender << endl;
921 #endif
922 
923   return canRender;
924 }
925 
926 namespace
927 {
BuildAShader(vtkOpenGLRenderWindow * renWin,vtkOpenGLHelper ** cbor,const char * vert,const char * frag)928 void BuildAShader(
929   vtkOpenGLRenderWindow* renWin, vtkOpenGLHelper** cbor, const char* vert, const char* frag)
930 {
931   if (*cbor == nullptr)
932   {
933     *cbor = new vtkOpenGLHelper;
934   }
935   if (!(*cbor)->Program)
936   {
937     (*cbor)->Program = renWin->GetShaderCache()->ReadyShaderProgram(vert, frag, "");
938   }
939   else
940   {
941     renWin->GetShaderCache()->ReadyShaderProgram((*cbor)->Program);
942   }
943 }
944 }
945 
946 //------------------------------------------------------------------------------
InitializeResources()947 void vtkSurfaceLICInterface::InitializeResources()
948 {
949   bool initialized = true;
950 
951   // noise image
952   if (!this->Internals->NoiseImage)
953   {
954     initialized = false;
955 
956     this->UpdateNoiseImage(this->Internals->Context);
957   }
958 
959   // compositer for parallel operation
960   if (!this->Internals->Compositor)
961   {
962     this->Internals->UpdateAll();
963     vtkSurfaceLICComposite* compositor = vtkSurfaceLICComposite::New();
964     compositor->SetContext(this->Internals->Context);
965     this->Internals->Compositor = compositor;
966     compositor->Delete();
967   }
968 
969   // image LIC
970   if (!this->Internals->LICer)
971   {
972     initialized = false;
973 
974     vtkLineIntegralConvolution2D* LICer = vtkLineIntegralConvolution2D::New();
975     LICer->SetContext(this->Internals->Context);
976     this->Internals->LICer = LICer;
977     LICer->Delete();
978   }
979 
980   // frame buffers
981   if (!this->Internals->FBO)
982   {
983     initialized = false;
984 
985     vtkOpenGLFramebufferObject* fbo = vtkOpenGLFramebufferObject::New();
986     fbo->SetContext(this->Internals->Context);
987     this->Internals->FBO = fbo;
988     fbo->Delete();
989   }
990 
991   // load shader codes
992   vtkOpenGLRenderWindow* renWin = this->Internals->Context;
993 
994   if (!this->Internals->ColorPass || !this->Internals->ColorPass->Program)
995   {
996     initialized = false;
997     BuildAShader(
998       renWin, &this->Internals->ColorPass, vtkTextureObjectVS, vtkSurfaceLICInterface_SC);
999   }
1000 
1001   if (!this->Internals->ColorEnhancePass || !this->Internals->ColorEnhancePass->Program)
1002   {
1003     initialized = false;
1004     BuildAShader(
1005       renWin, &this->Internals->ColorEnhancePass, vtkTextureObjectVS, vtkSurfaceLICInterface_CE);
1006   }
1007 
1008   if (!this->Internals->CopyPass || !this->Internals->CopyPass->Program)
1009   {
1010     initialized = false;
1011     BuildAShader(
1012       renWin, &this->Internals->CopyPass, vtkTextureObjectVS, vtkSurfaceLICInterface_DCpy);
1013   }
1014 
1015   // if any of the above were not already initialized
1016   // then execute all stages
1017   if (!initialized)
1018   {
1019     this->Internals->UpdateAll();
1020   }
1021 }
1022 
1023 //------------------------------------------------------------------------------
NeedToUpdateCommunicator()1024 bool vtkSurfaceLICInterface::NeedToUpdateCommunicator()
1025 {
1026   // no comm or externally modified parameters
1027   if (this->Internals->CommunicatorNeedsUpdate || this->Internals->ContextNeedsUpdate ||
1028     !this->Internals->Communicator || this->AlwaysUpdate)
1029   {
1030     this->Internals->CommunicatorNeedsUpdate = true;
1031     this->Internals->UpdateAll();
1032   }
1033 
1034 #if vtkSurfaceLICInterfaceDEBUG >= 1
1035   cerr << this->Internals->Communicator->GetWorldRank() << " NeedToUpdateCommunicator "
1036        << this->Internals->CommunicatorNeedsUpdate << endl;
1037 #endif
1038 
1039   return this->Internals->CommunicatorNeedsUpdate;
1040 }
1041 
1042 //------------------------------------------------------------------------------
ValidateContext(vtkRenderer * renderer)1043 void vtkSurfaceLICInterface::ValidateContext(vtkRenderer* renderer)
1044 {
1045   bool modified = false;
1046 
1047   vtkOpenGLRenderWindow* context = vtkOpenGLRenderWindow::SafeDownCast(renderer->GetRenderWindow());
1048 
1049   // context changed
1050   if (this->Internals->Context != context)
1051   {
1052     modified = true;
1053     if (this->Internals->Context)
1054     {
1055       this->ReleaseGraphicsResources(this->Internals->Context);
1056     }
1057     this->Internals->Context = context;
1058   }
1059 
1060   // viewport size changed
1061   int viewsize[2];
1062   renderer->GetTiledSize(&viewsize[0], &viewsize[1]);
1063   if (this->Internals->Viewsize[0] != viewsize[0] || this->Internals->Viewsize[1] != viewsize[1])
1064   {
1065     modified = true;
1066 
1067     // update view size
1068     this->Internals->Viewsize[0] = viewsize[0];
1069     this->Internals->Viewsize[1] = viewsize[1];
1070 
1071     // resize textures
1072     this->Internals->ClearTextures();
1073     this->Internals->AllocateTextures(context, viewsize);
1074   }
1075 
1076   // if anything changed execute all stages
1077   if (modified)
1078   {
1079     this->Internals->UpdateAll();
1080   }
1081 
1082 #if vtkSurfaceLICInterfaceDEBUG >= 1
1083   cerr << this->Internals->Communicator->GetWorldRank() << " NeedToUpdatContext " << modified
1084        << endl;
1085 #endif
1086 }
1087 
SetHasVectors(bool v)1088 void vtkSurfaceLICInterface::SetHasVectors(bool v)
1089 {
1090   this->Internals->HasVectors = v;
1091 }
1092 
GetHasVectors()1093 bool vtkSurfaceLICInterface::GetHasVectors()
1094 {
1095   return this->Internals->HasVectors;
1096 }
1097 
1098 //------------------------------------------------------------------------------
GetCommunicator()1099 vtkPainterCommunicator* vtkSurfaceLICInterface::GetCommunicator()
1100 {
1101   return this->Internals->Communicator;
1102 }
1103 
1104 //------------------------------------------------------------------------------
CreateCommunicator(int)1105 vtkPainterCommunicator* vtkSurfaceLICInterface::CreateCommunicator(int)
1106 {
1107   return new vtkPainterCommunicator;
1108 }
1109 
1110 //------------------------------------------------------------------------------
CreateCommunicator(vtkRenderer * ren,vtkActor * act,vtkDataObject * input)1111 void vtkSurfaceLICInterface::CreateCommunicator(
1112   vtkRenderer* ren, vtkActor* act, vtkDataObject* input)
1113 {
1114   // compute screen space pixel extent of local blocks and
1115   // union of local blocks. only blocks that pass view frustum
1116   // visibility test are used in the computation.
1117   this->Internals->DataSetExt.Clear();
1118   this->Internals->BlockExts.clear();
1119 
1120   int includeRank = this->Internals->ProjectBounds(ren, act, input, this->Internals->Viewsize,
1121     this->Internals->DataSetExt, this->Internals->BlockExts);
1122 
1123   delete this->Internals->Communicator;
1124   this->Internals->Communicator = this->CreateCommunicator(includeRank);
1125 
1126 #if vtkSurfaceLICInterfaceDEBUG >= 1
1127   cerr << this->Internals->Communicator->GetWorldRank() << " is rendering " << includeRank << endl;
1128 #endif
1129 }
1130 
1131 //------------------------------------------------------------------------------
SetUpdateAll()1132 void vtkSurfaceLICInterface::SetUpdateAll()
1133 {
1134   this->Internals->UpdateAll();
1135 }
1136 
1137 //------------------------------------------------------------------------------
PrintSelf(ostream & os,vtkIndent indent)1138 void vtkSurfaceLICInterface::PrintSelf(ostream& os, vtkIndent indent)
1139 {
1140   this->Superclass::PrintSelf(os, indent);
1141   os << indent << "NumberOfSteps=" << this->NumberOfSteps << endl
1142      << indent << "StepSize=" << this->StepSize << endl
1143      << indent << "NormalizeVectors=" << this->NormalizeVectors << endl
1144      << indent << "EnhancedLIC=" << this->EnhancedLIC << endl
1145      << indent << "EnhanceContrast=" << this->EnhanceContrast << endl
1146      << indent << "LowLICContrastEnhancementFactor=" << this->LowLICContrastEnhancementFactor
1147      << endl
1148      << indent << "HighLICContrastEnhancementFactor=" << this->HighLICContrastEnhancementFactor
1149      << endl
1150      << indent << "LowColorContrastEnhancementFactor=" << this->LowColorContrastEnhancementFactor
1151      << endl
1152      << indent << "HighColorContrastEnhancementFactor=" << this->HighColorContrastEnhancementFactor
1153      << endl
1154      << indent << "AntiAlias=" << this->AntiAlias << endl
1155      << indent << "MaskOnSurface=" << this->MaskOnSurface << endl
1156      << indent << "MaskThreshold=" << this->MaskThreshold << endl
1157      << indent << "MaskIntensity=" << this->MaskIntensity << endl
1158      << indent << "MaskColor=" << this->MaskColor[0] << ", " << this->MaskColor[1] << ", "
1159      << this->MaskColor[2] << endl
1160      << indent << "ColorMode=" << this->ColorMode << endl
1161      << indent << "LICIntensity=" << this->LICIntensity << endl
1162      << indent << "MapModeBias=" << this->MapModeBias << endl
1163      << indent << "GenerateNoiseTexture=" << this->GenerateNoiseTexture << endl
1164      << indent << "NoiseType=" << this->NoiseType << endl
1165      << indent << "NoiseTextureSize=" << this->NoiseTextureSize << endl
1166      << indent << "NoiseGrainSize=" << this->NoiseGrainSize << endl
1167      << indent << "MinNoiseValue=" << this->MinNoiseValue << endl
1168      << indent << "MaxNoiseValue=" << this->MaxNoiseValue << endl
1169      << indent << "NumberOfNoiseLevels=" << this->NumberOfNoiseLevels << endl
1170      << indent << "ImpulseNoiseProbablity=" << this->ImpulseNoiseProbability << endl
1171      << indent << "ImpulseNoiseBackgroundValue=" << this->ImpulseNoiseBackgroundValue << endl
1172      << indent << "NoiseGeneratorSeed=" << this->NoiseGeneratorSeed << endl
1173      << indent << "AlwaysUpdate=" << this->AlwaysUpdate << endl
1174      << indent << "CompositeStrategy=" << this->CompositeStrategy << endl;
1175 }
1176