Topic: DXF import/export coding

I try to explain how a dxf file is constructed and what have to be changed on exportdxf.cpp to get it working again.


if we take a look at the exportdxf.cpp file, a lot of the basic drawing types are there and maybe need some fine tunning on function of the changes that have to be made for the dxf export.

How is a dxf file constructed :

The file is devide into sections, each section is starting with a 0, SECTION, 2 HEADER

0
SECTION
  2
HEADER
  9
$ACADVER
  1
AC1012

The key code in a dxf file = 0
followed by the command = SECTION
The code 2 give section name.


if we take a look to createdxf.cpp : void Createdxf::dxfBegin (const QString& fileName)
 

 QTextStream To_Dxf(&file);
            To_Dxf << 999           << "\r\n";
            To_Dxf << "QET"         << "\r\n";
            To_Dxf << 0             << "\r\n";
            To_Dxf << "SECTION"     << "\r\n";
            To_Dxf << 2             << "\r\n";
            To_Dxf << "HEADER"      << "\r\n";
            To_Dxf << 9             << "\r\n";
            To_Dxf << "$ACADVER"    << "\r\n";
            To_Dxf << 1             << "\r\n";
            To_Dxf << "AC1006"      << "\r\n";

The linse 58-59 have to be removed, the are not neaded and telling autocad that it is not a acad created dxf file.

