[CC]LOD技术「建议收藏」

[CC]LOD技术

大家好,又见面了,我是全栈君。

ccGLWindow::paintGL()

             |

  ccGLWindow::fullRenderingPass(…)

        |

      ccGLWindow::drawBackground(context, renderingParams);

      ccGLWindow::draw3D(context, renderingParams);//ccGLWindow::draw3D(CC_DRAW_CONTEXT& CONTEXT, RenderingParams& renderingParams)

          |

         m_globalDBRoot->draw(CONTEXT); // ccHObject*

         m_winDBRoot->draw(CONTEXT);  //ccHObject*

 

 1 void ccHObject::draw(CC_DRAW_CONTEXT& context)
 2 {
 3     if (!isEnabled())
 4         return;
 5 
 6     //are we currently drawing objects in 2D or 3D?
 7     bool draw3D = MACRO_Draw3D(context);
 8     
 9     //the entity must be either visible or selected, and of course it should be displayed in this context
10     bool drawInThisContext = ((m_visible || m_selected) && m_currentDisplay == context._win);
11 
12     //no need to display anything but clouds and meshes in "element picking mode"
13     drawInThisContext &= (    ( !MACRO_DrawPointNames(context)    || isKindOf(CC_TYPES::POINT_CLOUD) ) || 
14                             ( !MACRO_DrawTriangleNames(context)    || isKindOf(CC_TYPES::MESH) ));
15 
16     if (draw3D)
17     {
18         //apply 3D 'temporary' transformation (for display only)
19         if (m_glTransEnabled)
20         {
21             glMatrixMode(GL_MODELVIEW);
22             glPushMatrix();
23             glMultMatrixf(m_glTrans.data());
24         }
25 
26         if (    context.decimateCloudOnMove                        //LOD for clouds is enabled?
27             &&    context.currentLODLevel >= context.minLODLevel    //and we are currently rendering higher levels?
28             )
29         {
30             //only for real clouds
31             drawInThisContext &= isA(CC_TYPES::POINT_CLOUD);
32         }
33     }
34 
35     //draw entity
36     if (m_visible && drawInThisContext)
37     {
38         if (( !m_selected || !MACRO_SkipSelected(context) ) &&
39             (  m_selected || !MACRO_SkipUnselected(context) ))
40         {
41             //apply default color (in case of)
42             ccGL::Color3v(context.pointsDefaultCol.rgb);
43 
44             drawMeOnly(context);
45 
46             //draw name in 3D (we display it in the 2D foreground layer in fact!)
47             if (m_showNameIn3D && MACRO_Draw2D(context) && MACRO_Foreground(context) && !MACRO_DrawNames(context))
48                 drawNameIn3D(context);
49         }
50     }
51 
52     //draw entity's children
53     for (Container::iterator it = m_children.begin(); it != m_children.end(); ++it)
54         (*it)->draw(context);
55 
56     //if the entity is currently selected, we draw its bounding-box
57     if (m_selected && draw3D && drawInThisContext && !MACRO_DrawNames(context) && context.currentLODLevel == 0)
58     {
59         drawBB(context.bbDefaultCol);
60     }
61 
62     if (draw3D && m_glTransEnabled)
63         glPopMatrix();
64 }

 点云八叉树

class QCC_DB_LIB_API ccOctree : public CCLib::DgmOctree, public ccHObject

  八叉树的网格显示,QCC_DB_LIB项目下。

