Port set version bug from solvespace fork and cleanup version handling in DRW_TextCodec.

One of the most intrusive changes in QGIS' fork was that the debugging code was replaced with hardcoded changes to redirect the output to QGIS' internal logging mechanism. In this PR I've setup an interface to allow clients to create custom output debugging classes and assign these to be used by the library.

This will allow me to remove all the related downstream changes in QGIS' fork and re-sync these files back to upstream.
Interface for debug printers.
This commit is contained in:
Roman Telezhynskyi 2021-11-23 13:11:56 +02:00
parent a8d8fa0946
commit 6a219c5ed4
7 changed files with 189 additions and 71 deletions

View File

@ -0,0 +1,19 @@
/******************************************************************************
** libDXFrw - Library to read/write DXF files (ascii & binary) **
** **
** Copyright (C) 2011-2015 José F. Soriano, rallazz@gmail.com **
** **
** This library is free software, licensed under the terms of the GNU **
** General Public License as published by the Free Software Foundation, **
** either version 2 of the License, or (at your option) any later version. **
** You should have received a copy of the GNU General Public License **
** along with this program. If not, see <http://www.gnu.org/licenses/>. **
******************************************************************************/
#include "drw_base.h"
#include "intern/drw_dbg.h"
void DRW::setCustomDebugPrinter(DebugPrinter *printer)
{
DRW_dbg::getInstance()->setCustomDebugPrinter(std::unique_ptr<DebugPrinter>(printer));
}

View File

