void DistanceToleranceFunction::extractCells( unsigned int numCells, const vigra::MultiArray<3, unsigned int>& cellLabels, const ImageStack& recLabels, const ImageStack& gtLabels) { _depth = gtLabels.size(); _width = gtLabels.width(); _height = gtLabels.height(); createBoundaryMap(recLabels); createBoundaryDistanceMap(); //vigra::exportVolume(cellLabels, vigra::VolumeExportInfo("cell_labels/cell_labels", ".tif").setPixelType("FLOAT")); //vigra::exportVolume(_boundaryMap, vigra::VolumeExportInfo("boundaries/boundaries", ".tif").setPixelType("FLOAT")); //vigra::exportVolume(_boundaryDistance2, vigra::VolumeExportInfo("distances/boundary_distance2", ".tif").setPixelType("FLOAT")); // create a cell for each found connected component in cellLabels _cells->resize(numCells); // the maximum boundary distance of any location for each cell std::vector<float> maxBoundaryDistances(numCells, 0); std::set<unsigned int> foundCells; for (unsigned int z = 0; z < _depth; z++) { boost::shared_ptr<const Image> gt = gtLabels[z]; boost::shared_ptr<const Image> rec = recLabels[z]; for (unsigned int x = 0; x < _width; x++) for (unsigned int y = 0; y < _height; y++) { float gtLabel = (*gt)(x, y); float recLabel = (*rec)(x, y); // argh, vigra starts counting at 1! unsigned int cellIndex = cellLabels(x, y, z) - 1; (*_cells)[cellIndex].add(cell_t::Location(x, y, z)); (*_cells)[cellIndex].setReconstructionLabel(recLabel); (*_cells)[cellIndex].setGroundTruthLabel(gtLabel); maxBoundaryDistances[cellIndex] = std::max(maxBoundaryDistances[cellIndex], _boundaryDistance2(x, y, z)); if (foundCells.count(cellIndex) == 0) { registerPossibleMatch(gtLabel, recLabel); foundCells.insert(cellIndex); } } } _relabelCandidates.clear(); for (unsigned int cellIndex = 0; cellIndex < numCells; cellIndex++) if (maxBoundaryDistances[cellIndex] <= _maxDistanceThreshold*_maxDistanceThreshold) _relabelCandidates.push_back(cellIndex); enumerateCellLabels(recLabels); }
void readImageStackFromOption(ImageStack& stack, std::string option) { // hdf file given? size_t sepPos = option.find_first_of(":"); if (sepPos != std::string::npos) { #ifdef HAVE_HDF5 std::string hdfFileName = option.substr(0, sepPos); std::string dataset = option.substr(sepPos + 1); vigra::HDF5File file(hdfFileName, vigra::HDF5File::OpenMode::ReadOnly); vigra::MultiArray<3, float> volume; file.readAndResize(dataset, volume); stack.clear(); for (int z = 0; z < volume.size(2); z++) { boost::shared_ptr<Image> image = boost::make_shared<Image>(volume.size(0), volume.size(1)); vigra::MultiArrayView<2, float> imageView = *image; imageView = volume.bind<2>(z); stack.add(image); } vigra::MultiArray<1, float> p(3); if (file.existsAttribute(dataset, "resolution")) { // resolution file.readAttribute( dataset, "resolution", p); stack.setResolution(p[0], p[1], p[2]); } #else UTIL_THROW_EXCEPTION( UsageError, "This build does not support reading form HDF5 files. Set CMake variable BUILD_WITH_HDF5 and recompile."); #endif // read stack from directory of images } else { pipeline::Process<ImageStackDirectoryReader> stackReader(option); pipeline::Value<ImageStack> output = stackReader->getOutput(); stack = *output; } }
void EditableMask::generateFrom(const ImageStack & images) { width = images.getWidth(); height = images.getHeight(); numLayers = images.size(); editActions.clear(); nextAction = editActions.end(); size_t size = width*height; Timer t("Generate mask"); mask.reset(new uint8_t[size]); std::fill_n(mask.get(), size, 0); for (size_t y = 0, pos = 0; y < height; ++y) { for (size_t x = 0; x < width; ++x, ++pos) { int i = mask[pos]; while (i < numLayers - 1 && (!images.getImage(i).contains(x, y) || images.getImage(i).isSaturated(x, y) || images.getImage(i).isSaturatedAround(x, y))) ++i; if (mask[pos] < i) { mask[pos] = i; //if (!images.getImage(i - 1).isSaturatedAround(x, y)) { paintCircle(x, y, 4, [&] (int col, int row) { size_t pos = row*width + col; if (mask[pos] < i && images.getImage(i).contains(col, row)) { mask[pos] = i; } }); //} } } } }
void EditableMask::paintPixels(const ImageStack & images, int x, int y, size_t radius) { EditAction & e = editActions.back(); paintCircle(x, y, radius, [&] (int col, int row) { size_t pos = row*width + col; if (mask[pos] == e.oldLayer && images.getImage(e.newLayer).contains(col, row)) { e.points.push_back({col, row}); mask[pos] = e.newLayer; } }); }