[CC]LOD技术「建议收藏」
[CC]LOD技术「建议收藏」

 1 /*** RENDERING METHODS ***/  2  3 void ccOctree::RenderOctreeAs( CC_OCTREE_DISPLAY_TYPE octreeDisplayType,  4 ccOctree* theOctree,  5 unsigned char level,  6 ccGenericPointCloud* theAssociatedCloud,  7 int &octreeGLListID,  8 bool updateOctreeGLDisplay)  9 {  10 if (!theOctree || !theAssociatedCloud)  11 return;  12  13  glPushAttrib(GL_LIGHTING_BIT);  14  15 if (octreeDisplayType == WIRE)  16  {  17 //cet affichage demande trop de memoire pour le stocker sous forme de liste OpenGL  18 //donc on doit le generer dynamiquement  19  20 glDisable(GL_LIGHTING); //au cas où la lumiere soit allumee  21  ccGL::Color3v(ccColor::green.rgba);  22  23 void* additionalParameters[] = { theOctree->m_frustrumIntersector };  24 theOctree->executeFunctionForAllCellsAtLevel( level,  25 &DrawCellAsABox,  26  additionalParameters);  27  }  28 else  29  {  30  glDrawParams glParams;  31 theAssociatedCloud->getDrawingParameters(glParams);  32  33 if (glParams.showNorms)  34  {  35 //DGM: Strangely, when Qt::renderPixmap is called, the OpenGL version is sometimes 1.0!  36 glEnable((QGLFormat::openGLVersionFlags() & QGLFormat::OpenGL_Version_1_2 ? GL_RESCALE_NORMAL : GL_NORMALIZE));  37  glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, CC_DEFAULT_CLOUD_AMBIENT_COLOR.rgba );  38  glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, CC_DEFAULT_CLOUD_SPECULAR_COLOR.rgba );  39  glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, CC_DEFAULT_CLOUD_DIFFUSE_COLOR.rgba );  40  glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, CC_DEFAULT_CLOUD_EMISSION_COLOR.rgba );  41  glMaterialf (GL_FRONT_AND_BACK, GL_SHININESS, CC_DEFAULT_CLOUD_SHININESS);  42  glEnable(GL_LIGHTING);  43  44  glEnable(GL_COLOR_MATERIAL);  45  glColorMaterial(GL_FRONT_AND_BACK, GL_DIFFUSE);  46  }  47  48 if (!glParams.showColors)  49  ccGL::Color3v(ccColor::white.rgba);  50  51 if (updateOctreeGLDisplay || octreeGLListID < 0)  52  {  53 if (octreeGLListID < 0)  54 octreeGLListID = glGenLists(1);  55 else if (glIsList(octreeGLListID))  56 glDeleteLists(octreeGLListID,1);  57  glNewList(octreeGLListID,GL_COMPILE);  58  59 if (octreeDisplayType == MEAN_POINTS)  60  {  61 void* additionalParameters[2] = { reinterpret_cast<void*>(&glParams),  62 reinterpret_cast<void*>(theAssociatedCloud),  63  };  64  65  glBegin(GL_POINTS);  66 theOctree->executeFunctionForAllCellsAtLevel( level,  67 &DrawCellAsAPoint,  68  additionalParameters);  69  glEnd();  70  }  71 else  72  {  73 //by default we use a box as primitive  74 PointCoordinateType cs = theOctree->getCellSize(level);  75  CCVector3 dims(cs,cs,cs);  76  ccBox box(dims);  77 box.showColors(glParams.showColors || glParams.showSF);  78  box.showNormals(glParams.showNorms);  79  80 //trick: replace all normal indexes so that they point on the first one  81  {  82 if (box.arePerTriangleNormalsEnabled())  83 for (unsigned i=0;i<box.size();++i)  84 box.setTriangleNormalIndexes(i,0,0,0);  85  }  86  87 //fake context  88  CC_DRAW_CONTEXT context;  89 context.flags = CC_DRAW_3D | CC_DRAW_FOREGROUND| CC_LIGHT_ENABLED;  90 context._win = 0;  91  92 void* additionalParameters[4] = { reinterpret_cast<void*>(&glParams),  93 reinterpret_cast<void*>(theAssociatedCloud),  94 reinterpret_cast<void*>(&box),  95 reinterpret_cast<void*>(&context)  96  };  97  98 theOctree->executeFunctionForAllCellsAtLevel( level,  99 &DrawCellAsAPrimitive, 100  additionalParameters); 101  } 102 103  glEndList(); 104  } 105 106  glCallList(octreeGLListID); 107 108 if (glParams.showNorms) 109  { 110  glDisable(GL_COLOR_MATERIAL); 111 glDisable((QGLFormat::openGLVersionFlags() & QGLFormat::OpenGL_Version_1_2 ? GL_RESCALE_NORMAL : GL_NORMALIZE)); 112  glDisable(GL_LIGHTING); 113  } 114  } 115 116  glPopAttrib(); 117 }

ccOctree::RenderOctreeAs

 

点云类

class QCC_DB_LIB_API ccPointCloud : public CCLib::ChunkedPointCloud, public ccGenericPointCloud

class QCC_DB_LIB_API ccGenericPointCloud : public ccShiftedObject,  virtual public CCLib::GenericIndexedCloudPersist

class CC_CORE_LIB_API GenericIndexedCloudPersist : virtual public GenericIndexedCloud

class CC_CORE_LIB_API GenericIndexedCloud : virtual public GenericCloud

注意ccPointCloud重载了ccHObject的一些方法

1 virtual void drawMeOnly(CC_DRAW_CONTEXT& context); 2 virtual void applyGLTransformation(const ccGLMatrix& trans); 3 virtual bool toFile_MeOnly(QFile& out) const; 4 virtual bool fromFile_MeOnly(QFile& in, short dataVersion, int flags); 5 virtual void notifyGeometryUpdate();

以下为drawMeOnly方法:

[CC]LOD技术「建议收藏」
[CC]LOD技术「建议收藏」

 1 void ccPointCloud::drawMeOnly(CC_DRAW_CONTEXT& context)  2 {  3 if (!m_points->isAllocated())  4 return;  5  6 if (MACRO_Draw3D(context))  7  {  8 //we get display parameters  9  glDrawParams glParams;  10  getDrawingParameters(glParams);  11 //no normals shading without light!  12 if (!MACRO_LightIsEnabled(context))  13 glParams.showNorms = false;  14  15 //can't display a SF without... a SF... and an active color scale!  16 assert(!glParams.showSF || hasDisplayedScalarField());  17  18 //standard case: list names pushing  19 bool pushName = MACRO_DrawEntityNames(context);  20 //special case: point names pushing (for picking)  21 bool pushPointNames = MACRO_DrawPointNames(context);  22 pushName |= pushPointNames;  23  24 if (pushName)  25  {  26 //not fast at all!  27 if (MACRO_DrawFastNamesOnly(context))  28 return;  29  30  glPushName(getUniqueIDForDisplay());  31 //minimal display for picking mode!  32 glParams.showNorms = false;  33 glParams.showColors = false;  34 if (glParams.showSF && m_currentDisplayedScalarField->areNaNValuesShownInGrey())  35 glParams.showSF = false; //--> we keep it only if SF 'NaN' values are potentially hidden  36  }  37  38 // L.O.D. display  39 DisplayDesc toDisplay(0,size());  40 if (!pushName)  41  {  42 if ( context.decimateCloudOnMove  43 && toDisplay.count > context.minLODPointCount  44 && MACRO_LODActivated(context)  45  )  46  {  47 bool skipLoD = false;  48  49 //is there a LoD structure associated yet?  50 if (!m_lod.isBroken())  51  {  52 if (m_lod.isNull())  53  {  54 //auto-init LoD structure  55 //ccProgressDialog pDlg(false,context._win ? context._win->asWidget() : 0);  56 initLOD(0/*&pDlg*/);  57  }  58 else  59  {  60 unsigned char maxLevel = m_lod.maxLevel();  61 bool underConstruction = m_lod.isUnderConstruction();  62  63 //if the cloud has less LOD levels than the minimum to display  64 if (maxLevel <= context.minLODLevel)  65  {  66 if (context.currentLODLevel == 0)  67  {  68 //we can display the cloud in fill resolution  69 if (!underConstruction)  70  {  71 //no need for LOD display  72 skipLoD = true;  73  }  74  }  75 else  76  {  77 //already displayed!  78 return;  79  }  80  }  81 else  82  {  83 if (context.currentLODLevel == 0)  84  {  85 toDisplay.indexMap = m_lod.indexes();  86  assert(toDisplay.indexMap);  87 //the first time (LoD level = 0), we display all the small levels at once  88 toDisplay.startIndex = 0;  89 toDisplay.count = 0;  90  {  91 for (unsigned char l = 1; l < context.minLODLevel; ++l)  92 toDisplay.count += m_lod.level(l).count;  93  }  94 toDisplay.endIndex = toDisplay.startIndex + toDisplay.count;  95  96 //could we draw more points? yes (we know that lod.levels.size() > context.minLODLevel)  97 context.higherLODLevelsAvailable = true;  98  }  99 else if (context.currentLODLevel < maxLevel) 100  { 101 toDisplay = m_lod.level(context.currentLODLevel); 102 103 if (toDisplay.count < context.currentLODStartIndex) 104  { 105 //nothing to do at this level 106 toDisplay.indexMap = 0; 107  } 108 else 109  { 110 toDisplay.indexMap = m_lod.indexes(); 111  assert(toDisplay.indexMap); 112 //shift current draw range 113 toDisplay.startIndex += context.currentLODStartIndex; 114 toDisplay.count -= context.currentLODStartIndex; 115 116 if (toDisplay.count > MAX_POINT_COUNT_PER_LOD_RENDER_PASS) 117  { 118 toDisplay.count = MAX_POINT_COUNT_PER_LOD_RENDER_PASS; 119 context.moreLODPointsAvailable = true; 120  } 121  } 122 123 //could we draw more points at the next level? 124 context.higherLODLevelsAvailable = underConstruction || (context.currentLODLevel + 1 < maxLevel); 125  } 126  } 127  } 128  } 129 130 if (!toDisplay.indexMap && !skipLoD) 131  { 132 //if we don't have a LoD map, we can only display points at level 0! 133 if (context.currentLODLevel != 0) 134  { 135 return; 136  } 137 138 if (toDisplay.count > context.minLODPointCount && context.minLODPointCount != 0) 139  { 140 toDisplay.decimStep = static_cast<int>(ceil(static_cast<float>(toDisplay.count) / context.minLODPointCount)); 141  } 142  } 143  } 144  } 145 //ccLog::Print(QString("Rendering %1 points starting from index %2 (LoD = %3 / PN = %4)").arg(toDisplay.count).arg(toDisplay.startIndex).arg(toDisplay.indexMap ? "yes" : "no").arg(pushName ? "yes" : "no")); 146 bool colorMaterialEnabled = false; 147 148 if (glParams.showSF || glParams.showColors) 149  { 150  glColorMaterial(GL_FRONT_AND_BACK, GL_DIFFUSE); 151  glEnable(GL_COLOR_MATERIAL); 152 colorMaterialEnabled = true; 153  } 154 155 if (glParams.showColors && isColorOverriden()) 156  { 157  ccGL::Color3v(m_tempColor.rgb); 158 glParams.showColors = false; 159  } 160 else 161  { 162  glColor3ubv(context.pointsDefaultCol.rgb); 163  } 164 165 //in the case we need normals (i.e. lighting) 166 if (glParams.showNorms) 167  { 168 //DGM: Strangely, when Qt::renderPixmap is called, the OpenGL version is sometimes 1.0! 169 glEnable((QGLFormat::openGLVersionFlags() & QGLFormat::OpenGL_Version_1_2 ? GL_RESCALE_NORMAL : GL_NORMALIZE)); 170  glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, CC_DEFAULT_CLOUD_AMBIENT_COLOR.rgba ); 171  glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, CC_DEFAULT_CLOUD_SPECULAR_COLOR.rgba ); 172  glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, CC_DEFAULT_CLOUD_DIFFUSE_COLOR.rgba ); 173  glMaterialfv(GL_FRONT_AND_BACK, GL_EMISSION, CC_DEFAULT_CLOUD_EMISSION_COLOR.rgba ); 174  glMaterialf (GL_FRONT_AND_BACK, GL_SHININESS, CC_DEFAULT_CLOUD_SHININESS); 175  glEnable(GL_LIGHTING); 176 177 if (glParams.showSF) 178  { 179 //we must get rid of lights 'color' if a scalar field is displayed! 180  glPushAttrib(GL_LIGHTING_BIT); 181  ccMaterial::MakeLightsNeutral(); 182  } 183  } 184 185 /*** DISPLAY ***/ 186 187 //custom point size? 188  glPushAttrib(GL_POINT_BIT); 189 if (m_pointSize != 0) 190 glPointSize(static_cast<GLfloat>(m_pointSize)); 191 192 if (!pushPointNames) //standard "full" display 193  { 194 //if some points are hidden (= visibility table instantiated), we can't use display arrays :( 195 if (isVisibilityTableInstantiated()) 196  { 197  assert(m_pointsVisibility); 198 //compressed normals set 199 const ccNormalVectors* compressedNormals = ccNormalVectors::GetUniqueInstance(); 200  assert(compressedNormals); 201 202  glBegin(GL_POINTS); 203 204 for (unsigned j=toDisplay.startIndex; j<toDisplay.endIndex; j+=toDisplay.decimStep) 205  { 206 //we must test each point visibility 207 unsigned pointIndex = toDisplay.indexMap ? toDisplay.indexMap->getValue(j) : j; 208 if (!m_pointsVisibility || m_pointsVisibility->getValue(pointIndex) == POINT_VISIBLE) 209  { 210 if (glParams.showSF) 211  { 212 assert(pointIndex < m_currentDisplayedScalarField->currentSize()); 213 const ColorCompType* col = m_currentDisplayedScalarField->getValueColor(pointIndex); 214 //we force display of points hidden because of their scalar field value 215 //to be sure that the user don't miss them (during manual segmentation for instance) 216 glColor3ubv(col ? col : ccColor::lightGrey.rgba); 217  } 218 else if (glParams.showColors) 219  { 220 glColor3ubv(m_rgbColors->getValue(pointIndex)); 221  } 222 if (glParams.showNorms) 223  { 224 ccGL::Normal3v(compressedNormals->getNormal(m_normals->getValue(pointIndex)).u); 225  } 226 ccGL::Vertex3v(m_points->getValue(pointIndex)); 227  } 228  } 229 230  glEnd(); 231  } 232 else if (glParams.showSF) //no visibility table enabled + scalar field 233  { 234  assert(m_currentDisplayedScalarField); 235 236 //if some points may not be displayed, we'll have to be smarter! 237 bool hiddenPoints = m_currentDisplayedScalarField->mayHaveHiddenValues(); 238 239 //whether VBOs are available (for faster display) or not 240 bool useVBOs = false; 241 if (!hiddenPoints && context.useVBOs && !toDisplay.indexMap) //VBOs are not compatible with LoD 242  { 243 //can't use VBOs if some points are hidden 244 useVBOs = updateVBOs(glParams); 245  } 246 247 //color ramp shader initialization 248 ccColorRampShader* colorRampShader = context.colorRampShader; 249  { 250 //color ramp shader is not compatible with VBOs (and VBOs are faster) 251 if (useVBOs) 252  { 253 colorRampShader = 0; 254  } 255 //FIXME: color ramp shader doesn't support log scale yet! 256 if (m_currentDisplayedScalarField->logScale()) 257  { 258 colorRampShader = 0; 259  } 260  } 261 262 const ccScalarField::Range& sfDisplayRange = m_currentDisplayedScalarField->displayRange(); 263 const ccScalarField::Range& sfSaturationRange = m_currentDisplayedScalarField->saturationRange(); 264 265 if (colorRampShader) 266  { 267 //max available space for frament's shader uniforms 268 GLint maxBytes = 0; 269 glGetIntegerv(GL_MAX_FRAGMENT_UNIFORM_COMPONENTS,&maxBytes); 270 GLint maxComponents = (maxBytes>>2)-4; //leave space for the other uniforms! 271 unsigned steps = m_currentDisplayedScalarField->getColorRampSteps(); 272 assert(steps != 0); 273 274 if (steps > CC_MAX_SHADER_COLOR_RAMP_SIZE || maxComponents < (GLint)steps) 275  { 276 ccLog::WarningDebug("Color ramp steps exceed shader limits!"); 277 colorRampShader = 0; 278  } 279 else 280  { 281 float sfMinSatRel = 0.0f; 282 float sfMaxSatRel = 1.0f; 283 if (!m_currentDisplayedScalarField->symmetricalScale()) 284  { 285 sfMinSatRel = GetNormalizedValue(sfSaturationRange.start(),sfDisplayRange); //doesn't need to be between 0 and 1! 286 sfMaxSatRel = GetNormalizedValue(sfSaturationRange.stop(),sfDisplayRange); //doesn't need to be between 0 and 1! 287  } 288 else 289  { 290 //we can only handle 'maximum' saturation 291 sfMinSatRel = GetSymmetricalNormalizedValue(-sfSaturationRange.stop(),sfSaturationRange); 292 sfMaxSatRel = GetSymmetricalNormalizedValue(sfSaturationRange.stop(),sfSaturationRange); 293 //we'll have to handle the 'minimum' saturation manually! 294  } 295 296 const ccColorScale::Shared& colorScale = m_currentDisplayedScalarField->getColorScale(); 297  assert(colorScale); 298 299 colorRampShader->start(); 300 if (!colorRampShader->setup(sfMinSatRel, sfMaxSatRel, steps, colorScale)) 301  { 302 //An error occurred during shader initialization? 303 ccLog::WarningDebug("Failed to init ColorRamp shader!"); 304 colorRampShader->stop(); 305 colorRampShader = 0; 306  } 307 else if (glParams.showNorms) 308  { 309 //we must get rid of lights material (other than ambient) for the red and green fields 310  glPushAttrib(GL_LIGHTING_BIT); 311 312 //we use the ambient light to pass the scalar value (and 'grayed' marker) without any 313 //modification from the GPU pipeline, even if normals are enabled! 314  glDisable(GL_COLOR_MATERIAL); 315  glColorMaterial(GL_FRONT_AND_BACK, GL_DIFFUSE); 316  glColorMaterial(GL_FRONT_AND_BACK, GL_AMBIENT); 317  glEnable(GL_COLOR_MATERIAL); 318 319  GLint maxLightCount; 320 glGetIntegerv(GL_MAX_LIGHTS,&maxLightCount); 321 for (GLint i=0; i<maxLightCount; ++i) 322  { 323 if (glIsEnabled(GL_LIGHT0+i)) 324  { 325 float diffuse[4],ambiant[4],specular[4]; 326 327 glGetLightfv(GL_LIGHT0+i,GL_AMBIENT,ambiant); 328 glGetLightfv(GL_LIGHT0+i,GL_DIFFUSE,diffuse); 329 glGetLightfv(GL_LIGHT0+i,GL_SPECULAR,specular); 330 331 ambiant[0] = ambiant[1] = 1.0f; 332 diffuse[0] = diffuse[1] = 0.0f; 333 specular[0] = specular[1] = 0.0f; 334 335 glLightfv(GL_LIGHT0+i,GL_DIFFUSE,diffuse); 336 glLightfv(GL_LIGHT0+i,GL_AMBIENT,ambiant); 337 glLightfv(GL_LIGHT0+i,GL_SPECULAR,specular); 338  } 339  } 340  } 341  } 342  } 343 344 //if all points should be displayed (fastest case) 345 if (!hiddenPoints) 346  { 347  glEnableClientState(GL_VERTEX_ARRAY); 348  glEnableClientState(GL_COLOR_ARRAY); 349 if (glParams.showNorms) 350  glEnableClientState(GL_NORMAL_ARRAY); 351 352 if (toDisplay.indexMap) //LoD display 353  { 354 unsigned s = toDisplay.startIndex; 355 while (s < toDisplay.endIndex) 356  { 357 unsigned count = std::min(MAX_POINT_COUNT_PER_LOD_RENDER_PASS,toDisplay.endIndex-s); 358 unsigned e = s+count; 359 360 //points 361 glLODChunkVertexPointer(*toDisplay.indexMap,s,e); 362 //normals 363 if (glParams.showNorms) 364 glLODChunkNormalPointer(*toDisplay.indexMap,s,e); 365 //SF colors 366 if (colorRampShader) 367  { 368 float* _sfColors = s_rgbBuffer3f; 369 bool symScale = m_currentDisplayedScalarField->symmetricalScale(); 370 for (unsigned j=s; j<e; j++,_sfColors+=3) 371  { 372 unsigned pointIndex = toDisplay.indexMap->getValue(j); 373 ScalarType sfVal = m_currentDisplayedScalarField->getValue(pointIndex); 374 //normalized sf value 375 _sfColors[0] = symScale ? GetSymmetricalNormalizedValue(sfVal,sfSaturationRange) : GetNormalizedValue(sfVal,sfDisplayRange); 376 //flag: whether point is grayed out or not (NaN values are also rejected!) 377 _sfColors[1] = sfDisplayRange.isInRange(sfVal) ? 1.0f : 0.0f; 378 //reference value (to get the true lighting value) 379 _sfColors[2] = 1.0f; 380  } 381 glColorPointer(3,GL_FLOAT,0,s_rgbBuffer3f); 382  } 383 else 384  { 385 glLODChunkSFPointer(*toDisplay.indexMap,s,e); 386  } 387 388 glDrawArrays(GL_POINTS,0,count); 389 390 s = e; 391  } 392  } 393 else 394  { 395 unsigned chunks = m_points->chunksCount(); 396 for (unsigned k=0; k<chunks; ++k) 397  { 398 unsigned chunkSize = m_points->chunkSize(k); 399 400 //points 401  glChunkVertexPointer(k,toDisplay.decimStep,useVBOs); 402 //normals 403 if (glParams.showNorms) 404  glChunkNormalPointer(k,toDisplay.decimStep,useVBOs); 405 //SF colors 406 if (colorRampShader) 407  { 408 ScalarType* _sf = m_currentDisplayedScalarField->chunkStartPtr(k); 409 float* _sfColors = s_rgbBuffer3f; 410 bool symScale = m_currentDisplayedScalarField->symmetricalScale(); 411 for (unsigned j=0; j<chunkSize; j+=toDisplay.decimStep,_sf+=toDisplay.decimStep,_sfColors+=3) 412  { 413 //normalized sf value 414 _sfColors[0] = symScale ? GetSymmetricalNormalizedValue(*_sf,sfSaturationRange) : GetNormalizedValue(*_sf,sfDisplayRange); 415 //flag: whether point is grayed out or not (NaN values are also rejected!) 416 _sfColors[1] = sfDisplayRange.isInRange(*_sf) ? 1.0f : 0.0f; 417 //reference value (to get the true lighting value) 418 _sfColors[2] = 1.0f; 419  } 420 glColorPointer(3,GL_FLOAT,0,s_rgbBuffer3f); 421  } 422 else 423  { 424  glChunkSFPointer(k,toDisplay.decimStep,useVBOs); 425  } 426 427 if (toDisplay.decimStep > 1) 428 chunkSize = static_cast<unsigned>( floor(static_cast<float>(chunkSize)/toDisplay.decimStep) ); 429 glDrawArrays(GL_POINTS,0,chunkSize); 430  } 431  } 432 433 if (glParams.showNorms) 434  glDisableClientState(GL_NORMAL_ARRAY); 435  glDisableClientState(GL_COLOR_ARRAY); 436  glDisableClientState(GL_VERTEX_ARRAY); 437  } 438 else //potentially hidden points 439  { 440 //compressed normals set 441 const ccNormalVectors* compressedNormals = ccNormalVectors::GetUniqueInstance(); 442  assert(compressedNormals); 443 444  glBegin(GL_POINTS); 445 446 if (glParams.showNorms) //with normals (slowest case!) 447  { 448 if (colorRampShader) 449  { 450 if (!m_currentDisplayedScalarField->symmetricalScale()) 451  { 452 for (unsigned j=toDisplay.startIndex; j<toDisplay.endIndex; j+=toDisplay.decimStep) 453  { 454 unsigned pointIndex = (toDisplay.indexMap ? toDisplay.indexMap->getValue(j) : j); 455 assert(pointIndex < m_currentDisplayedScalarField->currentSize()); 456 const ScalarType sf = m_currentDisplayedScalarField->getValue(pointIndex); 457 if (sfDisplayRange.isInRange(sf)) //NaN values are rejected 458  { 459 glColor3f(GetNormalizedValue(sf,sfDisplayRange),1.0f,1.0f); 460 ccGL::Normal3v(compressedNormals->getNormal(m_normals->getValue(pointIndex)).u); 461 ccGL::Vertex3v(m_points->getValue(pointIndex)); 462  } 463  } 464  } 465 else 466  { 467 for (unsigned j=toDisplay.startIndex; j<toDisplay.endIndex; j+=toDisplay.decimStep) 468  { 469 unsigned pointIndex = (toDisplay.indexMap ? toDisplay.indexMap->getValue(j) : j); 470 assert(pointIndex < m_currentDisplayedScalarField->currentSize()); 471 const ScalarType sf = m_currentDisplayedScalarField->getValue(pointIndex); 472 if (sfDisplayRange.isInRange(sf)) //NaN values are rejected 473  { 474 glColor3f(GetSymmetricalNormalizedValue(sf,sfSaturationRange),1.0f,1.0f); 475 ccGL::Normal3v(compressedNormals->getNormal(m_normals->getValue(pointIndex)).u); 476 ccGL::Vertex3v(m_points->getValue(pointIndex)); 477  } 478  } 479  } 480  } 481 else 482  { 483 for (unsigned j=toDisplay.startIndex; j<toDisplay.endIndex; j+=toDisplay.decimStep) 484  { 485 unsigned pointIndex = (toDisplay.indexMap ? toDisplay.indexMap->getValue(j) : j); 486 assert(pointIndex < m_currentDisplayedScalarField->currentSize()); 487 const ColorCompType* col = m_currentDisplayedScalarField->getValueColor(pointIndex); 488 if (col) 489  { 490  glColor3ubv(col); 491 ccGL::Normal3v(compressedNormals->getNormal(m_normals->getValue(pointIndex)).u); 492 ccGL::Vertex3v(m_points->getValue(pointIndex)); 493  } 494  } 495  } 496  } 497 else //potentially hidden points without normals (a bit faster) 498  { 499 if (colorRampShader) 500  { 501 if (!m_currentDisplayedScalarField->symmetricalScale()) 502  { 503 for (unsigned j=toDisplay.startIndex; j<toDisplay.endIndex; j+=toDisplay.decimStep) 504  { 505 unsigned pointIndex = (toDisplay.indexMap ? toDisplay.indexMap->getValue(j) : j); 506 assert(pointIndex < m_currentDisplayedScalarField->currentSize()); 507 const ScalarType sf = m_currentDisplayedScalarField->getValue(pointIndex); 508 if (sfDisplayRange.isInRange(sf)) //NaN values are rejected 509  { 510 glColor3f(GetNormalizedValue(sf,sfDisplayRange),1.0f,1.0f); 511 ccGL::Vertex3v(m_points->getValue(pointIndex)); 512  } 513  } 514  } 515 else 516  { 517 for (unsigned j=toDisplay.startIndex; j<toDisplay.endIndex; j+=toDisplay.decimStep) 518  { 519 unsigned pointIndex = (toDisplay.indexMap ? toDisplay.indexMap->getValue(j) : j); 520 assert(pointIndex < m_currentDisplayedScalarField->currentSize()); 521 const ScalarType sf = m_currentDisplayedScalarField->getValue(pointIndex); 522 if (sfDisplayRange.isInRange(sf)) //NaN values are rejected 523  { 524 glColor3f(GetSymmetricalNormalizedValue(sf,sfSaturationRange),1.0f,1.0f); 525 ccGL::Vertex3v(m_points->getValue(pointIndex)); 526  } 527  } 528  } 529  } 530 else 531  { 532 for (unsigned j=toDisplay.startIndex; j<toDisplay.endIndex; j+=toDisplay.decimStep) 533  { 534 unsigned pointIndex = (toDisplay.indexMap ? toDisplay.indexMap->getValue(j) : j); 535 assert(pointIndex < m_currentDisplayedScalarField->currentSize()); 536 const ColorCompType* col = m_currentDisplayedScalarField->getValueColor(pointIndex); 537 if (col) 538  { 539  glColor3ubv(col); 540 ccGL::Vertex3v(m_points->getValue(pointIndex)); 541  } 542  } 543  } 544  } 545  glEnd(); 546  } 547 548 if (colorRampShader) 549  { 550 colorRampShader->stop(); 551 552 if (glParams.showNorms) 553 glPopAttrib(); //GL_LIGHTING_BIT 554  } 555  } 556 else //no visibility table enabled, no scalar field 557  { 558 bool useVBOs = context.useVBOs && !toDisplay.indexMap ? updateVBOs(glParams) : false; //VBOs are not compatible with LoD 559 560 unsigned chunks = m_points->chunksCount(); 561 562  glEnableClientState(GL_VERTEX_ARRAY); 563 if (glParams.showNorms) 564  glEnableClientState(GL_NORMAL_ARRAY); 565 if (glParams.showColors) 566  glEnableClientState(GL_COLOR_ARRAY); 567 568 if (toDisplay.indexMap) //LoD display 569  { 570 unsigned s = toDisplay.startIndex; 571 while (s < toDisplay.endIndex) 572  { 573 unsigned count = std::min(MAX_POINT_COUNT_PER_LOD_RENDER_PASS,toDisplay.endIndex-s); 574 unsigned e = s+count; 575 576 //points 577 glLODChunkVertexPointer(*toDisplay.indexMap,s,e); 578 //normals 579 if (glParams.showNorms) 580 glLODChunkNormalPointer(*toDisplay.indexMap,s,e); 581 //colors 582 if (glParams.showColors) 583 glLODChunkColorPointer(*toDisplay.indexMap,s,e); 584 585 glDrawArrays(GL_POINTS,0,count); 586 s = e; 587  } 588  } 589 else 590  { 591 for (unsigned k=0; k<chunks; ++k) 592  { 593 unsigned chunkSize = m_points->chunkSize(k); 594 595 //points 596  glChunkVertexPointer(k,toDisplay.decimStep,useVBOs); 597 //normals 598 if (glParams.showNorms) 599  glChunkNormalPointer(k,toDisplay.decimStep,useVBOs); 600 //colors 601 if (glParams.showColors) 602  glChunkColorPointer(k,toDisplay.decimStep,useVBOs); 603 604 if (toDisplay.decimStep > 1) 605 chunkSize = static_cast<unsigned>(floor(static_cast<float>(chunkSize)/toDisplay.decimStep)); 606 glDrawArrays(GL_POINTS,0,chunkSize); 607  } 608  } 609 610  glDisableClientState(GL_VERTEX_ARRAY); 611 if (glParams.showNorms) 612  glDisableClientState(GL_NORMAL_ARRAY); 613 if (glParams.showColors) 614  glDisableClientState(GL_COLOR_ARRAY); 615  } 616  } 617 else //special case: point names pushing (for picking) --> no need for colors, normals, etc. 618  { 619 glPushName(0); 620 //however we must take hidden points into account! 621 if (isVisibilityTableInstantiated()) 622  { 623 for (unsigned j=toDisplay.startIndex; j<toDisplay.endIndex; j+=toDisplay.decimStep) 624  { 625 unsigned pointIndex = (toDisplay.indexMap ? toDisplay.indexMap->getValue(j) : j); 626 if (m_pointsVisibility->getValue(j) == POINT_VISIBLE) 627  { 628  glLoadName(pointIndex); 629  glBegin(GL_POINTS); 630 ccGL::Vertex3v(m_points->getValue(pointIndex)); 631  glEnd(); 632  } 633  } 634  } 635 else //no visibility table instantiated... 636  { 637 //... but potentially points with NAN SF values (also hidden!) 638 bool hiddenPoints = false; 639 if (glParams.showSF) 640  { 641  assert(m_currentDisplayedScalarField); 642 hiddenPoints = m_currentDisplayedScalarField->mayHaveHiddenValues() && m_currentDisplayedScalarField->getColorScale(); 643  } 644 645 if (hiddenPoints) //potentially hidden points 646  { 647 for (unsigned j=toDisplay.startIndex; j<toDisplay.endIndex; j+=toDisplay.decimStep) 648  { 649 unsigned pointIndex = (toDisplay.indexMap ? toDisplay.indexMap->getValue(j) : j); 650 //we must generate the synthetic "color" of each point 651 const ColorCompType* col = getPointScalarValueColor(pointIndex); 652 if (col) 653  { 654  glLoadName(pointIndex); 655  glBegin(GL_POINTS); 656 ccGL::Vertex3v(m_points->getValue(pointIndex)); 657  glEnd(); 658  } 659  } 660  } 661 else 662  { 663 //no hidden point 664 for (unsigned j=toDisplay.startIndex; j<toDisplay.endIndex; j+=toDisplay.decimStep) 665  { 666 unsigned pointIndex = (toDisplay.indexMap ? toDisplay.indexMap->getValue(j) : j); 667  glLoadName(pointIndex); 668  glBegin(GL_POINTS); 669 ccGL::Vertex3v(m_points->getValue(pointIndex)); 670  glEnd(); 671  } 672  } 673  } 674 675 //glEnd(); 676  glPopName(); 677  } 678 679 /*** END DISPLAY ***/ 680 681 glPopAttrib(); //GL_POINT_BIT 682 683 if (colorMaterialEnabled) 684  glDisable(GL_COLOR_MATERIAL); 685 686 //we can now switch the light off 687 if (glParams.showNorms) 688  { 689 if (glParams.showSF) 690 glPopAttrib(); //GL_LIGHTING_BIT 691 692 glDisable((QGLFormat::openGLVersionFlags() & QGLFormat::OpenGL_Version_1_2 ? GL_RESCALE_NORMAL : GL_NORMALIZE)); 693  glDisable(GL_LIGHTING); 694  } 695 696 if (pushName) 697  glPopName(); 698  } 699 else if (MACRO_Draw2D(context)) 700  { 701 if (MACRO_Foreground(context) && !context.sfColorScaleToDisplay) 702  { 703 if (sfColorScaleShown() && sfShown()) 704  { 705 //drawScale(context); 706  addColorRampInfo(context); 707  } 708  } 709  } 710 }

ccPointCloud::drawMeOnly

 

转载于:https://www.cnblogs.com/yhlx125/p/6020857.html

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

发布者:全栈程序员-用户IM,转载请注明出处:https://javaforall.cn/108809.html原文链接:https://javaforall.cn

【正版授权,激活自己账号】: Jetbrains全家桶Ide使用,1年售后保障,每天仅需1毛

【官方授权 正版激活】: 官方授权 正版激活 支持Jetbrains家族下所有IDE 使用个人JB账号...

(0)
blank

相关推荐

  • c语言字符串赋值_c++中字符串变量

    c语言字符串赋值_c++中字符串变量从大一学c语言到现在都快三年了,今天居然还在简单的字符串赋值的过程中犯了错误,应该记下来,以免日后再犯。这是一个结构体typedefstructstudent{charname[21];charsno[21];intgrade;}student;现在又两个student类型的变量stu1,stu2,当我想把stu2的值赋给stu1是我一开始是这样…

    2022年10月27日
  • fwrite与fread_fwrite和fprintf

    fwrite与fread_fwrite和fprintffread()函数与fwrite函数

  • linux磁盘分区fdisk命令详解及云硬盘挂载实操「建议收藏」

    linux磁盘分区fdisk命令详解及云硬盘挂载实操「建议收藏」本文主要介绍了linux磁盘分区fdisk命令,并详细介绍了服务器挂载云硬盘方法。

    2022年10月29日
  • 2020最新-精选基础算法100题(面试必备)[通俗易懂]

    2020最新-精选基础算法100题(面试必备)[通俗易懂]0x01.概述作为一个程序员,算法能力必不可少,虽然不一定是算法工程师,但是算法还是彰显着个人的编码能力,面试中也经常会被问到,甚至会被要求临场做算法题,所以,还是好好积累吧。个人其实对算法挺有兴趣的,从3月份开始,陆陆续续刷了一些算法题,把一些有意义的记录下来了,也顺便写了一些题解,个人认为,还是挺有收获的。之前写了一篇算法文章的目录,不过后来就忘了实时去更新了,于是现在,想把之前做过的一些有意义的算法题分享出来,刚好整理了100篇比较有意义的。希望对大家有所帮助。0x02.说明关

  • Webdriver下载及使用

    Webdriver下载及使用Chrome浏览器驱动下载地址:http://chromedriver.storage.proxy.ustclug.org/index.htmlFirfox浏览器驱动下载地址:https://github.com/mozilla/geckodriver/releasesIE浏览器驱动下载地址:https://www.selenium.dev/downloads/Edge浏览器驱动下载地址:https://developer.microsoft.com/en-us/microsoft-edg…

  • html设置ie9兼容性视图,ie9兼容性设置在哪里 IE兼容性视图在哪里设置?「建议收藏」

    html设置ie9兼容性视图,ie9兼容性设置在哪里 IE兼容性视图在哪里设置?「建议收藏」找不到“兼容性视图设置”子菜单如何在360浏览器IE9上设置兼容性视图还有一种方法打开菜单栏,就是鼠标右键点击上方的空白处,选择“菜单栏”,然后菜单栏就显示“工具”。【兼容性视图设置】的窗口,选择“添加此网址”。IE兼容性视图设置在哪兼容性视图怎么设置在浏览器右上角的设置里设置,设置方法如下:方法1首先,打开电脑,找到电脑桌面上的IE浏览器,并点击打开,打开后,进入任一网页,找到页面右上方的…

发表回复

您的电子邮箱地址不会被公开。

关注全栈程序员社区公众号