コード例 #1
0
ファイル: odafc.py プロジェクト: Rahulghuge94/ezdxf
def export_dwg(
    doc: Drawing,
    filename: str,
    version: Optional[str] = None,
    *,
    audit: bool = False,
    replace: bool = False,
) -> None:
    """Use an installed `ODA File Converter`_ to export a DXF document `doc`
    as a DWG file.

    Saves a temporary DXF file and convert this DXF file into a DWG file by the
    ODA File Converter. If `version` is not specified the DXF version of the
    source document is used.

    Args:
        doc: `ezdxf` DXF document as :class:`~ezdxf.drawing.Drawing` object
        filename: export filename of DWG file, extension will be changed to ".dwg"
        version: export file as specific version, by default the same version as
            the source document.
        audit: audit source file by ODA File Converter at exporting
        replace: replace existing DWG file if ``True``

    .. versionchanged:: 0.15

        added `replace` option

    """
    if version is None:
        version = doc.dxfversion
    export_version = VERSION_MAP[version]
    dwg_file = Path(filename).absolute()
    out_folder = Path(dwg_file.parent)
    if dwg_file.exists():
        if replace:
            dwg_file.unlink()
        else:
            raise FileExistsError(f"File already exists: {dwg_file}")
    if out_folder.exists():
        with tempfile.TemporaryDirectory(prefix="odafc_") as tmp_dir:
            dxf_file = Path(tmp_dir) / dwg_file.with_suffix(".dxf").name

            # Save DXF document
            old_filename = doc.filename
            doc.saveas(dxf_file)
            doc.filename = old_filename

            arguments = _odafc_arguments(
                dxf_file.name,
                tmp_dir,
                str(out_folder),
                output_format="DWG",
                version=export_version,
                audit=audit,
            )
            _execute_odafc(arguments)
    else:
        raise FileNotFoundError(
            f"No such file or directory: '{str(out_folder)}'")
コード例 #2
0
def add_graphic_entity_to_root_dict(doc: Drawing):
    msp = doc.modelspace()
    line = msp.add_line((0, 0), (1, 0))
    # Question: is it possible to store graphical entities which reside in a
    # layout in the root dictionary (Autodesk term: the named dictionary)
    # doc.rootdict["LINE"] = line  # this does not work for v0.17 as consequence!
    # HACK HACK HACK!!! - DO NOT USE HANDLES IN PRODUCTION CODE!
    doc.rootdict["LINE"] = line.dxf.handle
コード例 #3
0
def read(stream: TextIO, legacy_mode: bool = False) -> 'Drawing':
    """ Read a DXF document from a text-stream. Open stream in text mode
    (``mode='rt'``) and set correct text encoding, the stream requires at least
    a :meth:`readline` method.

    Since DXF version R2007 (AC1021) file encoding is always "utf-8",
    use the helper function :func:`dxf_stream_info` to detect the required
    text encoding for prior DXF versions.

    If this function struggles to load the DXF document and raises a
    :class:`DXFStructureError` exception, try the :func:`ezdxf.recover.read`
    function to load this corrupt DXF document.

    Args:
        stream: input text stream opened with correct encoding
        legacy_mode: adds an extra trouble shooting import layer if ``True``
            (deprecated)

    Raises:
        DXFStructureError: for invalid DXF structure

    .. deprecated:: v0.14

        argument `legacy_mode`, use module :mod:`ezdxf.recover`
        to load DXF documents with structural flaws.

    """
    from ezdxf.document import Drawing
    if legacy_mode:
        warnings.warn(
            '"legacy_mode" is deprecated (removed in v0.16), replace call by '
            'ezdxf.recover.readfile().', DeprecationWarning)
    return Drawing.read(stream, legacy_mode=legacy_mode)
