28#if QT_VERSION < QT_VERSION_CHECK(6, 0, 0)
30bool qMapLessThanKey<QPair<QgsCoordinateReferenceSystem, QgsCoordinateReferenceSystem>>(
const QPair<QgsCoordinateReferenceSystem, QgsCoordinateReferenceSystem> &key1,
31 const QPair<QgsCoordinateReferenceSystem, QgsCoordinateReferenceSystem> &key2 )
33 const QPair< QString, QString > key1String = qMakePair(
crsToKey( key1.first ),
crsToKey( key1.second ) );
34 const QPair< QString, QString > key2String = qMakePair(
crsToKey( key2.first ),
crsToKey( key2.second ) );
35 return key1String < key2String;
40 : d( new QgsCoordinateTransformContextPrivate() )
60 d->mLock.lockForRead();
61 rhs.d->mLock.lockForRead();
62 const bool equal = d->mSourceDestDatumTransforms == rhs.d->mSourceDestDatumTransforms;
64 rhs.d->mLock.unlock();
70 return !( *
this == rhs );
77 d->mLock.lockForWrite();
78 d->mSourceDestDatumTransforms.clear();
89 d->mLock.lockForRead();
90 auto res = d->mSourceDestDatumTransforms;
93 QMap<QPair<QString, QString>, QString> results;
94 for (
auto it = res.constBegin(); it != res.constEnd(); ++it )
95 results.insert( qMakePair( it.key().first.authid(), it.key().second.authid() ), it.value().operation );
104 Q_UNUSED( sourceTransform )
105 Q_UNUSED( destinationTransform )
114 d->mLock.lockForWrite();
115 QgsCoordinateTransformContextPrivate::OperationDetails details;
116 details.operation = coordinateOperationProjString;
117 details.allowFallback = allowFallback;
118 d->mSourceDestDatumTransforms.insert( qMakePair( sourceCrs, destinationCrs ), details );
130 d->mSourceDestDatumTransforms.remove( qMakePair( sourceCrs, destinationCrs ) );
142 Q_UNUSED( destination )
151 d->mLock.lockForRead();
153 auto it = d->mSourceDestDatumTransforms.constFind( qMakePair( source, destination ) );
154 if ( it == d->mSourceDestDatumTransforms.constEnd() )
157 it = d->mSourceDestDatumTransforms.constFind( qMakePair( destination, source ) );
160 const QString result = it == d->mSourceDestDatumTransforms.constEnd() ? QString() : it.value().operation;
170 d->mLock.lockForRead();
171 QgsCoordinateTransformContextPrivate::OperationDetails res = d->mSourceDestDatumTransforms.value( qMakePair( source, destination ), QgsCoordinateTransformContextPrivate::OperationDetails() );
172 if ( res.operation.isEmpty() )
175 res = d->mSourceDestDatumTransforms.value( qMakePair( destination, source ), QgsCoordinateTransformContextPrivate::OperationDetails() );
178 return res.allowFallback;
186 d->mLock.lockForRead();
187 QgsCoordinateTransformContextPrivate::OperationDetails res = d->mSourceDestDatumTransforms.value( qMakePair( source, destination ), QgsCoordinateTransformContextPrivate::OperationDetails() );
188 if ( !res.operation.isEmpty() )
194 res = d->mSourceDestDatumTransforms.value( qMakePair( destination, source ), QgsCoordinateTransformContextPrivate::OperationDetails() );
195 if ( !res.operation.isEmpty() )
208 d->mLock.lockForWrite();
210 d->mSourceDestDatumTransforms.clear();
212 const QDomNodeList contextNodes = element.elementsByTagName( QStringLiteral(
"transformContext" ) );
213 if ( contextNodes.count() < 1 )
219 missingTransforms.clear();
222 const QDomElement contextElem = contextNodes.at( 0 ).toElement();
225 const QDomNodeList srcDestNodes = contextElem.elementsByTagName( QStringLiteral(
"srcDest" ) );
226 for (
int i = 0; i < srcDestNodes.size(); ++i )
228 const QDomElement transformElem = srcDestNodes.at( i ).toElement();
230 const QDomElement srcElem = transformElem.firstChildElement( QStringLiteral(
"src" ) );
231 const QDomElement destElem = transformElem.firstChildElement( QStringLiteral(
"dest" ) );
235 if ( !srcElem.isNull() && !destElem.isNull() )
243 const QString key1 = transformElem.attribute( QStringLiteral(
"source" ) );
244 const QString key2 = transformElem.attribute( QStringLiteral(
"dest" ) );
252 const QString coordinateOp = transformElem.attribute( QStringLiteral(
"coordinateOp" ) );
253 const bool allowFallback = transformElem.attribute( QStringLiteral(
"allowFallback" ), QStringLiteral(
"1" ) ).toInt();
263 QgsCoordinateTransformContextPrivate::OperationDetails deets;
264 deets.operation = coordinateOp;
265 deets.allowFallback = allowFallback;
266 d->mSourceDestDatumTransforms.insert( qMakePair( srcCrs, destCrs ), deets );
275 d->mLock.lockForRead();
277 QDomDocument doc = element.ownerDocument();
279 QDomElement contextElem = doc.createElement( QStringLiteral(
"transformContext" ) );
282 for (
auto it = d->mSourceDestDatumTransforms.constBegin(); it != d->mSourceDestDatumTransforms.constEnd(); ++ it )
284 QDomElement transformElem = doc.createElement( QStringLiteral(
"srcDest" ) );
285 QDomElement srcElem = doc.createElement( QStringLiteral(
"src" ) );
286 QDomElement destElem = doc.createElement( QStringLiteral(
"dest" ) );
288 it.key().first.writeXml( srcElem, doc );
289 it.key().second.writeXml( destElem, doc );
291 transformElem.appendChild( srcElem );
292 transformElem.appendChild( destElem );
294 transformElem.setAttribute( QStringLiteral(
"coordinateOp" ), it.value().operation );
295 transformElem.setAttribute( QStringLiteral(
"allowFallback" ), it.value().allowFallback ? QStringLiteral(
"1" ) : QStringLiteral(
"0" ) );
296 contextElem.appendChild( transformElem );
299 element.appendChild( contextElem );
306 d->mLock.lockForWrite();
308 d->mSourceDestDatumTransforms.clear();
311 settings.
beginGroup( QStringLiteral(
"/Projections" ) );
312 const QStringList projectionKeys = settings.
allKeys();
315 QMap< QPair< QgsCoordinateReferenceSystem, QgsCoordinateReferenceSystem >, QgsCoordinateTransformContextPrivate::OperationDetails > transforms;
316 QStringList::const_iterator pkeyIt = projectionKeys.constBegin();
317 for ( ; pkeyIt != projectionKeys.constEnd(); ++pkeyIt )
319 if ( pkeyIt->contains( QLatin1String(
"coordinateOp" ) ) )
321 const QStringList split = pkeyIt->split(
'/' );
322 QString srcAuthId, destAuthId;
323 if ( ! split.isEmpty() )
325 srcAuthId = split.at( 0 );
327 if ( split.size() > 1 )
329 destAuthId = split.at( 1 ).split(
'_' ).at( 0 );
332 if ( srcAuthId.isEmpty() || destAuthId.isEmpty() )
335 const QString proj = settings.
value( *pkeyIt ).toString();
336 const bool allowFallback = settings.
value( QStringLiteral(
"%1//%2_allowFallback" ).arg( srcAuthId, destAuthId ) ).toBool();
337 QgsCoordinateTransformContextPrivate::OperationDetails deets;
338 deets.operation = proj;
339 deets.allowFallback = allowFallback;
345 auto transformIt = transforms.constBegin();
346 for ( ; transformIt != transforms.constEnd(); ++transformIt )
348 d->mSourceDestDatumTransforms.insert( transformIt.key(), transformIt.value() );
358 settings.
beginGroup( QStringLiteral(
"/Projections" ) );
359 const QStringList groupKeys = settings.
allKeys();
360 QStringList::const_iterator groupKeyIt = groupKeys.constBegin();
361 for ( ; groupKeyIt != groupKeys.constEnd(); ++groupKeyIt )
363 if ( groupKeyIt->contains( QLatin1String(
"srcTransform" ) ) || groupKeyIt->contains( QLatin1String(
"destTransform" ) ) || groupKeyIt->contains( QLatin1String(
"coordinateOp" ) ) )
365 settings.
remove( *groupKeyIt );
369 for (
auto transformIt = d->mSourceDestDatumTransforms.constBegin(); transformIt != d->mSourceDestDatumTransforms.constEnd(); ++transformIt )
371 const QString srcAuthId = transformIt.key().first.authid();
372 const QString destAuthId = transformIt.key().second.authid();
374 if ( srcAuthId.isEmpty() || destAuthId.isEmpty() )
377 const QString proj = transformIt.value().operation;
378 const bool allowFallback = transformIt.value().allowFallback;
379 settings.
setValue( srcAuthId +
"//" + destAuthId +
"_coordinateOp", proj );
380 settings.
setValue( srcAuthId +
"//" + destAuthId +
"_allowFallback", allowFallback );
@ Preferred
Preferred format, matching the most recent WKT ISO standard. Currently an alias to WKT2_2019,...
This class represents a coordinate reference system (CRS).
bool isValid() const
Returns whether this CRS is correctly initialized and usable.
bool readXml(const QDomNode &node)
Restores state from the given DOM node.
QString toWkt(Qgis::CrsWktVariant variant=Qgis::CrsWktVariant::Wkt1Gdal, bool multiline=false, int indentationWidth=4) const
Returns a WKT representation of this CRS.
Contains information about the context in which a coordinate transform is executed.
void clear()
Clears all stored transform information from the context.
bool allowFallbackTransform(const QgsCoordinateReferenceSystem &source, const QgsCoordinateReferenceSystem &destination) const
Returns true if approximate "ballpark" transforms may be used when transforming between a source and ...
QString calculateCoordinateOperation(const QgsCoordinateReferenceSystem &source, const QgsCoordinateReferenceSystem &destination) const
Returns the Proj coordinate operation string to use when transforming from the specified source CRS t...
void readSettings()
Reads the context's state from application settings.
void writeSettings()
Write the context's state to application settings.
Q_DECL_DEPRECATED bool addSourceDestinationDatumTransform(const QgsCoordinateReferenceSystem &sourceCrs, const QgsCoordinateReferenceSystem &destinationCrs, int sourceTransformId, int destinationTransformId)
Adds a new sourceTransform and destinationTransform to use when projecting coordinates from the speci...
QMap< QPair< QString, QString >, QString > coordinateOperations() const
Returns the stored mapping for source to destination CRS pairs to associated coordinate operation to ...
void writeXml(QDomElement &element, const QgsReadWriteContext &context) const
Writes the context's state to a DOM element.
Q_DECL_DEPRECATED QgsDatumTransform::TransformPair calculateDatumTransforms(const QgsCoordinateReferenceSystem &source, const QgsCoordinateReferenceSystem &destination) const
Returns the pair of source and destination datum transforms to use for a transform from the specified...
Q_DECL_DEPRECATED QMap< QPair< QString, QString >, QgsDatumTransform::TransformPair > sourceDestinationDatumTransforms() const
Returns the stored mapping for source to destination CRS pairs to associated datum transforms to use.
~QgsCoordinateTransformContext()
bool readXml(const QDomElement &element, const QgsReadWriteContext &context, QStringList &missingTransforms)
Reads the context's state from a DOM element.
bool addCoordinateOperation(const QgsCoordinateReferenceSystem &sourceCrs, const QgsCoordinateReferenceSystem &destinationCrs, const QString &coordinateOperationProjString, bool allowFallback=true)
Adds a new coordinateOperationProjString to use when projecting coordinates from the specified source...
void removeCoordinateOperation(const QgsCoordinateReferenceSystem &sourceCrs, const QgsCoordinateReferenceSystem &destinationCrs)
Removes the coordinate operation for the specified sourceCrs and destinationCrs.
QgsCoordinateTransformContext()
Constructor for QgsCoordinateTransformContext.
bool hasTransform(const QgsCoordinateReferenceSystem &source, const QgsCoordinateReferenceSystem &destination) const
Returns true if the context has a valid coordinate operation to use when transforming from the specif...
bool mustReverseCoordinateOperation(const QgsCoordinateReferenceSystem &source, const QgsCoordinateReferenceSystem &destination) const
Returns true if the coordinate operation returned by calculateCoordinateOperation() for the source to...
bool operator==(const QgsCoordinateTransformContext &rhs) const
Q_DECL_DEPRECATED void removeSourceDestinationDatumTransform(const QgsCoordinateReferenceSystem &sourceCrs, const QgsCoordinateReferenceSystem &destinationCrs)
Removes the source to destination datum transform pair for the specified sourceCrs and destinationCrs...
QgsCoordinateTransformContext & operator=(const QgsCoordinateTransformContext &rhs)
bool operator!=(const QgsCoordinateTransformContext &rhs) const
static bool coordinateOperationIsAvailable(const QString &projDef)
Returns true if a coordinate operation (specified via proj string) is available.
The class is used as a container of context for various read/write operations on other objects.
This class is a composition of two QSettings instances:
void endGroup()
Resets the group to what it was before the corresponding beginGroup() call.
QVariant value(const QString &key, const QVariant &defaultValue=QVariant(), Section section=NoSection) const
Returns the value for setting key.
void beginGroup(const QString &prefix, QgsSettings::Section section=QgsSettings::NoSection)
Appends prefix to the current group.
void remove(const QString &key, QgsSettings::Section section=QgsSettings::NoSection)
Removes the setting key and any sub-settings of key in a section.
void setValue(const QString &key, const QVariant &value, QgsSettings::Section section=QgsSettings::NoSection)
Sets the value of setting key to value.
QStringList allKeys() const
Returns a list of all keys, including subkeys, that can be read using the QSettings object.
QString crsToKey(const QgsCoordinateReferenceSystem &crs)
const QgsCoordinateReferenceSystem & crs