bool ccKdTree::convertCellIndexToRandomColor() { if (!m_associatedGenericCloud || !m_associatedGenericCloud->isA(CC_TYPES::POINT_CLOUD)) return false; //get leaves std::vector<Leaf*> leaves; if (!getLeaves(leaves) || leaves.empty()) return false; ccPointCloud* pc = static_cast<ccPointCloud*>(m_associatedGenericCloud); if (!pc->resizeTheRGBTable()) return false; //for each cell for (size_t i=0; i<leaves.size(); ++i) { colorType col[3]; ccColor::Generator::Random(col); CCLib::ReferenceCloud* subset = leaves[i]->points; if (subset) { for (unsigned j=0; j<subset->size(); ++j) pc->setPointColor(subset->getPointGlobalIndex(j),col); } } pc->showColors(true); return true; }
void qHPR::doAction() { assert(m_app); if (!m_app) return; const ccHObject::Container& selectedEntities = m_app->getSelectedEntities(); size_t selNum = selectedEntities.size(); if ( selNum != 1 || !selectedEntities.front()->isA(CC_TYPES::POINT_CLOUD)) { m_app->dispToConsole("Select only one cloud!",ccMainAppInterface::ERR_CONSOLE_MESSAGE); return; } ccPointCloud* cloud = static_cast<ccPointCloud*>(selectedEntities[0]); ccGLWindow* win = m_app->getActiveGLWindow(); if (!win) { m_app->dispToConsole("No active window!",ccMainAppInterface::ERR_CONSOLE_MESSAGE); return; } //display parameters const ccViewportParameters& params = win->getViewportParameters(); if (!params.perspectiveView) { m_app->dispToConsole("Perspective mode only!",ccMainAppInterface::ERR_CONSOLE_MESSAGE); return; } ccHprDlg dlg(m_app->getMainWindow()); if (!dlg.exec()) return; //progress dialog ccProgressDialog progressCb(false,m_app->getMainWindow()); //unique parameter: the octree subdivision level int octreeLevel = dlg.octreeLevelSpinBox->value(); assert(octreeLevel >= 0 && octreeLevel <= CCLib::DgmOctree::MAX_OCTREE_LEVEL); //compute octree if cloud hasn't any ccOctree::Shared theOctree = cloud->getOctree(); if (!theOctree) { theOctree = cloud->computeOctree(&progressCb); if (theOctree && cloud->getParent()) { m_app->addToDB(cloud->getOctreeProxy()); } } if (!theOctree) { m_app->dispToConsole("Couldn't compute octree!",ccMainAppInterface::ERR_CONSOLE_MESSAGE); return; } CCVector3d viewPoint = params.cameraCenter; if (params.objectCenteredView) { CCVector3d PC = params.cameraCenter - params.pivotPoint; params.viewMat.inverse().apply(PC); viewPoint = params.pivotPoint + PC; } //HPR CCLib::ReferenceCloud* visibleCells = 0; { QElapsedTimer eTimer; eTimer.start(); CCLib::ReferenceCloud* theCellCenters = CCLib::CloudSamplingTools::subsampleCloudWithOctreeAtLevel( cloud, static_cast<unsigned char>(octreeLevel), CCLib::CloudSamplingTools::NEAREST_POINT_TO_CELL_CENTER, &progressCb, theOctree.data()); if (!theCellCenters) { m_app->dispToConsole("Error while simplifying point cloud with octree!",ccMainAppInterface::ERR_CONSOLE_MESSAGE); return; } visibleCells = removeHiddenPoints(theCellCenters,viewPoint,3.5); m_app->dispToConsole(QString("[HPR] Cells: %1 - Time: %2 s").arg(theCellCenters->size()).arg(eTimer.elapsed()/1.0e3)); //warning: after this, visibleCells can't be used anymore as a //normal cloud (as it's 'associated cloud' has been deleted). //Only its indexes are valid! (they are corresponding to octree cells) delete theCellCenters; theCellCenters = 0; } if (visibleCells) { //DGM: we generate a new cloud now, instead of playing with the points visiblity! (too confusing for the user) /*if (!cloud->isVisibilityTableInstantiated() && !cloud->resetVisibilityArray()) { m_app->dispToConsole("Visibility array allocation failed! (Not enough memory?)",ccMainAppInterface::ERR_CONSOLE_MESSAGE); return; } ccPointCloud::VisibilityTableType* pointsVisibility = cloud->getTheVisibilityArray(); assert(pointsVisibility); pointsVisibility->fill(POINT_HIDDEN); //*/ CCLib::ReferenceCloud visiblePoints(theOctree->associatedCloud()); unsigned visiblePointCount = 0; unsigned visibleCellsCount = visibleCells->size(); CCLib::DgmOctree::cellIndexesContainer cellIndexes; if (!theOctree->getCellIndexes(static_cast<unsigned char>(octreeLevel), cellIndexes)) { m_app->dispToConsole("Couldn't fetch the list of octree cell indexes! (Not enough memory?)",ccMainAppInterface::ERR_CONSOLE_MESSAGE); delete visibleCells; return; } for (unsigned i=0; i<visibleCellsCount; ++i) { //cell index unsigned index = visibleCells->getPointGlobalIndex(i); //points in this cell... CCLib::ReferenceCloud Yk(theOctree->associatedCloud()); theOctree->getPointsInCellByCellIndex(&Yk,cellIndexes[index],static_cast<unsigned char>(octreeLevel)); //...are all visible /*unsigned count = Yk.size(); for (unsigned j=0;j<count;++j) pointsVisibility->setValue(Yk.getPointGlobalIndex(j),POINT_VISIBLE); visiblePointCount += count; //*/ if (!visiblePoints.add(Yk)) { m_app->dispToConsole("Not enough memory!",ccMainAppInterface::ERR_CONSOLE_MESSAGE); delete visibleCells; return; } } delete visibleCells; visibleCells = 0; m_app->dispToConsole(QString("[HPR] Visible points: %1").arg(visiblePointCount)); if (visiblePoints.size() == cloud->size()) { m_app->dispToConsole("No points were removed!",ccMainAppInterface::ERR_CONSOLE_MESSAGE); } else { //create cloud from visibility selection ccPointCloud* newCloud = cloud->partialClone(&visiblePoints); if (newCloud) { newCloud->setDisplay(newCloud->getDisplay()); newCloud->setVisible(true); newCloud->setName(cloud->getName()+QString(".visible_points")); cloud->setEnabled(false); //add associated viewport object cc2DViewportObject* viewportObject = new cc2DViewportObject(QString("Viewport")); viewportObject->setParameters(params); newCloud->addChild(viewportObject); m_app->addToDB(newCloud); newCloud->redrawDisplay(); } else { m_app->dispToConsole("Not enough memory!",ccMainAppInterface::ERR_CONSOLE_MESSAGE); } } } //currently selected entities appearance may have changed! m_app->refreshAll(); }