@ -18,6 +18,7 @@
#include <string> #include <string>
#include <list> #include <list>
#include <cmath> #include <cmath>
#include <unordered_map>
#include <QtGlobal> #include <QtGlobal>
#include <ciso646> #include <ciso646>
@ -100,16 +101,46 @@ namespace DRW {
//! Version numbers for the DXF Format. //! Version numbers for the DXF Format.
enum Version { enum Version {
UNKNOWNV, /*!< UNKNOWN VERSION. */ UNKNOWNV, //!< UNKNOWN VERSION.
AC1006, /*!< R10. */ MC00, //!< DWG Release 1.1
AC1009, /*!< R11 & R12. */ AC12, //!< DWG Release 1.2
AC1012, /*!< R13. */ AC14, //!< DWG Release 1.4
AC1014, /*!< R14. */ AC150, //!< DWG Release 2.0
AC1015, /*!< ACAD 2000. */ AC210, //!< DWG Release 2.10
AC1018, /*!< ACAD 2004. */ AC1002, //!< DWG Release 2.5
AC1021, /*!< ACAD 2007. */ AC1003, //!< DWG Release 2.6
AC1024, /*!< ACAD 2010. */ AC1004, //!< DWG Relase 9
AC1027 /*!< ACAD 2013. */ AC1006, //!< DWG Release 10 (R10)
AC1009, //!< DWG Release 11/12 (LT R1/R2) (R11 & R12)
AC1012, //!< DWG Release 13 (LT95) (R13)
AC1014, //!< DWG Release 14/14.01 (LT97/LT98) (R14)
AC1015, //!< AutoCAD 2000/2000i/2002 (ACAD 2000)
AC1018, //!< AutoCAD 2004/2005/2006 (ACAD 2004)
AC1021, //!< AutoCAD 2007/2008/2009 (ACAD 2007)
AC1024, //!< AutoCAD 2010/2011/2012 (ACAD 2010)
AC1027, //!< AutoCAD 2013/2014/2015/2016/2017 (ACAD 2013)
AC1032, //!< AutoCAD 2018/2019/2020 (ACAD 2018)
};
const std::unordered_map< const char*, DRW::Version > dwgVersionStrings {
{ "MC0.0", DRW::MC00 },
{ "AC1.2", DRW::AC12 },
{ "AC1.4", DRW::AC14 },
{ "AC1.50", DRW::AC150 },
{ "AC2.10", DRW::AC210 },
{ "AC1002", DRW::AC1002 },
{ "AC1003", DRW::AC1003 },
{ "AC1004", DRW::AC1004 },
{ "AC1006", DRW::AC1006 },
{ "AC1009", DRW::AC1009 },
{ "AC1012", DRW::AC1012 },
{ "AC1014", DRW::AC1014 },
{ "AC1015", DRW::AC1015 },
{ "AC1018", DRW::AC1018 },
{ "AC1021", DRW::AC1021 },
{ "AC1024", DRW::AC1024 },
{ "AC1027", DRW::AC1027 },
{ "AC1032", DRW::AC1032 },
}; };
enum error { enum error {
@ -133,6 +164,32 @@ enum class DebugLevel {
Debug Debug
}; };
/**
* Interface for debug printers.
*
* The base class is silent and ignores all debugging.
*/
class DebugPrinter {
public:
virtual void printS(const std::string &s){(void)s;}
virtual void printI(long long int i){(void)i;}
virtual void printUI(long long unsigned int i){(void)i;}
virtual void printD(double d){(void)d;}
virtual void printH(long long int i){(void)i;}
virtual void printB(int i){(void)i;}
virtual void printHL(int c, int s, int h){(void)c;(void)s;(void)h;}
virtual void printPT(double x, double y, double z){(void)x;(void)y;(void)z;}
DebugPrinter()=default;
virtual ~DebugPrinter()=default;
};
/**
* Sets a custom debug printer to use when outputting debug messages.
*
* Ownership of `printer` is transferred.
*/
void setCustomDebugPrinter( DebugPrinter* printer );
//! Special codes for colors //! Special codes for colors
enum ColorCodes { enum ColorCodes {
black = 250, black = 250,

View File

@ -18,21 +18,8 @@
DRW_dbg *DRW_dbg::instance{nullptr}; DRW_dbg *DRW_dbg::instance{nullptr};
/*********private clases*************/ /*********private clases*************/
class print_none {
public:
virtual void printS(const std::string &s){(void)s;}
virtual void printI(long long int i){(void)i;}
virtual void printUI(long long unsigned int i){(void)i;}
virtual void printD(double d){(void)d;}
virtual void printH(long long int i){(void)i;}
virtual void printB(int i){(void)i;}
virtual void printHL(int c, int s, int h){(void)c;(void)s;(void)h;}
virtual void printPT(double x, double y, double z){(void)x;(void)y;(void)z;}
print_none()= default;
virtual ~print_none()=default;
};
class print_debug : public print_none { class print_debug : public DRW::DebugPrinter {
public: public:
void printS(const std::string &s) override; void printS(const std::string &s) override;
void printI(long long int i) override; void printI(long long int i) override;
@ -56,17 +43,28 @@ DRW_dbg *DRW_dbg::getInstance(){
} }
DRW_dbg::DRW_dbg() : DRW_dbg::DRW_dbg() :
prClass(std::make_unique<print_none>()) debugPrinter(std::make_unique<print_debug>())
{} {
currentPrinter = &silentDebug;
}
void DRW_dbg::setCustomDebugPrinter(std::unique_ptr<DRW::DebugPrinter> printer)
{
debugPrinter = std::move( printer );
if (level == Level::Debug){
currentPrinter = debugPrinter.get();
}
}
void DRW_dbg::setLevel(Level lvl){ void DRW_dbg::setLevel(Level lvl){
level = lvl; level = lvl;
switch (level){ switch (level){
case Level::Debug: case Level::Debug:
prClass = std::make_unique<print_debug>(); currentPrinter = debugPrinter.get();
break; break;
default: default:
prClass = std::make_unique<print_none>(); currentPrinter = &silentDebug;
break;
} }
} }
@ -75,46 +73,46 @@ DRW_dbg::Level DRW_dbg::getLevel() const{
} }
void DRW_dbg::print(const std::string &s){ void DRW_dbg::print(const std::string &s){
prClass->printS(s); currentPrinter->printS(s);
} }
void DRW_dbg::print(int i){ void DRW_dbg::print(int i){
prClass->printI(i); currentPrinter->printI(i);
} }
void DRW_dbg::print(unsigned int i){ void DRW_dbg::print(unsigned int i){
prClass->printUI(i); currentPrinter->printUI(i);
} }
void DRW_dbg::print(long long int i){ void DRW_dbg::print(long long int i){
prClass->printI(i); currentPrinter->printI(i);
} }
void DRW_dbg::print(long unsigned int i){ void DRW_dbg::print(long unsigned int i){
prClass->printUI(i); currentPrinter->printUI(i);
} }
void DRW_dbg::print(long long unsigned int i){ void DRW_dbg::print(long long unsigned int i){
prClass->printUI(i); currentPrinter->printUI(i);
} }
void DRW_dbg::print(double d){ void DRW_dbg::print(double d){
prClass->printD(d); currentPrinter->printD(d);
} }
void DRW_dbg::printH(long long int i){ void DRW_dbg::printH(long long int i){
prClass->printH(i); currentPrinter->printH(i);
} }
void DRW_dbg::printB(int i){ void DRW_dbg::printB(int i){
prClass->printB(i); currentPrinter->printB(i);
} }
void DRW_dbg::printHL(int c, int s, int h){ void DRW_dbg::printHL(int c, int s, int h){
prClass->printHL(c, s, h); currentPrinter->printHL(c, s, h);
} }
void DRW_dbg::printPT(double x, double y, double z){ void DRW_dbg::printPT(double x, double y, double z){
prClass->printPT(x, y, z); currentPrinter->printPT(x, y, z);
} }
void print_debug::printS(const std::string &s){ void print_debug::printS(const std::string &s){

View File

@ -17,6 +17,7 @@
#include <iostream> #include <iostream>
#include <QtGlobal> #include <QtGlobal>
#include <memory> #include <memory>
#include "../drw_base.h"
//#include <iomanip> //#include <iomanip>
#define DRW_DBGSL(a) DRW_dbg::getInstance()->setLevel(a) #define DRW_DBGSL(a) DRW_dbg::getInstance()->setLevel(a)
@ -37,6 +38,11 @@ public:
Debug Debug
}; };
void setLevel(Level lvl); void setLevel(Level lvl);
/**
* Sets a custom debug printer to use when non-silent output
* is required.
*/
void setCustomDebugPrinter(std::unique_ptr<DRW::DebugPrinter> printer);
Level getLevel() const; Level getLevel() const;
static DRW_dbg *getInstance(); static DRW_dbg *getInstance();
void print(const std::string &s); void print(const std::string &s);
@ -57,8 +63,9 @@ private:
~DRW_dbg(); ~DRW_dbg();
static DRW_dbg *instance; static DRW_dbg *instance;
Level level{Level::None}; Level level{Level::None};
std::ios_base::fmtflags flags{std::cerr.flags()}; DRW::DebugPrinter silentDebug{};
std::unique_ptr<print_none> prClass; std::unique_ptr< DRW::DebugPrinter > debugPrinter;
DRW::DebugPrinter* currentPrinter{nullptr};
}; };

View File

@ -2,6 +2,7 @@
#include <sstream> #include <sstream>
#include <iomanip> #include <iomanip>
#include <algorithm> #include <algorithm>
#include <cstring>
#include <QString> #include <QString>
#include <QTextCodec> #include <QTextCodec>
#include <QDebug> #include <QDebug>
@ -42,44 +43,78 @@ QMap<QString, QStringList> QtCodecs()
{"UTF-16", {"UTF-16", "UTF16", "UTF16-BIT"}}, {"UTF-16", {"UTF-16", "UTF16", "UTF16-BIT"}},
}; };
} }
} } // namespace
DRW_TextCodec::DRW_TextCodec() DRW_TextCodec::DRW_TextCodec()
: version(DRW::AC1021) : version(DRW::AC1021)
{} {}
void DRW_TextCodec::setVersion(int v, bool dxfFormat){ void DRW_TextCodec::setVersion(DRW::Version v, bool dxfFormat){
if (v == DRW::AC1009 || v == DRW::AC1006) { switch (v)
{
case DRW::UNKNOWNV:
case DRW::MC00:
case DRW::AC12:
case DRW::AC14:
case DRW::AC150:
case DRW::AC210:
case DRW::AC1002:
case DRW::AC1003:
case DRW::AC1004:
// unhandled?
break;
case DRW::AC1006:
case DRW::AC1009:
{
version = DRW::AC1009; version = DRW::AC1009;
cp = "ANSI_1252"; cp = "ANSI_1252";
setCodePage(cp, dxfFormat); setCodePage(cp, dxfFormat);
} else if (v == DRW::AC1012 || v == DRW::AC1014 break;
|| v == DRW::AC1015 || v == DRW::AC1018) { }
case DRW::AC1012:
case DRW::AC1014:
case DRW::AC1015:
case DRW::AC1018:
{
version = DRW::AC1015; version = DRW::AC1015;
// if (cp.empty()) { //codepage not set, initialize // if (cp.empty()) { //codepage not set, initialize
cp = "ANSI_1252"; cp = "ANSI_1252";
setCodePage(cp, dxfFormat); setCodePage(cp, dxfFormat);
// } // }
} else { break;
}
case DRW::AC1021:
case DRW::AC1024:
case DRW::AC1027:
case DRW::AC1032:
{
version = DRW::AC1021; version = DRW::AC1021;
if (dxfFormat) if (dxfFormat)
{
cp = "UTF-8";//RLZ: can be UCS2 or UTF-16 16bits per char cp = "UTF-8";//RLZ: can be UCS2 or UTF-16 16bits per char
else
cp = "UTF-16";//RLZ: can be UCS2 or UTF-16 16bits per char
setCodePage(cp, dxfFormat);
}
}
void DRW_TextCodec::setVersion(const std::string &versionStr, bool dxfFormat){
if (versionStr == "AC1009" || versionStr == "AC1006") {
setVersion(DRW::AC1009, dxfFormat);
} else if (versionStr == "AC1012" || versionStr == "AC1014"
|| versionStr == "AC1015" || versionStr == "AC1018") {
setVersion(DRW::AC1015, dxfFormat);
} }
else else
{ {
setVersion(DRW::AC1021, dxfFormat); cp = "UTF-16";//RLZ: can be UCS2 or UTF-16 16bits per char
}
setCodePage(cp, dxfFormat);
break;
}
default:
break;
}
}
void DRW_TextCodec::setVersion(const std::string &v, bool dxfFormat){
version = DRW::UNKNOWNV;
for (auto dwgVersionString : DRW::dwgVersionStrings)
{
if (std::strcmp( v.c_str(), dwgVersionString.first ) == 0)
{
version = dwgVersionString.second;
setVersion( dwgVersionString.second, dxfFormat);
break;
}
} }
} }

