28using namespace Qt::StringLiterals;
30QgsSfcgalGeometry::QgsSfcgalGeometry()
31 : mIsPrimitive( false )
35 : mIsPrimitive( false )
40 sfcgal::errorHandler()->clearText( &errorMsg );
41 mSfcgalGeom = QgsSfcgalEngine::fromAbstractGeometry( qgsGeom, &errorMsg );
42 THROW_ON_ERROR( &errorMsg );
47 : mIsPrimitive( false )
50 sfcgal::errorHandler()->clearText( &errorMsg );
51 mSfcgalGeom = QgsSfcgalEngine::fromAbstractGeometry( &qgsGeom, &errorMsg );
52 THROW_ON_ERROR( &errorMsg );
55QgsSfcgalGeometry::QgsSfcgalGeometry( sfcgal::shared_geom sfcgalGeom )
56 : mSfcgalGeom( sfcgalGeom )
57 , mIsPrimitive( false )
60QgsSfcgalGeometry::QgsSfcgalGeometry( sfcgal::shared_prim sfcgalPrim, sfcgal::primitiveType type )
61 : mIsPrimitive( true )
63#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
64 mSfcgalPrim = sfcgalPrim;
69 throw QgsNotSupportedException( QObject::tr(
"This operation requires a QGIS build based on SFCGAL 2.3 or later" ) );
73QgsSfcgalGeometry::QgsSfcgalGeometry(
const QgsGeometry &qgsGeom )
76 sfcgal::errorHandler()->clearText( &errorMsg );
77 mSfcgalGeom = QgsSfcgalEngine::fromAbstractGeometry( qgsGeom.
constGet(), &errorMsg );
78 THROW_ON_ERROR( &errorMsg );
81QgsSfcgalGeometry::QgsSfcgalGeometry(
const QgsSfcgalGeometry &otherGeom )
84 sfcgal::errorHandler()->clearText( &errorMsg );
85 mIsPrimitive = otherGeom.mIsPrimitive;
86#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
87 mPrimType = otherGeom.mPrimType;
88 mPrimTransform = otherGeom.mPrimTransform;
90 mSfcgalPrim = QgsSfcgalEngine::primitiveClone( otherGeom.mSfcgalPrim.get(), &errorMsg );
93 mSfcgalGeom = QgsSfcgalEngine::cloneGeometry( otherGeom.mSfcgalGeom.get(), &errorMsg );
94 THROW_ON_ERROR( &errorMsg );
97QgsSfcgalGeometry::QgsSfcgalGeometry(
const QString &wkt )
100 sfcgal::errorHandler()->clearText( &errorMsg );
101 mSfcgalGeom = QgsSfcgalEngine::fromWkt( wkt, &errorMsg );
102 THROW_ON_ERROR( &errorMsg );
105sfcgal::shared_geom QgsSfcgalGeometry::workingGeom()
const
107 sfcgal::shared_geom geom;
109#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
113 geom = QgsSfcgalEngine::primitiveAsPolyhedral( mSfcgalPrim.get(), mPrimTransform, &errorMsg );
114 THROW_ON_ERROR( &errorMsg );
127 sfcgal::errorHandler()->clearText( &errorMsg );
129#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
134 Qgis::WkbType out = QgsSfcgalEngine::wkbType( mSfcgalGeom.get(), &errorMsg );
135 THROW_ON_ERROR( &errorMsg );
139QString QgsSfcgalGeometry::geometryType()
const
142 sfcgal::errorHandler()->clearText( &errorMsg );
145#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
150 case sfcgal::primitiveType::SFCGAL_TYPE_CYLINDER:
153 case sfcgal::primitiveType::SFCGAL_TYPE_SPHERE:
156 case sfcgal::primitiveType::SFCGAL_TYPE_TORUS:
159 case sfcgal::primitiveType::SFCGAL_TYPE_BOX:
162 case sfcgal::primitiveType::SFCGAL_TYPE_CUBE:
165 case sfcgal::primitiveType::SFCGAL_TYPE_CONE:
169 sfcgal::errorHandler()->addText( u
"Type '%1' is unknown."_s.arg( mPrimType ) );
175 out = QgsSfcgalEngine::geometryType( mSfcgalGeom.get(), &errorMsg );
176 THROW_ON_ERROR( &errorMsg );
181std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::clone()
const
183 return std::make_unique<QgsSfcgalGeometry>( *
this );
186std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::fromWkb(
const QgsConstWkbPtr &wkbPtr )
194 sfcgal::shared_geom sfcgalGeom = QgsSfcgalEngine::fromWkb( wkbPtr, &errorMsg );
195 THROW_ON_ERROR( &errorMsg );
197 return std::make_unique<QgsSfcgalGeometry>( sfcgalGeom );
204 sfcgal::errorHandler()->clearText( &errorMsg );
206 sfcgal::shared_geom geom = workingGeom();
207 QByteArray wkbArray = QgsSfcgalEngine::toWkb( geom.get(), &errorMsg );
208 THROW_ON_ERROR( &errorMsg );
213QString QgsSfcgalGeometry::asWkt(
int precision )
const
216 sfcgal::errorHandler()->clearText( &errorMsg );
218 sfcgal::shared_geom geom = workingGeom();
219 QString out = QgsSfcgalEngine::toWkt( geom.get(), precision, &errorMsg );
220 THROW_ON_ERROR( &errorMsg );
225std::unique_ptr<QgsAbstractGeometry> QgsSfcgalGeometry::asQgisGeometry()
const
228 sfcgal::errorHandler()->clearText( &errorMsg );
230 sfcgal::shared_geom geom = workingGeom();
231 std::unique_ptr<QgsAbstractGeometry> out = QgsSfcgalEngine::toAbstractGeometry( geom.get(), &errorMsg );
232 THROW_ON_ERROR( &errorMsg );
236std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::boundary()
const
239 sfcgal::errorHandler()->clearText( &errorMsg );
241 sfcgal::shared_geom geom = workingGeom();
242 sfcgal::shared_geom boundary = QgsSfcgalEngine::boundary( geom.get(), &errorMsg );
243 THROW_ON_ERROR( &errorMsg );
245 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( boundary, &errorMsg );
246 THROW_ON_ERROR( &errorMsg );
250bool QgsSfcgalGeometry::operator==(
const QgsSfcgalGeometry &other )
const
252#if SFCGAL_VERSION_NUM < SFCGAL_MAKE_VERSION( 2, 1, 0 )
254 throw QgsNotSupportedException( QObject::tr(
"This operation requires a QGIS build based on SFCGAL 2.1 or later" ) );
257 sfcgal::errorHandler()->clearText( &errorMsg );
260#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
261 if ( mIsPrimitive != other.mIsPrimitive )
266 if ( mPrimTransform != other.mPrimTransform )
270 out = QgsSfcgalEngine::primitiveIsEqual( mSfcgalPrim.get(), other.mSfcgalPrim.get(), -1.0, &errorMsg );
275 out = QgsSfcgalEngine::isEqual( mSfcgalGeom.get(), other.mSfcgalGeom.get(), -1.0, &errorMsg );
277 THROW_ON_ERROR( &errorMsg );
282bool QgsSfcgalGeometry::operator!=(
const QgsSfcgalGeometry &other )
const
284 return !( *
this == other );
287bool QgsSfcgalGeometry::fuzzyEqual(
const QgsSfcgalGeometry &other,
double epsilon )
const
290 sfcgal::errorHandler()->clearText( &errorMsg );
294#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
295 if ( mIsPrimitive != other.mIsPrimitive )
300 if ( !mPrimTransform.fuzzyEqual( other.mPrimTransform, epsilon ) )
304 out = QgsSfcgalEngine::primitiveIsEqual( mSfcgalPrim.get(), other.mSfcgalPrim.get(), epsilon, &errorMsg );
309 out = QgsSfcgalEngine::isEqual( mSfcgalGeom.get(), other.mSfcgalGeom.get(), epsilon, &errorMsg );
312 THROW_ON_ERROR( &errorMsg );
316int QgsSfcgalGeometry::dimension()
const
319 sfcgal::errorHandler()->clearText( &errorMsg );
324 int result = QgsSfcgalEngine::dimension( mSfcgalGeom.get(), &errorMsg );
325 THROW_ON_ERROR( &errorMsg );
330std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::fromWkt(
const QString &wkt )
334 sfcgal::shared_geom sfcgalGeom = QgsSfcgalEngine::fromWkt( wkt, &errorMsg );
335 THROW_ON_ERROR( &errorMsg );
337 return std::make_unique<QgsSfcgalGeometry>( sfcgalGeom );
340int QgsSfcgalGeometry::partCount()
const
343 sfcgal::errorHandler()->clearText( &errorMsg );
348 int out = QgsSfcgalEngine::partCount( mSfcgalGeom.get(), &errorMsg );
349 THROW_ON_ERROR( &errorMsg );
354bool QgsSfcgalGeometry::addZValue(
double zValue )
357 sfcgal::errorHandler()->clearText( &errorMsg );
362 const bool added = QgsSfcgalEngine::addZValue( mSfcgalGeom.get(), zValue, &errorMsg );
363 THROW_ON_ERROR( &errorMsg );
370bool QgsSfcgalGeometry::addMValue(
double mValue )
373 sfcgal::errorHandler()->clearText( &errorMsg );
378 const bool added = QgsSfcgalEngine::addMValue( mSfcgalGeom.get(), mValue, &errorMsg );
379 THROW_ON_ERROR( &errorMsg );
386bool QgsSfcgalGeometry::dropZValue()
389 sfcgal::errorHandler()->clearText( &errorMsg );
394 const bool dropped = QgsSfcgalEngine::dropZValue( mSfcgalGeom.get(), &errorMsg );
395 THROW_ON_ERROR( &errorMsg );
402bool QgsSfcgalGeometry::dropMValue()
405 sfcgal::errorHandler()->clearText( &errorMsg );
410 const bool dropped = QgsSfcgalEngine::dropMValue( mSfcgalGeom.get(), &errorMsg );
411 THROW_ON_ERROR( &errorMsg );
418void QgsSfcgalGeometry::swapXy()
421 sfcgal::errorHandler()->clearText( &errorMsg );
426 QgsSfcgalEngine::swapXy( mSfcgalGeom.get(), &errorMsg );
427 THROW_ON_ERROR( &errorMsg );
432bool QgsSfcgalGeometry::isValid()
const
435 sfcgal::errorHandler()->clearText( &errorMsg );
440 const bool valid = QgsSfcgalEngine::isValid( mSfcgalGeom.get(), &errorMsg,
nullptr );
441 THROW_ON_ERROR( &errorMsg );
445void QgsSfcgalGeometry::clearCache()
const
448bool QgsSfcgalGeometry::isSimple()
const
451 sfcgal::errorHandler()->clearText( &errorMsg );
456 bool result = QgsSfcgalEngine::isSimple( mSfcgalGeom.get(), &errorMsg );
457 THROW_ON_ERROR( &errorMsg );
461std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::geometryN(
unsigned int index )
const
464 sfcgal::errorHandler()->clearText( &errorMsg );
466 sfcgal::shared_geom geom = workingGeom();
467 sfcgal::shared_geom result = QgsSfcgalEngine::geometryN( geom.get(), index );
468 THROW_ON_ERROR( &errorMsg );
470 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
471 THROW_ON_ERROR( &errorMsg );
475QgsPoint QgsSfcgalGeometry::centroid()
const
478 sfcgal::errorHandler()->clearText( &errorMsg );
480 sfcgal::shared_geom geom = workingGeom();
481 return QgsSfcgalEngine::centroid( geom.get(), &errorMsg );
484bool QgsSfcgalGeometry::isEmpty()
const
487 sfcgal::errorHandler()->clearText( &errorMsg );
492 bool result = QgsSfcgalEngine::isEmpty( mSfcgalGeom.get(), &errorMsg );
493 THROW_ON_ERROR( &errorMsg );
498std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::translate(
const QgsVector3D &translation )
const
501 sfcgal::errorHandler()->clearText( &errorMsg );
503 std::unique_ptr<QgsSfcgalGeometry> resultGeom;
504#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
507 resultGeom = clone();
508 resultGeom->setPrimitiveTranslate( translation );
513 sfcgal::shared_geom result = QgsSfcgalEngine::translate( mSfcgalGeom.get(), translation, &errorMsg );
514 THROW_ON_ERROR( &errorMsg );
515 resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
518 THROW_ON_ERROR( &errorMsg );
522std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::scale(
const QgsVector3D &scaleFactor,
const QgsPoint ¢er )
const
525 sfcgal::errorHandler()->clearText( &errorMsg );
527 std::unique_ptr<QgsSfcgalGeometry> resultGeom;
528#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
531 resultGeom = clone();
532 resultGeom->setPrimitiveScale( scaleFactor, center );
537 sfcgal::shared_geom result = QgsSfcgalEngine::scale( mSfcgalGeom.get(), scaleFactor, center, &errorMsg );
538 THROW_ON_ERROR( &errorMsg );
539 resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
542 THROW_ON_ERROR( &errorMsg );
546std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::rotate2D(
double angle,
const QgsPoint ¢er )
const
549 sfcgal::errorHandler()->clearText( &errorMsg );
551 std::unique_ptr<QgsSfcgalGeometry> resultGeom;
552#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
555 resultGeom = clone();
556 resultGeom->setPrimitiveRotation( angle, { 0.0, 0.0, 1.0 }, center );
561 sfcgal::shared_geom result = QgsSfcgalEngine::rotate2D( mSfcgalGeom.get(), angle, center, &errorMsg );
562 THROW_ON_ERROR( &errorMsg );
564 resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
567 THROW_ON_ERROR( &errorMsg );
571std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::transform(
const QgsMatrix4x4 &mat )
const
574 sfcgal::errorHandler()->clearText( &errorMsg );
576#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
577 sfcgal::shared_geom geom = workingGeom();
579 sfcgal::shared_geom result = QgsSfcgalEngine::transform( geom.get(), mat );
580 THROW_ON_ERROR( &errorMsg );
582 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
583 THROW_ON_ERROR( &errorMsg );
587 throw QgsNotSupportedException( QObject::tr(
"This operation requires a QGIS build based on SFCGAL 2.3 or later" ) );
591std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::rotate3D(
double angle,
const QgsVector3D &axisVector,
const QgsPoint ¢er )
const
594 sfcgal::errorHandler()->clearText( &errorMsg );
596 std::unique_ptr<QgsSfcgalGeometry> resultGeom;
597#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
600 resultGeom = clone();
601 resultGeom->setPrimitiveRotation( angle, axisVector, center );
606 sfcgal::shared_geom result = QgsSfcgalEngine::rotate3D( mSfcgalGeom.get(), angle, axisVector, center, &errorMsg );
607 THROW_ON_ERROR( &errorMsg );
609 resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
612 THROW_ON_ERROR( &errorMsg );
616double QgsSfcgalGeometry::area(
bool withDiscretization )
const
619 sfcgal::errorHandler()->clearText( &errorMsg );
622#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
625 result = QgsSfcgalEngine::primitiveArea( mSfcgalPrim.get(), mPrimTransform, withDiscretization, &errorMsg );
630 ( void ) withDiscretization;
631 result = QgsSfcgalEngine::area( mSfcgalGeom.get(), &errorMsg );
634 THROW_ON_ERROR( &errorMsg );
638double QgsSfcgalGeometry::length()
const
641 sfcgal::errorHandler()->clearText( &errorMsg );
646 double result = QgsSfcgalEngine::length( mSfcgalGeom.get(), &errorMsg );
647 THROW_ON_ERROR( &errorMsg );
652double QgsSfcgalGeometry::volume(
bool withDiscretization )
const
655 sfcgal::errorHandler()->clearText( &errorMsg );
661#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
662 result = QgsSfcgalEngine::primitiveVolume( mSfcgalPrim.get(), mPrimTransform, withDiscretization, &errorMsg );
664 ( void ) withDiscretization;
665 throw QgsNotSupportedException( QObject::tr(
"This operation requires a QGIS build based on SFCGAL 2.3 or later" ) );
668 THROW_ON_ERROR( &errorMsg );
675 sfcgal::errorHandler()->clearText( &errorMsg );
676 sfcgal::shared_geom otherShared = QgsSfcgalEngine::fromAbstractGeometry( otherGeom, &errorMsg );
677 THROW_ON_ERROR( &errorMsg );
679 sfcgal::shared_geom geom = workingGeom();
680 bool out = QgsSfcgalEngine::intersects( geom.get(), otherShared.get(), &errorMsg );
681 THROW_ON_ERROR( &errorMsg );
685bool QgsSfcgalGeometry::intersects(
const QgsSfcgalGeometry &otherGeom )
const
688 sfcgal::errorHandler()->clearText( &errorMsg );
690 sfcgal::shared_geom geom = workingGeom();
691 bool out = QgsSfcgalEngine::intersects( geom.get(), otherGeom.workingGeom().get(), &errorMsg );
692 THROW_ON_ERROR( &errorMsg );
696std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::intersection(
const QgsAbstractGeometry *otherGeom )
const
699 sfcgal::errorHandler()->clearText( &errorMsg );
700 sfcgal::shared_geom otherShared = QgsSfcgalEngine::fromAbstractGeometry( otherGeom, &errorMsg );
701 THROW_ON_ERROR( &errorMsg );
703 sfcgal::shared_geom geom = workingGeom();
704 sfcgal::shared_geom result = QgsSfcgalEngine::intersection( geom.get(), otherShared.get(), &errorMsg );
705 THROW_ON_ERROR( &errorMsg );
707 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
708 THROW_ON_ERROR( &errorMsg );
712std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::intersection(
const QgsSfcgalGeometry &otherGeom )
const
715 sfcgal::errorHandler()->clearText( &errorMsg );
717 sfcgal::shared_geom geom = workingGeom();
718 sfcgal::shared_geom result = QgsSfcgalEngine::intersection( geom.get(), otherGeom.workingGeom().get(), &errorMsg );
719 THROW_ON_ERROR( &errorMsg );
721 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
722 THROW_ON_ERROR( &errorMsg );
726std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::combine(
const QVector<QgsAbstractGeometry *> &geomList )
const
729 sfcgal::errorHandler()->clearText( &errorMsg );
730 QVector<sfcgal::shared_geom> sfcgalGeomList;
732 sfcgal::shared_geom geom = workingGeom();
733 sfcgalGeomList.append( geom );
734 for ( QVector<QgsAbstractGeometry *>::const_iterator ite = geomList.constBegin(); ite != geomList.constEnd(); ++ite )
736 sfcgal::shared_geom otherShared = QgsSfcgalEngine::fromAbstractGeometry( *ite, &errorMsg );
737 THROW_ON_ERROR( &errorMsg );
738 sfcgalGeomList.append( otherShared );
741 sfcgal::shared_geom result = QgsSfcgalEngine::combine( sfcgalGeomList, &errorMsg );
742 THROW_ON_ERROR( &errorMsg );
744 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
745 THROW_ON_ERROR( &errorMsg );
749std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::difference(
const QgsAbstractGeometry *otherGeom )
const
752 sfcgal::errorHandler()->clearText( &errorMsg );
753 sfcgal::shared_geom otherSharedr = QgsSfcgalEngine::fromAbstractGeometry( otherGeom, &errorMsg );
754 THROW_ON_ERROR( &errorMsg );
756 sfcgal::shared_geom geom = workingGeom();
757 sfcgal::shared_geom result = QgsSfcgalEngine::difference( geom.get(), otherSharedr.get(), &errorMsg );
758 THROW_ON_ERROR( &errorMsg );
760 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
761 THROW_ON_ERROR( &errorMsg );
765std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::difference(
const QgsSfcgalGeometry &otherGeom )
const
768 sfcgal::errorHandler()->clearText( &errorMsg );
770 sfcgal::shared_geom geom = workingGeom();
771 sfcgal::shared_geom result = QgsSfcgalEngine::difference( geom.get(), otherGeom.workingGeom().get(), &errorMsg );
772 THROW_ON_ERROR( &errorMsg );
774 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
775 THROW_ON_ERROR( &errorMsg );
779std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::triangulate()
const
782 sfcgal::errorHandler()->clearText( &errorMsg );
784 sfcgal::shared_geom geom = workingGeom();
785 sfcgal::shared_geom result = QgsSfcgalEngine::triangulate( geom.get(), &errorMsg );
786 THROW_ON_ERROR( &errorMsg );
788 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
789 THROW_ON_ERROR( &errorMsg );
793std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::convexHull()
const
796 sfcgal::errorHandler()->clearText( &errorMsg );
798 sfcgal::shared_geom geom = workingGeom();
799 sfcgal::shared_geom result = QgsSfcgalEngine::convexHull( geom.get(), &errorMsg );
800 THROW_ON_ERROR( &errorMsg );
802 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
803 THROW_ON_ERROR( &errorMsg );
807std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::envelope()
const
810 sfcgal::errorHandler()->clearText( &errorMsg );
812 sfcgal::shared_geom geom = workingGeom();
813 sfcgal::shared_geom result = QgsSfcgalEngine::envelope( geom.get(), &errorMsg );
814 THROW_ON_ERROR( &errorMsg );
816 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
817 THROW_ON_ERROR( &errorMsg );
821bool QgsSfcgalGeometry::covers(
const QgsSfcgalGeometry &otherGeom )
const
824 sfcgal::errorHandler()->clearText( &errorMsg );
826 sfcgal::shared_geom geom = workingGeom();
827 bool out = QgsSfcgalEngine::covers( geom.get(), otherGeom.workingGeom().get(), &errorMsg );
828 THROW_ON_ERROR( &errorMsg );
832std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::buffer3D(
double radius,
int segments,
Qgis::JoinStyle3D joinStyle3D )
const
835 sfcgal::errorHandler()->clearText( &errorMsg );
837 sfcgal::shared_geom geom = workingGeom();
838 sfcgal::shared_geom result = QgsSfcgalEngine::buffer3D( geom.get(), radius, segments, joinStyle3D, &errorMsg );
839 THROW_ON_ERROR( &errorMsg );
841 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
842 THROW_ON_ERROR( &errorMsg );
846std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::buffer2D(
double radius,
int segments,
Qgis::JoinStyle joinStyle )
const
849 sfcgal::errorHandler()->clearText( &errorMsg );
851 sfcgal::shared_geom geom = workingGeom();
852 sfcgal::shared_geom result = QgsSfcgalEngine::buffer2D( geom.get(), radius, segments, joinStyle, &errorMsg );
853 THROW_ON_ERROR( &errorMsg );
855 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
856 THROW_ON_ERROR( &errorMsg );
860std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::simplify(
double tolerance,
bool preserveTopology )
const
863 sfcgal::errorHandler()->clearText( &errorMsg );
865 sfcgal::shared_geom geom = workingGeom();
866 sfcgal::shared_geom result = QgsSfcgalEngine::simplify( geom.get(), tolerance, preserveTopology, &errorMsg );
867 THROW_ON_ERROR( &errorMsg );
869 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
870 THROW_ON_ERROR( &errorMsg );
874std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::extrude(
const QgsVector3D &extrusion )
const
877 sfcgal::errorHandler()->clearText( &errorMsg );
879 sfcgal::shared_geom geom = workingGeom();
880 sfcgal::shared_geom result = QgsSfcgalEngine::extrude( geom.get(), extrusion, &errorMsg );
881 THROW_ON_ERROR( &errorMsg );
883 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
884 THROW_ON_ERROR( &errorMsg );
888std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::approximateMedialAxis(
bool extendToEdges )
const
891 sfcgal::errorHandler()->clearText( &errorMsg );
893 sfcgal::shared_geom geom = workingGeom();
894 sfcgal::shared_geom result = QgsSfcgalEngine::approximateMedialAxis( geom.get(), extendToEdges, &errorMsg );
895 THROW_ON_ERROR( &errorMsg );
897 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
898 THROW_ON_ERROR( &errorMsg );
902std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::toSolid()
const
905 sfcgal::errorHandler()->clearText( &errorMsg );
907 sfcgal::shared_geom geom = workingGeom();
908 sfcgal::shared_geom solid = QgsSfcgalEngine::toSolid( geom.get(), &errorMsg );
909 THROW_ON_ERROR( &errorMsg );
911 std::unique_ptr<QgsSfcgalGeometry> solidGeom = QgsSfcgalEngine::toSfcgalGeometry( solid, &errorMsg );
912 THROW_ON_ERROR( &errorMsg );
916std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::split3D(
const QgsPoint &planePoint,
const QgsVector3D &planeNormal,
bool closeGeometries )
const
919 sfcgal::errorHandler()->clearText( &errorMsg );
921#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
922 sfcgal::shared_geom geom = workingGeom();
924 sfcgal::shared_geom result = QgsSfcgalEngine::split3D( geom.get(), planePoint, planeNormal, closeGeometries );
925 THROW_ON_ERROR( &errorMsg );
927 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
928 THROW_ON_ERROR( &errorMsg );
931 Q_UNUSED( planePoint )
932 Q_UNUSED( planeNormal )
933 Q_UNUSED( closeGeometries )
934 throw QgsNotSupportedException( QObject::tr(
"This operation requires a QGIS build based on SFCGAL 2.3 or later" ) );
938std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::toPolyhedralSurface()
const
941 sfcgal::errorHandler()->clearText( &errorMsg );
943 sfcgal::shared_geom geom = workingGeom();
944 sfcgal::shared_geom phs = QgsSfcgalEngine::toPolyhedralSurface( geom.get(), &errorMsg );
945 THROW_ON_ERROR( &errorMsg );
947 std::unique_ptr<QgsSfcgalGeometry> phsGeom = QgsSfcgalEngine::toSfcgalGeometry( phs, &errorMsg );
948 THROW_ON_ERROR( &errorMsg );
952std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::createBox(
double sizeX,
double sizeY,
double sizeZ )
954#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
956 sfcgal::errorHandler()->clearText( &errorMsg );
957 sfcgal::shared_prim result = QgsSfcgalEngine::createBox( sizeX, sizeY, sizeZ, &errorMsg );
958 THROW_ON_ERROR( &errorMsg );
960 auto resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, sfcgal::primitiveType::SFCGAL_TYPE_BOX, &errorMsg );
961 THROW_ON_ERROR( &errorMsg );
967 throw QgsNotSupportedException( QObject::tr(
"This operation requires a QGIS build based on SFCGAL 2.3 or later" ) );
971std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::createCone(
double bottomRadius,
double height,
double topRadius,
unsigned int radial )
973#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
975 sfcgal::errorHandler()->clearText( &errorMsg );
976 sfcgal::shared_prim result = QgsSfcgalEngine::createCone( bottomRadius, height, topRadius, radial, &errorMsg );
977 THROW_ON_ERROR( &errorMsg );
979 auto resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, sfcgal::primitiveType::SFCGAL_TYPE_CONE, &errorMsg );
980 THROW_ON_ERROR( &errorMsg );
983 ( void ) bottomRadius;
987 throw QgsNotSupportedException( QObject::tr(
"This operation requires a QGIS build based on SFCGAL 2.3 or later" ) );
991std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::createCube(
double size )
993#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
995 sfcgal::errorHandler()->clearText( &errorMsg );
996 sfcgal::shared_prim result = QgsSfcgalEngine::createCube( size, &errorMsg );
997 THROW_ON_ERROR( &errorMsg );
999 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, sfcgal::primitiveType::SFCGAL_TYPE_CUBE, &errorMsg );
1000 THROW_ON_ERROR( &errorMsg );
1004 throw QgsNotSupportedException( QObject::tr(
"This operation requires a QGIS build based on SFCGAL 2.3 or later" ) );
1008std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::createCylinder(
double radius,
double height,
unsigned int radial )
1010#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
1012 sfcgal::errorHandler()->clearText( &errorMsg );
1013 sfcgal::shared_prim result = QgsSfcgalEngine::createCylinder( radius, height, radial, &errorMsg );
1014 THROW_ON_ERROR( &errorMsg );
1016 auto resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, sfcgal::primitiveType::SFCGAL_TYPE_CYLINDER, &errorMsg );
1017 THROW_ON_ERROR( &errorMsg );
1023 throw QgsNotSupportedException( QObject::tr(
"This operation requires a QGIS build based on SFCGAL 2.3 or later" ) );
1027std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::createSphere(
double radius,
unsigned int subdivisions )
1029#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
1031 sfcgal::errorHandler()->clearText( &errorMsg );
1032 sfcgal::shared_prim result = QgsSfcgalEngine::createSphere( radius, subdivisions, &errorMsg );
1033 THROW_ON_ERROR( &errorMsg );
1035 auto resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, sfcgal::primitiveType::SFCGAL_TYPE_SPHERE, &errorMsg );
1036 THROW_ON_ERROR( &errorMsg );
1040 ( void ) subdivisions;
1041 throw QgsNotSupportedException( QObject::tr(
"This operation requires a QGIS build based on SFCGAL 2.3 or later" ) );
1045std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::createTorus(
double mainRadius,
double tubeRadius,
unsigned int mainRadial,
unsigned int tubeRadial )
1047#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
1049 sfcgal::errorHandler()->clearText( &errorMsg );
1050 sfcgal::shared_prim result = QgsSfcgalEngine::createTorus( mainRadius, tubeRadius, mainRadial, tubeRadial, &errorMsg );
1051 THROW_ON_ERROR( &errorMsg );
1053 auto resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, sfcgal::primitiveType::SFCGAL_TYPE_TORUS, &errorMsg );
1054 THROW_ON_ERROR( &errorMsg );
1057 ( void ) mainRadius;
1058 ( void ) tubeRadius;
1059 ( void ) mainRadial;
1060 ( void ) tubeRadial;
1061 throw QgsNotSupportedException( QObject::tr(
"This operation requires a QGIS build based on SFCGAL 2.3 or later" ) );
1065std::unique_ptr<QgsSfcgalGeometry> QgsSfcgalGeometry::primitiveAsPolyhedralSurface()
const
1067#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
1068 if ( !mIsPrimitive )
1072 sfcgal::errorHandler()->clearText( &errorMsg );
1073 sfcgal::shared_prim result = QgsSfcgalEngine::primitiveAsPolyhedral( mSfcgalPrim.get(), mPrimTransform, &errorMsg );
1074 THROW_ON_ERROR( &errorMsg );
1076 std::unique_ptr<QgsSfcgalGeometry> resultGeom = QgsSfcgalEngine::toSfcgalGeometry( result, &errorMsg );
1077 THROW_ON_ERROR( &errorMsg );
1080 throw QgsNotSupportedException( QObject::tr(
"This operation requires a QGIS build based on SFCGAL 2.3 or later" ) );
1084QgsMatrix4x4 QgsSfcgalGeometry::primitiveTransform()
const
1086#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
1087 if ( !mIsPrimitive )
1090 return mPrimTransform;
1092 throw QgsNotSupportedException( QObject::tr(
"This operation requires a QGIS build based on SFCGAL 2.3 or later" ) );
1096QList<std::pair<QString, QString>> QgsSfcgalGeometry::primitiveParameters()
const
1098#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
1099 if ( !mIsPrimitive )
1103 sfcgal::errorHandler()->clearText( &errorMsg );
1104 QVector<sfcgal::PrimitiveParameterDesc> result = QgsSfcgalEngine::primitiveParameters( mSfcgalPrim.get(), &errorMsg );
1105 THROW_ON_ERROR( &errorMsg );
1107 QList<QPair<QString, QString>> out;
1108 for (
const auto ¶m : result )
1110 out.append( std::pair<QString, QString>( QString::fromStdString( param.name ), QString::fromStdString( param.type ) ) );
1115 throw QgsNotSupportedException( QObject::tr(
"This operation requires a QGIS build based on SFCGAL 2.3 or later" ) );
1119QVariant QgsSfcgalGeometry::primitiveParameter(
const QString &name )
const
1121#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
1122 if ( !mIsPrimitive )
1126 sfcgal::errorHandler()->clearText( &errorMsg );
1127 QVariant result = QgsSfcgalEngine::primitiveParameter( mSfcgalPrim.get(), name, &errorMsg );
1128 THROW_ON_ERROR( &errorMsg );
1133 throw QgsNotSupportedException( QObject::tr(
"This operation requires a QGIS build based on SFCGAL 2.3 or later" ) );
1137void QgsSfcgalGeometry::primitiveSetParameter(
const QString &name,
const QVariant &value )
1139#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
1140 if ( !mIsPrimitive )
1144 sfcgal::errorHandler()->clearText( &errorMsg );
1145 QgsSfcgalEngine::primitiveSetParameter( mSfcgalPrim.get(), name, value, &errorMsg );
1146 THROW_ON_ERROR( &errorMsg );
1151 throw QgsNotSupportedException( QObject::tr(
"This operation requires a QGIS build based on SFCGAL 2.3 or later" ) );
1156#if SFCGAL_VERSION_NUM >= SFCGAL_MAKE_VERSION( 2, 3, 0 )
1157void QgsSfcgalGeometry::setPrimitiveTranslate(
const QgsVector3D &translation )
1161 mPrimTransform = mat * mPrimTransform;
1164void QgsSfcgalGeometry::setPrimitiveScale(
const QgsVector3D &scaleFactor,
const QgsPoint ¢er )
1178 mat.
scale( scaleFactor );
1181 mPrimTransform = mat * mPrimTransform;
1184void QgsSfcgalGeometry::setPrimitiveRotation(
double angle,
const QgsVector3D &axisVector,
const QgsPoint ¢er )
1198 mat.
rotate( angle * 180.0 / M_PI, axisVector );
1201 mPrimTransform = mat * mPrimTransform;
JoinStyle3D
Join styles for 3D buffers.
JoinStyle
Join styles for buffers.
WkbType
The WKB type describes the number of dimensions a geometry has.
@ PolyhedralSurfaceZ
PolyhedralSurfaceZ.
Abstract base class for all geometries.
QFlags< WkbFlag > WkbFlags
A geometry is the spatial representation of a feature.
const QgsAbstractGeometry * constGet() const
Returns a non-modifiable (const) reference to the underlying abstract geometry primitive.
A simple 4x4 matrix implementation useful for transformation in 3D space.
void scale(const QgsVector3D &vector)
Multiplies this matrix by another that scales coordinates by the components of a vector.
void translate(const QgsVector3D &vector)
Multiplies this matrix by another that translates coordinates by the components of a vector.
void rotate(double angle, double x, double y, double z)
Multiples this matrix by another that rotates coordinates through angle degrees about the vector (x,...
Custom exception class which is raised when an operation is not supported.
Point geometry type, with support for z-dimension and m-values.
bool isEmpty() const override
Returns true if the geometry is empty.
Custom exception class for SfCGAL related operations.
A 3D vector (similar to QVector3D) with the difference that it uses double precision instead of singl...