From 9d73304c6075e47913cdcd70d2ddfa735e97eef2 Mon Sep 17 00:00:00 2001 From: Andrea Giudiceandrea Date: Sat, 1 Mar 2025 10:46:50 +0100 Subject: [PATCH 1/4] [DXF] Fix writing encoding name --- src/core/dxf/qgsdxfexport.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/core/dxf/qgsdxfexport.cpp b/src/core/dxf/qgsdxfexport.cpp index 8384965658a6..9791783a749a 100644 --- a/src/core/dxf/qgsdxfexport.cpp +++ b/src/core/dxf/qgsdxfexport.cpp @@ -2361,7 +2361,7 @@ QString QgsDxfExport::dxfEncoding( const QString &name ) continue; int i; - for ( i = 0; i < static_cast< int >( sizeof( DXF_ENCODINGS ) / sizeof( *DXF_ENCODINGS ) ) && name != DXF_ENCODINGS[i][1]; ++i ) + for ( i = 0; i < static_cast< int >( sizeof( DXF_ENCODINGS ) / sizeof( *DXF_ENCODINGS ) ) && strcasecmp( codec.data(), DXF_ENCODINGS[i][1] ) != 0; ++i ) ; if ( i == static_cast< int >( sizeof( DXF_ENCODINGS ) / sizeof( *DXF_ENCODINGS ) ) ) From f56bfa9a756aa1d4cd69a33691465d6e53ef876e Mon Sep 17 00:00:00 2001 From: Andrea Giudiceandrea Date: Sat, 1 Mar 2025 15:02:40 +0100 Subject: [PATCH 2/4] [DXF] Avoid a loop in dxfEncoding and make it case insensitive --- src/core/dxf/qgsdxfexport.cpp | 15 ++++++--------- 1 file changed, 6 insertions(+), 9 deletions(-) diff --git a/src/core/dxf/qgsdxfexport.cpp b/src/core/dxf/qgsdxfexport.cpp index 9791783a749a..38c8271d2dd5 100644 --- a/src/core/dxf/qgsdxfexport.cpp +++ b/src/core/dxf/qgsdxfexport.cpp @@ -2354,20 +2354,17 @@ QString QgsDxfExport::layerName( const QString &id, const QgsFeature &f ) const QString QgsDxfExport::dxfEncoding( const QString &name ) { - const QList< QByteArray > codecs = QTextCodec::availableCodecs(); - for ( const QByteArray &codec : codecs ) + const QByteArray codec = name.toLocal8Bit(); + if ( QTextCodec::codecForName( codec ) ) { - if ( name != codec ) - continue; - int i; for ( i = 0; i < static_cast< int >( sizeof( DXF_ENCODINGS ) / sizeof( *DXF_ENCODINGS ) ) && strcasecmp( codec.data(), DXF_ENCODINGS[i][1] ) != 0; ++i ) ; - if ( i == static_cast< int >( sizeof( DXF_ENCODINGS ) / sizeof( *DXF_ENCODINGS ) ) ) - continue; - - return DXF_ENCODINGS[i][0]; + if ( i != static_cast< int >( sizeof( DXF_ENCODINGS ) / sizeof( *DXF_ENCODINGS ) ) ) + { + return DXF_ENCODINGS[i][0]; + } } return QString(); From 1f76ece71b1f753e614b8f8df4bfea7574068ee0 Mon Sep 17 00:00:00 2001 From: Andrea Giudiceandrea Date: Sat, 1 Mar 2025 17:43:19 +0100 Subject: [PATCH 3/4] [DXF] Add test for codepage writing --- tests/src/core/testqgsdxfexport.cpp | 30 +++++++++++++++++++++++++++++ 1 file changed, 30 insertions(+) diff --git a/tests/src/core/testqgsdxfexport.cpp b/tests/src/core/testqgsdxfexport.cpp index fe8e80c1a5e7..5ad5031fecad 100644 --- a/tests/src/core/testqgsdxfexport.cpp +++ b/tests/src/core/testqgsdxfexport.cpp @@ -84,6 +84,7 @@ class TestQgsDxfExport : public QObject void testExtentWithSelection(); void testOutputLayerNamePrecedence(); void testMinimumLineWidthExport(); + void testWritingCodepage(); private: QgsVectorLayer *mPointLayer = nullptr; @@ -1958,6 +1959,35 @@ void TestQgsDxfExport::testMinimumLineWidthExport() QVERIFY( !fileContainsText( file, QStringLiteral( " 43\n7.0" ) ) ); } +void TestQgsDxfExport::testWritingCodepage() +{ + QgsDxfExport d; + d.addLayers( QList() << QgsDxfExport::DxfLayer( mPointLayer ) ); + + QgsMapSettings mapSettings; + const QSize size( 640, 480 ); + mapSettings.setOutputSize( size ); + mapSettings.setExtent( mPointLayer->extent() ); + mapSettings.setLayers( QList() << mPointLayer ); + mapSettings.setOutputDpi( 96 ); + mapSettings.setDestinationCrs( mPointLayer->crs() ); + + d.setMapSettings( mapSettings ); + d.setSymbologyScale( 1000 ); + + const QString file1 = getTempFileName( "CP1252UpperCase_dxf" ); + QFile dxfFile1( file1 ); + QCOMPARE( d.writeToFile( &dxfFile1, QStringLiteral( "CP1252" ) ), QgsDxfExport::ExportResult::Success ); + dxfFile1.close(); + QVERIFY( fileContainsText( file1, QStringLiteral( "ANSI_1252" ) ) ); + + const QString file2 = getTempFileName( "cp1252lowercase_dxf" ); + QFile dxfFile2( file2 ); + QCOMPARE( d.writeToFile( &dxfFile2, QStringLiteral( "cp1252" ) ), QgsDxfExport::ExportResult::Success ); + dxfFile2.close(); + QVERIFY( fileContainsText( file2, QStringLiteral( "ANSI_1252" ) ) ); +} + bool TestQgsDxfExport::fileContainsText( const QString &path, const QString &text, QString *debugInfo ) const { QStringList debugLines; From fa7d1e0311a797e0f4b00d7a360f50fb67b49686 Mon Sep 17 00:00:00 2001 From: Andrea Giudiceandrea Date: Sat, 1 Mar 2025 19:30:15 +0100 Subject: [PATCH 4/4] [DXF] Set $ACADVER to AC1018 (AutoCAD 2004) because codes 420 and 440 (which are written in the DXF file by QgsDxfEport) are listed in DXF specs only since AutoCAD 2004 --- src/core/dxf/qgsdxfexport.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/core/dxf/qgsdxfexport.cpp b/src/core/dxf/qgsdxfexport.cpp index 38c8271d2dd5..5916c0b7e5f3 100644 --- a/src/core/dxf/qgsdxfexport.cpp +++ b/src/core/dxf/qgsdxfexport.cpp @@ -319,7 +319,7 @@ void QgsDxfExport::writeHeader( const QString &codepage ) // ACADVER writeGroup( 9, QStringLiteral( "$ACADVER" ) ); - writeGroup( 1, QStringLiteral( "AC1015" ) ); + writeGroup( 1, QStringLiteral( "AC1018" ) ); // EXTMIN writeGroup( 9, QStringLiteral( "$EXTMIN" ) );