コード例 #4
0
ファイル: filemanagement.py プロジェクト: yanbin-ha/ezdxf
def read(stream: TextIO) -> 'Drawing':
    """ Read a DXF document from a text-stream. Open stream in text mode
    (``mode='rt'``) and set correct text encoding, the stream requires at least
    a :meth:`readline` method.

    Since DXF version R2007 (AC1021) file encoding is always "utf-8",
    use the helper function :func:`dxf_stream_info` to detect the required
    text encoding for prior DXF versions. To preserve possible binary data in
    use :code:`errors='surrogateescape'` as error handler for the import stream.

    If this function struggles to load the DXF document and raises a
    :class:`DXFStructureError` exception, try the :func:`ezdxf.recover.read`
    function to load this corrupt DXF document.

    Args:
        stream: input text stream opened with correct encoding

    Raises:
        DXFStructureError: for invalid or corrupted DXF structures

    .. deprecated:: v0.14

        argument `legacy_mode`, use module :mod:`ezdxf.recover`
        to load DXF documents with structural flaws.

    """
    from ezdxf.document import Drawing
    return Drawing.read(stream)
コード例 #5
0
def test_has_outside_text_and_arrows(doc: Drawing, angle):
    """The space between extension lines is too narrow to place text and arrows."""
    for dim in measure_fixed_angle(doc.modelspace(), angle=angle):
        render_obj = dim.render()
        assert isinstance(render_obj, _CurvedDimensionLine)
        assert render_obj.arrows_outside is True
        assert render_obj.measurement.text_is_outside is True
        assert render_obj.measurement.is_wide_text is True
コード例 #6
0
def _get_text_visible_when(doc: Drawing, active_layers: Set[str]) -> List[str]:
    ctx = RenderContext(doc)
    # set given layer to ON, others to OFF
    ctx.set_layers_state(active_layers, state=True)

    backend = BasicBackend()
    Frontend(ctx, backend).draw_layout(doc.modelspace())
    visible_text = [x[1] for x in backend.collector if x[0] == 'text']
    return visible_text
コード例 #7
0
def test_has_outside_text_and_arrows_but_not_a_wide_text(doc: Drawing):
    """The space between extension lines is too narrow to place text and arrows,
    but the text alone has enough space.
    """
    for dim in measure_fixed_angle(doc.modelspace(), angle=9):
        render_obj = dim.render()
        assert isinstance(render_obj, _CurvedDimensionLine)
        assert render_obj.arrows_outside is True
        assert render_obj.measurement.text_is_outside is True
        assert render_obj.measurement.is_wide_text is False
コード例 #8
0
def dimstyle():
    doc = Drawing.new()
    doc.blocks.new('left_arrow')
    doc.blocks.new('right_arrow')
    doc.blocks.new('arrow')
    doc.blocks.new('_DOT')
    doc.blocks.new('_OPEN')
    return DimStyle.new('FFFF', doc=doc, dxfattribs={
        'name': 'DIMSTYLE1',
    })
コード例 #9
0
def dimstyle():
    doc = Drawing.new()
    setup_doc(doc)
    return DimStyle.new(
        "FFFF",
        doc=doc,
        dxfattribs={
            "name": "DIMSTYLE1",
        },
    )
コード例 #10
0
def test_text_and_arrows_fit_between_extension_lines(doc: Drawing):
    """There is enough space between extension lines is to place text and
    arrows.
    """
    for dim in measure_fixed_angle(doc.modelspace(), angle=20):
        render_obj = dim.render()
        assert isinstance(render_obj, _CurvedDimensionLine)
        assert render_obj.arrows_outside is False
        assert render_obj.measurement.is_wide_text is False
        assert render_obj.measurement.text_is_outside is False
コード例 #11
0
ファイル: filemanagement.py プロジェクト: Rahulghuge94/ezdxf
def new(
    dxfversion: str = DXF2013,
    setup: Union[str, bool, Sequence[str]] = False,
    units: int = 6,
) -> "Drawing":
    """Create a new :class:`~ezdxf.drawing.Drawing` from scratch, `dxfversion`
    can be either "AC1009" the official DXF version name or "R12" the
    AutoCAD release name.

    :func:`new` can create drawings for following DXF versions:

    ======= ========================
    Version AutoCAD Release
    ======= ========================
    AC1009  AutoCAD R12
    AC1015  AutoCAD R2000
    AC1018  AutoCAD R2004
    AC1021  AutoCAD R2007
    AC1024  AutoCAD R2010
    AC1027  AutoCAD R2013
    AC1032  AutoCAD R2018
    ======= ========================

    The `units` argument defines th document and modelspace units. The header
    variable $MEASUREMENT will be set according to the given `units`, 0 for
    inch, feet, miles, ... and 1 for metric units. For more information go to
    module :mod:`ezdxf.units`

    Args:
        dxfversion: DXF version specifier as string, default is "AC1027"
            respectively "R2013"
        setup: setup default styles, ``False`` for no setup,
            ``True`` to setup everything or a list of topics as strings,
            e.g. ["linetypes", "styles"] to setup only some topics:

            ================== ========================================
            Topic              Description
            ================== ========================================
            linetypes          setup line types
            styles             setup text styles
            dimstyles          setup default `ezdxf` dimension styles
            visualstyles       setup 25 standard visual styles
            ================== ========================================
        units: document and modelspace units, default is 6 for meters

    """
    doc = Drawing.new(dxfversion)
    doc.units = units
    doc.header["$MEASUREMENT"] = 0 if units in (1, 2, 3, 8, 9, 10) else 1
    if setup:
        setup_drawing(doc, topics=setup)
    return doc
コード例 #12
0
    def _setup_doc(self) -> Drawing:
        doc = Drawing(dxfversion=self.specs.version)
        doc.encoding = self.specs.encoding
        doc.header = HeaderSection.new()

        # Setup basic header variables not stored in the header section of the DWG file.
        doc.header["$ACADVER"] = self.specs.version
        doc.header["$ACADMAINTVER"] = self.specs.maintenance_release_version
        doc.header["$DWGCODEPAGE"] = codepage.tocodepage(self.specs.encoding)

        doc.classes = ClassesSection(doc)
        # doc.tables = TablesSection(doc)
        # doc.blocks = BlocksSection(doc)
        # doc.entities = EntitySection(doc)
        # doc.objects = ObjectsSection(doc)
        # doc.acdsdata = AcDsDataSection(doc)
        return doc
コード例 #13
0
def test_fixed_length_extension_lines(doc: Drawing):
    msp = doc.modelspace()
    dim = msp.add_angular_dim_cra(
        center=(0, 0),
        radius=5,
        distance=2,
        start_angle=0,
        end_angle=90,
        override={
            "dimfxlon": 1,  # use fixed length extension lines
            "dimexe": 0.7,  # length "above" the dimension line
            "dimfxl": 0.5,  # length "below" the dimension line
        },
    ).render()
    # only the extension lines are LINE entities:
    for line in dim.dimension.get_geometry_block().query("LINE"):
        length = line.dxf.start.distance(line.dxf.end)
        assert length == pytest.approx(0.5 + 0.7)
コード例 #14
0
ファイル: cad_viewer.py プロジェクト: ericgcc/ezdxf
 def set_document(self, document: Drawing):
     auditor = document.audit()
     error_count = len(auditor.errors)
     if error_count > 0:
         ret = qw.QMessageBox.question(
             self, 'Found DXF Errors',
             f'Found {error_count} errors in file "{document.filename}"\nLoad file anyway? '
         )
         if ret == qw.QMessageBox.No:
             auditor.print_error_report(auditor.errors)
             return
     self.doc = document
     self._render_context = RenderContext(document)
     self._visible_layers = None
     self._current_layout = None
     self._populate_layouts()
     self._populate_layer_list()
     self.draw_layout('Model')
     self.setWindowTitle('CAD Viewer - ' + str(document.filename))
コード例 #15
0
def test_dimension_line_divided_by_measurement_text(doc: Drawing, s, e):
    """Vertical centered measurement text should hide the part of the
    dimension line beneath the text. This creates two arcs instead of one.
    """
    msp = doc.modelspace()
    dim = msp.add_angular_dim_cra(
        center=Vec2(),
        radius=5,
        start_angle=s,
        end_angle=e,
        distance=2,
        override={"dimtad": 0},  # vertical centered text
    )
    dim.render()
    arcs = dim.dimension.get_geometry_block().query("ARC")
    assert len(arcs) == 2
    assert sum(
        arc_angle_span_deg(arc.dxf.start_angle, arc.dxf.end_angle)
        for arc in arcs) < arc_angle_span_deg(
            s, e), "sum of visual arcs should be smaller than the full arc"
コード例 #16
0
def new(dxfversion: str = DXF2013,
        setup: Union[str, bool, Sequence[str]] = False) -> 'Drawing':
    """ Create a new :class:`~ezdxf.drawing.Drawing` from scratch, `dxfversion`
    can be either "AC1009" the official DXF version name or "R12" the
    AutoCAD release name.

    :func:`new` can create drawings for following DXF versions:

    ======= ========================
    Version AutoCAD Release
    ======= ========================
    AC1009  AutoCAD R12
    AC1015  AutoCAD R2000
    AC1018  AutoCAD R2004
    AC1021  AutoCAD R2007
    AC1024  AutoCAD R2010
    AC1027  AutoCAD R2013
    AC1032  AutoCAD R2018
    ======= ========================

    Args:
        dxfversion: DXF version specifier as string, default is "AC1027"
            respectively "R2013"
        setup: setup default styles, ``False`` for no setup,
            ``True`` to setup everything or a list of topics as strings,
            e.g. ["linetypes", "styles"] to setup only some topics:

            ================== ========================================
            Topic              Description
            ================== ========================================
            linetypes          setup line types
            styles             setup text styles
            dimstyles          setup default `ezdxf` dimension styles
            visualstyles       setup 25 standard visual styles
            ================== ========================================

    """
    doc = Drawing.new(dxfversion)
    if setup:
        setup_drawing(doc, topics=setup)
    return doc
コード例 #17
0
def min_r12():
    return Drawing.from_tags(internal_tag_compiler(MINIMALISTIC_DXF12))
コード例 #18
0
def test_dxfversion_1():
    doc = Drawing.from_tags(internal_tag_compiler(TEST_HEADER))
    assert "AC1009" == doc.dxfversion
コード例 #19
0
def dwg_r2000():
    return Drawing.new("AC1015")
コード例 #20
0
def dwg_r12():
    return Drawing.new("AC1009")
コード例 #21
0
def doc():
    return Drawing.new("r2018")
コード例 #22
0
ファイル: filemanagement.py プロジェクト: yanbin-ha/ezdxf
def readfile(filename: Union[str, 'Path'],
             encoding: str = None,
             errors: str = 'surrogateescape') -> 'Drawing':
    """  Read the DXF document `filename` from the file-system.

    This is the preferred method to load existing ASCII or Binary DXF files,
    the required text encoding will be detected automatically and decoding
    errors will be ignored.

    Override encoding detection by setting argument `encoding` to the
    estimated encoding. (use Python encoding names like in the :func:`open`
    function).

    If this function struggles to load the DXF document and raises a
    :class:`DXFStructureError` exception, try the :func:`ezdxf.recover.readfile`
    function to load this corrupt DXF document.

    Args:
        filename: filename of the ASCII- or Binary DXF document
        encoding: use ``None`` for auto detect (default), or set a specific
            encoding like "utf-8", argument is ignored for Binary DXF files
        errors: specify decoding error handler

            - "surrogateescape" to preserve possible binary data (default)
            - "ignore" to use the replacement char U+FFFD "\ufffd" for invalid data
            - "strict" to raise an :class:`UnicodeDecodeError` exception for invalid data

    Raises:
        IOError: not a DXF file or file does not exist
        DXFStructureError: for invalid or corrupted DXF structures
        UnicodeDecodeError: if `errors` is "strict" and a decoding error occurs

    .. deprecated:: v0.14

        argument `legacy_mode`, use module :mod:`ezdxf.recover`
        to load DXF documents with structural flaws.

    """
    from ezdxf.lldxf.validator import is_dxf_file, is_binary_dxf_file
    from ezdxf.tools.codepage import is_supported_encoding
    from ezdxf.lldxf.tagger import binary_tags_loader

    filename = str(filename)
    if is_binary_dxf_file(filename):
        with open(filename, 'rb') as fp:
            data = fp.read()
            loader = binary_tags_loader(data, errors=errors)
            return Drawing.load(loader)

    if not is_dxf_file(filename):
        raise IOError(f"File '{filename}' is not a DXF file.")

    info = dxf_file_info(filename)
    if encoding is not None:
        # override default encodings if absolute necessary
        info.encoding = encoding
    with open(filename, mode='rt', encoding=info.encoding,
              errors=errors) as fp:
        doc = read(fp)

    doc.filename = filename
    if encoding is not None and is_supported_encoding(encoding):
        # store overridden encoding if supported by AutoCAD, else default
        # encoding stored in $DWGENCODING is used as document encoding or
        # 'cp1252' if $DWGENCODING is unset.
        doc.encoding = encoding
    return doc
