Commit 81bde409 authored by Yiting Shao's avatar Yiting Shao Committed by David Flynn
Browse files

slice/m44910: add longest-edge slice partitioning scheme

This partitioning method (--partitionMethod=2) finds the longest edge of
the point cloud and divides it into --partitionNumUniformGeom=n slices
along the longest edge.

If n = 0, the ratio of longest edge to shortest edge determines
the number of slices.
parent 693f8517
......@@ -125,8 +125,14 @@ attribute coding, as if they had never been configured.
Selects the partitioning method to map points to tiles and slices:
| Value | Description |
|:-----:| --------------------|
|:-----:| ----------------------------------------|
| 0 | none (single slice) |
| 2 | uniform partitioning along longest edge |
### `--partitionNumUniformGeom=INT-VALUE`
Sets the number of slices to generate using `partitionMethod=2`.
If equal to zero, the number of slices is the integer ratio of the
longest to shortest edges of the point cloud bounding box.
Geometry coding
......
......@@ -118,6 +118,7 @@ file(GLOB PROJECT_CPP_FILES
"io_hls.cpp"
"io_tlv.cpp"
"osspecific.cpp"
"partitioning.cpp"
"pcc_chrono.cpp"
"tables.cpp"
"../dependencies/arithmetic-coding/src/*.cpp"
......
......@@ -53,6 +53,9 @@ enum class PartitionMethod
{
// Don't partition input
kNone = 0,
// Partition according to uniform geometry
kUniformGeom = 2,
};
//============================================================================
......@@ -73,6 +76,9 @@ struct EncoderParams {
// Method for partitioning the input cloud
PartitionMethod partitionMethod;
// Number of slices used by PartitionMethod::kUniformGeom
int partitionNumUniformGeom;
};
//============================================================================
......
......@@ -168,6 +168,8 @@ operator<<(std::ostream& out, const PartitionMethod& val)
{
switch (val) {
case PartitionMethod::kNone: out << "0 (None)"; break;
case PartitionMethod::kUniformGeom: out << "0 (UniformGeom)"; break;
default: out << int(val) << " (Unknown)"; break;
}
return out;
}
......@@ -319,7 +321,15 @@ ParseParameters(int argc, char* argv[], Parameters& params)
("partitionMethod",
params.encoder.partitionMethod, PartitionMethod::kNone,
"Method used to partition input point cloud into slices/tiles:\n"
" 0: none")
" 0: none\n"
" 1: none (deprecated)\n"
" 2: n Uniform-Geometry partition bins along the longest edge")
("partitionNumUniformGeom",
params.encoder.partitionNumUniformGeom, 0,
"Number of bins for partitionMethod=2:\n"
" 0: slice partition with adaptive-defined bins\n"
" >=1: slice partition with user-defined bins\n")
("disableAttributeCoding",
params.disableAttributeCoding, false,
......
......@@ -122,6 +122,11 @@ PCCTMC3Encoder3::compress(
switch (params->partitionMethod) {
// NB: this method is handled earlier
case PartitionMethod::kNone: return 1;
case PartitionMethod::kUniformGeom:
partitions = partitionByUniformGeom(
quantizedInputCloud, params->partitionNumUniformGeom);
break;
}
} while (0);
......
/* The copyright in this software is being made available under the BSD
* Licence, included below. This software may be subject to other third
* party and contributor rights, including patent rights, and no such
* rights are granted under this licence.
*
* Copyright (c) 2017-2018, ISO/IEC
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* * Neither the name of the ISO/IEC nor the names of its contributors
* may be used to endorse or promote products derived from this
* software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#include "partitioning.h"
#include <algorithm>
#include <cstdlib>
namespace pcc {
//============================================================================
template<typename T>
static int
longestAxis(const PCCBox3<T>& curBox)
{
int edgeAxis = 0;
for (int i = 1; i < 3; i++) {
T axisLength = curBox.max[i] - curBox.min[i];
T longestLength = curBox.max[edgeAxis] - curBox.min[edgeAxis];
if (axisLength > longestLength)
edgeAxis = i;
}
return edgeAxis;
}
//----------------------------------------------------------------------------
template<typename T>
static int
shortestAxis(const PCCBox3<T>& curBox)
{
int edgeAxis = 0;
for (int i = 1; i < 3; i++) {
T axisLength = curBox.max[i] - curBox.min[i];
T shortestLength = curBox.max[edgeAxis] - curBox.min[edgeAxis];
if (axisLength < shortestLength)
edgeAxis = i;
}
return edgeAxis;
}
//----------------------------------------------------------------------------
// Split point cloud into slices along the longest axis.
// numPartitions describes the number of slices to produce (if zero, the
// ratio of longest:shortest axis is used).
// No tile metadata is generated.
PartitionSet
partitionByUniformGeom(const PCCPointSet3& cloud, int numPartitions)
{
PartitionSet partitions;
PCCBox3D bbox = cloud.computeBoundingBox();
int maxEdgeAxis = longestAxis(bbox);
int maxEdge = bbox.max[maxEdgeAxis] - bbox.min[maxEdgeAxis];
int minEdgeAxis = shortestAxis(bbox);
int minEdge = bbox.max[minEdgeAxis] - bbox.min[minEdgeAxis];
int sliceNum;
int sliceSize;
if (!numPartitions) {
sliceNum = maxEdge / minEdge;
sliceSize = minEdge;
} else {
sliceNum = numPartitions;
sliceSize = maxEdge / sliceNum;
}
partitions.slices.resize(sliceNum);
for (int i = 0; i < sliceNum; i++) {
auto& slice = partitions.slices[i];
slice.sliceId = i;
slice.tileId = -1;
slice.origin = PCCVector3<int>{0};
}
for (int n = 0; n < cloud.getPointCount(); n++) {
for (int p = sliceNum - 1; p >= 0; p--) {
if (
cloud[n][maxEdgeAxis] >= int(p * sliceSize + bbox.min[maxEdgeAxis])) {
auto& slice = partitions.slices[p];
slice.pointIndexes.push_back(n);
break;
}
}
}
// Delete the slice that with no points
partitions.slices.erase(
std::remove_if(
partitions.slices.begin(), partitions.slices.end(),
[](const Partition& p) { return p.pointIndexes.empty(); }),
partitions.slices.end());
return partitions;
}
//============================================================================
} // namespace pcc
......@@ -72,4 +72,9 @@ struct PartitionSet {
//============================================================================
PartitionSet
partitionByUniformGeom(const PCCPointSet3& cloud, int numPartitions);
//============================================================================
} // namespace pcc
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment