Skip to content
Snippets Groups Projects
import_svg.py 28.7 KiB
Newer Older


class SVGGeometryDEFS(SVGGeometryContainer):
    """
    Container for referenced elements
    """

    def _doCreateGeom(self):
        """
        Create real geometries
        """

        pass


class SVGGeometrySYMBOL(SVGGeometryContainer):
    """
    Referenced element
    """

    def _doCreateGeom(self):
        """
        Create real geometries
        """

        pass


class SVGGeometryG(SVGGeometryContainer):
    """
    Geometry group
    """

    pass


class SVGGeometryUSE(SVGGeometry):
    """
    User of referenced elements
    """

    def _doCreateGeom(self):
        """
        Create real geometries
        """

        geometries = []
        ref = self._node.getAttribute('xlink:href')
        geom = self._context['defines'].get(ref)

        if geom is not None:
            self._pushMatrix(self.getNodeMatrix())
            self._pushMatrix(geom.getNodeMatrix())

            if isinstance(geom, SVGGeometryContainer):
                geometries = geom.getGeometries()
            else:
                geometries = [geom]

            for g in geometries:
                g.createGeom()

            self._popMatrix()
            self._popMatrix()


class SVGGeometrySVG(SVGGeometryContainer):
    """
    Main geometry holder
    """

    def _doCreateGeom(self):
        """
        Create real geometries
        """

        rect = SVGRectFromNode(self._node, self._context)

        self._pushMatrix(self.getNodeMatrix())
        self._pushRect(rect)

        super()._doCreateGeom()

        self._popRect()
        self._popMatrix()


class SVGLoader(SVGGeometryContainer):
    """
    SVG file loader
    """

    def __init__(self, filepath):
        """
        Initialize SVG loader
        """

        node = xml.dom.minidom.parse(filepath)

        m = Matrix()
        m = m * m.Scale(1.0 / 90.0, 4, Vector((1.0, 0.0, 0.0)))
        m = m * m.Scale(-1.0 / 90.0, 4, Vector((0.0, 1.0, 0.0)))

        rect = (1, 1)

        self._context = {'defines': {},
                         'transform': [],
                         'rects': [rect],
                         'rect': rect,
                         'matrix': m,
                         'materials': {}}

        super().__init__(node, self._context)


svgGeometryClasses = {
    'svg': SVGGeometrySVG,
    'path': SVGGeometryPATH,
    'defs': SVGGeometryDEFS,
    'symbol': SVGGeometrySYMBOL,
    'use': SVGGeometryUSE,
    'g': SVGGeometryG}


def parseAbstractNode(node, context):
    name = node.tagName.lower()
    geomClass = svgGeometryClasses.get(name)

    if geomClass is not None:
        ob = geomClass(node, context)
        ob.parse()

        return ob

    return None


def load_svg(filepath):
    """
    Load specified SVG file
    """

    if bpy.ops.object.mode_set.poll():
        bpy.ops.object.mode_set(mode='OBJECT')

    loader = SVGLoader(filepath)
    loader.parse()
    loader.createGeom()


def load(operator, context, filepath=""):

    load_svg(filepath)

    return {'FINISHED'}