Skip to content

Commit

Permalink
Merge pull request #1345 from rolanddenis/fix_pointvector
Browse files Browse the repository at this point in the history
Fixing PointVector implicit conversions
  • Loading branch information
dcoeurjo committed Mar 17, 2019
2 parents 461346b + 2932594 commit 6570103
Show file tree
Hide file tree
Showing 35 changed files with 2,943 additions and 1,116 deletions.
23 changes: 23 additions & 0 deletions ChangeLog.md
Expand Up @@ -21,6 +21,17 @@
- Adding PointFunctorHolder to transform any callable object (e.g. function,
functor, lambda function,...) into a CPointFunctor model.
(Roland Denis, [#1332](https://github.com/DGtal-team/DGtal/pull/1332))
- The conversion between PointVector of different component types now follows
the classical conversion rules (e.g. float to double is OK but double
to int fails if the conversion is not explicitly specified).
Component type after an arithmetic operation also follows the classical
arithmetic conversion rules (e.g int * double returns a double).
Adding some related conversion functors.
(Roland Denis, [#1345](https://github.com/DGtal-team/DGtal/pull/1345))
- Making binary operators of PointVector (+-\*/ but also dot, crossProduct,
inf, isLower,...) available as external functions. The component type of
the result follows the classical arithmetic conversion rules.
(Roland Denis, [#1345](https://github.com/DGtal-team/DGtal/pull/1345))
- Adding square norm method to Point/Vector class. (David Coeurjolly,
[#1365](https://github.com/DGtal-team/DGtal/pull/1365))

Expand Down Expand Up @@ -138,6 +149,18 @@
[#1365](https://github.com/DGtal-team/DGtal/pull/1365))
- Fix NumberTraits for `long long int` types and refactor it.
(Roland Denis, [#1397](https://github.com/DGtal-team/DGtal/pull/1397))
- Fixing issue #1341 about unwanted conversions between PointVector with
different component types (like from double to int) by making explicit
the default conversion constructor and checking type compatiblity when
using operators.
(Roland Denis, [#1345](https://github.com/DGtal-team/DGtal/pull/1345))
- Fixing issue #1387 about the wrong result of PointVector::crossProduct
in 2D. Also disabling this method for dimensions other than 2 and 3.
(Roland Denis, [#1345](https://github.com/DGtal-team/DGtal/pull/1345))
- Fixing many issues related to invalid conversion between PointVectors
of different component types.
(David Coeurjolly, Roland Denis, Monir Hadji, Bertrand Kerautret,
Tristan Roussillon, [#1345](https://github.com/DGtal-team/DGtal/pull/1345))

- *Helpers*
- Small fixes in Shortcuts and ShortcutsGeometry, doc, and colormaps.
Expand Down
35 changes: 18 additions & 17 deletions examples/geometry/curves/exampleAlphaThickSegment.cpp
Expand Up @@ -72,43 +72,44 @@ int main( )

//construction of an AlphaThickSegmentComputer2D from the freemanchain iterator
AlphaThickSegmentComputer2D anAlphaSegment(15), anAlphaSegment2(5), anAlphaSegment3(2);
anAlphaSegment.init(fc.begin());
while (anAlphaSegment.end() != fc.end() &&
anAlphaSegment.init(fc.begin());
while (anAlphaSegment.end() != fc.end() &&
anAlphaSegment.extendFront()) {
}
aBoard << anAlphaSegment;

anAlphaSegment2.init(fc.begin());
while (anAlphaSegment2.end() != fc.end() && anAlphaSegment2.extendFront()) {
}
aBoard << CustomStyle( anAlphaSegment2.className(), new CustomColors( DGtal::Color::Blue, DGtal::Color::None ) );
aBoard << anAlphaSegment2;

aBoard << anAlphaSegment;
// Example of thickness definition change: usin the euclidean thickness definition.
//! [exampleAlphaThickSegmentEuclDef]
AlphaThickSegmentComputer2D anAlphaSegment2Eucl(5, functions::Hull2D::EuclideanThickness);
//! [exampleAlphaThickSegmentEuclDef]

anAlphaSegment2Eucl.init(fc.begin());
while (anAlphaSegment2Eucl.end() != fc.end() &&
while (anAlphaSegment2Eucl.end() != fc.end() &&
anAlphaSegment2Eucl.extendFront()) {
}

aBoard << CustomStyle( anAlphaSegment2Eucl.className(),
new CustomColors( DGtal::Color(20, 250, 255), DGtal::Color::None ) );
aBoard << CustomStyle( anAlphaSegment2Eucl.className(),
new CustomColors( DGtal::Color(20, 250, 255), DGtal::Color::None ) );
aBoard << anAlphaSegment2Eucl;



anAlphaSegment2.init(fc.begin());
while (anAlphaSegment2.end() != fc.end() && anAlphaSegment2.extendFront()) {
}
aBoard << CustomStyle( anAlphaSegment2.className(), new CustomColors( DGtal::Color::Blue, DGtal::Color::None ) );
aBoard << anAlphaSegment2;



FCConstIterator fcIt = fc.begin();
while (anAlphaSegment3.extendFront(*fcIt)) {
fcIt++;
}


aBoard << CustomStyle( anAlphaSegment3.className(), new CustomColors( DGtal::Color::Green, DGtal::Color::None ) );
aBoard << CustomStyle( anAlphaSegment3.className(), new CustomColors( DGtal::Color::Green, DGtal::Color::None ) );
aBoard << anAlphaSegment3;



aBoard.saveEPS("exampleAlphaThickSegment.eps");

Expand Down
8 changes: 4 additions & 4 deletions examples/graph/volDistanceTraversal.cpp
Expand Up @@ -40,7 +40,7 @@
#include "DGtal/graph/DistanceBreadthFirstVisitor.h"
#include "DGtal/topology/DigitalSurface.h"
#include "DGtal/topology/LightImplicitDigitalSurface.h"
#include "DGtal/geometry/volumes/distance/ExactPredicateLpSeparableMetric.h"
#include "DGtal/geometry/volumes/distance/LpMetric.h"
#include "DGtal/io/readers/VolReader.h"
#include "DGtal/io/viewers/Viewer3D.h"

Expand Down Expand Up @@ -128,16 +128,16 @@ int main( int argc, char** argv )
typedef CanonicSCellEmbedder<KSpace> SCellEmbedder;
typedef SCellEmbedder::Value RealPoint;
typedef RealPoint::Coordinate Scalar;
typedef ExactPredicateLpSeparableMetric<Space,2> Distance;
using DistanceToPoint = std::function<double(const Space::Point &)>;
typedef LpMetric<Space> Distance;
using DistanceToPoint = std::function<double(const Space::RealPoint &)>;
typedef DGtal::functors::Composer<SCellEmbedder, DistanceToPoint, Scalar> VertexFunctor;
typedef DistanceBreadthFirstVisitor< MyDigitalSurface, VertexFunctor, std::set<SCell> >
MyDistanceVisitor;
typedef MyDistanceVisitor::Node MyNode;
typedef MyDistanceVisitor::Scalar MySize;

SCellEmbedder embedder( ks );
Distance distance;
Distance distance(2.0);
DistanceToPoint distanceToPoint = std::bind( distance, embedder( bel ), std::placeholders::_1 );
VertexFunctor vfunctor( embedder, distanceToPoint );
MyDistanceVisitor visitor( digSurf, vfunctor, bel );
Expand Down
5 changes: 3 additions & 2 deletions examples/images/exampleArrayImageAdapter.cpp
Expand Up @@ -55,9 +55,10 @@ void ArrayImageAdapter_example()
//! [ArrayImageAdapter_example]
using Space = SpaceND<2>;
using Domain = HyperRectDomain<Space>;
using Point = Domain::Point;
using Value = double;

const Domain domain{ {0, 1}, {4, 3} };
const Domain domain( Point(0, 1), Point(4, 3) );

Value* data = new Value[ domain.size() ];

Expand All @@ -73,7 +74,7 @@ void ArrayImageAdapter_example()
}

// Get a constant view on a sub-domain.
const Domain sub_domain{ {1, 1}, {3, 2} };
const Domain sub_domain( Point(1, 1), Point(3, 2) );
ArrayImageAdapter< Value const*, Domain > cst_image( data, domain, sub_domain );
// Alternative syntax using the helpers:
// auto const cst_image = makeArrayImageAdapterFromImage( image, sub_domain );
Expand Down
6 changes: 3 additions & 3 deletions examples/io/viewers/viewer3D-8bis-2Dimages.cpp
Expand Up @@ -86,9 +86,9 @@ int main( int argc, char** argv )
//! [ExampleViewer3D2DImagesExtractImagesNonSliceExtract]
// Extracting images from 3D embeder
DGtal::functors::Point2DEmbedderIn3D<DGtal::Z3i::Domain > embedder(imageVol.domain(),
ptCenter+DGtal::Z3i::RealPoint(200.0*cos(alpha),100.0*sin(alpha)),
DGtal::Z3i::RealPoint(cos(alpha),sin(alpha),cos(2.0*alpha)),
IMAGE_PATCH_WIDTH);
ptCenter+DGtal::Z3i::Point(static_cast<int>(200.0*cos(alpha)),static_cast<int>(100.0*sin(alpha))),
DGtal::Z3i::RealPoint(cos(alpha),sin(alpha),cos(2.0*alpha)),
IMAGE_PATCH_WIDTH);
ImageAdapterExtractor extractedImage(imageVol, domainImage2D, embedder, idV);
//! [ExampleViewer3D2DImagesExtractImagesNonSliceExtract]

Expand Down
5 changes: 2 additions & 3 deletions examples/tutorial-examples/volDTGranulo.cpp
Expand Up @@ -133,11 +133,10 @@ int main(int argc, char ** argv)
Z3i::RealPoint center = *it;
unsigned int radius = (unsigned int)distancemap(*it);
ImplicitBall<Z3i::Space> ball(center,radius);
Z3i::Point low = center - Z3i::Point::diagonal( radius+1 );
Z3i::Point up = center + Z3i::Point::diagonal( radius+1 );
Z3i::Point low(ball.getLowerBound() - Z3i::RealPoint::diagonal(1.0), functors::Floor<>());
Z3i::Point up (ball.getUpperBound() + Z3i::RealPoint::diagonal(1.0), functors::Ceil<>());
Z3i::Domain dom(low,up);


for(Z3i::Domain::ConstIterator itball = dom.begin(), itendball= dom.end();
itball != itendball; itball++)
if (imageGranulo.domain().isInside(*itball) &&
Expand Down
136 changes: 134 additions & 2 deletions src/DGtal/base/BasicFunctors.h
Expand Up @@ -89,7 +89,7 @@ namespace DGtal
/**
* Abs functor.
*/
template <class T>
template <class T = void>
struct Abs
{
inline
Expand Down Expand Up @@ -120,7 +120,7 @@ namespace DGtal
};

/**
* Unary minus functor.
* Multiplication by a scalar functor.
*/
template <class T>
struct MultiplicationByScalar
Expand All @@ -143,6 +143,138 @@ namespace DGtal
T myValue;
};

/** @brief Functor that rounds to the nearest integer.
*
* @tparam T Type to be rounded. If not specified (void), the type is deduced at evaluation.
*/
template < typename T = void >
struct Round
{
inline
auto operator() ( const T & value ) const
-> decltype(std::round(value))
{
return std::round( value );
}
};

/** @brief Functor that rounds to the nearest integer.
*
* This specialization deduces the value type at evaluation.
*
* @see Round
*/
template <>
struct Round<void>
{
template < typename T >
inline
auto operator() ( const T & value ) const
-> decltype(std::round(value))
{
return std::round( value );
}
};

/** @brief Functor that rounds down.
*
* @tparam T Type to be rounded. If not specified (void), the type is deduced at evaluation.
*/
template < typename T = void >
struct Floor
{
inline
auto operator() ( const T & value ) const
-> decltype(std::floor(value))
{
return std::floor( value );
}
};

/** @brief Functor that rounds down.
*
* This specialization deduces the value type at evaluation.
*
* @see Floor
*/
template <>
struct Floor<void>
{
template < typename T >
inline
auto operator() ( const T & value ) const
-> decltype(std::floor(value))
{
return std::floor( value );
}
};

/** @brief Functor that rounds up.
*
* @tparam T Type to be rounded. If not specified (void), the type is deduced at evaluation.
*/
template < typename T = void >
struct Ceil
{
inline
auto operator() ( const T & value ) const
-> decltype(std::ceil(value))
{
return std::ceil( value );
}
};

/** @brief Functor that rounds up.
*
* This specialization deduces the value type at evaluation.
*
* @see Ceil
*/
template <>
struct Ceil<void>
{
template < typename T >
inline
auto operator() ( const T & value ) const
-> decltype(std::ceil(value))
{
return std::ceil( value );
}
};

/** @brief Functor that rounds towards zero.
*
* @tparam T Type to be rounded. If not specified (void), the type is deduced at evaluation.
*/
template < typename T = void >
struct Trunc
{
inline
auto operator() ( const T & value ) const
-> decltype(std::trunc(value))
{
return std::trunc( value );
}
};

/** @brief Functor that rounds towards zero.
*
* This specialization deduces the value type at evaluation.
*
* @see Trunc
*/
template <>
struct Trunc<void>
{
template < typename T >
inline
auto operator() ( const T & value ) const
-> decltype(std::trunc(value))
{
return std::trunc( value );
}
};

///////////////////////////////////////////////////////////////////////////////
// Some basic unary functors that may be useful
//////////////////////////////////////////////////////////////////////////////
Expand Down
8 changes: 4 additions & 4 deletions src/DGtal/geometry/curves/AlphaThickSegmentComputer.h
Expand Up @@ -148,7 +148,7 @@ class AlphaThickSegmentComputer

typedef typename InputPointContainer::iterator Iterator;
typedef TConstIterator ConstIterator;
typedef ParallelStrip< SpaceND< 2, DGtal::int32_t > ,true,true> Primitive;
typedef ParallelStrip< SpaceND< 2, DGtal::int32_t > ,true,true> Primitive;

/**
* Type of embedded points
Expand Down Expand Up @@ -663,9 +663,9 @@ class AlphaThickSegmentComputer
* @param[out] ptProjected the projected point.
* @return true if ptProjected is inside the segment [A,B].
**/
template<typename TPointD>
bool projectOnStraightLine(const TPointD & ptA, const TPointD & ptB,
const TPointD & ptC, PointD & ptProjected) const;
template<typename TPoint, typename TPointD>
bool projectOnStraightLine(const TPoint & ptA, const TPoint & ptB,
const TPoint & ptC, TPointD & ptProjected) const;


/**
Expand Down

0 comments on commit 6570103

Please sign in to comment.