View File

@ -3,6 +3,7 @@
#include <string> #include <string>
#include <QtGlobal> #include <QtGlobal>
#include "../drw_base.h"
class QTextCodec; class QTextCodec;
class QStringList; class QStringList;
@ -15,8 +16,8 @@ public:
std::string fromUtf8(const std::string &s); std::string fromUtf8(const std::string &s);
std::string toUtf8(const std::string &s); std::string toUtf8(const std::string &s);
int getVersion() const {return version;} int getVersion() const {return version;}
void setVersion(const std::string &versionStr, bool dxfFormat); void setVersion(const std::string &v, bool dxfFormat);
void setVersion(int v, bool dxfFormat); void setVersion(DRW::Version v, bool dxfFormat);
void setCodePage(const std::string &c, bool dxfFormat); void setCodePage(const std::string &c, bool dxfFormat);
std::string getCodePage() const {return cp;} std::string getCodePage() const {return cp;}
@ -28,7 +29,7 @@ private:
private: private:
Q_DISABLE_COPY(DRW_TextCodec) Q_DISABLE_COPY(DRW_TextCodec)
int version; DRW::Version version{DRW::UNKNOWNV};
std::string cp{}; std::string cp{};
QTextCodec *conv{nullptr}; QTextCodec *conv{nullptr};
}; };

View File

@ -2,6 +2,7 @@
# This need for corect working file translations.pro # This need for corect working file translations.pro
SOURCES += \ SOURCES += \
$$PWD/libdxfrw/drw_base.cpp \
$$PWD/vdxfengine.cpp \ $$PWD/vdxfengine.cpp \
$$PWD/vdxfpaintdevice.cpp \ $$PWD/vdxfpaintdevice.cpp \
$$PWD/libdxfrw/intern/drw_dbg.cpp \ $$PWD/libdxfrw/intern/drw_dbg.cpp \