Advertisement
danfalck

dxf2sketch

Jan 25th, 2012
206
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 11.74 KB | None | 0 0
  1.  
  2. # -*- coding: utf8 -*-
  3.  
  4. #***************************************************************************
  5. #*                                                                         *
  6. #*   Copyright (c) 2009 Yorik van Havre <yorik@gmx.fr>                     *
  7. #*   Dan Falck ddfalck@gmail.com                                           *
  8. #*   This program is free software; you can redistribute it and/or modify  *
  9. #*   it under the terms of the GNU General Public License (GPL)            *
  10. #*   as published by the Free Software Foundation; either version 2 of     *
  11. #*   the License, or (at your option) any later version.                   *
  12. #*   for detail see the LICENCE text file.                                 *
  13. #*                                                                         *
  14. #*   This program is distributed in the hope that it will be useful,       *
  15. #*   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
  16. #*   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
  17. #*   GNU Library General Public License for more details.                  *
  18. #*                                                                         *
  19. #*   You should have received a copy of the GNU Library General Public     *
  20. #*   License along with this program; if not, write to the Free Software   *
  21. #*   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  *
  22. #*   USA                                                                   *
  23. #*                                                                         *
  24. #***************************************************************************
  25.  
  26. __title__="FreeCAD DXF to Sketcher importer"
  27. __author__ = "Yorik van Havre <yorik@gmx.fr>, Dan Falck <ddfalck@gmail.com>"
  28. __url__ = ["http://yorik.orgfree.com","http://free-cad.sourceforge.net"]
  29.  
  30. '''
  31. This script uses a DXF-parsing library created by Stani,
  32. Kitsu and Migius for Blender
  33.  
  34. imports:
  35. line,  arcs, circles,
  36. to the constraints Sketcher
  37.  
  38. '''
  39.  
  40. import FreeCAD, os, Part, math, re, string, Mesh, Draft
  41. from draftlibs import fcvec, dxfColorMap, dxfLibrary, fcgeo
  42. from draftlibs.dxfReader import readDXF
  43. from FreeCAD import Vector
  44. from importDXF import decodeName,locateLayer,calcBulge,getGroup,getACI,rawValue,vec,fcformat
  45. from Sketcher import *
  46. from PyQt4 import QtGui
  47.  
  48. try: import FreeCADGui
  49. except: gui = False
  50. else: gui = True
  51. try: draftui = FreeCADGui.draftToolBar
  52. except: draftui = None
  53.  
  54. pythonopen = open # to distinguish python built-in open function from the one declared here
  55. prec = FreeCAD.ParamGet("User parameter:BaseApp/Preferences/Mod/Draft").GetInt("precision")
  56.  
  57. def drawLine(line):
  58.     "returns a Sketch line from a dxf line"
  59.     if (len(line.points) > 1):
  60.         v1=vec(line.points[0])
  61.         v2=vec(line.points[1])
  62.         if not fcvec.equals(v1,v2):
  63.             try:
  64.                 return Part.Line((v1),(v2))
  65.             except:
  66.                 warn(line)
  67.     return None
  68.  
  69. def drawArc(arc):
  70.     "returns a Part shape from a dxf arc"
  71.     v=vec(arc.loc)
  72.     d=FreeCAD.Vector(0,0,1)
  73.     firstangle=math.radians(arc.start_angle)
  74.     lastangle=math.radians(arc.end_angle)
  75.     try:
  76.         return v, d, arc.radius,firstangle,lastangle
  77.     except:
  78.         warn(arc)
  79.     return None
  80.  
  81. def drawCircle(circle):
  82.     "returns a Part shape from a dxf circle"
  83.     v = vec(circle.loc)
  84.     d=FreeCAD.Vector(0,0,1)
  85.     curve = Part.Circle()
  86.     curve.Radius = circle.radius
  87.     curve.Center = v
  88.     #print v,d,circle.radius
  89.     try:
  90.         return v, d, circle.radius
  91.     except:
  92.         warn(circle)
  93.     return None
  94.  
  95. #def drawPolyline(polyline,count):
  96. #    "returns a Part shape from a dxf polyline"
  97. #    if (len(polyline.points) > 1):
  98. #        edges = []
  99. #        curves = False
  100. #        verts = []
  101. #        for p in range(len(polyline.points)-1):
  102. #            p1 = polyline.points[p]
  103. #            p2 = polyline.points[p+1]
  104. #            v1 = FreeCAD.Vector(round(p1[0],prec),round(p1[1],prec),round(p2[2],prec))
  105. #            v2 = FreeCAD.Vector(round(p2[0],prec),round(p2[1],prec),round(p2[2],prec))
  106. #            verts.append(v1)
  107. #            if not fcvec.equals(v1,v2):
  108. #                if polyline.points[p].bulge:
  109. #                    curves = True
  110. #                    cv = calcBulge(v1,polyline.points[p].bulge,v2)
  111. #                    if fcvec.isColinear([v1,cv,v2]):
  112. #                        #try: edges.append(Part.Line(v1,v2).toShape())
  113. #                        try: f.addGeometry(Part.Line((v1),(v2)))
  114. #                        count = count +1
  115. #                        except: warn(polyline)
  116. #                    else:
  117. #                        #try: edges.append(Part.Arc(v1,cv,v2).toShape())
  118. #                        try: f.addGeometry(Part.Arc(v1,cv,v2))
  119. #                        count = count +1
  120. #                        except: warn(polyline)
  121. #                else:
  122. #                    #try: edges.append(Part.Line(v1,v2).toShape())
  123. #                    try: f.addGeometry(Part.Line((v1),(v2)))
  124. #                    count = count +1
  125. #                    except: warn(polyline)
  126. #        verts.append(v2)
  127. #        if polyline.closed:
  128. #            p1 = polyline.points[len(polyline.points)-1]
  129. #            p2 = polyline.points[0]
  130. #            v1 = FreeCAD.Vector(round(p1[0],prec),round(p1[1],prec),round(p1[2],prec))
  131. #            v2 = FreeCAD.Vector(round(p2[0],prec),round(p2[1],prec),round(p2[2],prec))
  132. #            cv = calcBulge(v1,polyline.points[-1].bulge,v2)
  133. #            if not fcvec.equals(v1,v2):
  134. #                if fcvec.isColinear([v1,cv,v2]):
  135. #                    #try: edges.append(Part.Line(v1,v2).toShape())
  136. #                    try: f.addGeometry(Part.Line((v1),(v2)))
  137. #                    count = count +1
  138. #                    except: warn(polyline)
  139. #                else:
  140. #                    #try: edges.append(Part.Arc(v1,cv,v2).toShape())
  141. #                    try: f.addGeometry(Part.Arc(v1,cv,v2))
  142. #                    count = count +1
  143. #                    except: warn(polyline)
  144. #    return count
  145.  
  146. def addObject(shape,name="Shape",layer=None):
  147.     "adds a new object to the document with passed arguments"
  148.     if isinstance(shape,Part.Shape):
  149.         newob=doc.addObject("Part::Feature",name)
  150.         newob.Shape = shape
  151.     else:
  152.         newob = shape
  153.     if layer:
  154.         lay=locateLayer(layer)
  155.         lay.addObject(newob)
  156.     return newob
  157.  
  158. #def addToBlock(shape,layer):
  159. #    "adds given shape to the layer dict"
  160. #    if layer in layerBlocks:
  161. #        layerBlocks[layer].append(shape)
  162. #    else:
  163. #        layerBlocks[layer] = [shape]
  164.  
  165. def new_sketch(sketch_name):
  166.     FreeCAD.ActiveDocument.addObject("Sketcher::SketchObject",sketch_name)
  167.    
  168. def processdxf(document,filename):
  169.     "this does the translation of the dxf contents into FreeCAD Part objects"
  170.     global drawing # for debugging - so drawing is still accessible to python after the script
  171.     FreeCAD.Console.PrintMessage("opening "+filename+"...\n")
  172.     drawing = readDXF(filename)
  173.     global layers
  174.     layers = []
  175.     global doc
  176.     doc = document
  177.     global blockshapes
  178.     blockshapes = {}
  179.     global badobjects
  180.     badobjects = []
  181.     global layerBlocks
  182.     layerBlocks = {}
  183.     App = FreeCAD
  184.     f = App.activeDocument().addObject("Sketcher::SketchObject","newSketch")
  185.     # getting config parameters
  186.    
  187.     global fmt
  188.     fmt = fcformat(drawing)
  189.     shapes = []
  190.  
  191.     count = 0
  192.  
  193.     # drawing lines
  194.     sketch = 'f'
  195.     lines = drawing.entities.get_type("line")
  196.     if lines: FreeCAD.Console.PrintMessage("drawing "+str(len(lines))+" lines...\n")
  197.     for line in lines:
  198.         if fmt.dxflayout or (not rawValue(line,67)):
  199.             shape = drawLine(line)
  200.             if shape:
  201.                 f.addGeometry(shape)
  202.                 if line.layer == 'Construction':
  203.                     f.toggleConstruction(count)
  204.                 count = count +1
  205.                 FreeCAD.Console.PrintMessage("count = "+ str(count) + "\n")
  206.                 FreeCAD.Console.PrintMessage("layer = "+ line.layer + "\n")
  207.  
  208.     # drawing arcs
  209.     arcs = drawing.entities.get_type("arc")
  210.     if arcs: FreeCAD.Console.PrintMessage("drawing "+str(len(arcs))+" arcs...\n")
  211.     for arc in arcs:
  212.         if fmt.dxflayout or (not rawValue(arc,67)):
  213.             shape = drawArc(arc)
  214.             #print shape
  215.             if shape:
  216.                 f.addGeometry(Part.ArcOfCircle(Part.Circle(shape[0],shape[1],shape[2]),shape[3],shape[4]))
  217.                 if arc.layer == 'Construction':
  218.                     f.toggleConstruction(count)
  219.                 count = count +1
  220.                 FreeCAD.Console.PrintMessage("count = "+ str(count) + "\n")
  221.  
  222.     # drawing circles
  223.     circles = drawing.entities.get_type("circle")
  224.     if circles: FreeCAD.Console.PrintMessage("drawing "+str(len(circles))+" circles...\n")
  225.     for circle in circles:
  226.         if fmt.dxflayout or (not rawValue(circle,67)):
  227.             shape = drawCircle(circle)
  228.             if shape:
  229.                 f.addGeometry(Part.Circle((shape[0]), (shape[1]), (shape[2]) ) )
  230.                 if circle.layer == 'Construction':
  231.                     f.toggleConstruction(count)
  232.                 count = count +1
  233.                 FreeCAD.Console.PrintMessage("count = "+ str(count) + "\n")
  234.  
  235.     # drawing polylines
  236. #    pls = drawing.entities.get_type("lwpolyline")
  237. #    pls.extend(drawing.entities.get_type("polyline"))
  238. #    polylines = []
  239. #    meshes = []
  240. #    for p in pls:
  241. #        if hasattr(p,"flags"):
  242. #            if p.flags in [16,64]:
  243. #                meshes.append(p)
  244. #            else:
  245. #                polylines.append(p)
  246. #        else:
  247. #            polylines.append(p)
  248. #    if polylines: FreeCAD.Console.PrintMessage("drawing "+str(len(polylines))+" polylines...\n")
  249. #    for polyline in polylines:
  250. #        if fmt.dxflayout or (not rawValue(polyline,67)):
  251. #            shape = drawPolyline(polyline,count)
  252. #            if shape:
  253. #                if fmt.join:
  254. #                    if isinstance(shape,Part.Shape):
  255. #                        shapes.append(shape)
  256. #                    else:
  257. #                        shapes.append(shape.Shape)
  258. #                elif fmt.makeBlocks:
  259. #                    if isinstance(shape,Part.Shape):
  260. #                        addToBlock(shape,polyline.layer)
  261. #                    else:                                        
  262. #                        addToBlock(shape.Shape,polyline.layer)              
  263. #                else:
  264. #                    newob = addObject(shape,"Polyline",polyline.layer)
  265. #                    if gui: fmt.formatObject(newob,polyline)
  266.  
  267.     # finishing
  268.  
  269.     doc.recompute()
  270.     FreeCAD.Console.PrintMessage("successfully imported "+filename+"\n")
  271.     if badobjects: print "dxf: ",len(badobjects)," objects were not imported"
  272.     del fmt
  273.     del doc
  274.     del blockshapes
  275.  
  276. def warn(dxfobject):
  277.     "outputs a warning if a dxf object couldn't be imported"
  278.     print "dxf: couldn't import", dxfobject
  279.     badobjects.append(dxfobject)
  280.  
  281. def open(filename):
  282.     "called when freecad opens a file."
  283.     docname = os.path.splitext(os.path.basename(filename))[0]
  284.     doc = FreeCAD.newDocument(docname)
  285.     doc.Label = decodeName(docname)
  286.     processdxf(doc,filename)
  287.     return doc
  288.  
  289. def insert(filename,docname):
  290.     "called when freecad imports a file"
  291.     #groupname = os.path.splitext(os.path.basename(filename))[0]
  292.     try:
  293.         doc=FreeCAD.getDocument(docname)
  294.     except:
  295.         doc=FreeCAD.newDocument(docname)
  296.     #importgroup = doc.addObject("App::DocumentObjectGroup",groupname)
  297.     #importgroup.Label = decodeName(groupname)
  298.     processdxf(doc,filename)
  299.     for l in layers:
  300.         importgroup.addObject(l)
  301.  
  302.  
  303. doc = FreeCAD.ActiveDocument.Name
  304. filename = QtGui.QFileDialog.getOpenFileName(QtGui.qApp.activeWindow(),'Open DXF file','*.txt')
  305. insert(filename,doc)
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement