45 #include <pcl/point_cloud.h>
46 #include <pcl/pcl_base.h>
49 #include <pcl/search/search.h>
53 namespace segmentation
97 addEdge (
int u,
int v,
double cap_uv,
double cap_vu = 0.0);
109 operator() (
int u,
int v)
const;
119 enum nodestate { FREE = 0x00, SOURCE = 0x01, TARGET = 0x02 };
123 using edge_pair = std::pair<capacitated_edge::iterator, capacitated_edge::iterator>;
135 augmentPath (
const std::pair<int, int>& path, std::deque<int>& orphans);
146 isActive (
int u)
const {
return ((u == active_head_) || (active_list_[u].first != TERMINAL)); }
160 double flow_value_{0.0};
162 std::vector<unsigned char>
cut_;
166 static const int TERMINAL;
168 std::vector<std::pair<int, edge_pair> > parents_;
170 std::vector<std::pair<int, int> > active_list_;
171 int active_head_, active_tail_;
178 Color (
float _r,
float _g,
float _b) :
r(_r),
g(_g),
b(_b) {}
181 template<
typename Po
intT>
184 template<
typename Po
intT>
226 GMM () : gaussians_ (0) {}
228 GMM (std::size_t
K) : gaussians_ (
K) {}
233 getK ()
const {
return gaussians_.size (); }
239 operator[] (std::size_t pos) {
return (gaussians_[pos]); }
242 operator[] (std::size_t pos)
const {
return (gaussians_[pos]); }
252 std::vector<Gaussian> gaussians_;
268 fit (
Gaussian& g, std::size_t total_count,
bool compute_eigens =
false)
const;
281 Eigen::Vector3f sum_{Eigen::Vector3f::Zero ()};
283 Eigen::Matrix3f accumulator_{Eigen::Matrix3f::Zero ()};
285 std::uint32_t count_{0};
295 const std::vector<SegmentationValue> &hardSegmentation,
296 std::vector<std::size_t> &components,
297 GMM &background_GMM,
GMM &foreground_GMM);
302 const std::vector<SegmentationValue>& hard_segmentation,
303 std::vector<std::size_t>& components,
304 GMM& background_GMM,
GMM& foreground_GMM);
316 template <
typename Po
intT>
389 extract (std::vector<pcl::PointIndices>& clusters);
463 std::vector<segmentation::grabcut::TrimapValue>
trimap_{};
477 #include <pcl/segmentation/impl/grabcut_segmentation.hpp>
Implementation of the GrabCut segmentation in "GrabCut — Interactive Foreground Extraction using Iter...
void computeL()
Compute L parameter from given lambda.
std::uint32_t K_
Number of GMM components.
void setBackgroundPoints(const PointCloudConstPtr &background_points)
Set background points, foreground points = points \ background points.
void addEdge(vertex_descriptor v1, vertex_descriptor v2, float capacity, float rev_capacity)
Add an edge to the graph, graph must be oriented so we add the edge and its reverse.
std::vector< float > soft_segmentation_
void setLambda(float lambda)
Set lambda parameter to user given value.
virtual void fitGMMs()
Fit Gaussian Multi Models.
int updateHardSegmentation()
void computeNLinksNonOrganized()
Compute NLinks from cloud.
typename KdTree::Ptr KdTreePtr
void setSearchMethod(const KdTreePtr &tree)
Provide a pointer to the search object.
virtual void refine()
Run Grabcut refinement on the hard segmentation.
void setTrimap(const PointIndicesConstPtr &indices, segmentation::grabcut::TrimapValue t)
Edit Trimap.
pcl::segmentation::grabcut::BoykovKolmogorov graph_
Graph for Graphcut.
std::vector< std::size_t > GMM_component_
std::uint32_t width_
image width
std::uint32_t height_
image height
void setNumberOfNeighbours(int nb_neighbours)
Allows to set the number of neighbours to find.
pcl::segmentation::grabcut::BoykovKolmogorov::vertex_descriptor vertex_descriptor
void extract(std::vector< pcl::PointIndices > &clusters)
This method launches the segmentation algorithm and returns the clusters that were obtained during th...
void initGraph()
Build the graph for GraphCut.
segmentation::grabcut::GMM background_GMM_
void computeBetaOrganized()
Compute beta from image.
~GrabCut() override=default
Destructor.
float L_
L = a large value to force a pixel to be foreground or background.
float lambda_
lambda = 50. This value was suggested the GrabCut paper.
std::vector< segmentation::grabcut::SegmentationValue > hard_segmentation_
void computeNLinksOrganized()
Compute NLinks from image.
bool isSource(vertex_descriptor v)
std::vector< NLinks > n_links_
Precomputed N-link weights.
void setTerminalWeights(vertex_descriptor v, float source_capacity, float sink_capacity)
Set the weights of SOURCE --> v and v --> SINK.
segmentation::grabcut::GMM foreground_GMM_
segmentation::grabcut::Image::Ptr image_
Converted input.
KdTreePtr getSearchMethod()
Get a pointer to the search method used.
KdTreePtr tree_
Pointer to the spatial search object.
float beta_
beta = 1/2 * average of the squared color distances between all pairs of 8-neighboring pixels.
void setBackgroundPointsIndices(int x1, int y1, int x2, int y2)
Set background indices, foreground indices = indices \ background indices.
int nb_neighbours_
Number of neighbours.
std::vector< vertex_descriptor > graph_nodes_
Graph nodes.
void setK(std::uint32_t K)
Set K parameter to user given value.
void setInputCloud(const PointCloudConstPtr &cloud) override
Provide a pointer to the input dataset.
void computeBetaNonOrganized()
Compute beta from cloud.
GrabCut(std::uint32_t K=5, float lambda=50.f)
Constructor.
bool initialized_
is segmentation initialized
std::vector< segmentation::grabcut::TrimapValue > trimap_
int getNumberOfNeighbours() const
Returns the number of neighbours to find.
typename PointCloud::Ptr PointCloudPtr
typename PointCloud::ConstPtr PointCloudConstPtr
PointIndices::ConstPtr PointIndicesConstPtr
PointCloud represents the base class in PCL for storing collections of 3D points.
shared_ptr< PointCloud< PointT > > Ptr
shared_ptr< pcl::search::Search< PointT > > Ptr
boost implementation of Boykov and Kolmogorov's maxflow algorithm doesn't support negative flows whic...
void preAugmentPaths()
pre-augment s-u-t and s-u-v-t paths
bool inSourceTree(int u) const
return true if u is in the s-set after calling solve.
double getTargetEdgeCapacity(int u) const
std::vector< unsigned char > cut_
identifies which side of the cut a node falls
std::pair< capacitated_edge::iterator, capacitated_edge::iterator > edge_pair
edge pair
void addSourceEdge(int u, double cap)
add edge from s to nodeId
void addTargetEdge(int u, double cap)
add edge from nodeId to t
std::vector< capacitated_edge > nodes_
nodes and their outgoing internal edges
double edge_capacity_type
void markActive(int u)
mark vertex as active
void augmentPath(const std::pair< int, int > &path, std::deque< int > &orphans)
augment the path found by expandTrees; return orphaned subtrees
bool isActive(int u) const
active if head or previous node is not the terminal
void reset()
reset all edge capacities to zero (but don't free the graph)
std::map< int, double > capacitated_edge
capacitated edge
bool isActiveSetEmpty() const
double getSourceEdgeCapacity(int u) const
std::vector< double > target_edges_
edges entering the target
void markInactive(int u)
mark vertex as inactive
std::pair< int, int > expandTrees()
expand trees until a path is found (or no path (-1, -1))
bool inSinkTree(int u) const
return true if u is in the t-set after calling solve
std::size_t numNodes() const
get number of nodes in the graph
void clear()
clear the graph and internal datastructures
BoykovKolmogorov(std::size_t max_nodes=0)
construct a maxflow/mincut problem with estimated max_nodes
void clearActive()
clear active set
void adoptOrphans(std::deque< int > &orphans)
adopt orphaned subtrees
double solve()
solve the max-flow problem and return the flow
int addNodes(std::size_t n=1)
add nodes to the graph (returns the id of the first node added)
void addConstant(double c)
add constant flow to graph
void initializeTrees()
initialize trees from source and target
virtual ~BoykovKolmogorov()=default
destructor
void addEdge(int u, int v, double cap_uv, double cap_vu=0.0)
add edge from u to v and edge from v to u (requires cap_uv + cap_vu >= 0)
std::vector< double > source_edges_
edges leaving the source
float probabilityDensity(std::size_t i, const Color &c)
GMM()
Initialize GMM with ddesired number of gaussians.
GMM(std::size_t K)
Initialize GMM with ddesired number of gaussians.
void resize(std::size_t K)
resize gaussians
float probabilityDensity(const Color &c)
~GMM()=default
Destructor.
Helper class that fits a single Gaussian to color samples.
void setEpsilon(float epsilon)
set epsilon which will be added to the covariance matrix diagonal which avoids singular covariance ma...
GaussianFitter(float epsilon=0.0001f)
void add(const Color &c)
Add a color sample.
void fit(Gaussian &g, std::size_t total_count, bool compute_eigens=false) const
Build the gaussian out of all the added color samples.
Defines all the PCL implemented PointT point type structures.
#define PCL_MAKE_ALIGNED_OPERATOR_NEW
Macro to signal a class requires a custom allocator.
Defines functions, macros and traits for allocating and using memory.
TrimapValue
User supplied Trimap values.
float colorDistance(const Color &c1, const Color &c2)
Compute squared distance between two colors.
PCL_EXPORTS void buildGMMs(const Image &image, const Indices &indices, const std::vector< SegmentationValue > &hardSegmentation, std::vector< std::size_t > &components, GMM &background_GMM, GMM &foreground_GMM)
Build the initial GMMs using the Orchard and Bouman color clustering algorithm.
SegmentationValue
Grabcut derived hard segmentation values.
PCL_EXPORTS void learnGMMs(const Image &image, const Indices &indices, const std::vector< SegmentationValue > &hard_segmentation, std::vector< std::size_t > &components, GMM &background_GMM, GMM &foreground_GMM)
Iteratively learn GMMs using GrabCut updating algorithm.
IndicesAllocator<> Indices
Type used for indices in PCL.
Defines all the PCL and non-PCL macros used.
std::vector< float > weights
std::vector< float > dists
A point structure representing Euclidean xyz coordinates, and the RGB color.
A structure representing RGB color information.
Structure to save RGB colors into floats.
Color(const pcl::RGB &color)
Color(float _r, float _g, float _b)
float pi
weighting of this gaussian in the GMM.
float determinant
determinant of the covariance matrix
Eigen::Matrix3f covariance
covariance matrix of the gaussian
Eigen::Matrix3f inverse
inverse of the covariance matrix
Eigen::Vector3f eigenvector
eigenvector corresponding to the highest eigenvector
float eigenvalue
highest eigenvalue of covariance matrix
Color mu
mean of the gaussian