A good starting point for dxf codes :[url=https://knowledge.autodesk.com/search-result/caas/CloudHelp/cloudhelp/2017/ENU/AutoCAD-DXF/files/GUID-235B22E0-A567-4CF6-92D3-38A2306D73F3-htm.html] acad dxf codes
[/url]
see also numerical list o dxf codes
A dxf file have 7 sections, so we need to created for each section a function to file it.We don't need to use them all, just the one we need.

The following functions have to be created :

I we look to the existhing code, everthing is put into the dxf file like it is.

The major change that have to be made is that the titelblocks and elements used i a qet page has to be writen to the block section and be used in the entities section, it is the same way you are using them in qelectrotech.

If we take a look to a simple  qeletrotech project file :

<project folioSheetQuantity="0" version="0.70" title="">
    <properties>
        <property show="1" name="saveddate">2019-08-18</property>
        <property show="1" name="savedfilepath">C:/Users/ronny.desmedt/OneDrive/dxf/basic file.qet</property>
        <property show="1" name="savedtime">17:53</property>
        <property show="1" name="savedfilename">basic file</property>
    </properties>
    <newdiagrams>
        <border cols="17" rowsize="80" displaycols="true" displayrows="true" colsize="60" rows="8"/>
        <inset filename="" folio="%id/%total" auto_page_num="" version="" author="" locmach="" title="" date="null" indexrev="" displayAt="bottom" plant="">
            <properties>
                <property show="1" name="project"></property>
                <property show="1" name="file"></property>
            </properties>
        </inset>
        <conductors type="multi" color2="#000000" function="" tension-protocol="" bicolor="false" dash-size="2" vertirotatetext="270" condsize="1" displaytext="1" onetextperfolio="0" vertical-alignment="AlignRight" num="_" numsize="7" formula="" horizrotatetext="0" horizontal-alignment="AlignBottom"/>
        <report label="%f-%l%c"/>
        <xrefs>
            <xref type="commutator" snapto="label" displayhas="cross" powerprefix="" master_label="%f-%l%c" delayprefix="" showpowerctc="false" slave_label="(%f-%l%c)" switchprefix="" offset="0"/>
            <xref type="coil" snapto="label" displayhas="cross" powerprefix="" master_label="%f-%l%c" delayprefix="" showpowerctc="false" slave_label="(%f-%l%c)" switchprefix="" offset="40"/>
            <xref type="protection" snapto="label" displayhas="cross" powerprefix="" master_label="%f-%l%c" delayprefix="" showpowerctc="false" slave_label="(%f-%l%c)" switchprefix="" offset="0"/>
        </xrefs>
        <conductors_autonums current_autonum="" freeze_new_conductors="false"/>
        <folio_autonums/>
        <element_autonums freeze_new_elements="false" current_autonum=""/>
    </newdiagrams>
    <diagram freezeNewConductor="false" title="" colsize="60" cols="17" filename="" date="null" order="1" height="660" indexrev="" auto_page_num="" freezeNewElement="false" displayrows="true" version="0.70-RC2+474c94469d79751d3" rows="8" rowsize="80" locmach="" author="" displaycols="true" displayAt="bottom" folio="%id/%total" plant="">
        <properties>
            <property show="1" name="project"></property>
            <property show="1" name="file"></property>
        </properties>
        <defaultconductor type="multi" color2="#000000" function="" tension-protocol="" bicolor="false" dash-size="2" vertirotatetext="270" condsize="1" displaytext="1" onetextperfolio="0" vertical-alignment="AlignRight" num="_" numsize="7" formula="" horizrotatetext="0" horizontal-alignment="AlignBottom"/>
        <elements>
            <element type="embed://import/10_electric/10_allpole/200_fuses&amp;protective_gears/11_circuit_breakers/disjonct-m_2f.elmt" z="10" x="330" prefix="F" uuid="{4696d54d-0f44-409b-94c5-34fc2acfb74c}" orientation="0" y="320" freezeLabel="false">
                <terminals>
                    <terminal id="0" x="-10" number="_" nameHidden="0" orientation="0" y="-26" name="_"/>
                    <terminal id="1" x="10" number="_" nameHidden="0" orientation="0" y="-26" name="_"/>
                    <terminal id="2" x="-10" number="_" nameHidden="0" orientation="2" y="16" name="_"/>
                    <terminal id="3" x="10" number="_" nameHidden="0" orientation="2" y="16" name="_"/>
                </terminals>
                <inputs/>
                <elementInformations>
                    <elementInformation show="1" name="formula"></elementInformation>
                </elementInformations>
                <dynamic_texts>
                    <dynamic_elmt_text text_width="-1" Halignment="AlignLeft" Valignment="AlignTop" x="16" font="Sans Serif,9,-1,5,0,0,0,0,0,0,normal" rotation="0" uuid="{da0adb6c-9a34-488e-bc13-06186c2ec811}" y="-17.3334" frame="false" text_from="ElementInfo">
                        <text></text>
                        <info_name>label</info_name>
                    </dynamic_elmt_text>
                </dynamic_texts>
                <texts_groups/>
            </element>
        </elements>
        <shapes>
            <shape is_movable="1" type="Rectangle" x1="530" z="0" closed="0" y1="100" ry="0" y2="210" rx="0" x2="650">
                <pen color="#000000" widthF="1" style="SolidLine"/>
                <brush color="#000000" style="NoBrush"/>
            </shape>
            <shape is_movable="1" type="Line" x1="810" z="0" closed="0" y1="190" y2="470" x2="550">
                <pen color="#000000" widthF="1" style="SolidLine"/>
                <brush color="#000000" style="NoBrush"/>
            </shape>
        </shapes>
    </diagram>
    <collection>
        <category name="import">
            <names>
                <name lang="pl">Elementy importowane</name>
                <name lang="en">Imported elements</name>
                <name lang="da">Importerede elementer</name>
                <name lang="el">Εισηγμένα στοιχεία</name>
                <name lang="fr">Éléments importés</name>
                <name lang="nl">Elementen geïmporteerd</name>
                <name lang="tr">İthal öğeler</name>
                <name lang="es">Elementos importados</name>
                <name lang="ru">Импортированные элементы</name>
                <name lang="hr">Uvezeni elementi</name>
                <name lang="de">Importierte elemente</name>
                <name lang="sl">Uvoženi elementi</name>
                <name lang="ca">Elements importats</name>
                <name lang="cs">Zavedené prvky</name>
                <name lang="pt">elementos importados</name>
                <name lang="it">Elementi importati</name>
                <name lang="ro">Elemente importate</name>
            </names>
            <category name="10_electric">
                <names>
                    <name lang="pl">Elektrotechnika</name>
                    <name lang="en">Electric</name>
                    <name lang="da">Elektrisk</name>
                    <name lang="el">Ηλεκτρικά</name>
                    <name lang="nl">Elektrotechniek</name>
                    <name lang="fr">Electrique</name>
                    <name lang="ru">Электротехника</name>
                    <name lang="es">Eléctrica</name>
                    <name lang="de">Elektrik</name>
                    <name lang="it">Elettrica</name>
                    <name lang="cs">Elektrotechnika</name>
                </names>
                <category name="10_allpole">
                    <names>
                        <name lang="pl">Schematy wieloliniowe</name>
                        <name lang="en">All-pole</name>
                        <name lang="da">Flere ledere</name>
                        <name lang="el">Πολυγραμμικό</name>
                        <name lang="fr">Multifilaire</name>
                        <name lang="nl">Veel polig</name>
                        <name lang="ru">Многополюсные</name>
                        <name lang="es">Multifilar</name>
                        <name lang="de">Allpolig</name>
                        <name lang="cs">Vícežilový</name>
                        <name lang="it">Multifilare</name>
                    </names>
                    <category name="200_fuses&amp;protective_gears">
                        <names>
                            <name lang="pl">Łączniki i zabezpieczenia</name>
                            <name lang="en">Fuses and protective gears</name>
                            <name lang="da">Sikringer og beskyttelsesudstyr</name>
                            <name lang="el">Ασφάλειες και εξαρτήματα προστασίας</name>
                            <name lang="fr">Fusibles et protections</name>
                            <name lang="nl">Zekeringen en beveiligingen</name>
                            <name lang="ru">Предохранители и элементы защиты</name>
                            <name lang="es">Fusibles y protecciones</name>
                            <name lang="de">Sicherungen und Schutzeinrichtungen</name>
                            <name lang="it">Fusibili e protezioni</name>
                            <name lang="cs">Tavné pojistky a ochrany</name>
                        </names>
                        <category name="11_circuit_breakers">
                            <names>
                                <name lang="pl">Wyłączniki</name>
                                <name lang="en">Circuit-breakers</name>
                                <name lang="ar">قواطع</name>
                                <name lang="da">Afbryder</name>
                                <name lang="el">Αυτόματοι διακόπτες</name>
                                <name lang="fr">Disjoncteurs</name>
                                <name lang="nl">Lastscheiders</name>
                                <name lang="ru">Выключатели</name>
                                <name lang="es">Disyuntores</name>
                                <name lang="de">Leitungsschutzschalter und Lastschalter</name>
                                <name lang="cs">Jističe</name>
                                <name lang="pt">Disjuntores</name>
                                <name lang="it">Relè termici</name>
                            </names>
                            <element name="disjonct-m_2f.elmt">
                                <definition type="element" hotspot_y="34" version="0.4" height="60" width="40" link_type="master" hotspot_x="20" orientation="dyyy">
                                    <uuid uuid="{AFE0F3B3-00EE-4EC2-9458-E7934876F42B}"/>
                                    <names>
                                        <name lang="ar">قطب ثنائي القطبية قطبين محميين</name>
                                        <name lang="de">Leitungsschutzschalter 2P</name>
                                        <name lang="en">Circuit-breaker</name>
                                        <name lang="es">Disyuntor termico magnetico en 2P</name>
                                        <name lang="it">Int. Aut. Magneto-termico 2P</name>
                                        <name lang="fr">Disjoncteur bipolaire 2 poles proteges</name>
                                        <name lang="pl">Wyłącznik</name>
                                        <name lang="nl">Lastscheider 2</name>
                                        <name lang="cs">Dvojpólový jistič 2 póly chránící</name>
                                    </names>
                                    <kindInformations>
                                        <kindInformation show="1" name="type">protection</kindInformation>
                                    </kindInformations>
                                    <informations>Author: The QElectroTech team
License: see http://qelectrotech.org/wiki/doc/elements_license</informations>
                                    <description>
                                        <line antialias="false" x1="-12" y1="-10" end2="none" length2="1.5" style="line-style:dashed;line-weight:thin;filling:none;color:black" y2="-10" length1="1.5" end1="none" x2="7"/>
                                        <line antialias="false" x1="-10" y1="16" end2="none" length2="1.5" style="line-style:normal;line-weight:normal;filling:none;color:black" y2="20" length1="1.5" end1="none" x2="-10"/>
                                        <arc antialias="true" angle="-180" x="-14" height="5" style="line-style:normal;line-weight:normal;filling:none;color:black" width="8" start="90" y="10.5"/>
                                        <line antialias="false" x1="-10" y1="8" end2="none" length2="1.5" style="line-style:normal;line-weight:normal;filling:none;color:black" y2="10" length1="1.5" end1="none" x2="-10"/>
                                        <polygon antialias="true" x1="-10" x3="-15" y3="-20" closed="false" y1="3" style="line-style:normal;line-weight:normal;filling:none;color:black" y2="0" x2="-10"/>
                                        <line antialias="false" x1="-10" y1="8" end2="none" length2="1.5" style="line-style:normal;line-weight:normal;filling:none;color:black" y2="8" length1="1.5" end1="none" x2="-5"/>
                                        <line antialias="false" x1="-5" y1="3" end2="none" length2="1.5" style="line-style:normal;line-weight:normal;filling:none;color:black" y2="8" length1="1.5" end1="none" x2="-5"/>
                                        <line antialias="false" x1="-10" y1="3" end2="none" length2="1.5" style="line-style:normal;line-weight:normal;filling:none;color:black" y2="3" length1="1.5" end1="none" x2="-5"/>
                                        <line antialias="false" x1="10" y1="16" end2="none" length2="1.5" style="line-style:normal;line-weight:normal;filling:none;color:black" y2="20" length1="1.5" end1="none" x2="10"/>
                                        <polygon antialias="true" x1="10" x3="5" y3="-20" closed="false" y1="3" style="line-style:normal;line-weight:normal;filling:none;color:black" y2="0" x2="10"/>
                                        <input tagg="label" size="9" x="16" y="-6.3334" text="_"/>
                                        <arc antialias="true" angle="-180" x="6" height="5" style="line-style:normal;line-weight:normal;filling:none;color:black" width="8" start="90" y="10.5"/>
                                        <line antialias="false" x1="-10" y1="-30" end2="none" length2="1.5" style="line-style:normal;line-weight:normal;filling:none;color:black" y2="-20" length1="1.5" end1="none" x2="-10"/>
                                        <line antialias="false" x1="10" y1="8" end2="none" length2="1.5" style="line-style:normal;line-weight:normal;filling:none;color:black" y2="10" length1="1.5" end1="none" x2="10"/>
                                        <line antialias="false" x1="10" y1="8" end2="none" length2="1.5" style="line-style:normal;line-weight:normal;filling:none;color:black" y2="8" length1="1.5" end1="none" x2="15"/>
                                        <line antialias="false" x1="15" y1="3" end2="none" length2="1.5" style="line-style:normal;line-weight:normal;filling:none;color:black" y2="8" length1="1.5" end1="none" x2="15"/>
                                        <line antialias="true" x1="-8" y1="-22" end2="none" length2="1.5" style="line-style:normal;line-weight:normal;filling:none;color:black" y2="-18" length1="1.5" end1="none" x2="-12"/>
                                        <line antialias="false" x1="10" y1="3" end2="none" length2="1.5" style="line-style:normal;line-weight:normal;filling:none;color:black" y2="3" length1="1.5" end1="none" x2="15"/>
                                        <line antialias="true" x1="-12" y1="-22" end2="none" length2="1.5" style="line-style:normal;line-weight:normal;filling:none;color:black" y2="-18" length1="1.5" end1="none" x2="-8"/>
                                        <line antialias="false" x1="10" y1="-30" end2="none" length2="1.5" style="line-style:normal;line-weight:normal;filling:none;color:black" y2="-20" length1="1.5" end1="none" x2="10"/>
                                        <line antialias="true" x1="12" y1="-22" end2="none" length2="1.5" style="line-style:normal;line-weight:normal;filling:none;color:black" y2="-18" length1="1.5" end1="none" x2="8"/>
                                        <line antialias="true" x1="8" y1="-22" end2="none" length2="1.5" style="line-style:normal;line-weight:normal;filling:none;color:black" y2="-18" length1="1.5" end1="none" x2="12"/>
                                        <terminal x="-10" orientation="n" y="-30"/>
                                        <terminal x="10" orientation="s" y="20"/>
                                        <terminal x="10" orientation="n" y="-30"/>
                                        <terminal x="-10" orientation="s" y="20"/>
                                    </description>
                                </definition>
                            </element>
                        </category>
                    </category>
                </category>
            </category>
        </category>
    </collection>
</project>
  • <properties> : some parts belong to header section of a dxf file

  • <newdiagrams>: if this the basic titelblock definition then i belong to the block section an will be used in the entitie section with a "INSERT" dxf type

  • <elements> : use in the entitie section with a "INSERT" dxf type

  • <shapes> : these will be directly used in the entitie section

  • <collection> : these will alle be placed into the block section and used in the entitie section with the "INSERT" dxf type

DXF coding exist of to lines i a dxf file, a code line and a value line:

  • code 10 (11-18) : x coordinate

  • code 20 (21-28) : y coordinate

  • code 30 (31-38) : z coordinate

For example a line :

  • 10 : value : x start point

  • 20 : value : y start point

  • 11 : value : x end point

  • 21 : value : y end point

Header section

 0
SECTION
  2
HEADER
  9
$ACADVER
  1
AC1015
  9
$ACADMAINTVER
 70
    20
  9
$DWGCODEPAGE
  3
ANSI_1252
  9
$INSBASE
 10
0.0
 20
0.0
 30
0.0
  9
$EXTMIN
 10
-0.0000065245499172
 20
-92.07012943410845
 30
0.0
  9
$EXTMAX
 10
245.7932157966029
 20
92.03646890741342
 30
0.0
  

Every section starts with :

  • 0

  • SECTION

  • 2

  • HEADER

  • ....

and ends with

  • 0

  • ENDSEC

every header items starts with code 9 (only used in the header section)

  • 9 : start code

  • $ACADVER : acad settings variable name

  • 1 : Primary text value for an entity

  • AC1015 : value for code 1

  • 9 : next start code for a acad settings variable

base point of a acad.dxf/dwg drawing (this must be in the export file)


  • 9

  • $INSBASE

  • 10 [color=#ff3333]: x reference[/color]

  • 0.0 [color=#3333ff]: value of x[/color]

  • 20 : [color=#ff3333]y reference[/color]

  • 0.0 : [color=#3333ff]value of y[/color]

  • 30 : [color=#ff3333]z reference[/color]

  • 0.0 : [color=#3333ff]value of z[/color]

In DXF TABLES SECTION we need to create following tables :

  • BLOCK_RECORD (posible needed, have to checkout this table)

  • LAYER

  • LTYPE

Layer table

We created layers to separate qet sections:

  • Titelblock

  • Elements

  • Text

  • Shapes

  • ....

Everithing of a titelblock wil be drawn on the layer "Titelblock" and so on for the other types.

LTYPE table

This table is used to converd the QET line types to acad line types


exportdxf.CPP


connectors will be transformet to points in DXF

0
SECTION
2
ENTITIES
0
POINT
8
0
10
111.9573116635928
20
4.929017205688296
30
0
6
Continuous

these points positions will be neded to convert the connector lines to dxf.

A symbol with connectors is insert at coordinates x,Y and the connector is relatief to these insert points (this is for both systems the same) so for drawing a line between to connectors we have to calculate the exact positions of the two connectors and the draw a  polyline with 3 x,y points

0
LWPOLYLINE
5
31C1
330
1F
100
AcDbEntity
  8
0
  6
Continuous
100
AcDbPolyline
 90
        5
 70
     0
 43
0.364575
 10
111.9573116635928
 20
4.929017205688296
 10
116.9052366635928
 20
4.929017205688296
 10
116.9052366635928
 20
-14.7584827943117
 10
111.9573116635928
 20
-14.7584827943117
 10
111.9573116635928
 20
4.929017205688296

Like you can see we need tree times code 10 and 20 to define a polyline

Re: DXF import/export coding

Header function

Header_function () /* step 1 things to write to dxf file */
{

to_dxf << "O"
to_dxf << "SECTION"
to_dxf << "2"
to_dxf << "HEADER"
to_dxf << "9"
to_dxf << "$ACADVER"
to_dxf << "1"
to_dxf << "AC1015"
to_dxf << "9"
to_dxf << "$DWGCODEPAGE"
to_dxf << "3"
to_dxf << "ANSI_1252"
to_dxf << "9"
to_dxf << "$INSBASE"
to_dxf << "10"
to_dxf << "0.0"
to_dxf << "20"
to_dxf << "0.0"
to_dxf << "30"
to_dxf << "0.0"


to_dxf << "0"
to_dxf << "ENDSEC"


}

Re: DXF import/export coding

Tables function

Function_table () /* 2 things to write to dxf file */
{

to_dxf << "0"
to_dxf << "SECTION"
to_dxf << "2"
to_dxf << "TABLES"
to_dxf << "0"
to_dxf << "TABLE" /* line type tables starts here */
to_dxf << "2"
to_dxf << "LTYPE" /* table entry */
to_dxf << "5"
to_dxf << "5"
to_dxf << "330"
to_dxf << "0"
to_dxf << "70"
to_dxf << "1"
to_dxf << "0"
to_dxf << "LTYPE"
to_dxf << "5"
to_dxf << "14"
to_dxf << "330"
to_dxf << "5"
to_dxf << "2"
to_dxf << "ByBlock"
to_dxf << "70"
to_dxf << "0"
to_dxf << "3"
to_dxf << " "
to_dxf << "72"
to_dxf << "65"
to_dxf << "73"
to_dxf << "0"
to_dxf << "40"
to_dxf << "0.0"
to_dxf << "0"
to_dxf << "LTYPE"
to_dxf << "5"
to_dxf << "15"
to_dxf << "330"
to_dxf << "5"
to_dxf << "2"
to_dxf << "ByLayer"
to_dxf << "70"
to_dxf << "0"
to_dxf << "3"
to_dxf << " "
to_dxf << "72"
to_dxf << "65"
to_dxf << "73"
to_dxf << "0"
to_dxf << "40"
to_dxf << "0.0"
to_dxf << "0"
to_dxf << "LTYPE"
to_dxf << "5"
to_dxf << "16"
to_dxf << "330"
to_dxf << "5"
to_dxf << "2"
to_dxf << "Continuous"
to_dxf << "70"
to_dxf << "0"
to_dxf << "3"
to_dxf << "Solid line"
to_dxf << "72"
to_dxf << "65"
to_dxf << "73"
to_dxf << "0"
to_dxf << "40"
to_dxf << "0.0"
to_dxf << "0"
to_dxf << "ENDTAB"

to_dxf << "0"
to_dxf << "TABLE" /* second layer tables */
to_dxf << "2"
to_dxf << "LAYER"
to_dxf << "5"
to_dxf << "2"





}

Re: DXF import/export coding

Thanks Ronny.

but convertion not read the XML but the mapscene.
I hope Joshua can explain it better than me. ;-)

"Le jour où tu découvres le Libre, tu sais que tu ne pourras jamais plus revenir en arrière..."

Re: DXF import/export coding

Hi Lauret,

Try to explain wath we need to ceat dxf export (or import)

So i try to explain tha dxf parts with a example from the code of the exporter now.

These basic function are all working i think, if not we have to check whats be wrong on them.

How the current exporter is reading the qet file is for me not clear, i have to spent to match time to figure out how qet is prosesing the qet file.

We need to change the current sequence on how the dxf file is created and add some extra function to get it to work correctly.

nomicons/smile

Re: DXF import/export coding

Compare qet format agains dxf :


<elements> = dwg blocks = symbols

dxf/dwg layers : are used to make it posible (in acad) to switch on and off, if u have a drawing with a lot  of information, the you can show less or more information with turning layers on and off in acad, also usefull when defining printouts and you dont wont to show some information

These layer are definet in a Layer table


Line types

The line types are also define into a table, so in the convertion to dxf we have to create a line type table with the acad names in it and use these names when creathing the nesecary

Re: DXF import/export coding

Hi Ronny,

in exportdialog you can found functions to export project to DXF :

// Determine les elements a "XMLiser"
 
        foreach(QGraphicsItem *qgi, diagram -> items()) {
 
            if (Element *elmt = qgraphicsitem_cast<Element *>(qgi)) {
 
                list_elements << elmt;
 
            } else if (Conductor *f = qgraphicsitem_cast<Conductor *>(qgi)) {
 
                list_conductors << f;
 
            } else if (IndependentTextItem *iti = qgraphicsitem_cast<IndependentTextItem *>(qgi)) {
 
                list_texts << iti;
 
            } else if (DiagramImageItem *dii = qgraphicsitem_cast<DiagramImageItem *>(qgi)) {
 
                list_images << dii;
 
            } else if (QetShapeItem *dii = qgraphicsitem_cast<QetShapeItem *>(qgi)) {
 
                list_shapes << dii;
 
            } else if (DynamicElementTextItem *deti = qgraphicsitem_cast<DynamicElementTextItem *>(qgi)) {
 
                list_texts << deti;
 
            }
 
        }
 
    }

After for parsing to QTextStream


//Draw elements
    foreach(Element *elmt, list_elements)
    {
        double rotation_angle = elmt -> orientation() * 90;
 
        qreal elem_pos_x = elmt -> pos().x();
        qreal elem_pos_y = elmt -> pos().y();// - (diagram -> margin / 2);
 
        qreal hotspot_x = (elem_pos_x) * Createdxf::xScale;
        qreal hotspot_y = Createdxf::sheetHeight - (elem_pos_y) * Createdxf::yScale;
 
        ElementPictureFactory::primitives primitives = ElementPictureFactory::instance()->getPrimitives(elmt->location());
 
        for(QGraphicsSimpleTextItem *text : primitives.m_texts)
        {
            qreal fontSize = text->font().pointSizeF();
            if (fontSize < 0)
                fontSize = text->font().pixelSize();
 
            fontSize *= Createdxf::yScale;
            qreal x = elem_pos_x + text->pos().x();
            qreal y = elem_pos_y + text->pos().y();
            x *= Createdxf::xScale;
            y = Createdxf::sheetHeight - (y * Createdxf::yScale);// - fontSize;
            QPointF transformed_point = rotation_transformed(x, y, hotspot_x, hotspot_y, rotation_angle);
            x = transformed_point.x();
            y = transformed_point.y();
            QStringList lines = text->text().split('\n');
            y += (fontSize/2) * (lines.count()-1);
            for (QString line : lines)
            {
                qreal angle = 360 - (text->rotation() + rotation_angle);
                if (line.size() > 0 && line != "_" ) {
                    Createdxf::drawText(file_path, line, x, y, fontSize, angle, 0);
                }
                angle += 1080;
                // coordinates for next line
                if (int(angle) % 360 == 0) // no rotation
                    y -= fontSize*1.06;
                else if (int(angle - 180) % 360 == 0) // 180 degrees rotation
                    y += fontSize*1.06;
                else if (int(angle - 270) % 360 == 0) // 270 degrees rotation
                    x -= fontSize*1.06;
                else // ((angle - 90) % 360 == 0) 90 degrees rotation
                    x += fontSize*1.06;
            }
        }
 
        for (QLineF line : primitives.m_lines)
        {
            qreal x1 = (elem_pos_x + line.p1().x()) * Createdxf::xScale;
            qreal y1 = Createdxf::sheetHeight - (elem_pos_y + line.p1().y()) * Createdxf::yScale;
            QPointF transformed_point = rotation_transformed(x1, y1, hotspot_x, hotspot_y, rotation_angle);
            x1 = transformed_point.x();
            y1 = transformed_point.y();
            qreal x2 = (elem_pos_x + line.p2().x()) * Createdxf::xScale;
            qreal y2 = Createdxf::sheetHeight - (elem_pos_y + line.p2().y()) * Createdxf::yScale;
            transformed_point = rotation_transformed(x2, y2, hotspot_x, hotspot_y, rotation_angle);
            x2 = transformed_point.x();
            y2 = transformed_point.y();
            Createdxf::drawLine(file_path, x1, y1, x2, y2, 0);
        }
 
        for (QRectF rect : primitives.m_rectangles)
        {
            qreal x1 = (elem_pos_x + rect.bottomLeft().x()) * Createdxf::xScale;
            qreal y1 = Createdxf::sheetHeight - (elem_pos_y + rect.bottomLeft().y()) * Createdxf::yScale;
            qreal w = rect.width() * Createdxf::xScale;
            qreal h = rect.height() * Createdxf::yScale;
            // opposite corner
            qreal x2 = x1 + w;
            qreal y2 = y1 + h;
            QPointF transformed_point = rotation_transformed(x1, y1, hotspot_x, hotspot_y, rotation_angle);
            x1 = transformed_point.x();
            y1 = transformed_point.y();
            transformed_point = rotation_transformed(x2, y2, hotspot_x, hotspot_y, rotation_angle);
            x2 = transformed_point.x();
            y2 = transformed_point.y();
            qreal bottom_left_x = (x1 < x2) ? x1 : x2;
            qreal bottom_left_y = (y1 < y2) ? y1 : y2;
            w = (x1 < x2) ? x2-x1 : x1-x2;
            h = (y1 < y2) ? y2-y1 : y1-y2;
            Createdxf::drawRectangle(file_path, bottom_left_x, bottom_left_y, w, h, 0);
        }
 
        for (QRectF circle_rect : primitives.m_circles)
        {
            qreal x1 = (elem_pos_x + circle_rect.center().x()) * Createdxf::xScale;
            qreal y1 = Createdxf::sheetHeight - (elem_pos_y + circle_rect.center().y()) * Createdxf::yScale;
            qreal r = circle_rect.width() * Createdxf::xScale / 2;
            QPointF transformed_point = rotation_transformed(x1, y1, hotspot_x, hotspot_y, rotation_angle);
            x1 = transformed_point.x();
            y1 = transformed_point.y();
            Createdxf::drawCircle(file_path, r, x1, y1, 0);
        }
 
        for (QVector<QPointF> polygon : primitives.m_polygons)
        {
            if (polygon.size() == 0)
                continue;
            qreal x1 = (elem_pos_x + polygon.at(0).x()) * Createdxf::xScale;
            qreal y1 = Createdxf::sheetHeight - (elem_pos_y + polygon.at(0).y()) * Createdxf::yScale;
            QPointF transformed_point = rotation_transformed(x1, y1, hotspot_x, hotspot_y, rotation_angle);
            x1 = transformed_point.x();
            y1 = transformed_point.y();
            for (int i = 1; i < polygon.size(); ++i ) {
                qreal x2 = (elem_pos_x + polygon.at(i).x()) * Createdxf::xScale;
                qreal y2 = Createdxf::sheetHeight - (elem_pos_y + polygon.at(i).y()) * Createdxf::yScale;
                QPointF transformed_point = rotation_transformed(x2, y2, hotspot_x, hotspot_y, rotation_angle);
                x2 = transformed_point.x();
                y2 = transformed_point.y();
                Createdxf::drawLine(file_path, x1, y1, x2, y2, 0);
                x1 = x2;
                y1 = y2;
            }
        }
 
        // Draw arcs and ellipses
        for (QVector<qreal> arc : primitives.m_arcs)
        {
            if (arc.size() == 0)
                continue;
            qreal x = (elem_pos_x + arc.at(0)) * Createdxf::xScale;
            qreal y = Createdxf::sheetHeight - (elem_pos_y + arc.at(1)) * Createdxf::yScale;
            qreal w = arc.at(2) * Createdxf::xScale;
            qreal h = arc.at(3) * Createdxf::yScale;
            qreal startAngle = arc.at(4);
            qreal spanAngle = arc .at(5);
            Createdxf::drawArcEllipse(file_path, x, y, w, h, startAngle, spanAngle, hotspot_x, hotspot_y, rotation_angle, 0);
        }
    }
 
    //Draw conductors
    foreach(Conductor *cond, list_conductors) {
        foreach(ConductorSegment *segment, cond -> segmentsList()) {
            qreal x1 = (segment -> firstPoint().x()) * Createdxf::xScale;
            qreal y1 = Createdxf::sheetHeight - (segment -> firstPoint().y() * Createdxf::yScale);
            qreal x2 = (segment -> secondPoint().x()) * Createdxf::xScale;
            qreal y2 = Createdxf::sheetHeight - (segment -> secondPoint().y() * Createdxf::yScale);
            Createdxf::drawLine(file_path, x1, y1, x2, y2, 0);
        }
        //Draw conductor text item
        ConductorTextItem *textItem = cond -> textItem();
        if (textItem) {
            qreal fontSize = textItem -> font().pointSizeF();
            if (fontSize < 0)
                fontSize = textItem -> font().pixelSize();
            fontSize *= Createdxf::yScale;
            qreal x = (textItem -> pos().x()) * Createdxf::xScale;
            qreal y = Createdxf::sheetHeight - (textItem -> pos().y() * Createdxf::yScale) - fontSize;
            QStringList lines = textItem->toPlainText().split('\n');
            foreach (QString line, lines) {
                qreal angle = 360 - (textItem -> rotation());
                if (line.size() > 0 && line != "_" )
                    Createdxf::drawText(file_path, line, x, y, fontSize, angle, 0 );
 
                angle += 1080;
                // coordinates for next line
                if (int(angle) % 360 == 0) // no rotation
                    y -= fontSize*1.06;
                else if (int(angle - 180) % 360 == 0) // 180 degrees rotation
                    y += fontSize*1.06;
                else if (int(angle - 270) % 360 == 0) // 270 degrees rotation
                    x -= fontSize*1.06;
                else // ((angle - 90) % 360 == 0) 90 degrees rotation
                    x += fontSize*1.06;
            }
 
        }
    }
 
    //Draw text items
    foreach(DiagramTextItem *dti, list_texts) {
        qreal fontSize = dti -> font().pointSizeF();
        if (fontSize < 0)
            fontSize = dti -> font().pixelSize();
        fontSize *= Createdxf::yScale;
        qreal x = (dti->scenePos().x()) * Createdxf::xScale;
        qreal y = Createdxf::sheetHeight - (dti->scenePos().y() * Createdxf::yScale) - fontSize*1.05;
        QStringList lines = dti -> toPlainText().split('\n');
        foreach (QString line, lines) {
            qreal angle = 360 - (dti -> rotation());
            if (line.size() > 0 && line != "_" )
                Createdxf::drawText(file_path, line, x, y, fontSize, angle, 0);
 
            angle += 1080;
            // coordinates for next line
            if (int(angle) % 360 == 0) // no rotation
                y -= fontSize*1.06;
            else if (int(angle - 180) % 360 == 0) // 180 degrees rotation
                y += fontSize*1.06;
            else if (int(angle - 270) % 360 == 0) // 270 degrees rotation
                x -= fontSize*1.06;
            else // ((angle - 90) % 360 == 0) 90 degrees rotation
                x += fontSize*1.06;
        }
    }
    Createdxf::dxfEnd(file_path);
 
saveReloadDiagramParameters(diagram, false);
}
 
void ExportDialog::fillRow(const QString& file_path, const QRectF &row_rect, QString author, const QString& title,
                             QString folio, QString date)
{
    qreal x = row_rect.bottomLeft().x();
    qreal y = row_rect.bottomLeft().y();
 
    x *= Createdxf::xScale;
    y = Createdxf::sheetHeight - y * Createdxf::yScale;
    qreal height = row_rect.height() * Createdxf::yScale *0.7;
    y += height*0.2;
 
    Createdxf::drawTextAligned(file_path, std::move(folio),
                             x + 0.02*DiagramFolioList::colWidths[0]*row_rect.width()*Createdxf::xScale, y, height, 0, 0, 5, 0,
                             x + 0.95*DiagramFolioList::colWidths[0]*row_rect.width()*Createdxf::xScale, 0);
 
    x += DiagramFolioList::colWidths[0]*row_rect.width()*Createdxf::xScale;
    QString heading = tr("Titre");
    if (title == heading)
        Createdxf::drawTextAligned(file_path, title,
                                 x + 0.02*DiagramFolioList::colWidths[1]*row_rect.width()*Createdxf::xScale, y, height, 0, 0, 5, 0,
                                 x + 0.02*DiagramFolioList::colWidths[1]*row_rect.width()*Createdxf::xScale, 0);
    else
        Createdxf::drawTextAligned(file_path, title,
                                 x + 0.02*DiagramFolioList::colWidths[1]*row_rect.width()*Createdxf::xScale, y, height, 0, 0, 5, 0,
                                 x + 0.02*DiagramFolioList::colWidths[1]*row_rect.width()*Createdxf::xScale, 0, true);
 
    x += DiagramFolioList::colWidths[1]*row_rect.width()*Createdxf::xScale;
    Createdxf::drawTextAligned(file_path, std::move(author),
                             x + 0.02*DiagramFolioList::colWidths[2]*row_rect.width()*Createdxf::xScale, y, height, 0, 0, 5, 0,
                             x + 3.02*DiagramFolioList::colWidths[2]*row_rect.width()*Createdxf::xScale, 0);
 
    x += DiagramFolioList::colWidths[2]*row_rect.width()*Createdxf::xScale;
    Createdxf::drawTextAligned(file_path, std::move(date),
                             x + 0.02*DiagramFolioList::colWidths[3]*row_rect.width()*Createdxf::xScale, y, height, 0, 0, 5, 0,
                             x + 5.02*DiagramFolioList::colWidths[3]*row_rect.width()*Createdxf::xScale, 0);
}
 
QPointF ExportDialog::rotation_transformed(qreal px, qreal py , qreal origin_x, qreal origin_y, qreal angle) {
 
    angle *= -3.14159265 / 180;
 
    float s = sin(angle);
    float c = cos(angle);
 
    // Vector to rotate:
    qreal Vx = px - origin_x;
    qreal Vy = py - origin_y;
 
    // rotate vector
    float xnew = Vx * c - Vy * s;
    float ynew = Vx * s + Vy * c;
 
    return QPointF(xnew + origin_x, ynew + origin_y);
}

"Le jour où tu découvres le Libre, tu sais que tu ne pourras jamais plus revenir en arrière..."

Re: DXF import/export coding

Here DXF export commits :
https://git.tuxfamily.org/qet/qet.git/l … &q=dxf 

"Le jour où tu découvres le Libre, tu sais que tu ne pourras jamais plus revenir en arrière..."

Re: DXF import/export coding

OK, but we have to change the sequence on how to export.

if we look to a drawing page in qet, it is build with

  • elements

  • lines between connectors

  • titelblock

  • shapes and free text

Before we can export the entities section in dxf
we need to create the dxf block section where we create a block definition for eacht

  • element

  • titelblock

this block section is fillet with the same basic functions already in the dxfexport functions.

After this is write to the dxf file we can create the entities section in dxf
this have a command insert block to write a element in the entities sections.

shapes and free text is writen directly in the entitie sections

The conected lines are also writen in the entities sections