コード例 #23
0
def doc():
    return Drawing.new('r2018')
コード例 #24
0
def readfile(filename: str,
             encoding: str = None,
             legacy_mode: bool = False) -> 'Drawing':
    """  Read the DXF document `filename` from the file-system.

    This is the preferred method to load existing ASCII or Binary DXF files,
    the required text encoding will be detected automatically and decoding
    errors will be ignored.

    Override encoding detection by setting argument `encoding` to the
    estimated encoding. (use Python encoding names like in the :func:`open`
    function).

    If this function struggles to load the DXF document and raises a
    :class:`DXFStructureError` exception, try the :func:`ezdxf.recover.readfile`
    function to load this corrupt DXF document.

    Args:
        filename: filename of the ASCII- or Binary DXF document
        encoding: use ``None`` for auto detect (default), or set a specific
            encoding like "utf-8", argument is ignored for Binary DXF files
        legacy_mode: adds an extra trouble shooting import layer if ``True``
            (deprecated)

    Raises:
        IOError: File `filename` is not a DXF file or does not exist.
        DXFStructureError: for invalid DXF structure

    .. deprecated:: v0.14

        argument `legacy_mode`, use module :mod:`ezdxf.recover`
        to load DXF documents with structural flaws.

    """
    from ezdxf.lldxf.validator import is_dxf_file, is_binary_dxf_file
    from ezdxf.tools.codepage import is_supported_encoding
    from ezdxf.lldxf.tagger import binary_tags_loader
    if legacy_mode:
        warnings.warn(
            '"legacy_mode" is deprecated (removed in v0.16), replace call by '
            'ezdxf.recover.read().', DeprecationWarning)

    filename = str(filename)
    if is_binary_dxf_file(filename):
        with open(filename, 'rb') as fp:
            data = fp.read()
            loader = binary_tags_loader(data)
            return Drawing.load(loader, legacy_mode)

    if not is_dxf_file(filename):
        raise IOError("File '{}' is not a DXF file.".format(filename))

    info = dxf_file_info(filename)
    if encoding is not None:
        # override default encodings if absolute necessary
        info.encoding = encoding
    with open(filename, mode='rt', encoding=info.encoding,
              errors='ignore') as fp:
        doc = read(fp, legacy_mode=legacy_mode)

    doc.filename = filename
    if encoding is not None and is_supported_encoding(encoding):
        # store overridden encoding if supported by AutoCAD, else default
        # encoding stored in $DWGENCODING is used as document encoding or
        # 'cp1252' if $DWGENCODING is unset.
        doc.encoding = encoding
    return doc
コード例 #25
0
def dwg_r12():
    return Drawing.new('AC1009')
コード例 #26
0
def dwg_r2000():
    return Drawing.new('AC1015')