diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml
index b2e2b4e758..eede2a8aa7 100644
--- a/.pre-commit-config.yaml
+++ b/.pre-commit-config.yaml
@@ -13,6 +13,7 @@ files: |
src/Mod/BIM|
src/Mod/CAM|
src/Mod/Cloud|
+ src/Mod/Draft|
src/Mod/Fem|
src/Mod/Help|
src/Mod/Import|
diff --git a/src/Mod/Draft/App/AppDraftUtils.cpp b/src/Mod/Draft/App/AppDraftUtils.cpp
index a6742cd5fd..a56f6a42c1 100644
--- a/src/Mod/Draft/App/AppDraftUtils.cpp
+++ b/src/Mod/Draft/App/AppDraftUtils.cpp
@@ -26,7 +26,8 @@
#include
-namespace DraftUtils {
+namespace DraftUtils
+{
extern PyObject* initModule();
}
@@ -37,7 +38,7 @@ PyMOD_INIT_FUNC(DraftUtils)
try {
Base::Interpreter().loadModule("Part");
}
- catch(const Base::Exception& e) {
+ catch (const Base::Exception& e) {
PyErr_SetString(PyExc_ImportError, e.what());
PyMOD_Return(nullptr);
}
diff --git a/src/Mod/Draft/App/AppDraftUtilsPy.cpp b/src/Mod/Draft/App/AppDraftUtilsPy.cpp
index a0ab38b580..831b7841c8 100644
--- a/src/Mod/Draft/App/AppDraftUtilsPy.cpp
+++ b/src/Mod/Draft/App/AppDraftUtilsPy.cpp
@@ -25,20 +25,25 @@
#include
-namespace DraftUtils {
-class Module : public Py::ExtensionModule
+namespace DraftUtils
+{
+class Module: public Py::ExtensionModule
{
public:
- Module() : Py::ExtensionModule("DraftUtils")
+ Module()
+ : Py::ExtensionModule("DraftUtils")
{
- add_varargs_method("readDXF",&Module::readDXF,
- "readDXF(filename,[document,ignore_errors]): "
- "Imports a DXF file into the given document. "
- "ignore_errors is True by default. "
- "NOTE: DraftUtils.readDXF is removed. "
- "Use Import.readDxf instead."
- );
- initialize("The DraftUtils module contains utility functions for the Draft module."); // register with Python
+ add_varargs_method("readDXF",
+ &Module::readDXF,
+ "readDXF(filename,[document,ignore_errors]): "
+ "Imports a DXF file into the given document. "
+ "ignore_errors is True by default. "
+ "NOTE: DraftUtils.readDXF is removed. "
+ "Use Import.readDxf instead.");
+ initialize(
+ "The DraftUtils module contains utility functions for the Draft module."); // register
+ // with
+ // Python
}
private:
@@ -55,4 +60,4 @@ PyObject* initModule()
return Base::Interpreter().addModule(new Module);
}
-} // namespace DraftUtils
+} // namespace DraftUtils
diff --git a/src/Mod/Draft/Draft.py b/src/Mod/Draft/Draft.py
index 558dcfd68e..f32d14773b 100644
--- a/src/Mod/Draft/Draft.py
+++ b/src/Mod/Draft/Draft.py
@@ -35,6 +35,7 @@ import FreeCAD as App
if App.GuiUp:
import Draft_rc
+
gui = True
# To prevent complaints from code checkers (flake8)
True if Draft_rc.__name__ else False
@@ -42,8 +43,9 @@ else:
gui = False
__title__ = "FreeCAD Draft Workbench"
-__author__ = ("Yorik van Havre, Werner Mayer, Martin Burbaum, Ken Cline, "
- "Dmitry Chigrin, Daniel Falck")
+__author__ = (
+ "Yorik van Havre, Werner Mayer, Martin Burbaum, Ken Cline, " "Dmitry Chigrin, Daniel Falck"
+)
__url__ = "https://www.freecad.org"
# ---------------------------------------------------------------------------
@@ -51,80 +53,80 @@ __url__ = "https://www.freecad.org"
# ---------------------------------------------------------------------------
from draftutils.utils import ARROW_TYPES as arrowtypes
-from draftutils.utils import (type_check,
- typecheck,
- precision,
- tolerance)
+from draftutils.utils import type_check, typecheck, precision, tolerance
-from draftutils.utils import (get_real_name,
- getRealName,
- get_type,
- getType,
- get_objects_of_type,
- getObjectsOfType,
- is_clone,
- isClone,
- get_clone_base,
- getCloneBase,
- print_shape,
- printShape,
- compare_objects,
- compareObjects,
- shapify,
- is_closed_edge)
+from draftutils.utils import (
+ get_real_name,
+ getRealName,
+ get_type,
+ getType,
+ get_objects_of_type,
+ getObjectsOfType,
+ is_clone,
+ isClone,
+ get_clone_base,
+ getCloneBase,
+ print_shape,
+ printShape,
+ compare_objects,
+ compareObjects,
+ shapify,
+ is_closed_edge,
+)
-from draftutils.utils import (string_encode_coin,
- stringencodecoin,
- load_svg_patterns,
- loadSvgPatterns,
- svg_patterns,
- svgpatterns,
- get_rgb,
- getrgb,
- argb_to_rgba,
- rgba_to_argb,
- get_rgba_tuple)
+from draftutils.utils import (
+ string_encode_coin,
+ stringencodecoin,
+ load_svg_patterns,
+ loadSvgPatterns,
+ svg_patterns,
+ svgpatterns,
+ get_rgb,
+ getrgb,
+ argb_to_rgba,
+ rgba_to_argb,
+ get_rgba_tuple,
+)
-from draftfunctions.svg import (get_svg,
- getSVG)
+from draftfunctions.svg import get_svg, getSVG
-from draftfunctions.dxf import (get_dxf,
- getDXF)
+from draftfunctions.dxf import get_dxf, getDXF
-from draftutils.gui_utils import (get3DView,
- get_3d_view,
- autogroup,
- removeHidden,
- remove_hidden,
- get_diffuse_color,
- apply_current_style,
- restore_view_object,
- formatObject,
- format_object,
- getSelection,
- get_selection,
- getSelectionEx,
- get_selection_ex,
- select,
- loadTexture,
- load_texture,
- get_bbox,
- end_all_events)
+from draftutils.gui_utils import (
+ get3DView,
+ get_3d_view,
+ autogroup,
+ removeHidden,
+ remove_hidden,
+ get_diffuse_color,
+ apply_current_style,
+ restore_view_object,
+ formatObject,
+ format_object,
+ getSelection,
+ get_selection,
+ getSelectionEx,
+ get_selection_ex,
+ select,
+ loadTexture,
+ load_texture,
+ get_bbox,
+ end_all_events,
+)
-from draftutils.gui_utils import (dim_symbol,
- dimSymbol,
- dim_dash,
- dimDash)
+from draftutils.gui_utils import dim_symbol, dimSymbol, dim_dash, dimDash
-from draftutils.groups import (is_group,
- get_group_names,
- getGroupNames,
- ungroup,
- get_windows,
- get_group_contents,
- getGroupContents,
- get_movable_children,
- getMovableChildren)
+from draftutils.groups import (
+ is_group,
+ get_group_names,
+ getGroupNames,
+ ungroup,
+ get_windows,
+ get_group_contents,
+ getGroupContents,
+ get_movable_children,
+ getMovableChildren,
+)
# ---------------------------------------------------------------------------
# Draft functions
@@ -143,25 +145,13 @@ from draftfunctions.fuse import fuse
from draftfunctions.heal import heal
-from draftfunctions.move import (move,
- move_vertex,
- move_edge,
- copy_moved_edge)
+from draftfunctions.move import move, move_vertex, move_edge, copy_moved_edge
-from draftfunctions.rotate import (rotate,
- rotate_vertex,
- rotate_edge,
- copy_rotated_edge)
+from draftfunctions.rotate import rotate, rotate_vertex, rotate_edge, copy_rotated_edge
-from draftfunctions.scale import (scale,
- scale_vertex,
- scale_edge,
- copy_scaled_edge)
+from draftfunctions.scale import scale, scale_vertex, scale_edge, copy_scaled_edge
-from draftfunctions.join import (join_wires,
- joinWires,
- join_two_wires,
- joinTwoWires)
+from draftfunctions.join import join_wires, joinWires, join_two_wires, joinTwoWires
from draftfunctions.split import split
@@ -177,178 +167,135 @@ from draftfunctions.upgrade import upgrade
# ---------------------------------------------------------------------------
# base object
-from draftobjects.base import (DraftObject,
- _DraftObject)
+from draftobjects.base import DraftObject, _DraftObject
# base viewprovider
-from draftviewproviders.view_base import (ViewProviderDraft,
- _ViewProviderDraft,
- ViewProviderDraftAlt,
- _ViewProviderDraftAlt,
- ViewProviderDraftPart,
- _ViewProviderDraftPart)
+from draftviewproviders.view_base import (
+ ViewProviderDraft,
+ _ViewProviderDraft,
+ ViewProviderDraftAlt,
+ _ViewProviderDraftAlt,
+ ViewProviderDraftPart,
+ _ViewProviderDraftPart,
+)
# App::Link support, used by the arrays
-from draftobjects.draftlink import (DraftLink,
- _DraftLink)
-from draftviewproviders.view_draftlink import (ViewProviderDraftLink,
- _ViewProviderDraftLink)
+from draftobjects.draftlink import DraftLink, _DraftLink
+from draftviewproviders.view_draftlink import ViewProviderDraftLink, _ViewProviderDraftLink
# circle
-from draftobjects.circle import (Circle,
- _Circle)
-from draftmake.make_circle import (make_circle,
- makeCircle)
+from draftobjects.circle import Circle, _Circle
+from draftmake.make_circle import make_circle, makeCircle
# arcs
from draftmake.make_arc_3points import make_arc_3points
-
# ellipse
-from draftobjects.ellipse import (Ellipse,
- _Ellipse)
-from draftmake.make_ellipse import (make_ellipse,
- makeEllipse)
+from draftobjects.ellipse import Ellipse, _Ellipse
+from draftmake.make_ellipse import make_ellipse, makeEllipse
# rectangle
-from draftobjects.rectangle import (Rectangle,
- _Rectangle)
-from draftmake.make_rectangle import (make_rectangle,
- makeRectangle)
+from draftobjects.rectangle import Rectangle, _Rectangle
+from draftmake.make_rectangle import make_rectangle, makeRectangle
if App.GuiUp:
- from draftviewproviders.view_rectangle import (ViewProviderRectangle,
- _ViewProviderRectangle)
+ from draftviewproviders.view_rectangle import ViewProviderRectangle, _ViewProviderRectangle
# polygon
-from draftobjects.polygon import (Polygon,
- _Polygon)
-from draftmake.make_polygon import (make_polygon,
- makePolygon)
+from draftobjects.polygon import Polygon, _Polygon
+from draftmake.make_polygon import make_polygon, makePolygon
# wire and line
-from draftobjects.wire import (Wire,
- _Wire)
+from draftobjects.wire import Wire, _Wire
-from draftmake.make_line import (make_line,
- makeLine)
-from draftmake.make_wire import (make_wire,
- makeWire)
+from draftmake.make_line import make_line, makeLine
+from draftmake.make_wire import make_wire, makeWire
if App.GuiUp:
- from draftviewproviders.view_wire import (ViewProviderWire,
- _ViewProviderWire)
+ from draftviewproviders.view_wire import ViewProviderWire, _ViewProviderWire
# bspline
-from draftobjects.bspline import (BSpline,
- _BSpline)
-from draftmake.make_bspline import (make_bspline,
- makeBSpline)
+from draftobjects.bspline import BSpline, _BSpline
+from draftmake.make_bspline import make_bspline, makeBSpline
if App.GuiUp:
- from draftviewproviders.view_bspline import (ViewProviderBSpline,
- _ViewProviderBSpline)
+ from draftviewproviders.view_bspline import ViewProviderBSpline, _ViewProviderBSpline
# bezcurve
-from draftobjects.bezcurve import (BezCurve,
- _BezCurve)
-from draftmake.make_bezcurve import (make_bezcurve,
- makeBezCurve)
+from draftobjects.bezcurve import BezCurve, _BezCurve
+from draftmake.make_bezcurve import make_bezcurve, makeBezCurve
if App.GuiUp:
- from draftviewproviders.view_bezcurve import (ViewProviderBezCurve,
- _ViewProviderBezCurve)
+ from draftviewproviders.view_bezcurve import ViewProviderBezCurve, _ViewProviderBezCurve
# copy
from draftmake.make_copy import make_copy
from draftmake.make_copy import make_copy as makeCopy
# clone
-from draftobjects.clone import (Clone,
- _Clone)
-from draftmake.make_clone import (make_clone,
- clone)
+from draftobjects.clone import Clone, _Clone
+from draftmake.make_clone import make_clone, clone
if App.GuiUp:
- from draftviewproviders.view_clone import (ViewProviderClone,
- _ViewProviderClone)
+ from draftviewproviders.view_clone import ViewProviderClone, _ViewProviderClone
# point
-from draftobjects.point import (Point,
- _Point)
-from draftmake.make_point import (make_point,
- makePoint)
+from draftobjects.point import Point, _Point
+from draftmake.make_point import make_point, makePoint
if App.GuiUp:
- from draftviewproviders.view_point import (ViewProviderPoint,
- _ViewProviderPoint)
+ from draftviewproviders.view_point import ViewProviderPoint, _ViewProviderPoint
# arrays
-from draftobjects.array import (Array,
- _Array)
-from draftmake.make_array import (make_array,
- makeArray)
-from draftmake.make_orthoarray import (make_ortho_array,
- make_ortho_array2d,
- make_rect_array,
- make_rect_array2d)
+from draftobjects.array import Array, _Array
+from draftmake.make_array import make_array, makeArray
+from draftmake.make_orthoarray import (
+ make_ortho_array,
+ make_ortho_array2d,
+ make_rect_array,
+ make_rect_array2d,
+)
from draftmake.make_polararray import make_polar_array
from draftmake.make_circulararray import make_circular_array
-from draftobjects.patharray import (PathArray,
- _PathArray)
-from draftmake.make_patharray import (make_path_array,
- makePathArray,
- make_path_twisted_array)
+from draftobjects.patharray import PathArray, _PathArray
+from draftmake.make_patharray import make_path_array, makePathArray, make_path_twisted_array
-from draftobjects.pointarray import (PointArray,
- _PointArray)
-from draftmake.make_pointarray import (make_point_array,
- makePointArray)
+from draftobjects.pointarray import PointArray, _PointArray
+from draftmake.make_pointarray import make_point_array, makePointArray
if App.GuiUp:
- from draftviewproviders.view_array import (ViewProviderDraftArray,
- _ViewProviderDraftArray)
+ from draftviewproviders.view_array import ViewProviderDraftArray, _ViewProviderDraftArray
# facebinder
-from draftobjects.facebinder import (Facebinder,
- _Facebinder)
-from draftmake.make_facebinder import (make_facebinder,
- makeFacebinder)
+from draftobjects.facebinder import Facebinder, _Facebinder
+from draftmake.make_facebinder import make_facebinder, makeFacebinder
if App.GuiUp:
- from draftviewproviders.view_facebinder import (ViewProviderFacebinder,
- _ViewProviderFacebinder)
+ from draftviewproviders.view_facebinder import ViewProviderFacebinder, _ViewProviderFacebinder
# shapestring
-from draftobjects.block import (Block,
- _Block)
-from draftmake.make_block import (make_block,
- makeBlock)
+from draftobjects.block import Block, _Block
+from draftmake.make_block import make_block, makeBlock
# shapestring
-from draftobjects.shapestring import (ShapeString,
- _ShapeString)
-from draftmake.make_shapestring import (make_shapestring,
- makeShapeString)
+from draftobjects.shapestring import ShapeString, _ShapeString
+from draftmake.make_shapestring import make_shapestring, makeShapeString
+
if App.GuiUp:
from draftviewproviders.view_shapestring import ViewProviderShapeString
# shape 2d view
-from draftobjects.shape2dview import (Shape2DView,
- _Shape2DView)
-from draftmake.make_shape2dview import (make_shape2dview,
- makeShape2DView)
+from draftobjects.shape2dview import Shape2DView, _Shape2DView
+from draftmake.make_shape2dview import make_shape2dview, makeShape2DView
# sketch
-from draftmake.make_sketch import (make_sketch,
- makeSketch)
+from draftmake.make_sketch import make_sketch, makeSketch
# working plane proxy
from draftobjects.wpproxy import WorkingPlaneProxy
-from draftmake.make_wpproxy import (make_workingplaneproxy,
- makeWorkingPlaneProxy)
+from draftmake.make_wpproxy import make_workingplaneproxy, makeWorkingPlaneProxy
if App.GuiUp:
from draftviewproviders.view_wpproxy import ViewProviderWorkingPlaneProxy
@@ -359,59 +306,49 @@ from draftmake.make_fillet import make_fillet
if App.GuiUp:
from draftviewproviders.view_fillet import ViewProviderFillet
-from draftobjects.layer import (Layer,
- _VisGroup,
- get_layer)
+from draftobjects.layer import Layer, _VisGroup, get_layer
from draftmake.make_layer import make_layer
if App.GuiUp:
- from draftviewproviders.view_layer import (ViewProviderLayer,
- _ViewProviderVisGroup)
+ from draftviewproviders.view_layer import ViewProviderLayer, _ViewProviderVisGroup
# Annotation objects
-from draftobjects.dimension import (LinearDimension,
- _Dimension,
- AngularDimension,
- _AngularDimension)
-from draftmake.make_dimension import (make_dimension,
- makeDimension,
- make_linear_dimension,
- make_linear_dimension_obj,
- make_radial_dimension_obj,
- make_angular_dimension,
- makeAngularDimension)
+from draftobjects.dimension import LinearDimension, _Dimension, AngularDimension, _AngularDimension
+from draftmake.make_dimension import (
+ make_dimension,
+ makeDimension,
+ make_linear_dimension,
+ make_linear_dimension_obj,
+ make_radial_dimension_obj,
+ make_angular_dimension,
+ makeAngularDimension,
+)
if App.GuiUp:
- from draftviewproviders.view_dimension \
- import (ViewProviderLinearDimension,
- _ViewProviderDimension,
- ViewProviderAngularDimension,
- _ViewProviderAngularDimension)
+ from draftviewproviders.view_dimension import (
+ ViewProviderLinearDimension,
+ _ViewProviderDimension,
+ ViewProviderAngularDimension,
+ _ViewProviderAngularDimension,
+ )
-from draftobjects.label import (Label,
- DraftLabel)
-from draftmake.make_label import (make_label,
- makeLabel)
+from draftobjects.label import Label, DraftLabel
+from draftmake.make_label import make_label, makeLabel
if App.GuiUp:
- from draftviewproviders.view_label import (ViewProviderLabel,
- ViewProviderDraftLabel)
+ from draftviewproviders.view_label import ViewProviderLabel, ViewProviderDraftLabel
-from draftobjects.text import (Text,
- DraftText)
-from draftmake.make_text import (make_text,
- makeText,
- convert_draft_texts,
- convertDraftTexts)
+from draftobjects.text import Text, DraftText
+from draftmake.make_text import make_text, makeText, convert_draft_texts, convertDraftTexts
if App.GuiUp:
- from draftviewproviders.view_text import (ViewProviderText,
- ViewProviderDraftText)
+ from draftviewproviders.view_text import ViewProviderText, ViewProviderDraftText
+
+from draftobjects.hatch import Hatch
+from draftmake.make_hatch import make_hatch
-from draftobjects.hatch import (Hatch)
-from draftmake.make_hatch import (make_hatch)
if App.GuiUp:
- from draftviewproviders.view_hatch import (ViewProviderDraftHatch)
+ from draftviewproviders.view_hatch import ViewProviderDraftHatch
## @}
diff --git a/src/Mod/Draft/DraftGeomUtils.py b/src/Mod/Draft/DraftGeomUtils.py
index 0f76da33cb..227cca9fcc 100644
--- a/src/Mod/Draft/DraftGeomUtils.py
+++ b/src/Mod/Draft/DraftGeomUtils.py
@@ -40,130 +40,130 @@ __author__ = "Yorik van Havre, Jacques-Antoine Gaudin, Ken Cline"
__url__ = ["https://www.freecad.org"]
# Doesn't need requisites
-from draftgeoutils.linear_algebra import (linearFromPoints,
- determinant)
+from draftgeoutils.linear_algebra import linearFromPoints, determinant
# Needs math, Part, and vector tools
from draftgeoutils.general import NORM
-from draftgeoutils.general import (precision,
- vec,
- edg,
- getVerts,
- v1,
- isNull,
- isPtOnEdge,
- hasCurves,
- isAligned,
- getQuad,
- areColinear,
- hasOnlyWires,
- geomType,
- isValidPath,
- findClosest,
- getBoundaryAngles)
+from draftgeoutils.general import (
+ precision,
+ vec,
+ edg,
+ getVerts,
+ v1,
+ isNull,
+ isPtOnEdge,
+ hasCurves,
+ isAligned,
+ getQuad,
+ areColinear,
+ hasOnlyWires,
+ geomType,
+ isValidPath,
+ findClosest,
+ getBoundaryAngles,
+)
# Needs general functions
-from draftgeoutils.geometry import (findPerpendicular,
- findDistance,
- getSplineNormal,
- get_spline_normal,
- getNormal,
- get_normal,
- get_shape_normal,
- getRotation,
- isPlanar,
- is_planar,
- calculatePlacement,
- mirror,
- are_coplanar,
- is_straight_line,
- mirror_matrix,
- uv_vectors_from_face,
- placement_from_face,
- placement_from_points,
- distance_to_plane,
- project_point_on_plane)
+from draftgeoutils.geometry import (
+ findPerpendicular,
+ findDistance,
+ getSplineNormal,
+ get_spline_normal,
+ getNormal,
+ get_normal,
+ get_shape_normal,
+ getRotation,
+ isPlanar,
+ is_planar,
+ calculatePlacement,
+ mirror,
+ are_coplanar,
+ is_straight_line,
+ mirror_matrix,
+ uv_vectors_from_face,
+ placement_from_face,
+ placement_from_points,
+ distance_to_plane,
+ project_point_on_plane,
+)
-from draftgeoutils.edges import (findEdge,
- orientEdge,
- isSameLine,
- isLine,
- is_line,
- invert,
- findMidpoint,
- getTangent,
- get_referenced_edges)
+from draftgeoutils.edges import (
+ findEdge,
+ orientEdge,
+ isSameLine,
+ isLine,
+ is_line,
+ invert,
+ findMidpoint,
+ getTangent,
+ get_referenced_edges,
+)
-from draftgeoutils.faces import (concatenate,
- getBoundary,
- isCoplanar,
- is_coplanar,
- bind,
- cleanFaces,
- removeSplitter)
+from draftgeoutils.faces import (
+ concatenate,
+ getBoundary,
+ isCoplanar,
+ is_coplanar,
+ bind,
+ cleanFaces,
+ removeSplitter,
+)
-from draftgeoutils.arcs import (isClockwise,
- isWideAngle,
- arcFrom2Pts,
- arcFromSpline)
+from draftgeoutils.arcs import isClockwise, isWideAngle, arcFrom2Pts, arcFromSpline
-from draftgeoutils.cuboids import (isCubic,
- getCubicDimensions)
+from draftgeoutils.cuboids import isCubic, getCubicDimensions
# Needs geometry functions
-from draftgeoutils.circle_inversion import (pointInversion,
- polarInversion,
- circleInversion)
+from draftgeoutils.circle_inversion import pointInversion, polarInversion, circleInversion
# Needs edges functions
-from draftgeoutils.sort_edges import (sortEdges,
- sortEdgesOld)
+from draftgeoutils.sort_edges import sortEdges, sortEdgesOld
-from draftgeoutils.intersections import (findIntersection,
- wiresIntersect,
- connect,
- angleBisection)
+from draftgeoutils.intersections import findIntersection, wiresIntersect, connect, angleBisection
-from draftgeoutils.wires import (findWires,
- findWiresOld,
- findWiresOld2,
- flattenWire,
- superWire,
- isReallyClosed,
- curvetowire,
- curvetosegment,
- rebaseWire,
- removeInterVertices,
- cleanProjection,
- tessellateProjection,
- get_placement_perpendicular_to_wire,
- get_extended_wire)
+from draftgeoutils.wires import (
+ findWires,
+ findWiresOld,
+ findWiresOld2,
+ flattenWire,
+ superWire,
+ isReallyClosed,
+ curvetowire,
+ curvetosegment,
+ rebaseWire,
+ removeInterVertices,
+ cleanProjection,
+ tessellateProjection,
+ get_placement_perpendicular_to_wire,
+ get_extended_wire,
+)
# Needs wires functions
-from draftgeoutils.fillets import (fillet,
- filletWire)
+from draftgeoutils.fillets import fillet, filletWire
# Needs intersections functions
-from draftgeoutils.offsets import (pocket2d,
- offset,
- offsetWire)
+from draftgeoutils.offsets import pocket2d, offset, offsetWire
-from draftgeoutils.circles import (findClosestCircle,
- getCircleFromSpline,
- circlefrom1Line2Points,
- circlefrom2Lines1Point,
- circleFrom2LinesRadius,
- circleFrom3LineTangents,
- circleFromPointLineRadius,
- circleFrom2PointsRadius,
- findHomotheticCenterOfCircles,
- findRadicalAxis,
- findRadicalCenter)
+from draftgeoutils.circles import (
+ findClosestCircle,
+ getCircleFromSpline,
+ circlefrom1Line2Points,
+ circlefrom2Lines1Point,
+ circleFrom2LinesRadius,
+ circleFrom3LineTangents,
+ circleFromPointLineRadius,
+ circleFrom2PointsRadius,
+ findHomotheticCenterOfCircles,
+ findRadicalAxis,
+ findRadicalCenter,
+)
-from draftgeoutils.circles_apollonius import (outerSoddyCircle,
- innerSoddyCircle,
- circleFrom3CircleTangents)
+from draftgeoutils.circles_apollonius import (
+ outerSoddyCircle,
+ innerSoddyCircle,
+ circleFrom3CircleTangents,
+)
# Needs circles_apollonius functions
# These functions are not imported because they are incomplete;
diff --git a/src/Mod/Draft/DraftGlobal.h b/src/Mod/Draft/DraftGlobal.h
index 645fdca2e8..25f942fcbf 100644
--- a/src/Mod/Draft/DraftGlobal.h
+++ b/src/Mod/Draft/DraftGlobal.h
@@ -29,10 +29,10 @@
// Draft
#ifndef DraftUtilsExport
#ifdef DraftUtils_EXPORTS
-# define DraftUtilsExport FREECAD_DECL_EXPORT
+#define DraftUtilsExport FREECAD_DECL_EXPORT
#else
-# define DraftUtilsExport FREECAD_DECL_IMPORT
+#define DraftUtilsExport FREECAD_DECL_IMPORT
#endif
#endif
-#endif //DRAFT_GLOBAL_H
+#endif // DRAFT_GLOBAL_H
diff --git a/src/Mod/Draft/DraftGui.py b/src/Mod/Draft/DraftGui.py
index d11ed0598d..e8d8861db0 100644
--- a/src/Mod/Draft/DraftGui.py
+++ b/src/Mod/Draft/DraftGui.py
@@ -1,26 +1,26 @@
# -*- coding: utf8 -*-
-#***************************************************************************
-#* Copyright (c) 2009 Yorik van Havre *
-#* *
-#* This program is free software; you can redistribute it and/or modify *
-#* it under the terms of the GNU Lesser General Public License (LGPL) *
-#* as published by the Free Software Foundation; either version 2 of *
-#* the License, or (at your option) any later version. *
-#* for detail see the LICENCE text file. *
-#* *
-#* This program is distributed in the hope that it will be useful, *
-#* but WITHOUT ANY WARRANTY; without even the implied warranty of *
-#* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
-#* GNU Library General Public License for more details. *
-#* *
-#* You should have received a copy of the GNU Library General Public *
-#* License along with this program; if not, write to the Free Software *
-#* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 *
-#* USA *
-#* *
-#***************************************************************************
+# ***************************************************************************
+# * Copyright (c) 2009 Yorik van Havre *
+# * *
+# * This program is free software; you can redistribute it and/or modify *
+# * it under the terms of the GNU Lesser General Public License (LGPL) *
+# * as published by the Free Software Foundation; either version 2 of *
+# * the License, or (at your option) any later version. *
+# * for detail see the LICENCE text file. *
+# * *
+# * This program is distributed in the hope that it will be useful, *
+# * but WITHOUT ANY WARRANTY; without even the implied warranty of *
+# * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
+# * GNU Library General Public License for more details. *
+# * *
+# * You should have received a copy of the GNU Library General Public *
+# * License along with this program; if not, write to the Free Software *
+# * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 *
+# * USA *
+# * *
+# ***************************************************************************
-__title__ = "FreeCAD Draft Workbench - GUI part"
+__title__ = "FreeCAD Draft Workbench - GUI part"
__author__ = "Yorik van Havre "
__url__ = "https://www.freecad.org"
@@ -55,41 +55,52 @@ from draftutils.todo import todo
from draftutils.translate import translate
from draftutils.units import display_external
+
def _get_incmd_shortcut(itm):
return params.get_param("inCommandShortcut" + itm).upper()
-#---------------------------------------------------------------------------
+# ---------------------------------------------------------------------------
# Customized widgets
-#---------------------------------------------------------------------------
+# ---------------------------------------------------------------------------
+
class DraftBaseWidget(QtWidgets.QWidget):
- def __init__(self,parent = None):
+ def __init__(self, parent=None):
super().__init__(parent)
+
def eventFilter(self, widget, event):
- if (event.type() == QtCore.QEvent.KeyPress
- and event.text().upper() == _get_incmd_shortcut("CycleSnap")):
- if hasattr(FreeCADGui,"Snapper"):
+ if event.type() == QtCore.QEvent.KeyPress and event.text().upper() == _get_incmd_shortcut(
+ "CycleSnap"
+ ):
+ if hasattr(FreeCADGui, "Snapper"):
FreeCADGui.Snapper.cycleSnapObject()
return True
return super().eventFilter(widget, event)
+
class DraftDockWidget(DraftBaseWidget):
"""custom Widget that emits a resized() signal when resized"""
- def __init__(self,parent = None):
+
+ def __init__(self, parent=None):
super().__init__(parent)
- def resizeEvent(self,event):
+
+ def resizeEvent(self, event):
self.emit(QtCore.SIGNAL("resized()"))
+
def changeEvent(self, event):
if event.type() == QtCore.QEvent.LanguageChange:
self.emit(QtCore.SIGNAL("retranslate()"))
else:
super().changeEvent(event)
+
class DraftLineEdit(QtWidgets.QLineEdit):
"""custom QLineEdit widget that has the power to catch Escape keypress"""
+
def __init__(self, parent=None):
super().__init__(parent)
+
def keyPressEvent(self, event):
if event.key() == QtCore.Qt.Key_Escape:
self.emit(QtCore.SIGNAL("escaped()"))
@@ -100,24 +111,28 @@ class DraftLineEdit(QtWidgets.QLineEdit):
else:
super().keyPressEvent(event)
+
class DraftTaskPanel:
- def __init__(self,widget,extra=None):
+ def __init__(self, widget, extra=None):
if extra:
- if isinstance(extra,list):
+ if isinstance(extra, list):
self.form = [widget] + extra
else:
- self.form = [widget,extra]
+ self.form = [widget, extra]
else:
self.form = widget
+
def getStandardButtons(self):
return QtWidgets.QDialogButtonBox.Close
+
def accept(self):
- if hasattr(FreeCADGui,"draftToolBar"):
+ if hasattr(FreeCADGui, "draftToolBar"):
return FreeCADGui.draftToolBar.validatePoint()
else:
if FreeCADGui.ActiveDocument:
FreeCADGui.ActiveDocument.resetEdit()
return True
+
def reject(self):
# https://github.com/FreeCAD/FreeCAD/issues/17027
# Function can be called multiple times if Esc is pressed during mouse
@@ -129,9 +144,11 @@ class DraftTaskPanel:
if FreeCADGui.ActiveDocument:
FreeCADGui.ActiveDocument.resetEdit()
return True
+
def isAllowedAlterDocument(self):
return False
+
class DraftToolBar:
"""The Draft Task panel UI
Draft Toolbar is the main ui of the Draft Module. Once displayed as a
@@ -141,6 +158,7 @@ class DraftToolBar:
Draft Ui Commands call and get information such as point coordinates,
subcommands activation, continue mode, etc. from Task Panel Ui
"""
+
def __init__(self):
self.tray = None
self.sourceCmd = None
@@ -150,8 +168,12 @@ class DraftToolBar:
self.pointcallback = None
# OBSOLETE BUT STILL USED BY SOME ADDONS AND MACROS
- self.color = QtGui.QColor(utils.rgba_to_argb(params.get_param_view("DefaultShapeLineColor")))
- self.facecolor = QtGui.QColor(utils.rgba_to_argb(params.get_param_view("DefaultShapeColor")))
+ self.color = QtGui.QColor(
+ utils.rgba_to_argb(params.get_param_view("DefaultShapeLineColor"))
+ )
+ self.facecolor = QtGui.QColor(
+ utils.rgba_to_argb(params.get_param_view("DefaultShapeColor"))
+ )
self.linewidth = params.get_param_view("DefaultShapeLineWidth")
self.fontsize = params.get_param("textheight")
@@ -171,7 +193,7 @@ class DraftToolBar:
self.x = 0 # coord of the point as displayed in the task panel (global/local and relative/absolute)
self.y = 0 # idem
self.z = 0 # idem
- self.new_point = None # global point value
+ self.new_point = None # global point value
self.last_point = None # idem
self.lvalue = 0
self.pvalue = 90
@@ -183,12 +205,12 @@ class DraftToolBar:
self.autogroup = None
self.isCenterPlane = False
self.input_fields = {
- "xValue":{"value":"x","unit":"Length"},
- "yValue":{"value":"y","unit":"Length"},
- "zValue":{"value":"z","unit":"Length"},
- "lengthValue":{"value":"lvalue","unit":"Length"},
- "radiusValue":{"value":"radius","unit":"Length"},
- "angleValue":{"value":"avalue","unit":"Angle"}
+ "xValue": {"value": "x", "unit": "Length"},
+ "yValue": {"value": "y", "unit": "Length"},
+ "zValue": {"value": "z", "unit": "Length"},
+ "lengthValue": {"value": "lvalue", "unit": "Length"},
+ "radiusValue": {"value": "radius", "unit": "Length"},
+ "angleValue": {"value": "avalue", "unit": "Angle"},
}
# add only a dummy widget, since widgets are created on demand
@@ -206,12 +228,13 @@ class DraftToolBar:
self.tray.hide()
self.display_point_active = False # prevent cyclic processing of point values
-#---------------------------------------------------------------------------
-# General UI setup
-#---------------------------------------------------------------------------
+ # ---------------------------------------------------------------------------
+ # General UI setup
+ # ---------------------------------------------------------------------------
- def _pushbutton(self,name, layout, hide=True, icon=None,
- width=None, checkable=False, square=False):
+ def _pushbutton(
+ self, name, layout, hide=True, icon=None, width=None, checkable=False, square=False
+ ):
if square:
button = QtWidgets.QToolButton(self.baseWidget)
if width is not None:
@@ -226,40 +249,43 @@ class DraftToolBar:
if icon.endswith(".svg"):
button.setIcon(QtGui.QIcon(icon))
else:
- button.setIcon(QtGui.QIcon.fromTheme(
- icon, QtGui.QIcon(':/icons/'+icon+'.svg')))
+ button.setIcon(QtGui.QIcon.fromTheme(icon, QtGui.QIcon(":/icons/" + icon + ".svg")))
if checkable:
button.setCheckable(True)
button.setChecked(False)
layout.addWidget(button)
return button
- def _label (self,name, layout, hide=True, wrap=False):
+ def _label(self, name, layout, hide=True, wrap=False):
label = QtWidgets.QLabel(self.baseWidget)
label.setObjectName(name)
if wrap:
label.setWordWrap(True)
- if hide: label.hide()
+ if hide:
+ label.hide()
layout.addWidget(label)
return label
- def _lineedit (self,name, layout, hide=True, width=None):
+ def _lineedit(self, name, layout, hide=True, width=None):
bsize = params.get_param("ToolbarIconSize", path="General") - 2
lineedit = DraftLineEdit(self.baseWidget)
lineedit.setObjectName(name)
- if hide: lineedit.hide()
- #if not width: width = 800
- #lineedit.setMaximumSize(QtCore.QSize(width,bsize))
+ if hide:
+ lineedit.hide()
+ # if not width: width = 800
+ # lineedit.setMaximumSize(QtCore.QSize(width,bsize))
layout.addWidget(lineedit)
return lineedit
- def _inputfield (self,name, layout, hide=True, width=None):
+ def _inputfield(self, name, layout, hide=True, width=None):
inputfield = self.uiloader.createWidget("Gui::InputField")
inputfield.setObjectName(name)
- if hide: inputfield.hide()
+ if hide:
+ inputfield.hide()
if not width:
sizePolicy = QtWidgets.QSizePolicy(
- QtWidgets.QSizePolicy.Expanding, QtWidgets.QSizePolicy.Preferred)
+ QtWidgets.QSizePolicy.Expanding, QtWidgets.QSizePolicy.Preferred
+ )
inputfield.setSizePolicy(sizePolicy)
inputfield.setMinimumWidth(110)
else:
@@ -267,36 +293,40 @@ class DraftToolBar:
layout.addWidget(inputfield)
return inputfield
- def _spinbox (self,name, layout, val=None, vmax=None,
- hide=True, double=False, size=None):
+ def _spinbox(self, name, layout, val=None, vmax=None, hide=True, double=False, size=None):
if double:
sbox = QtWidgets.QDoubleSpinBox(self.baseWidget)
sbox.setDecimals(params.get_param("Decimals", path="Units"))
else:
sbox = QtWidgets.QSpinBox(self.baseWidget)
sbox.setObjectName(name)
- if vmax: sbox.setMaximum(vmax)
- if val: sbox.setValue(val)
- #if size: sbox.setMaximumSize(QtCore.QSize(size[0],size[1]))
- if hide: sbox.hide()
+ if vmax:
+ sbox.setMaximum(vmax)
+ if val:
+ sbox.setValue(val)
+ # if size: sbox.setMaximumSize(QtCore.QSize(size[0],size[1]))
+ if hide:
+ sbox.hide()
layout.addWidget(sbox)
return sbox
- def _checkbox (self,name, layout, checked=True, hide=True):
+ def _checkbox(self, name, layout, checked=True, hide=True):
chk = QtWidgets.QCheckBox(self.baseWidget)
chk.setChecked(checked)
chk.setObjectName(name)
- if hide: chk.hide()
+ if hide:
+ chk.hide()
layout.addWidget(chk)
return chk
- def _combo (self,name,layout,hide=True):
+ def _combo(self, name, layout, hide=True):
cb = QtWidgets.QComboBox(self.baseWidget)
cb.setObjectName(name)
- if hide: cb.hide()
+ if hide:
+ cb.hide()
layout.addWidget(cb)
- def setupToolBar(self,task=False):
+ def setupToolBar(self, task=False):
"""sets the draft toolbar up"""
# command
@@ -318,17 +348,21 @@ class DraftToolBar:
self.layout.addLayout(zl)
self.layout.addLayout(bl)
self.labelx = self._label("labelx", xl)
- self.xValue = self._inputfield("xValue", xl) #width=60
+ self.xValue = self._inputfield("xValue", xl) # width=60
self.xValue.installEventFilter(self.baseWidget)
- self.xValue.setText(FreeCAD.Units.Quantity(0,FreeCAD.Units.Length).UserString)
+ self.xValue.setText(FreeCAD.Units.Quantity(0, FreeCAD.Units.Length).UserString)
self.labely = self._label("labely", yl)
self.yValue = self._inputfield("yValue", yl)
- self.yValue.installEventFilter(self.baseWidget) # Required to detect snap cycling in case of Y constraining.
- self.yValue.setText(FreeCAD.Units.Quantity(0,FreeCAD.Units.Length).UserString)
+ self.yValue.installEventFilter(
+ self.baseWidget
+ ) # Required to detect snap cycling in case of Y constraining.
+ self.yValue.setText(FreeCAD.Units.Quantity(0, FreeCAD.Units.Length).UserString)
self.labelz = self._label("labelz", zl)
self.zValue = self._inputfield("zValue", zl)
- self.zValue.installEventFilter(self.baseWidget) # Required to detect snap cycling in case of Z constraining.
- self.zValue.setText(FreeCAD.Units.Quantity(0,FreeCAD.Units.Length).UserString)
+ self.zValue.installEventFilter(
+ self.baseWidget
+ ) # Required to detect snap cycling in case of Z constraining.
+ self.zValue.setText(FreeCAD.Units.Quantity(0, FreeCAD.Units.Length).UserString)
self.pointButton = self._pushbutton("addButton", bl, icon="Draft_AddPoint")
# text
@@ -350,12 +384,14 @@ class DraftToolBar:
self.layout.addLayout(al)
self.labellength = self._label("labellength", ll)
self.lengthValue = self._inputfield("lengthValue", ll)
- self.lengthValue.installEventFilter(self.baseWidget) # Required to detect snap cycling if focusOnLength is True.
- self.lengthValue.setText(FreeCAD.Units.Quantity(0,FreeCAD.Units.Length).UserString)
+ self.lengthValue.installEventFilter(
+ self.baseWidget
+ ) # Required to detect snap cycling if focusOnLength is True.
+ self.lengthValue.setText(FreeCAD.Units.Quantity(0, FreeCAD.Units.Length).UserString)
self.labelangle = self._label("labelangle", al)
- self.angleLock = self._checkbox("angleLock",al,checked=self.alock)
+ self.angleLock = self._checkbox("angleLock", al, checked=self.alock)
self.angleValue = self._inputfield("angleValue", al)
- self.angleValue.setText(FreeCAD.Units.Quantity(0,FreeCAD.Units.Angle).UserString)
+ self.angleValue.setText(FreeCAD.Units.Quantity(0, FreeCAD.Units.Angle).UserString)
# options
@@ -369,37 +405,36 @@ class DraftToolBar:
self.layout.addLayout(rl)
self.labelRadius = self._label("labelRadius", rl)
self.radiusValue = self._inputfield("radiusValue", rl)
- self.radiusValue.setText(FreeCAD.Units.Quantity(0,FreeCAD.Units.Length).UserString)
+ self.radiusValue.setText(FreeCAD.Units.Quantity(0, FreeCAD.Units.Length).UserString)
bl = QtWidgets.QHBoxLayout()
self.layout.addLayout(bl)
- self.undoButton = self._pushbutton("undoButton", bl, icon='Draft_Rotate')
+ self.undoButton = self._pushbutton("undoButton", bl, icon="Draft_Rotate")
bl = QtWidgets.QHBoxLayout()
self.layout.addLayout(bl)
- self.finishButton = self._pushbutton("finishButton", bl, icon='Draft_Finish')
+ self.finishButton = self._pushbutton("finishButton", bl, icon="Draft_Finish")
bl = QtWidgets.QHBoxLayout()
self.layout.addLayout(bl)
- self.closeButton = self._pushbutton("closeButton", bl, icon='Draft_Lock')
+ self.closeButton = self._pushbutton("closeButton", bl, icon="Draft_Lock")
bl = QtWidgets.QHBoxLayout()
self.layout.addLayout(bl)
- self.wipeButton = self._pushbutton("wipeButton", bl, icon='Draft_Wipe')
+ self.wipeButton = self._pushbutton("wipeButton", bl, icon="Draft_Wipe")
bl = QtWidgets.QHBoxLayout()
self.layout.addLayout(bl)
- self.orientWPButton = self._pushbutton("orientWPButton", bl, icon='Draft_SelectPlane')
+ self.orientWPButton = self._pushbutton("orientWPButton", bl, icon="Draft_SelectPlane")
bl = QtWidgets.QHBoxLayout()
self.layout.addLayout(bl)
- self.selectButton = self._pushbutton("selectButton", bl, icon='view-select')
+ self.selectButton = self._pushbutton("selectButton", bl, icon="view-select")
# update modes from parameters:
self.relativeMode = params.get_param("RelativeMode")
self.globalMode = params.get_param("GlobalMode")
self.makeFaceMode = params.get_param("MakeFaceMode")
- if getattr(FreeCAD, "activeDraftCommand", None) \
- and getattr(FreeCAD.activeDraftCommand, "featureName", None):
+ if getattr(FreeCAD, "activeDraftCommand", None) and getattr(
+ FreeCAD.activeDraftCommand, "featureName", None
+ ):
self.continueMode = params.get_param(
- FreeCAD.activeDraftCommand.featureName,
- "Mod/ContinueMode",
- silent=True
+ FreeCAD.activeDraftCommand.featureName, "Mod/ContinueMode", silent=True
)
self.chainedMode = params.get_param("ChainedMode")
@@ -411,10 +446,16 @@ class DraftToolBar:
self.isRelative = self._checkbox("isRelative", self.layout, checked=self.relativeMode)
self.isGlobal = self._checkbox("isGlobal", self.layout, checked=self.globalMode)
self.makeFace = self._checkbox("makeFace", self.layout, checked=self.makeFaceMode)
- self.continueCmd = self._checkbox("continueCmd", self.layout, checked=bool(self.continueMode))
- self.chainedModeCmd = self._checkbox("chainedModeCmd", self.layout, checked=self.chainedMode)
+ self.continueCmd = self._checkbox(
+ "continueCmd", self.layout, checked=bool(self.continueMode)
+ )
+ self.chainedModeCmd = self._checkbox(
+ "chainedModeCmd", self.layout, checked=self.chainedMode
+ )
- self.chainedModeCmd.setEnabled(not (hasattr(self.sourceCmd, "contMode") and self.continueMode))
+ self.chainedModeCmd.setEnabled(
+ not (hasattr(self.sourceCmd, "contMode") and self.continueMode)
+ )
self.continueCmd.setEnabled(not (hasattr(self.sourceCmd, "chain") and self.chainedMode))
# update checkboxes without parameters and without internal modes:
@@ -422,16 +463,15 @@ class DraftToolBar:
# update checkboxes with parameters but without internal modes:
# self.isCopy is also updated in modUi ("CopyMode") and offsetUi ("OffsetCopyMode")
- self.isCopy = self._checkbox("isCopy",
- self.layout,
- checked=params.get_param("CopyMode"))
- self.isSubelementMode = self._checkbox("isSubelementMode",
- self.layout,
- checked=params.get_param("SubelementMode"))
+ self.isCopy = self._checkbox("isCopy", self.layout, checked=params.get_param("CopyMode"))
+ self.isSubelementMode = self._checkbox(
+ "isSubelementMode", self.layout, checked=params.get_param("SubelementMode")
+ )
# spacer
- spacerItem = QtWidgets.QSpacerItem(20, 40, QtWidgets.QSizePolicy.Minimum,
- QtWidgets.QSizePolicy.Expanding)
+ spacerItem = QtWidgets.QSpacerItem(
+ 20, 40, QtWidgets.QSizePolicy.Minimum, QtWidgets.QSizePolicy.Expanding
+ )
self.layout.addItem(spacerItem)
self.xValue.valueChanged.connect(self.changeXValue)
@@ -439,9 +479,9 @@ class DraftToolBar:
self.zValue.valueChanged.connect(self.changeZValue)
self.lengthValue.valueChanged.connect(self.changeLengthValue)
self.angleValue.valueChanged.connect(self.changeAngleValue)
- if hasattr(self.angleLock, "checkStateChanged"): # Qt version >= 6.7.0
+ if hasattr(self.angleLock, "checkStateChanged"): # Qt version >= 6.7.0
self.angleLock.checkStateChanged.connect(self.toggleAngle)
- else: # Qt version < 6.7.0
+ else: # Qt version < 6.7.0
self.angleLock.stateChanged.connect(self.toggleAngle)
self.radiusValue.valueChanged.connect(self.changeRadiusValue)
self.xValue.returnPressed.connect(self.checkx)
@@ -467,7 +507,7 @@ class DraftToolBar:
self.orientWPButton.clicked.connect(self.orientWP)
self.undoButton.clicked.connect(self.undoSegment)
self.selectButton.clicked.connect(self.selectEdge)
- if hasattr(self.continueCmd, "checkStateChanged"): # Qt version >= 6.7.0
+ if hasattr(self.continueCmd, "checkStateChanged"): # Qt version >= 6.7.0
self.continueCmd.checkStateChanged.connect(self.setContinue)
self.chainedModeCmd.checkStateChanged.connect(self.setChainedMode)
self.isCopy.checkStateChanged.connect(self.setCopymode)
@@ -475,7 +515,7 @@ class DraftToolBar:
self.isRelative.checkStateChanged.connect(self.setRelative)
self.isGlobal.checkStateChanged.connect(self.setGlobal)
self.makeFace.checkStateChanged.connect(self.setMakeFace)
- else: # Qt version < 6.7.0
+ else: # Qt version < 6.7.0
self.continueCmd.stateChanged.connect(self.setContinue)
self.chainedModeCmd.stateChanged.connect(self.setChainedMode)
self.isCopy.stateChanged.connect(self.setCopymode)
@@ -488,20 +528,26 @@ class DraftToolBar:
"""sets draft tray buttons up"""
self.wplabel = self._pushbutton(
- "wplabel", self.toptray, icon='Draft_SelectPlane',
- hide=False,width=120)
+ "wplabel", self.toptray, icon="Draft_SelectPlane", hide=False, width=120
+ )
self.styleButton = self._pushbutton(
- "stylebutton", self.toptray, icon='Draft_Apply', hide=False,
- width=120)
+ "stylebutton", self.toptray, icon="Draft_Apply", hide=False, width=120
+ )
self.setStyleButton()
self.constrButton = self._pushbutton(
- "constrButton", self.toptray, hide=False, icon='Draft_Construction',
- width=self.styleButton.sizeHint().height(), checkable=True, square=True)
+ "constrButton",
+ self.toptray,
+ hide=False,
+ icon="Draft_Construction",
+ width=self.styleButton.sizeHint().height(),
+ checkable=True,
+ square=True,
+ )
self.constrColor = QtGui.QColor(self.paramconstr)
self.autoGroupButton = self._pushbutton(
- "autoGroup", self.bottomtray,icon=":/icons/button_invalid.svg",
- hide=False, width=120)
+ "autoGroup", self.bottomtray, icon=":/icons/button_invalid.svg", hide=False, width=120
+ )
self.autoGroupButton.setText(translate("draft", "None"))
self.autoGroupButton.setFlat(True)
@@ -510,23 +556,24 @@ class DraftToolBar:
self.constrButton.toggled.connect(self.toggleConstrMode)
self.autoGroupButton.clicked.connect(self.runAutoGroup)
- QtCore.QTimer.singleShot(2000,self.retranslateTray) # delay so translations get a chance to load
+ QtCore.QTimer.singleShot(
+ 2000, self.retranslateTray
+ ) # delay so translations get a chance to load
def setupStyle(self):
style = "#constrButton:Checked {background-color: "
- style += self.getDefaultColor("constr",rgb=True)+" } "
+ style += self.getDefaultColor("constr", rgb=True) + " } "
style += "#addButton:Checked, #delButton:checked, "
style += "#sharpButton:Checked, "
style += "#tangentButton:Checked, #symmetricButton:checked {"
style += "background-color: rgb(20,100,250) }"
self.baseWidget.setStyleSheet(style)
- #if hasattr(self,"tray"):
+ # if hasattr(self,"tray"):
# self.tray.setStyleSheet(style)
-
-#---------------------------------------------------------------------------
-# language tools
-#---------------------------------------------------------------------------
+ # ---------------------------------------------------------------------------
+ # language tools
+ # ---------------------------------------------------------------------------
def retranslateUi(self, widget=None):
self.promptlabel.setText(translate("draft", "active command:"))
@@ -539,75 +586,138 @@ class DraftToolBar:
self.yValue.setToolTip(translate("draft", "Y coordinate of the point"))
self.zValue.setToolTip(translate("draft", "Z coordinate of the point"))
self.pointButton.setText(translate("draft", "Enter Point"))
- self.pointButton.setToolTip(translate(
- "draft","Enter a point with given coordinates"))
+ self.pointButton.setToolTip(translate("draft", "Enter a point with given coordinates"))
self.labellength.setText(translate("draft", "Length"))
self.labelangle.setText(translate("draft", "Angle"))
self.lengthValue.setToolTip(translate("draft", "Length of the current segment"))
self.angleValue.setToolTip(translate("draft", "Angle of the current segment"))
- self.angleLock.setToolTip(translate(
- "draft", "Locks the current angle")\
- + " (" + _get_incmd_shortcut("Length") + ")")
+ self.angleLock.setToolTip(
+ translate("draft", "Locks the current angle")
+ + " ("
+ + _get_incmd_shortcut("Length")
+ + ")"
+ )
self.labelRadius.setText(translate("draft", "Radius"))
self.radiusValue.setToolTip(translate("draft", "Radius of the circle"))
- self.isRelative.setText(translate(
- "draft", "Relative") + " (" + _get_incmd_shortcut("Relative") + ")")
- self.isRelative.setToolTip(translate(
- "draft", "Coordinates relative to last point or to coordinate system "
- + "origin\nif is the first point to set"))
- self.isGlobal.setText(translate(
- "draft", "Global") + " (" + _get_incmd_shortcut("Global") + ")")
- self.isGlobal.setToolTip(translate(
- "draft", "Coordinates relative to global coordinate system."
- + "\nUncheck to use working plane coordinate system"))
- self.makeFace.setText(translate(
- "draft", "Make face") + " (" + _get_incmd_shortcut("MakeFace") + ")")
- self.makeFace.setToolTip(translate(
- "draft", "If checked, the object will be filled with a face."
- + "\nNot available if the 'Use Part Primitives' preference is enabled"))
- self.finishButton.setText(translate(
- "draft", "Finish") + " (" + _get_incmd_shortcut("Exit") + ")")
- self.finishButton.setToolTip(translate(
- "draft", "Finishes the current drawing or editing operation"))
- self.continueCmd.setText(translate(
- "draft", "Continue") + " (" + _get_incmd_shortcut("Continue") + ")")
- self.continueCmd.setToolTip(translate(
- "draft", "If checked, the command will not finish until pressing "
- + "the command button again"))
+ self.isRelative.setText(
+ translate("draft", "Relative") + " (" + _get_incmd_shortcut("Relative") + ")"
+ )
+ self.isRelative.setToolTip(
+ translate(
+ "draft",
+ "Coordinates relative to last point or to coordinate system "
+ + "origin\nif is the first point to set",
+ )
+ )
+ self.isGlobal.setText(
+ translate("draft", "Global") + " (" + _get_incmd_shortcut("Global") + ")"
+ )
+ self.isGlobal.setToolTip(
+ translate(
+ "draft",
+ "Coordinates relative to global coordinate system."
+ + "\nUncheck to use working plane coordinate system",
+ )
+ )
+ self.makeFace.setText(
+ translate("draft", "Make face") + " (" + _get_incmd_shortcut("MakeFace") + ")"
+ )
+ self.makeFace.setToolTip(
+ translate(
+ "draft",
+ "If checked, the object will be filled with a face."
+ + "\nNot available if the 'Use Part Primitives' preference is enabled",
+ )
+ )
+ self.finishButton.setText(
+ translate("draft", "Finish") + " (" + _get_incmd_shortcut("Exit") + ")"
+ )
+ self.finishButton.setToolTip(
+ translate("draft", "Finishes the current drawing or editing operation")
+ )
+ self.continueCmd.setText(
+ translate("draft", "Continue") + " (" + _get_incmd_shortcut("Continue") + ")"
+ )
+ self.continueCmd.setToolTip(
+ translate(
+ "draft",
+ "If checked, the command will not finish until pressing "
+ + "the command button again",
+ )
+ )
self.chainedModeCmd.setText(translate("draft", "Chained mode"))
- self.chainedModeCmd.setToolTip(translate("draft", "If checked, the next dimension will be placed in a chain" \
- " with the previously placed Dimension"))
+ self.chainedModeCmd.setToolTip(
+ translate(
+ "draft",
+ "If checked, the next dimension will be placed in a chain"
+ " with the previously placed Dimension",
+ )
+ )
self.occOffset.setText(translate("draft", "OCC-style offset"))
- self.occOffset.setToolTip(translate(
- "draft", "If checked, an OCC-style offset will be performed"
- + " instead of the classic offset"))
- self.undoButton.setText(translate("draft", "Undo") + " (" + _get_incmd_shortcut("Undo") + ")")
+ self.occOffset.setToolTip(
+ translate(
+ "draft",
+ "If checked, an OCC-style offset will be performed"
+ + " instead of the classic offset",
+ )
+ )
+ self.undoButton.setText(
+ translate("draft", "Undo") + " (" + _get_incmd_shortcut("Undo") + ")"
+ )
self.undoButton.setToolTip(translate("draft", "Undo the last segment"))
- self.closeButton.setText(translate("draft", "Close") + " (" + _get_incmd_shortcut("Close") + ")")
+ self.closeButton.setText(
+ translate("draft", "Close") + " (" + _get_incmd_shortcut("Close") + ")"
+ )
self.closeButton.setToolTip(translate("draft", "Finishes and closes the current line"))
- self.wipeButton.setText(translate("draft", "Wipe") + " (" + _get_incmd_shortcut("Wipe") + ")")
- self.wipeButton.setToolTip(translate("draft", "Wipes the existing segments of this line and starts again from the last point"))
- self.orientWPButton.setText(translate("draft", "Set Working Plane") + " (" + _get_incmd_shortcut("SetWP") + ")")
- self.orientWPButton.setToolTip(translate("draft", "Reorients the working plane on the last segment"))
- self.selectButton.setText(translate("draft", "Select Edge") + " (" + _get_incmd_shortcut("SelectEdge") + ")")
- self.selectButton.setToolTip(translate("draft", "Selects an existing edge to be measured by this dimension"))
+ self.wipeButton.setText(
+ translate("draft", "Wipe") + " (" + _get_incmd_shortcut("Wipe") + ")"
+ )
+ self.wipeButton.setToolTip(
+ translate(
+ "draft",
+ "Wipes the existing segments of this line and starts again from the last point",
+ )
+ )
+ self.orientWPButton.setText(
+ translate("draft", "Set Working Plane") + " (" + _get_incmd_shortcut("SetWP") + ")"
+ )
+ self.orientWPButton.setToolTip(
+ translate("draft", "Reorients the working plane on the last segment")
+ )
+ self.selectButton.setText(
+ translate("draft", "Select Edge") + " (" + _get_incmd_shortcut("SelectEdge") + ")"
+ )
+ self.selectButton.setToolTip(
+ translate("draft", "Selects an existing edge to be measured by this dimension")
+ )
self.numFacesLabel.setText(translate("draft", "Sides"))
self.numFaces.setToolTip(translate("draft", "Number of sides"))
self.isCopy.setText(translate("draft", "Copy") + " (" + _get_incmd_shortcut("Copy") + ")")
- self.isCopy.setToolTip(translate("draft", "If checked, objects will be copied instead of moved"))
- self.isSubelementMode.setText(translate("draft", "Modify subelements") + " (" + _get_incmd_shortcut("SubelementMode") + ")")
- self.isSubelementMode.setToolTip(translate("draft", "If checked, subelements will be modified instead of entire objects"))
+ self.isCopy.setToolTip(
+ translate("draft", "If checked, objects will be copied instead of moved")
+ )
+ self.isSubelementMode.setText(
+ translate("draft", "Modify subelements")
+ + " ("
+ + _get_incmd_shortcut("SubelementMode")
+ + ")"
+ )
+ self.isSubelementMode.setToolTip(
+ translate("draft", "If checked, subelements will be modified instead of entire objects")
+ )
self.textOkButton.setText(translate("draft", "Create Text"))
- self.textOkButton.setToolTip(translate("draft", "Creates the text object and finishes the command"))
+ self.textOkButton.setToolTip(
+ translate("draft", "Creates the text object and finishes the command")
+ )
self.retranslateTray(widget)
# Update the maximum width of the push buttons
- maxwidth = 66 # that's the default
+ maxwidth = 66 # that's the default
pb = []
for i in range(self.layout.count()):
w = self.layout.itemAt(i).widget()
- if w is not None and w.inherits('QPushButton'):
+ if w is not None and w.inherits("QPushButton"):
pb.append(w)
for i in pb:
@@ -615,27 +725,26 @@ class DraftToolBar:
fw = fm.width(i.text())
fw = max(fw, maxwidth)
- maxwidth = maxwidth + 16 +10 # add icon width and a margin
+ maxwidth = maxwidth + 16 + 10 # add icon width and a margin
for i in pb:
i.setMaximumWidth(maxwidth)
- def retranslateTray(self,widget=None):
+ def retranslateTray(self, widget=None):
self.styleButton.setToolTip(translate("draft", "Changes the default style for new objects"))
self.constrButton.setToolTip(translate("draft", "Toggles construction mode"))
self.autoGroupButton.setToolTip(translate("draft", "Autogroup off"))
-
-#---------------------------------------------------------------------------
-# Interface modes
-#---------------------------------------------------------------------------
+ # ---------------------------------------------------------------------------
+ # Interface modes
+ # ---------------------------------------------------------------------------
def _show_dialog(self, panel):
task = FreeCADGui.Control.showDialog(panel)
task.setDocumentName(FreeCADGui.ActiveDocument.Document.Name)
task.setAutoCloseOnDeletedDocument(True)
- def taskUi(self,title="Draft", extra=None, icon="Draft_Draft"):
+ def taskUi(self, title="Draft", extra=None, icon="Draft_Draft"):
# reset InputField values
self.reset_ui_values()
self.isTaskOn = True
@@ -663,37 +772,34 @@ class DraftToolBar:
else:
axis = WorkingPlane.get_working_plane(update=False).axis
constraint_dir = FreeCAD.Vector(
- 1 if f == "x" else 0,
- 1 if f == "y" else 0,
- 1 if f == "z" else 0
+ 1 if f == "x" else 0, 1 if f == "y" else 0, 1 if f == "z" else 0
)
# Using a high tolerance:
- if axis.isEqual(constraint_dir, 0.1) \
- or axis.isEqual(-constraint_dir, 0.1):
+ if axis.isEqual(constraint_dir, 0.1) or axis.isEqual(-constraint_dir, 0.1):
force_xyz = True
if not force_xyz and params.get_param("focusOnLength") and self.lengthValue.isVisible():
self.lengthValue.setFocus()
- self.lengthValue.setSelection(0,self.number_length(self.lengthValue.text()))
+ self.lengthValue.setSelection(0, self.number_length(self.lengthValue.text()))
elif not force_xyz and self.angleLock.isVisible() and self.angleLock.isChecked():
self.lengthValue.setFocus()
- self.lengthValue.setSelection(0,self.number_length(self.lengthValue.text()))
+ self.lengthValue.setSelection(0, self.number_length(self.lengthValue.text()))
elif f == "x":
self.xValue.setFocus()
- self.xValue.setSelection(0,self.number_length(self.xValue.text()))
+ self.xValue.setSelection(0, self.number_length(self.xValue.text()))
elif f == "y":
self.yValue.setFocus()
- self.yValue.setSelection(0,self.number_length(self.yValue.text()))
+ self.yValue.setSelection(0, self.number_length(self.yValue.text()))
elif f == "z":
self.zValue.setFocus()
- self.zValue.setSelection(0,self.number_length(self.zValue.text()))
+ self.zValue.setSelection(0, self.number_length(self.zValue.text()))
elif f == "radius":
self.radiusValue.setFocus()
- self.radiusValue.setSelection(0,self.number_length(self.radiusValue.text()))
+ self.radiusValue.setSelection(0, self.number_length(self.radiusValue.text()))
else:
# f is None
self.xValue.setFocus()
- self.xValue.setSelection(0,self.number_length(self.xValue.text()))
+ self.xValue.setSelection(0, self.number_length(self.xValue.text()))
def number_length(self, str):
nl = 0
@@ -703,7 +809,7 @@ class DraftToolBar:
return nl
def extraLineUi(self):
- '''shows length and angle controls'''
+ """shows length and angle controls"""
self.labellength.show()
self.lengthValue.show()
self.labelangle.show()
@@ -712,7 +818,7 @@ class DraftToolBar:
self.angleLock.setChecked(False)
def hideXYZ(self):
- ''' turn off all the point entry widgets '''
+ """turn off all the point entry widgets"""
self.labelx.hide()
self.labely.hide()
self.labelz.hide()
@@ -728,16 +834,30 @@ class DraftToolBar:
self.isRelative.hide()
self.isGlobal.hide()
- def lineUi(self, title=translate("draft", "Line"), cancel=None, extra=None,
- getcoords=None,rel=False,icon="Draft_Line"):
+ def lineUi(
+ self,
+ title=translate("draft", "Line"),
+ cancel=None,
+ extra=None,
+ getcoords=None,
+ rel=False,
+ icon="Draft_Line",
+ ):
self.pointUi(title, cancel, extra, getcoords, rel, icon)
self.extraLineUi()
self.xValue.setEnabled(True)
self.yValue.setEnabled(True)
self.continueCmd.show()
- def wireUi(self, title=translate("draft", "DWire"), cancel=None, extra=None,
- getcoords=None, rel=False, icon="Draft_Wire"):
+ def wireUi(
+ self,
+ title=translate("draft", "DWire"),
+ cancel=None,
+ extra=None,
+ getcoords=None,
+ rel=False,
+ icon="Draft_Wire",
+ ):
self.pointUi(title, cancel, extra, getcoords, rel, icon)
self.xValue.setEnabled(True)
self.yValue.setEnabled(True)
@@ -754,25 +874,34 @@ class DraftToolBar:
self.continueCmd.show()
def circleUi(self):
- self.pointUi(translate("draft", "Circle"),icon="Draft_Circle")
+ self.pointUi(translate("draft", "Circle"), icon="Draft_Circle")
self.extUi()
self.isRelative.hide()
def arcUi(self):
- self.pointUi(translate("draft", "Arc"),icon="Draft_Arc")
+ self.pointUi(translate("draft", "Arc"), icon="Draft_Arc")
self.continueCmd.show()
self.isRelative.hide()
def rotateSetCenterUi(self):
- self.pointUi(translate("draft", "Rotate"),icon="Draft_Rotate")
+ self.pointUi(translate("draft", "Rotate"), icon="Draft_Rotate")
self.modUi()
self.isRelative.hide()
- def pointUi(self, title=translate("draft","Point"), cancel=None, extra=None,
- getcoords=None, rel=False, icon="Draft_Draft"):
- if cancel: self.cancel = cancel
- if getcoords: self.pointcallback = getcoords
- self.taskUi(title,extra,icon)
+ def pointUi(
+ self,
+ title=translate("draft", "Point"),
+ cancel=None,
+ extra=None,
+ getcoords=None,
+ rel=False,
+ icon="Draft_Draft",
+ ):
+ if cancel:
+ self.cancel = cancel
+ if getcoords:
+ self.pointcallback = getcoords
+ self.taskUi(title, extra, icon)
self.xValue.setEnabled(True)
self.yValue.setEnabled(True)
self.isRelative.show()
@@ -785,24 +914,26 @@ class DraftToolBar:
self.yValue.show()
self.zValue.show()
# reset UI to (0,0,0) on start
- self.xValue.setText(FreeCAD.Units.Quantity(0,FreeCAD.Units.Length).UserString)
- self.yValue.setText(FreeCAD.Units.Quantity(0,FreeCAD.Units.Length).UserString)
- self.zValue.setText(FreeCAD.Units.Quantity(0,FreeCAD.Units.Length).UserString)
+ self.xValue.setText(FreeCAD.Units.Quantity(0, FreeCAD.Units.Length).UserString)
+ self.yValue.setText(FreeCAD.Units.Quantity(0, FreeCAD.Units.Length).UserString)
+ self.zValue.setText(FreeCAD.Units.Quantity(0, FreeCAD.Units.Length).UserString)
self.x = 0
self.y = 0
self.z = 0
self.new_point = None
self.last_point = None
self.pointButton.show()
- if rel: self.isRelative.show()
+ if rel:
+ self.isRelative.show()
todo.delay(self.setFocus, None)
- def labelUi(self,title=translate("draft","Label"),callback=None):
+ def labelUi(self, title=translate("draft", "Label"), callback=None):
w = QtWidgets.QWidget()
- w.setWindowTitle(translate("draft","Label Type"))
+ w.setWindowTitle(translate("draft", "Label Type"))
l = QtWidgets.QVBoxLayout(w)
combo = QtWidgets.QComboBox()
from draftobjects.label import get_label_types
+
types = get_label_types()
for s in types:
combo.addItem(translate("Draft", s), userData=s)
@@ -815,18 +946,18 @@ class DraftToolBar:
pass
def offsetUi(self):
- self.taskUi(translate("draft","Offset"), icon="Draft_Offset")
+ self.taskUi(translate("draft", "Offset"), icon="Draft_Offset")
self.radiusUi()
self.isCopy.show()
self.isCopy.setChecked(params.get_param("OffsetCopyMode"))
self.occOffset.show()
- self.labelRadius.setText(translate("draft","Distance"))
+ self.labelRadius.setText(translate("draft", "Distance"))
self.radiusValue.setToolTip(translate("draft", "Offset distance"))
- self.radiusValue.setText(FreeCAD.Units.Quantity(0,FreeCAD.Units.Length).UserString)
+ self.radiusValue.setText(FreeCAD.Units.Quantity(0, FreeCAD.Units.Length).UserString)
todo.delay(self.setFocus, "radius")
def offUi(self):
- todo.delay(FreeCADGui.Control.closeDialog,None)
+ todo.delay(FreeCADGui.Control.closeDialog, None)
self.cancel = None
self.sourceCmd = None
self.pointcallback = None
@@ -834,12 +965,12 @@ class DraftToolBar:
self.isTaskOn = False
self.baseWidget = QtWidgets.QWidget()
- def trimUi(self,title=translate("draft","Trimex")):
+ def trimUi(self, title=translate("draft", "Trimex")):
self.taskUi(title, icon="Draft_Trimex")
self.radiusUi()
- self.labelRadius.setText(translate("draft","Distance"))
+ self.labelRadius.setText(translate("draft", "Distance"))
self.radiusValue.setToolTip(translate("draft", "Offset distance"))
- self.radiusValue.setText(FreeCAD.Units.Quantity(0,FreeCAD.Units.Length).UserString)
+ self.radiusValue.setText(FreeCAD.Units.Quantity(0, FreeCAD.Units.Length).UserString)
todo.delay(self.setFocus, "radius")
def radiusUi(self):
@@ -847,7 +978,7 @@ class DraftToolBar:
self.labelRadius.setText(translate("draft", "Radius"))
self.radiusValue.setToolTip(translate("draft", "Radius of Circle"))
self.labelRadius.show()
- self.radiusValue.setText(FreeCAD.Units.Quantity(0,FreeCAD.Units.Length).UserString)
+ self.radiusValue.setText(FreeCAD.Units.Quantity(0, FreeCAD.Units.Length).UserString)
self.radiusValue.show()
todo.delay(self.setFocus, "radius")
@@ -855,15 +986,15 @@ class DraftToolBar:
self.hideXYZ()
self.textValue.show()
self.textOkButton.show()
- self.textValue.setText('')
- todo.delay(self.textValue.setFocus,None)
- self.textbuffer=[]
- self.textline=0
+ self.textValue.setText("")
+ todo.delay(self.textValue.setFocus, None)
+ self.textbuffer = []
+ self.textline = 0
self.continueCmd.show()
# Change the checkbox label as the in-command shortcut cannot be used:
self.continueCmd.setText(translate("draft", "Continue"))
- def switchUi(self,store=True):
+ def switchUi(self, store=True):
if store:
self.state = []
self.state.append(self.labelx.isVisible())
@@ -875,19 +1006,25 @@ class DraftToolBar:
self.hideXYZ()
else:
if self.state:
- if self.state[0]:self.labelx.show()
- if self.state[1]:self.labely.show()
- if self.state[2]:self.labelz.show()
- if self.state[3]:self.xValue.show()
- if self.state[4]:self.yValue.show()
- if self.state[5]:self.zValue.show()
+ if self.state[0]:
+ self.labelx.show()
+ if self.state[1]:
+ self.labely.show()
+ if self.state[2]:
+ self.labelz.show()
+ if self.state[3]:
+ self.xValue.show()
+ if self.state[4]:
+ self.yValue.show()
+ if self.state[5]:
+ self.zValue.show()
self.state = None
- def setTitle(self,title,icon="Draft_Draft"):
+ def setTitle(self, title, icon="Draft_Draft"):
self.baseWidget.setWindowTitle(title)
- self.baseWidget.setWindowIcon(QtGui.QIcon(":/icons/"+icon+".svg"))
+ self.baseWidget.setWindowIcon(QtGui.QIcon(":/icons/" + icon + ".svg"))
- def selectUi(self,extra=None, on_close_call=None):
+ def selectUi(self, extra=None, on_close_call=None):
self.makeDumbTask(extra, on_close_call)
def editUi(self):
@@ -910,7 +1047,9 @@ class DraftToolBar:
def checkLocal(self):
"""checks if x,y,z coords must be displayed as local or global"""
if not self.globalMode and self.relativeMode:
- self.labelx.setText(translate("draft", "Local {}").format("\u0394X")) # \u0394 = ∆ (Greek delta)
+ self.labelx.setText(
+ translate("draft", "Local {}").format("\u0394X")
+ ) # \u0394 = ∆ (Greek delta)
self.labely.setText(translate("draft", "Local {}").format("\u0394Y"))
self.labelz.setText(translate("draft", "Local {}").format("\u0394Z"))
elif not self.globalMode and not self.relativeMode:
@@ -932,6 +1071,7 @@ class DraftToolBar:
return True
else:
return False
+
if self.isTaskOn:
if isThere(self.xValue):
self.setFocus()
@@ -947,28 +1087,35 @@ class DraftToolBar:
def makeDumbTask(self, extra=None, on_close_call=None):
"""create a dumb taskdialog to prevent deleting the temp object"""
+
class TaskPanel:
def __init__(self, extra=None, callback=None):
if extra:
self.form = [extra]
self.callback = callback
+
def getStandardButtons(self):
return QtWidgets.QDialogButtonBox.Close
+
def reject(self):
if self.callback:
self.callback()
return True
+
todo.delay(FreeCADGui.Control.closeDialog, None)
panel = TaskPanel(extra, on_close_call)
todo.delay(self._show_dialog, panel)
-
-#---------------------------------------------------------------------------
-# Processing functions
-#---------------------------------------------------------------------------
+ # ---------------------------------------------------------------------------
+ # Processing functions
+ # ---------------------------------------------------------------------------
def setContinue(self, val):
- params.set_param(FreeCAD.activeDraftCommand.featureName, bool(getattr(val, "value", val)), "Mod/Draft/ContinueMode")
+ params.set_param(
+ FreeCAD.activeDraftCommand.featureName,
+ bool(getattr(val, "value", val)),
+ "Mod/Draft/ContinueMode",
+ )
self.continueMode = bool(getattr(val, "value", val))
self.chainedModeCmd.setEnabled(not bool(getattr(val, "value", val)))
@@ -990,9 +1137,9 @@ class DraftToolBar:
def setRelative(self, val=-1):
val = getattr(val, "value", val)
if val < 0:
- if hasattr(self.isRelative, "checkStateChanged"): # Qt version >= 6.7.0
+ if hasattr(self.isRelative, "checkStateChanged"): # Qt version >= 6.7.0
self.isRelative.checkStateChanged.disconnect(self.setRelative)
- else: # Qt version < 6.7.0
+ else: # Qt version < 6.7.0
self.isRelative.stateChanged.disconnect(self.setRelative)
if val == -1:
self.isRelative.setChecked(True)
@@ -1001,9 +1148,9 @@ class DraftToolBar:
val = params.get_param("RelativeMode")
self.isRelative.setChecked(val)
self.relativeMode = val
- if hasattr(self.isRelative, "checkStateChanged"): # Qt version >= 6.7.0
+ if hasattr(self.isRelative, "checkStateChanged"): # Qt version >= 6.7.0
self.isRelative.checkStateChanged.connect(self.setRelative)
- else: # Qt version < 6.7.0
+ else: # Qt version < 6.7.0
self.isRelative.stateChanged.connect(self.setRelative)
else:
params.set_param("RelativeMode", bool(val))
@@ -1040,7 +1187,7 @@ class DraftToolBar:
def checkx(self):
if self.yValue.isEnabled():
self.yValue.setFocus()
- self.yValue.setSelection(0,self.number_length(self.yValue.text()))
+ self.yValue.setSelection(0, self.number_length(self.yValue.text()))
self.updateSnapper()
else:
self.checky()
@@ -1048,7 +1195,7 @@ class DraftToolBar:
def checky(self):
if self.zValue.isEnabled():
self.zValue.setFocus()
- self.zValue.setSelection(0,self.number_length(self.zValue.text()))
+ self.zValue.setSelection(0, self.number_length(self.zValue.text()))
self.updateSnapper()
else:
self.validatePoint()
@@ -1056,7 +1203,7 @@ class DraftToolBar:
def checklength(self):
if self.angleValue.isEnabled():
self.angleValue.setFocus()
- self.angleValue.setSelection(0,self.number_length(self.angleValue.text()))
+ self.angleValue.setSelection(0, self.number_length(self.angleValue.text()))
self.updateSnapper()
else:
self.validatePoint()
@@ -1124,15 +1271,15 @@ class DraftToolBar:
def selectEdge(self):
"""allows the dimension command to select an edge"""
- if hasattr(self.sourceCmd,"selectEdge"):
+ if hasattr(self.sourceCmd, "selectEdge"):
self.sourceCmd.selectEdge()
def undoSegment(self):
"""undo last line segment"""
- if hasattr(self.sourceCmd,"undolast"):
+ if hasattr(self.sourceCmd, "undolast"):
self.sourceCmd.undolast()
- def checkSpecialChars(self,txt):
+ def checkSpecialChars(self, txt):
"""checks for special characters in the entered coords that must be
treated as shortcuts
"""
@@ -1188,11 +1335,11 @@ class DraftToolBar:
if self.closeButton.isVisible():
self.closeLine()
elif txt == _get_incmd_shortcut("AddHold"):
- if hasattr(FreeCADGui,"Snapper"):
+ if hasattr(FreeCADGui, "Snapper"):
FreeCADGui.Snapper.addHoldPoint()
spec = True
elif txt == _get_incmd_shortcut("Recenter"):
- if hasattr(FreeCADGui,"Snapper"):
+ if hasattr(FreeCADGui, "Snapper"):
FreeCADGui.Snapper.recenter_workingplane()
spec = True
elif txt == _get_incmd_shortcut("Snap"):
@@ -1237,7 +1384,7 @@ class DraftToolBar:
value = getattr(self, field["value"])
unit = getattr(FreeCAD.Units, field["unit"])
v = FreeCAD.Units.Quantity(value, unit).getUserPreferred()[0]
- widget.setProperty("text",v)
+ widget.setProperty("text", v)
widget.setFocus()
widget.selectAll()
self.updateSnapper()
@@ -1246,9 +1393,11 @@ class DraftToolBar:
"""updates the snapper track line if applicable"""
if not self.xValue.isVisible():
return
- if hasattr(FreeCADGui,"Snapper") \
- and FreeCADGui.Snapper.trackLine \
- and FreeCADGui.Snapper.trackLine.Visible:
+ if (
+ hasattr(FreeCADGui, "Snapper")
+ and FreeCADGui.Snapper.trackLine
+ and FreeCADGui.Snapper.trackLine.Visible
+ ):
point = self.get_new_point(FreeCAD.Vector(self.x, self.y, self.z))
FreeCADGui.Snapper.trackLine.p2(point)
@@ -1268,8 +1417,7 @@ class DraftToolBar:
self.mouse = False
recorded_input_start = self.mouse_delay_input_start
QtCore.QTimer.singleShot(
- delay * 1000,
- lambda: self.setMouseMode(True, recorded_input_start)
+ delay * 1000, lambda: self.setMouseMode(True, recorded_input_start)
)
def checkEnterText(self):
@@ -1282,11 +1430,13 @@ class DraftToolBar:
"""this function sends the entered text to the active draft command
if enter has been pressed twice. Otherwise it blanks the line.
"""
- self.sourceCmd.text = self.textValue.toPlainText()\
- .replace("\\","\\\\")\
- .replace("\"","\\\"")\
- .replace("\'","\\\'")\
+ self.sourceCmd.text = (
+ self.textValue.toPlainText()
+ .replace("\\", "\\\\")
+ .replace('"', '\\"')
+ .replace("'", "\\'")
.splitlines()
+ )
self.sourceCmd.createObject()
def displayPoint(self, point=None, last=None, plane=None, mask=None):
@@ -1328,11 +1478,11 @@ class DraftToolBar:
self.lvalue = length
self.avalue = phi
- self.xValue.setText(display_external(delta.x,None,'Length'))
- self.yValue.setText(display_external(delta.y,None,'Length'))
- self.zValue.setText(display_external(delta.z,None,'Length'))
- self.lengthValue.setText(display_external(length,None,'Length'))
- self.angleValue.setText(display_external(phi,None,'Angle'))
+ self.xValue.setText(display_external(delta.x, None, "Length"))
+ self.yValue.setText(display_external(delta.y, None, "Length"))
+ self.zValue.setText(display_external(delta.z, None, "Length"))
+ self.lengthValue.setText(display_external(length, None, "Length"))
+ self.angleValue.setText(display_external(phi, None, "Angle"))
# set masks
if (mask == "x") or (self.mask == "x"):
@@ -1370,7 +1520,9 @@ class DraftToolBar:
if typ == "snap":
r, g, b, _ = utils.get_rgba_tuple(params.get_param("snapcolor"))
elif typ == "ui":
- print("draft: deprecation warning: Do not use getDefaultColor(\"ui\") anymore - use getDefaultColor(\"line\") instead.")
+ print(
+ 'draft: deprecation warning: Do not use getDefaultColor("ui") anymore - use getDefaultColor("line") instead.'
+ )
r = float(self.color.red() / 255.0)
g = float(self.color.green() / 255.0)
b = float(self.color.blue() / 255.0)
@@ -1385,36 +1537,40 @@ class DraftToolBar:
else:
print("draft: error: couldn't get a color for ", typ, " typ.")
if rgb:
- return("rgb(" + str(int(r * 255)) + "," + str(int(g * 255)) + "," + str(int(b * 255)) + ")")
+ return (
+ "rgb(" + str(int(r * 255)) + "," + str(int(g * 255)) + "," + str(int(b * 255)) + ")"
+ )
else:
- return (r,g,b)
+ return (r, g, b)
- def cross(self,on=True):
+ def cross(self, on=True):
"""deprecated"""
pass
- def toggleConstrMode(self,checked):
+ def toggleConstrMode(self, checked):
self.baseWidget.setStyleSheet(
"#constrButton:Checked {background-color: "
- + self.getDefaultColor("constr",rgb=True)+" }")
+ + self.getDefaultColor("constr", rgb=True)
+ + " }"
+ )
self.constrMode = checked
def toggleContinue(self):
FreeCAD.Console.PrintMessage("toggle continue\n")
self.continueMode = not self.continueMode
try:
- if hasattr(self,"continueCmd"):
+ if hasattr(self, "continueCmd"):
if self.continueCmd.isVisible():
self.continueCmd.toggle()
- if hasattr(self,"panel"):
- if hasattr(self.panel,"form"):
- if isinstance(self.panel.form,list):
+ if hasattr(self, "panel"):
+ if hasattr(self.panel, "form"):
+ if isinstance(self.panel.form, list):
for w in self.panel.form:
- c = w.findChild(QtWidgets.QCheckBox,"ContinueCmd")
+ c = w.findChild(QtWidgets.QCheckBox, "ContinueCmd")
if c:
c.toggle()
else:
- c = self.panel.form.findChild(QtWidgets.QCheckBox,"ContinueCmd")
+ c = self.panel.form.findChild(QtWidgets.QCheckBox, "ContinueCmd")
if c:
c.toggle()
except Exception:
@@ -1433,22 +1589,25 @@ class DraftToolBar:
"sets icon and text on the style button"
linecolor = QtGui.QColor(utils.rgba_to_argb(params.get_param_view("DefaultShapeLineColor")))
facecolor = QtGui.QColor(utils.rgba_to_argb(params.get_param_view("DefaultShapeColor")))
- im = QtGui.QImage(32,32,QtGui.QImage.Format_ARGB32)
+ im = QtGui.QImage(32, 32, QtGui.QImage.Format_ARGB32)
im.fill(QtCore.Qt.transparent)
pt = QtGui.QPainter(im)
pt.setPen(QtGui.QPen(QtCore.Qt.black, 1, QtCore.Qt.SolidLine, QtCore.Qt.FlatCap))
pt.setBrush(QtGui.QBrush(linecolor, QtCore.Qt.SolidPattern))
- pts = [QtCore.QPointF(4.0,4.0), QtCore.QPointF(4.0,26.0), QtCore.QPointF(26.0,4.0)]
+ pts = [QtCore.QPointF(4.0, 4.0), QtCore.QPointF(4.0, 26.0), QtCore.QPointF(26.0, 4.0)]
pt.drawPolygon(pts, QtCore.Qt.OddEvenFill)
pt.setBrush(QtGui.QBrush(facecolor, QtCore.Qt.SolidPattern))
- pts = [QtCore.QPointF(28.0,28.0),QtCore.QPointF(8.0,28.0),QtCore.QPointF(28.0,8.0)]
- pt.drawPolygon(pts,QtCore.Qt.OddEvenFill)
+ pts = [QtCore.QPointF(28.0, 28.0), QtCore.QPointF(8.0, 28.0), QtCore.QPointF(28.0, 8.0)]
+ pt.drawPolygon(pts, QtCore.Qt.OddEvenFill)
pt.end()
icon = QtGui.QIcon(QtGui.QPixmap.fromImage(im))
linewidth = params.get_param_view("DefaultShapeLineWidth")
fontsize = params.get_param("textheight")
- txt = str(linewidth) + "px | "\
- + FreeCAD.Units.Quantity(fontsize,FreeCAD.Units.Length).UserString
+ txt = (
+ str(linewidth)
+ + "px | "
+ + FreeCAD.Units.Quantity(fontsize, FreeCAD.Units.Length).UserString
+ )
self.styleButton.setIcon(icon)
self.styleButton.setText(txt)
@@ -1458,17 +1617,17 @@ class DraftToolBar:
self.linewidth = linewidth
self.fontsize = fontsize
- def popupMenu(self,llist,ilist=None,pos=None):
+ def popupMenu(self, llist, ilist=None, pos=None):
"""pops up a menu filled with the given list
"---" in llist inserts a separator
"""
self.groupmenu = QtWidgets.QMenu()
- for i,l in enumerate(llist):
+ for i, l in enumerate(llist):
if "---" in l:
self.groupmenu.addSeparator()
elif ilist:
- self.groupmenu.addAction(ilist[i],l)
+ self.groupmenu.addAction(ilist[i], l)
else:
self.groupmenu.addAction(l)
if not pos:
@@ -1476,15 +1635,15 @@ class DraftToolBar:
self.groupmenu.popup(pos)
self.groupmenu.triggered.connect(self.popupTriggered)
- def getIcon(self,iconpath):
+ def getIcon(self, iconpath):
return QtGui.QIcon(iconpath)
- def popupTriggered(self,action):
+ def popupTriggered(self, action):
self.sourceCmd.proceed(str(action.text()))
- def setRadiusValue(self,val,unit=None):
+ def setRadiusValue(self, val, unit=None):
# print("DEBUG: setRadiusValue val: ", val, " unit: ", unit)
- if not isinstance(val, (int, float)): # some code passes strings
+ if not isinstance(val, (int, float)): # some code passes strings
t = val
elif unit:
t = display_external(val, None, unit)
@@ -1496,12 +1655,15 @@ class DraftToolBar:
def runAutoGroup(self):
FreeCADGui.runCommand("Draft_AutoGroup")
- def setAutoGroup(self,value=None):
+ def setAutoGroup(self, value=None):
if value is None:
self.autogroup = None
self.autoGroupButton.setText(translate("draft", "None"))
- self.autoGroupButton.setIcon(QtGui.QIcon.fromTheme('Draft_AutoGroup_off',
- QtGui.QIcon(':/icons/button_invalid.svg')))
+ self.autoGroupButton.setIcon(
+ QtGui.QIcon.fromTheme(
+ "Draft_AutoGroup_off", QtGui.QIcon(":/icons/button_invalid.svg")
+ )
+ )
self.autoGroupButton.setToolTip(translate("draft", "Autogroup off"))
self.autoGroupButton.setDown(False)
else:
@@ -1515,41 +1677,44 @@ class DraftToolBar:
else:
self.autogroup = None
self.autoGroupButton.setText(translate("draft", "None"))
- self.autoGroupButton.setIcon(QtGui.QIcon.fromTheme('Draft_AutoGroup_off',
- QtGui.QIcon(':/icons/button_invalid.svg')))
+ self.autoGroupButton.setIcon(
+ QtGui.QIcon.fromTheme(
+ "Draft_AutoGroup_off", QtGui.QIcon(":/icons/button_invalid.svg")
+ )
+ )
self.autoGroupButton.setToolTip(translate("draft", "Autogroup off"))
self.autoGroupButton.setDown(False)
- def getXPM(self,iconname,size=16):
- i = QtGui.QIcon(":/icons/"+iconname+".svg")
- p = i.pixmap(size,size)
+ def getXPM(self, iconname, size=16):
+ i = QtGui.QIcon(":/icons/" + iconname + ".svg")
+ p = i.pixmap(size, size)
a = QtCore.QByteArray()
b = QtCore.QBuffer(a)
b.open(QtCore.QIODevice.WriteOnly)
- p.save(b,"XPM")
+ p.save(b, "XPM")
b.close()
return str(a)
def togglesnap(self):
FreeCADGui.doCommand('FreeCADGui.runCommand("Draft_Snap_Lock")')
- def toggleradius(self,val):
- if hasattr(FreeCADGui,"Snapper"):
+ def toggleradius(self, val):
+ if hasattr(FreeCADGui, "Snapper"):
par = params.get_param("snapRange")
- params.set_param("snapRange", max(0, par+val))
+ params.set_param("snapRange", max(0, par + val))
FreeCADGui.Snapper.showradius()
- def constrain(self,val):
+ def constrain(self, val):
if val == "angle":
- self.alock = not(self.alock)
+ self.alock = not (self.alock)
self.angleLock.setChecked(self.alock)
elif self.mask == val:
self.mask = None
- if hasattr(FreeCADGui,"Snapper"):
+ if hasattr(FreeCADGui, "Snapper"):
FreeCADGui.Snapper.mask = None
else:
self.mask = val
- if hasattr(FreeCADGui,"Snapper"):
+ if hasattr(FreeCADGui, "Snapper"):
FreeCADGui.Snapper.mask = val
self.new_point = FreeCADGui.Snapper.constrain(self.new_point, self.get_last_point())
@@ -1612,7 +1777,7 @@ class DraftToolBar:
angle_vec = self.angle
FreeCADGui.Snapper.setAngle(angle_vec)
- def toggleAngle(self,b):
+ def toggleAngle(self, b):
self.alock = self.angleLock.isChecked()
self.update_cartesian_coords()
self.updateSnapper()
@@ -1628,24 +1793,26 @@ class DraftToolBar:
self.angle = None
def update_spherical_coords(self):
- length, theta, phi = DraftVecUtils.get_spherical_coords(
- self.x,self.y,self.z)
+ length, theta, phi = DraftVecUtils.get_spherical_coords(self.x, self.y, self.z)
self.lvalue = length
self.pvalue = math.degrees(theta)
self.avalue = math.degrees(phi)
- self.angle = FreeCAD.Vector(DraftVecUtils.get_cartesian_coords(
- 1, theta, phi))
- self.lengthValue.setText(display_external(self.lvalue,None,'Length'))
- self.angleValue.setText(display_external(self.avalue,None,'Angle'))
+ self.angle = FreeCAD.Vector(DraftVecUtils.get_cartesian_coords(1, theta, phi))
+ self.lengthValue.setText(display_external(self.lvalue, None, "Length"))
+ self.angleValue.setText(display_external(self.avalue, None, "Angle"))
def update_cartesian_coords(self):
self.x, self.y, self.z = DraftVecUtils.get_cartesian_coords(
- self.lvalue,math.radians(self.pvalue),math.radians(self.avalue))
- self.angle = FreeCAD.Vector(DraftVecUtils.get_cartesian_coords(
- 1, math.radians(self.pvalue), math.radians(self.avalue)))
- self.xValue.setText(display_external(self.x,None,'Length'))
- self.yValue.setText(display_external(self.y,None,'Length'))
- self.zValue.setText(display_external(self.z,None,'Length'))
+ self.lvalue, math.radians(self.pvalue), math.radians(self.avalue)
+ )
+ self.angle = FreeCAD.Vector(
+ DraftVecUtils.get_cartesian_coords(
+ 1, math.radians(self.pvalue), math.radians(self.avalue)
+ )
+ )
+ self.xValue.setText(display_external(self.x, None, "Length"))
+ self.yValue.setText(display_external(self.y, None, "Length"))
+ self.zValue.setText(display_external(self.z, None, "Length"))
def get_last_point(self):
"""Get the last point in the GCS."""
@@ -1673,51 +1840,70 @@ class DraftToolBar:
base_point = self.get_last_point()
return base_point + delta
-#---------------------------------------------------------------------------
-# TaskView operations
-#---------------------------------------------------------------------------
+ # ---------------------------------------------------------------------------
+ # TaskView operations
+ # ---------------------------------------------------------------------------
def setWatchers(self):
class DraftCreateWatcher:
def __init__(self):
- self.commands = ["Draft_Line","Draft_Wire",
- "Draft_Rectangle","Draft_Arc",
- "Draft_Circle","Draft_BSpline",
- "Draft_Text","Draft_Dimension",
- "Draft_ShapeString","Draft_BezCurve"]
+ self.commands = [
+ "Draft_Line",
+ "Draft_Wire",
+ "Draft_Rectangle",
+ "Draft_Arc",
+ "Draft_Circle",
+ "Draft_BSpline",
+ "Draft_Text",
+ "Draft_Dimension",
+ "Draft_ShapeString",
+ "Draft_BezCurve",
+ ]
self.title = "Create objects"
+
def shouldShow(self):
- return (FreeCAD.ActiveDocument is not None) and (not FreeCADGui.Selection.getSelection())
+ return (FreeCAD.ActiveDocument is not None) and (
+ not FreeCADGui.Selection.getSelection()
+ )
class DraftModifyWatcher:
def __init__(self):
- self.commands = ["Draft_Move","Draft_Rotate",
- "Draft_Scale","Draft_Offset",
- "Draft_Trimex","Draft_Upgrade",
- "Draft_Downgrade","Draft_Edit"]
+ self.commands = [
+ "Draft_Move",
+ "Draft_Rotate",
+ "Draft_Scale",
+ "Draft_Offset",
+ "Draft_Trimex",
+ "Draft_Upgrade",
+ "Draft_Downgrade",
+ "Draft_Edit",
+ ]
self.title = translate("draft", "Modify Objects")
- def shouldShow(self):
- return (FreeCAD.ActiveDocument is not None) and (FreeCADGui.Selection.getSelection() != [])
- FreeCADGui.Control.addTaskWatcher([DraftCreateWatcher(),DraftModifyWatcher()])
+ def shouldShow(self):
+ return (FreeCAD.ActiveDocument is not None) and (
+ FreeCADGui.Selection.getSelection() != []
+ )
+
+ FreeCADGui.Control.addTaskWatcher([DraftCreateWatcher(), DraftModifyWatcher()])
def changeEvent(self, event):
if event.type() == QtCore.QEvent.LanguageChange:
- #print("Language changed!")
+ # print("Language changed!")
self.ui.retranslateUi(self)
def Activated(self):
self.setWatchers()
- if hasattr(self,"tray"):
+ if hasattr(self, "tray"):
todo.delay(self.tray.show, None)
def Deactivated(self):
- if (FreeCAD.activeDraftCommand is not None):
+ if FreeCAD.activeDraftCommand is not None:
self.continueMode = False
FreeCAD.activeDraftCommand.finish()
FreeCADGui.Control.clearTaskWatcher()
- #self.tray = None
- if hasattr(self,"tray"):
+ # self.tray = None
+ if hasattr(self, "tray"):
todo.delay(self.tray.hide, None)
def reset_ui_values(self):
@@ -1736,7 +1922,8 @@ class DraftToolBar:
class FacebinderTaskPanel:
- '''A TaskPanel for the facebinder'''
+ """A TaskPanel for the facebinder"""
+
def __init__(self):
self.obj = None
@@ -1751,7 +1938,7 @@ class FacebinderTaskPanel:
self.tree = QtWidgets.QTreeWidget(self.form)
self.grid.addWidget(self.tree, 1, 0, 1, 2)
self.tree.setColumnCount(2)
- self.tree.setHeaderLabels(["Name","Subelement"])
+ self.tree.setHeaderLabels(["Name", "Subelement"])
# buttons
self.addButton = QtWidgets.QPushButton(self.form)
@@ -1782,17 +1969,17 @@ class FacebinderTaskPanel:
self.tree.clear()
if self.obj:
for f in self.obj.Faces:
- if isinstance(f[1],tuple):
+ if isinstance(f[1], tuple):
for subf in f[1]:
item = QtWidgets.QTreeWidgetItem(self.tree)
- item.setText(0,f[0].Name)
+ item.setText(0, f[0].Name)
item.setIcon(0, QtGui.QIcon(":/icons/Part_3D_object.svg"))
- item.setText(1,subf)
+ item.setText(1, subf)
else:
item = QtWidgets.QTreeWidgetItem(self.tree)
- item.setText(0,f[0].Name)
+ item.setText(0, f[0].Name)
item.setIcon(0, QtGui.QIcon(":/icons/Part_3D_object.svg"))
- item.setText(1,f[1])
+ item.setText(1, f[1])
self.retranslateUi(self.form)
def addElement(self):
@@ -1805,16 +1992,16 @@ class FacebinderTaskPanel:
flist = self.obj.Faces
found = False
for face in flist:
- if (face[0] == obj.Name):
- if isinstance(face[1],tuple):
+ if face[0] == obj.Name:
+ if isinstance(face[1], tuple):
for subf in face[1]:
if subf == elt:
found = True
else:
- if (face[1] == elt):
+ if face[1] == elt:
found = True
if not found:
- flist.append((obj,elt))
+ flist.append((obj, elt))
self.obj.Faces = flist
FreeCAD.ActiveDocument.recompute()
self.update()
@@ -1827,15 +2014,15 @@ class FacebinderTaskPanel:
elt = str(it.text(1))
flist = []
for face in self.obj.Faces:
- if (face[0].Name != obj.Name):
+ if face[0].Name != obj.Name:
flist.append(face)
else:
- if isinstance(face[1],tuple):
+ if isinstance(face[1], tuple):
for subf in face[1]:
if subf != elt:
- flist.append((obj,subf))
+ flist.append((obj, subf))
else:
- if (face[1] != elt):
+ if face[1] != elt:
flist.append(face)
self.obj.Faces = flist
FreeCAD.ActiveDocument.recompute()
@@ -1852,7 +2039,8 @@ class FacebinderTaskPanel:
self.addButton.setText(QtWidgets.QApplication.translate("draft", "Add", None))
self.title.setText(QtWidgets.QApplication.translate("draft", "Facebinder Elements", None))
-#def translateWidget(w, context=None, disAmb=None):
+
+# def translateWidget(w, context=None, disAmb=None):
# '''translator for items where retranslateUi() is unavailable.
# translates widget w and children.'''
# #handle w itself
@@ -1889,6 +2077,6 @@ class FacebinderTaskPanel:
## msg = "TranslateWidget: Can not translate widget: {0} type: {1}\n".format(w.objectName(),w.metaObject().className())
## FreeCAD.Console.PrintMessage(msg)
-if not hasattr(FreeCADGui,"draftToolBar"):
+if not hasattr(FreeCADGui, "draftToolBar"):
FreeCADGui.draftToolBar = DraftToolBar()
-#----End of Python Features Definitions----#
+# ----End of Python Features Definitions----#
diff --git a/src/Mod/Draft/DraftTools.py b/src/Mod/Draft/DraftTools.py
index a767de16ba..fa5ba57d86 100644
--- a/src/Mod/Draft/DraftTools.py
+++ b/src/Mod/Draft/DraftTools.py
@@ -61,8 +61,7 @@ True if Draft_rc.__name__ else False
True if DraftGui.__name__ else False
__title__ = "FreeCAD Draft Workbench GUI Tools"
-__author__ = ("Yorik van Havre, Werner Mayer, Martin Burbaum, Ken Cline, "
- "Dmitry Chigrin")
+__author__ = "Yorik van Havre, Werner Mayer, Martin Burbaum, Ken Cline, " "Dmitry Chigrin"
__url__ = "https://www.freecad.org"
if not hasattr(FreeCADGui, "Snapper"):
diff --git a/src/Mod/Draft/DraftVecUtils.py b/src/Mod/Draft/DraftVecUtils.py
index 57c83f612b..8bd3edb24e 100644
--- a/src/Mod/Draft/DraftVecUtils.py
+++ b/src/Mod/Draft/DraftVecUtils.py
@@ -50,6 +50,7 @@ __url__ = "https://www.freecad.org"
## \addtogroup DRAFTVECUTILS
# @{
+
# @deprecated("use Draft.precision() instead.")
def precision():
"""
@@ -65,11 +66,16 @@ def precision():
Return the number of fractional decimal digits as configured
in Draft preferences.
"""
- warnings.warn("Call to deprecated function 'DraftVecUtils.precision()'."
- + " Please consider using Draft.precision().",
- DeprecationWarning, stacklevel=2)
- messages._wrn("DraftVecUtils.precision() called, which is deprecated."
- + " Please consider using Draft.precision(). ")
+ warnings.warn(
+ "Call to deprecated function 'DraftVecUtils.precision()'."
+ + " Please consider using Draft.precision().",
+ DeprecationWarning,
+ stacklevel=2,
+ )
+ messages._wrn(
+ "DraftVecUtils.precision() called, which is deprecated."
+ + " Please consider using Draft.precision(). "
+ )
return draft_precision()
@@ -237,7 +243,7 @@ def scale(u, scalar):
The new vector with each of its elements multiplied by `scalar`.
"""
typecheck([(u, Vector), (scalar, (int, int, float))], "scale")
- return Vector(u.x*scalar, u.y*scalar, u.z*scalar)
+ return Vector(u.x * scalar, u.y * scalar, u.z * scalar)
def scaleTo(u, l):
@@ -270,8 +276,8 @@ def scaleTo(u, l):
if u.Length == 0:
return Vector(u)
else:
- a = l/u.Length
- return Vector(u.x*a, u.y*a, u.z*a)
+ a = l / u.Length
+ return Vector(u.x * a, u.y * a, u.z * a)
def dist(u, v):
@@ -338,7 +344,7 @@ def angle(u, v=Vector(1, 0, 0), normal=Vector(0, 0, 1)):
return 0
# The dot product indicates the projection of one vector over the other
- dp = u.dot(v)/ll
+ dp = u.dot(v) / ll
# Due to rounding errors, the dot product could be outside
# the range [-1, 1], so let's force it to be within this range.
@@ -390,7 +396,7 @@ def project(u, v):
return Vector(0, 0, 0) # to avoid division by zero
# Why specifically this value? This should be an else?
if dp != 15:
- return scale(v, u.dot(v)/dp)
+ return scale(v, u.dot(v) / dp)
# Return a null vector if the magnitude squared is 15, why?
return Vector(0, 0, 0)
@@ -476,9 +482,9 @@ def rotate(u, angle, axis=Vector(0, 0, 1)):
# Unit components, so that x**2 + y**2 + z**2 = 1
L = axis.Length
- x = axis.x/L
- y = axis.y/L
- z = axis.z/L
+ x = axis.x / L
+ y = axis.y / L
+ z = axis.z / L
c = math.cos(angle)
s = math.sin(angle)
@@ -571,7 +577,7 @@ def isNull(vector, precision=None):
x = round(vector.x, precision)
y = round(vector.y, precision)
z = round(vector.z, precision)
- return (x == 0 and y == 0 and z == 0)
+ return x == 0 and y == 0 and z == 0
def find(vector, vlist, precision=None):
@@ -724,7 +730,7 @@ def isColinear(vlist, precision=None):
return True
-def rounded(v,precision=None):
+def rounded(v, precision=None):
"""Return a vector rounded to the `precision` in the parameter database
or to the given decimals value
@@ -736,7 +742,7 @@ def rounded(v,precision=None):
v : Base::Vector3
The input vector.
precision : int | None
- mathematical precision - if None use configured draft
+ mathematical precision - if None use configured draft
precision
@@ -752,7 +758,7 @@ def rounded(v,precision=None):
return Vector(round(v.x, precision), round(v.y, precision), round(v.z, precision))
-def getPlaneRotation(u, v, _ = None):
+def getPlaneRotation(u, v, _=None):
"""Return a rotation matrix defining the (u,v,w) coordinate system.
The rotation matrix uses the elements from each vector.
@@ -840,12 +846,13 @@ def removeDoubles(vlist, precision=None):
# Iterate until the penultimate element, and test for equality
# with the element in front
for i in range(len(vlist) - 1):
- if not equals(vlist[i], vlist[i+1], precision):
+ if not equals(vlist[i], vlist[i + 1], precision):
nlist.append(vlist[i])
# Add the last element
nlist.append(vlist[-1])
return nlist
+
def get_spherical_coords(x, y, z, precision=None):
"""Get the Spherical coordinates of the vector represented
by Cartesian coordinates (x, y, z).
@@ -853,7 +860,7 @@ def get_spherical_coords(x, y, z, precision=None):
Parameters
----------
vector : Base::Vector3
- The input vector.
+ The input vector.
precision : int | None
mathematical precision - if None use configured draft
precision
@@ -877,23 +884,23 @@ def get_spherical_coords(x, y, z, precision=None):
if precision is None:
precision = params.get_param("precision")
- v = Vector(x,y,z)
- x_axis = Vector(1,0,0)
- z_axis = Vector(0,0,1)
- y_axis = Vector(0,1,0)
+ v = Vector(x, y, z)
+ x_axis = Vector(1, 0, 0)
+ z_axis = Vector(0, 0, 1)
+ y_axis = Vector(0, 1, 0)
rad = v.Length
if not bool(round(rad, precision)):
- return (0, math.pi/2, 0)
+ return (0, math.pi / 2, 0)
theta = v.getAngle(z_axis)
- v.projectToPlane(Vector(0,0,0), z_axis)
+ v.projectToPlane(Vector(0, 0, 0), z_axis)
phi = v.getAngle(x_axis)
if math.isnan(phi):
return (rad, theta, 0)
# projected vector is on 3rd or 4th quadrant
if v.dot(Vector(y_axis)) < 0:
- phi = -1*phi
+ phi = -1 * phi
return (rad, theta, phi)
@@ -917,9 +924,9 @@ def get_cartesian_coords(radius, theta, phi):
Tuple (x, y, z) with the Cartesian coordinates.
"""
- x = radius*math.sin(theta)*math.cos(phi)
- y = radius*math.sin(theta)*math.sin(phi)
- z = radius*math.cos(theta)
+ x = radius * math.sin(theta) * math.cos(phi)
+ y = radius * math.sin(theta) * math.sin(phi)
+ z = radius * math.cos(theta)
return (x, y, z)
diff --git a/src/Mod/Draft/DxfImportDialog.py b/src/Mod/Draft/DxfImportDialog.py
index c260b6fd92..bd9a992b04 100644
--- a/src/Mod/Draft/DxfImportDialog.py
+++ b/src/Mod/Draft/DxfImportDialog.py
@@ -2,10 +2,12 @@ import FreeCAD
import FreeCADGui
from PySide import QtCore, QtGui
+
class DxfImportDialog:
"""
A controller class that creates, manages, and shows the DXF import dialog.
"""
+
def __init__(self, entity_counts, parent=None):
# Step 1: Load the UI from the resource file. This returns a new QDialog instance.
self.dialog = FreeCADGui.PySideUic.loadUi(":/ui/preferences-dxf-import.ui")
@@ -21,7 +23,9 @@ class DxfImportDialog:
def setup_ui(self):
"""Perform initial UI setup."""
- self.dialog.label_Summary.setText(f"File contains approximately {self.total_entities} geometric entities.")
+ self.dialog.label_Summary.setText(
+ f"File contains approximately {self.total_entities} geometric entities."
+ )
self.dialog.label_Warning.hide()
def connect_signals(self):
@@ -42,14 +46,18 @@ class DxfImportDialog:
def on_accept(self):
"""Custom slot to debug the OK button click."""
- FreeCAD.Console.PrintLog("DxfImportDialog: 'OK' button clicked. Calling self.dialog.accept().\n")
+ FreeCAD.Console.PrintLog(
+ "DxfImportDialog: 'OK' button clicked. Calling self.dialog.accept().\n"
+ )
# Manually call the original slot
self.dialog.accept()
FreeCAD.Console.PrintLog("DxfImportDialog: self.dialog.accept() has been called.\n")
def on_reject(self):
"""Custom slot to debug the Cancel button click."""
- FreeCAD.Console.PrintLog("DxfImportDialog: 'Cancel' button clicked. Calling self.dialog.reject().\n")
+ FreeCAD.Console.PrintLog(
+ "DxfImportDialog: 'Cancel' button clicked. Calling self.dialog.reject().\n"
+ )
# Manually call the original slot
self.dialog.reject()
FreeCAD.Console.PrintLog("DxfImportDialog: self.dialog.reject() has been called.\n")
@@ -89,26 +97,40 @@ class DxfImportDialog:
current_mode = self.get_selected_mode()
if self.total_entities > 5000 and (current_mode == 0 or current_mode == 1):
- self.dialog.label_Warning.setText("Warning: Importing over 5000 entities as editable objects can be very slow.")
+ self.dialog.label_Warning.setText(
+ "Warning: Importing over 5000 entities as editable objects can be very slow."
+ )
self.dialog.label_Warning.show()
elif self.total_entities > 20000 and current_mode == 2:
- self.dialog.label_Warning.setText("Warning: Importing over 20,000 entities as individual shapes may be slow.")
+ self.dialog.label_Warning.setText(
+ "Warning: Importing over 20,000 entities as individual shapes may be slow."
+ )
self.dialog.label_Warning.show()
def exec_(self):
FreeCAD.Console.PrintLog("DxfImportDialog: Calling self.dialog.exec_()...\n")
result = self.dialog.exec_()
- FreeCAD.Console.PrintLog("DxfImportDialog: self.dialog.exec_() returned with result: {}\n".format(result))
+ FreeCAD.Console.PrintLog(
+ "DxfImportDialog: self.dialog.exec_() returned with result: {}\n".format(result)
+ )
# QDialog.Accepted is usually 1, Rejected is 0.
- FreeCAD.Console.PrintLog("(Note: QDialog.Accepted = {}, QDialog.Rejected = {})\n".format(QtGui.QDialog.Accepted, QtGui.QDialog.Rejected))
+ FreeCAD.Console.PrintLog(
+ "(Note: QDialog.Accepted = {}, QDialog.Rejected = {})\n".format(
+ QtGui.QDialog.Accepted, QtGui.QDialog.Rejected
+ )
+ )
return result
def get_selected_mode(self):
"""Return the integer value of the selected import mode."""
- if self.dialog.radio_ImportAs_Draft.isChecked(): return 0
- if self.dialog.radio_ImportAs_Primitives.isChecked(): return 1
- if self.dialog.radio_ImportAs_Fused.isChecked(): return 3
- if self.dialog.radio_ImportAs_Shapes.isChecked(): return 2
+ if self.dialog.radio_ImportAs_Draft.isChecked():
+ return 0
+ if self.dialog.radio_ImportAs_Primitives.isChecked():
+ return 1
+ if self.dialog.radio_ImportAs_Fused.isChecked():
+ return 3
+ if self.dialog.radio_ImportAs_Shapes.isChecked():
+ return 2
return 2
def get_show_dialog_again(self):
diff --git a/src/Mod/Draft/InitGui.py b/src/Mod/Draft/InitGui.py
index 7f014ea05c..8a7c7d0711 100644
--- a/src/Mod/Draft/InitGui.py
+++ b/src/Mod/Draft/InitGui.py
@@ -39,9 +39,7 @@ class DraftWorkbench(FreeCADGui.Workbench):
__dirname__ = os.path.join(FreeCAD.getResourceDir(), "Mod", "Draft")
_tooltip = "The Draft workbench is used for 2D drafting on a grid"
- self.__class__.Icon = os.path.join(__dirname__,
- "Resources", "icons",
- "DraftWorkbench.svg")
+ self.__class__.Icon = os.path.join(__dirname__, "Resources", "icons", "DraftWorkbench.svg")
self.__class__.MenuText = QT_TRANSLATE_NOOP("draft", "Draft")
self.__class__.ToolTip = QT_TRANSLATE_NOOP("draft", _tooltip)
@@ -55,21 +53,26 @@ class DraftWorkbench(FreeCADGui.Workbench):
dependencies_OK = False
try:
from pivy import coin
+
if FreeCADGui.getSoDBVersion() != coin.SoDB.getVersion():
- raise AssertionError("FreeCAD and Pivy use different versions "
- "of Coin. "
- "This will lead to unexpected behaviour.")
+ raise AssertionError(
+ "FreeCAD and Pivy use different versions "
+ "of Coin. "
+ "This will lead to unexpected behaviour."
+ )
except AssertionError:
- FreeCAD.Console.PrintWarning("Error: FreeCAD and Pivy "
- "use different versions of Coin. "
- "This will lead to unexpected "
- "behaviour.\n")
+ FreeCAD.Console.PrintWarning(
+ "Error: FreeCAD and Pivy "
+ "use different versions of Coin. "
+ "This will lead to unexpected "
+ "behaviour.\n"
+ )
except ImportError:
- FreeCAD.Console.PrintWarning("Error: Pivy not found, "
- "Draft Workbench will be disabled.\n")
+ FreeCAD.Console.PrintWarning(
+ "Error: Pivy not found, " "Draft Workbench will be disabled.\n"
+ )
except Exception:
- FreeCAD.Console.PrintWarning("Error: Unknown error "
- "while trying to load Pivy.\n")
+ FreeCAD.Console.PrintWarning("Error: Unknown error " "while trying to load Pivy.\n")
else:
dependencies_OK = True
@@ -81,16 +84,20 @@ class DraftWorkbench(FreeCADGui.Workbench):
import Draft_rc
import DraftTools
import DraftGui
+
FreeCADGui.addLanguagePath(":/translations")
FreeCADGui.addIconPath(":/icons")
except Exception as exc:
FreeCAD.Console.PrintError(exc)
- FreeCAD.Console.PrintError("Error: Initializing one or more "
- "of the Draft modules failed, "
- "Draft will not work as expected.\n")
+ FreeCAD.Console.PrintError(
+ "Error: Initializing one or more "
+ "of the Draft modules failed, "
+ "Draft will not work as expected.\n"
+ )
# Set up command lists
import draftutils.init_tools as it
+
self.drawing_commands = it.get_draft_drawing_commands()
self.annotation_commands = it.get_draft_annotation_commands()
self.modification_commands = it.get_draft_modification_commands()
@@ -99,51 +106,60 @@ class DraftWorkbench(FreeCADGui.Workbench):
self.context_commands = it.get_draft_context_commands()
# Set up toolbars
- it.init_toolbar(self,
- QT_TRANSLATE_NOOP("Workbench", "Draft Creation"),
- self.drawing_commands)
- it.init_toolbar(self,
- QT_TRANSLATE_NOOP("Workbench", "Draft Annotation"),
- self.annotation_commands)
- it.init_toolbar(self,
- QT_TRANSLATE_NOOP("Workbench", "Draft Modification"),
- self.modification_commands)
- it.init_toolbar(self,
- QT_TRANSLATE_NOOP("Workbench", "Draft Utility"),
- self.utility_commands_toolbar)
- it.init_toolbar(self,
- QT_TRANSLATE_NOOP("Workbench", "Draft Snap"),
- it.get_draft_snap_commands())
+ it.init_toolbar(
+ self, QT_TRANSLATE_NOOP("Workbench", "Draft Creation"), self.drawing_commands
+ )
+ it.init_toolbar(
+ self, QT_TRANSLATE_NOOP("Workbench", "Draft Annotation"), self.annotation_commands
+ )
+ it.init_toolbar(
+ self, QT_TRANSLATE_NOOP("Workbench", "Draft Modification"), self.modification_commands
+ )
+ it.init_toolbar(
+ self, QT_TRANSLATE_NOOP("Workbench", "Draft Utility"), self.utility_commands_toolbar
+ )
+ it.init_toolbar(
+ self, QT_TRANSLATE_NOOP("Workbench", "Draft Snap"), it.get_draft_snap_commands()
+ )
# Set up menus
- it.init_menu(self,
- [QT_TRANSLATE_NOOP("Workbench", "&Drafting")],
- self.drawing_commands)
- it.init_menu(self,
- [QT_TRANSLATE_NOOP("Workbench", "&Annotation")],
- self.annotation_commands)
- it.init_menu(self,
- [QT_TRANSLATE_NOOP("Workbench", "&Modification")],
- self.modification_commands)
- it.init_menu(self,
- [QT_TRANSLATE_NOOP("Workbench", "&Utilities")],
- self.utility_commands_menu)
+ it.init_menu(self, [QT_TRANSLATE_NOOP("Workbench", "&Drafting")], self.drawing_commands)
+ it.init_menu(
+ self, [QT_TRANSLATE_NOOP("Workbench", "&Annotation")], self.annotation_commands
+ )
+ it.init_menu(
+ self, [QT_TRANSLATE_NOOP("Workbench", "&Modification")], self.modification_commands
+ )
+ it.init_menu(
+ self, [QT_TRANSLATE_NOOP("Workbench", "&Utilities")], self.utility_commands_menu
+ )
# Set up preferences pages
if hasattr(FreeCADGui, "draftToolBar"):
if not hasattr(FreeCADGui.draftToolBar, "loadedPreferences"):
from draftutils import params
+
params._param_observer_start()
- FreeCADGui.addPreferencePage(":/ui/preferences-draft.ui", QT_TRANSLATE_NOOP("QObject", "Draft"))
- FreeCADGui.addPreferencePage(":/ui/preferences-draftinterface.ui", QT_TRANSLATE_NOOP("QObject", "Draft"))
- FreeCADGui.addPreferencePage(":/ui/preferences-draftsnap.ui", QT_TRANSLATE_NOOP("QObject", "Draft"))
- FreeCADGui.addPreferencePage(":/ui/preferences-draftvisual.ui", QT_TRANSLATE_NOOP("QObject", "Draft"))
- FreeCADGui.addPreferencePage(":/ui/preferences-drafttexts.ui", QT_TRANSLATE_NOOP("QObject", "Draft"))
+ FreeCADGui.addPreferencePage(
+ ":/ui/preferences-draft.ui", QT_TRANSLATE_NOOP("QObject", "Draft")
+ )
+ FreeCADGui.addPreferencePage(
+ ":/ui/preferences-draftinterface.ui", QT_TRANSLATE_NOOP("QObject", "Draft")
+ )
+ FreeCADGui.addPreferencePage(
+ ":/ui/preferences-draftsnap.ui", QT_TRANSLATE_NOOP("QObject", "Draft")
+ )
+ FreeCADGui.addPreferencePage(
+ ":/ui/preferences-draftvisual.ui", QT_TRANSLATE_NOOP("QObject", "Draft")
+ )
+ FreeCADGui.addPreferencePage(
+ ":/ui/preferences-drafttexts.ui", QT_TRANSLATE_NOOP("QObject", "Draft")
+ )
FreeCADGui.draftToolBar.loadedPreferences = True
FreeCADGui.getMainWindow().mainWindowClosed.connect(self.Deactivated)
- FreeCAD.Console.PrintLog('Loading Draft workbench, done.\n')
+ FreeCAD.Console.PrintLog("Loading Draft workbench, done.\n")
def Activated(self):
"""When entering the workbench."""
@@ -152,10 +168,13 @@ class DraftWorkbench(FreeCADGui.Workbench):
if hasattr(FreeCADGui, "Snapper"):
FreeCADGui.Snapper.show()
from draftutils import init_draft_statusbar
+
init_draft_statusbar.show_draft_statusbar()
import WorkingPlane
+
WorkingPlane._view_observer_start() # Updates the draftToolBar when switching views.
from draftutils import grid_observer
+
grid_observer._view_observer_setup()
FreeCAD.Console.PrintLog("Draft workbench activated.\n")
@@ -166,10 +185,13 @@ class DraftWorkbench(FreeCADGui.Workbench):
if hasattr(FreeCADGui, "Snapper"):
FreeCADGui.Snapper.hide()
from draftutils import init_draft_statusbar
+
init_draft_statusbar.hide_draft_statusbar()
import WorkingPlane
+
WorkingPlane._view_observer_stop()
from draftutils import grid_observer
+
grid_observer._view_observer_setup()
FreeCAD.Console.PrintLog("Draft workbench deactivated.\n")
@@ -186,7 +208,12 @@ class DraftWorkbench(FreeCADGui.Workbench):
from draftguitools import gui_hyperlink
hyperlinks_search = gui_hyperlink.Draft_Hyperlink()
- if hyperlinks_search.has_hyperlinks() and sys.platform in ["win32", "cygwin", "darwin", "linux"]:
+ if hyperlinks_search.has_hyperlinks() and sys.platform in [
+ "win32",
+ "cygwin",
+ "darwin",
+ "linux",
+ ]:
self.appendContextMenu("", ["Draft_Hyperlink"])
self.appendContextMenu("Utilities", self.context_commands)
@@ -202,9 +229,18 @@ FreeCADGui.addWorkbench(DraftWorkbench)
# are independent of the loading of the workbench and can be loaded at startup
import Draft_rc
from PySide.QtCore import QT_TRANSLATE_NOOP
-FreeCADGui.addPreferencePage(":/ui/preferences-dxf.ui", QT_TRANSLATE_NOOP("QObject", "Import-Export"))
-FreeCADGui.addPreferencePage(":/ui/preferences-dwg.ui", QT_TRANSLATE_NOOP("QObject", "Import-Export"))
-FreeCADGui.addPreferencePage(":/ui/preferences-svg.ui", QT_TRANSLATE_NOOP("QObject", "Import-Export"))
-FreeCADGui.addPreferencePage(":/ui/preferences-oca.ui", QT_TRANSLATE_NOOP("QObject", "Import-Export"))
+
+FreeCADGui.addPreferencePage(
+ ":/ui/preferences-dxf.ui", QT_TRANSLATE_NOOP("QObject", "Import-Export")
+)
+FreeCADGui.addPreferencePage(
+ ":/ui/preferences-dwg.ui", QT_TRANSLATE_NOOP("QObject", "Import-Export")
+)
+FreeCADGui.addPreferencePage(
+ ":/ui/preferences-svg.ui", QT_TRANSLATE_NOOP("QObject", "Import-Export")
+)
+FreeCADGui.addPreferencePage(
+ ":/ui/preferences-oca.ui", QT_TRANSLATE_NOOP("QObject", "Import-Export")
+)
FreeCAD.__unit_test__ += ["TestDraftGui"]
diff --git a/src/Mod/Draft/Resources/ui/preferences-dxf-import.ui b/src/Mod/Draft/Resources/ui/preferences-dxf-import.ui
index a6b6b883e6..41ceef7d97 100644
--- a/src/Mod/Draft/Resources/ui/preferences-dxf-import.ui
+++ b/src/Mod/Draft/Resources/ui/preferences-dxf-import.ui
@@ -151,4 +151,4 @@ shape. Best for viewing very large files with maximum performance.
-
\ No newline at end of file
+
diff --git a/src/Mod/Draft/SVGPath.py b/src/Mod/Draft/SVGPath.py
index de596412c5..e5a58a310e 100644
--- a/src/Mod/Draft/SVGPath.py
+++ b/src/Mod/Draft/SVGPath.py
@@ -16,15 +16,16 @@ from Part import (
Edge,
Wire,
Compound,
- OCCError
+ OCCError,
)
-def _tolerance(precision):
- return 10**(-precision)
-def _arc_end_to_center(lastvec, currentvec, rx, ry,
- x_rotation=0.0, correction=False):
- '''Calculate the possible centers for an arc in endpoint parameterization.
+def _tolerance(precision):
+ return 10 ** (-precision)
+
+
+def _arc_end_to_center(lastvec, currentvec, rx, ry, x_rotation=0.0, correction=False):
+ """Calculate the possible centers for an arc in endpoint parameterization.
Calculate (positive and negative) possible centers for an arc given in
``endpoint parametrization``.
@@ -63,7 +64,7 @@ def _arc_end_to_center(lastvec, currentvec, rx, ry,
The first element of the list is the positive tuple,
consisting of center, angle, and angle increment;
the second element is the negative tuple.
- '''
+ """
# scalefacsign = 1 if (largeflag != sweepflag) else -1
rx = float(rx)
ry = float(ry)
@@ -84,11 +85,11 @@ def _arc_end_to_center(lastvec, currentvec, rx, ry,
# If the division is very small, set the scaling factor to zero,
# otherwise try to calculate it by taking the square root
- if abs(numer/denom) < 1.0e-7:
+ if abs(numer / denom) < 1.0e-7:
scalefacpos = 0
else:
try:
- scalefacpos = math.sqrt(numer/denom)
+ scalefacpos = math.sqrt(numer / denom)
except ValueError:
_msg("sqrt({0}/{1})".format(numer, denom))
scalefacpos = 0
@@ -97,7 +98,7 @@ def _arc_end_to_center(lastvec, currentvec, rx, ry,
for scalefacsign in (1, -1):
scalefac = scalefacpos * scalefacsign
# Step2 eq. 5.2
- vcx1 = Vector(v1.y * rx/ry, -v1.x * ry/rx, 0).multiply(scalefac)
+ vcx1 = Vector(v1.y * rx / ry, -v1.x * ry / rx, 0).multiply(scalefac)
m2 = Matrix()
m2.rotateZ(x_rotation)
centeroff = currentvec.add(lastvec)
@@ -112,16 +113,13 @@ def _arc_end_to_center(lastvec, currentvec, rx, ry,
# (-v1.y - vcx1.y)/ry,
# 0)) # eq. 5.6
# we need the right sign for the angle
- angle1 = angle(Vector(1, 0, 0),
- Vector((v1.x - vcx1.x)/rx,
- (v1.y - vcx1.y)/ry,
- 0)) # eq. 5.5
- angledelta = angle(Vector((v1.x - vcx1.x)/rx,
- (v1.y - vcx1.y)/ry,
- 0),
- Vector((-v1.x - vcx1.x)/rx,
- (-v1.y - vcx1.y)/ry,
- 0)) # eq. 5.6
+ angle1 = angle(
+ Vector(1, 0, 0), Vector((v1.x - vcx1.x) / rx, (v1.y - vcx1.y) / ry, 0)
+ ) # eq. 5.5
+ angledelta = angle(
+ Vector((v1.x - vcx1.x) / rx, (v1.y - vcx1.y) / ry, 0),
+ Vector((-v1.x - vcx1.x) / rx, (-v1.y - vcx1.y) / ry, 0),
+ ) # eq. 5.6
results.append((vcenter, angle1, angledelta))
if rx < 0 or ry < 0:
@@ -131,7 +129,7 @@ def _arc_end_to_center(lastvec, currentvec, rx, ry,
def _arc_center_to_end(center, rx, ry, angle1, angledelta, xrotation=0.0):
- '''Calculate start and end points, and flags of an arc.
+ """Calculate start and end points, and flags of an arc.
Calculate start and end points, and flags of an arc given in
``center parametrization``.
@@ -158,11 +156,9 @@ def _arc_center_to_end(center, rx, ry, angle1, angledelta, xrotation=0.0):
Tuple indicating the end points of the arc, and two boolean values
indicating whether the arc is less than 180 degrees or not,
and whether the angledelta is negative.
- '''
+ """
vr1 = Vector(rx * math.cos(angle1), ry * math.sin(angle1), 0)
- vr2 = Vector(rx * math.cos(angle1 + angledelta),
- ry * math.sin(angle1 + angledelta),
- 0)
+ vr2 = Vector(rx * math.cos(angle1 + angledelta), ry * math.sin(angle1 + angledelta), 0)
mxrot = Matrix()
mxrot.rotateZ(xrotation)
v1 = mxrot.multiply(vr1).add(center)
@@ -192,8 +188,8 @@ def _approx_bspline(
return curve
-def _make_wire(path : list[Edge], precision : int, checkclosed : bool=False, donttry : bool=False):
- '''Try to make a wire out of the list of edges.
+def _make_wire(path: list[Edge], precision: int, checkclosed: bool = False, donttry: bool = False):
+ """Try to make a wire out of the list of edges.
If the wire functions fail or the wire is not closed,
if required the TopoShapeCompoundPy::connectEdgesToWires()
@@ -215,7 +211,7 @@ def _make_wire(path : list[Edge], precision : int, checkclosed : bool=False, don
A wire created from the ordered edges.
Part::Compound
A compound made of the edges, but unable to form a wire.
- '''
+ """
if not donttry:
try:
sh = Wire(path)
@@ -239,26 +235,25 @@ def _make_wire(path : list[Edge], precision : int, checkclosed : bool=False, don
class FaceTreeNode:
- '''
- Building Block of a tree structure holding one-closed-wire faces
+ """
+ Building Block of a tree structure holding one-closed-wire faces
sorted after their enclosure of each other.
This class only works with faces that have exactly one closed wire
- '''
- face : Face
- children : list
- name : str
+ """
+
+ face: Face
+ children: list
+ name: str
-
def __init__(self, face=None, name="root"):
super().__init__()
self.face = face
self.name = name
- self.children = []
+ self.children = []
-
- def insert (self, face, name):
- '''
- takes a single-wire named face, and inserts it into the tree
+ def insert(self, face, name):
+ """
+ takes a single-wire named face, and inserts it into the tree
depending on its enclosure in/of already added faces.
Parameters
@@ -266,42 +261,45 @@ class FaceTreeNode:
face : Face
single closed wire face to be added to the tree
name : str
- face identifier
- '''
+ face identifier
+ """
for node in self.children:
- if node.face.Area > face.Area:
+ if node.face.Area > face.Area:
# new face could be encompassed
- if (face.distToShape(node.face)[0] == 0.0 and
- face.Wires[0].distToShape(node.face.Wires[0])[0] != 0.0):
+ if (
+ face.distToShape(node.face)[0] == 0.0
+ and face.Wires[0].distToShape(node.face.Wires[0])[0] != 0.0
+ ):
# it is encompassed - enter next tree layer
node.insert(face, name)
return
else:
# new face could encompass
- if (node.face.distToShape(face)[0] == 0.0 and
- node.face.Wires[0].distToShape(face.Wires[0])[0] != 0.0):
+ if (
+ node.face.distToShape(face)[0] == 0.0
+ and node.face.Wires[0].distToShape(face.Wires[0])[0] != 0.0
+ ):
# it does encompass the current child nodes face
# create new node from face
new = FaceTreeNode(face, name)
- # swap the new one with the child node
+ # swap the new one with the child node
self.children.remove(node)
self.children.append(new)
# add former child node as child to the new node
new.children.append(node)
return
# the face is not encompassing and is not encompassed (from) any
- # other face, we add it as new child
+ # other face, we add it as new child
new = FaceTreeNode(face, name)
self.children.append(new)
-
def makeCuts(self):
- '''
- recursively traverse the tree and cuts all faces in even
- numbered tree levels with their direct childrens faces.
- Additionally the tree is shrunk by removing the odd numbered
- tree levels.
- '''
+ """
+ recursively traverse the tree and cuts all faces in even
+ numbered tree levels with their direct childrens faces.
+ Additionally the tree is shrunk by removing the odd numbered
+ tree levels.
+ """
result = self.face
if not result:
for node in self.children:
@@ -316,29 +314,27 @@ class FaceTreeNode:
self.children = new_children
self.face = result
-
def flatten(self):
- ''' creates a flattened list of face-name tuples from the facetree
- content
- '''
+ """creates a flattened list of face-name tuples from the facetree
+ content
+ """
result = []
result.append((self.name, self.face))
for node in self.children:
result.extend(node.flatten())
- return result
-
-
-
+ return result
+
+
class SvgPathElement:
- path : list[dict]
+ path: list[dict]
- def __init__(self, precision : int, interpol_pts : int, origin : Vector = Vector(0, 0, 0)):
+ def __init__(self, precision: int, interpol_pts: int, origin: Vector = Vector(0, 0, 0)):
self.precision = precision
self.interpol_pts = interpol_pts
- self.path = [{"type": "start", "last_v": origin }]
-
- def add_move(self, x : float, y : float, relative : bool) -> None:
+ self.path = [{"type": "start", "last_v": origin}]
+
+ def add_move(self, x: float, y: float, relative: bool) -> None:
if relative:
last_v = self.path[-1]["last_v"].add(Vector(x, -y, 0))
else:
@@ -380,8 +376,14 @@ class SvgPathElement:
def add_arcs(self, args: list[float], relative: bool) -> None:
p_iter = zip(
- args[0::7], args[1::7], args[2::7], args[3::7],
- args[4::7], args[5::7], args[6::7], strict=False,
+ args[0::7],
+ args[1::7],
+ args[2::7],
+ args[3::7],
+ args[4::7],
+ args[5::7],
+ args[6::7],
+ strict=False,
)
for rx, ry, x_rotation, large_flag, sweep_flag, x, y in p_iter:
# support for large-arc and x-rotation is missing
@@ -389,31 +391,43 @@ class SvgPathElement:
last_v = self.path[-1]["last_v"].add(Vector(x, -y, 0))
else:
last_v = Vector(x, -y, 0)
- self.path.append({
- "type": "arc",
- "rx": rx,
- "ry": ry,
- "x_rotation": x_rotation,
- "large_flag": large_flag != 0,
- "sweep_flag": sweep_flag != 0,
- "last_v": last_v
- })
+ self.path.append(
+ {
+ "type": "arc",
+ "rx": rx,
+ "ry": ry,
+ "x_rotation": x_rotation,
+ "large_flag": large_flag != 0,
+ "sweep_flag": sweep_flag != 0,
+ "last_v": last_v,
+ }
+ )
def add_cubic_beziers(self, args: list[float], relative: bool, smooth: bool) -> None:
last_v = self.path[-1]["last_v"]
if smooth:
p_iter = list(
zip(
- args[2::4], args[3::4],
- args[0::4], args[1::4],
- args[2::4], args[3::4], strict=False )
+ args[2::4],
+ args[3::4],
+ args[0::4],
+ args[1::4],
+ args[2::4],
+ args[3::4],
+ strict=False,
+ )
)
else:
p_iter = list(
zip(
- args[0::6], args[1::6],
- args[2::6], args[3::6],
- args[4::6], args[5::6], strict=False )
+ args[0::6],
+ args[1::6],
+ args[2::6],
+ args[3::6],
+ args[4::6],
+ args[5::6],
+ strict=False,
+ )
)
for p1x, p1y, p2x, p2y, x, y in p_iter:
if smooth:
@@ -433,21 +447,14 @@ class SvgPathElement:
pole2 = Vector(p2x, -p2y, 0)
last_v = Vector(x, -y, 0)
- self.path.append({
- "type": "cbezier",
- "pole1": pole1,
- "pole2": pole2,
- "last_v": last_v
- })
+ self.path.append({"type": "cbezier", "pole1": pole1, "pole2": pole2, "last_v": last_v})
def add_quadratic_beziers(self, args: list[float], relative: bool, smooth: bool):
last_v = self.path[-1]["last_v"]
if smooth:
- p_iter = list( zip( args[1::2], args[1::2],
- args[0::2], args[1::2], strict=False ) )
+ p_iter = list(zip(args[1::2], args[1::2], args[0::2], args[1::2], strict=False))
else:
- p_iter = list( zip( args[0::4], args[1::4],
- args[2::4], args[3::4], strict=False ) )
+ p_iter = list(zip(args[0::4], args[1::4], args[2::4], args[3::4], strict=False))
for px, py, x, y in p_iter:
if smooth:
if self.path[-1]["type"] == "qbezier":
@@ -464,14 +471,10 @@ class SvgPathElement:
else:
last_v = Vector(x, -y, 0)
- self.path.append({
- "type": "qbezier",
- "pole": pole,
- "last_v": last_v
- })
+ self.path.append({"type": "qbezier", "pole": pole, "last_v": last_v})
def add_close(self):
- last_v = self.path[-1]["last_v"]
+ last_v = self.path[-1]["last_v"]
first_v = self.__get_last_start()
if not equals(last_v, first_v, self.precision):
self.path.append({"type": "line", "last_v": first_v})
@@ -489,17 +492,16 @@ class SvgPathElement:
def __correct_last_v(self, pds: dict, last_v: Vector) -> None:
"""
- Correct the endpoint of the given path dataset to the
+ Correct the endpoint of the given path dataset to the
given vector and move possibly associated members accordingly.
"""
delta = last_v.sub(pds["last_v"])
- # we won't move last_v if it's already correct or if the delta
+ # we won't move last_v if it's already correct or if the delta
# is substantially greater than what rounding errors could accumulate,
- # so we assume the path is intended to be open.
- if (delta.x == 0 and delta.y == 0 and delta.z == 0 or
- not isNull(delta, self.precision)):
+ # so we assume the path is intended to be open.
+ if delta.x == 0 and delta.y == 0 and delta.z == 0 or not isNull(delta, self.precision):
return
-
+
# for cbeziers we also relocate the second pole
if pds["type"] == "cbezier":
pds["pole2"] = pds["pole2"].add(delta)
@@ -509,10 +511,9 @@ class SvgPathElement:
# all data types have last_v
pds["last_v"] = last_v
-
def correct_endpoints(self):
- """
- Correct the endpoints of all subpaths and move possibly
+ """
+ Correct the endpoints of all subpaths and move possibly
associated members accordingly.
"""
start = None
@@ -522,7 +523,7 @@ class SvgPathElement:
if start:
# there is already a start
if last:
- # and there are edges behind us.
+ # and there are edges behind us.
# we correct the last to the start vector
self.__correct_last_v(last, start["last_v"])
last = None
@@ -532,10 +533,9 @@ class SvgPathElement:
if start and last and start != last:
self.__correct_last_v(last, start["last_v"])
-
def create_edges(self) -> list[list[Edge]]:
"""
- Creates shapes from prepared path datasets and returns them in an
+ Creates shapes from prepared path datasets and returns them in an
ordered list of lists of edges, where each 1st order list entry
represents a single continuous (and probably closed) sub-path.
"""
@@ -546,7 +546,7 @@ class SvgPathElement:
next_v = pds["last_v"]
match pds["type"]:
case "start":
- if edges and len(edges) > 0 :
+ if edges and len(edges) > 0:
result.append(edges)
edges = []
case "line":
@@ -565,10 +565,7 @@ class SvgPathElement:
# in 'endpoint parameterization'.
_x_rot = math.radians(-x_rotation)
(solution, (rx, ry)) = _arc_end_to_center(
- last_v, next_v,
- rx, ry,
- _x_rot,
- correction=True
+ last_v, next_v, rx, ry, _x_rot, correction=True
)
# Choose one of the two solutions
neg_sol = large_flag != sweep_flag
@@ -633,57 +630,55 @@ class SvgPathElement:
seg = _approx_bspline(b, self.interpol_pts).toShape()
edges.append(seg)
case _:
- _msg("Illegal path_data type. {}".format(pds['type']))
+ _msg("Illegal path_data type. {}".format(pds["type"]))
return []
last_v = next_v
- if not edges is None and len(edges) > 0 :
+ if not edges is None and len(edges) > 0:
result.append(edges)
return result
-
class SvgPathParser:
"""Parse SVG path data and create FreeCAD Shapes."""
- commands : list[tuple]
- pointsre : re.Pattern
- data : dict
- shapes : list[list[Shape]]
- faces : FaceTreeNode
- name : str
+ commands: list[tuple]
+ pointsre: re.Pattern
+ data: dict
+ shapes: list[list[Shape]]
+ faces: FaceTreeNode
+ name: str
def __init__(self, data, name):
super().__init__()
"""Evaluate path data and initialize."""
- _op = '([mMlLhHvVaAcCqQsStTzZ])'
- _op2 = '([^mMlLhHvVaAcCqQsStTzZ]*)'
- _command = '\\s*?' + _op + '\\s*?' + _op2 + '\\s*?'
+ _op = "([mMlLhHvVaAcCqQsStTzZ])"
+ _op2 = "([^mMlLhHvVaAcCqQsStTzZ]*)"
+ _command = "\\s*?" + _op + "\\s*?" + _op2 + "\\s*?"
pathcommandsre = re.compile(_command, re.DOTALL)
-
- _num = '[-+]?[0-9]*\\.?[0-9]+'
- _exp = '([eE][-+]?[0-9]+)?'
- _arg = '(' + _num + _exp + ')'
- self.commands = pathcommandsre.findall(' '.join(data['d']))
+
+ _num = "[-+]?[0-9]*\\.?[0-9]+"
+ _exp = "([eE][-+]?[0-9]+)?"
+ _arg = "(" + _num + _exp + ")"
+ self.commands = pathcommandsre.findall(" ".join(data["d"]))
self.argsre = re.compile(_arg, re.DOTALL)
self.data = data
self.paths = []
self.shapes = []
self.faces = None
self.name = name
-
-
+
def parse(self):
- '''
- Creates lists of SvgPathElements from raw svg path
+ """
+ Creates lists of SvgPathElements from raw svg path
data. It's supposed to be called direct after SvgPath Object
creation.
- '''
+ """
path = SvgPathElement(svg_precision(), 10)
self.paths = []
for d, argsstr in self.commands:
relative = d.islower()
-
- _args = self.argsre.findall(argsstr.replace(',', ' '))
+
+ _args = self.argsre.findall(argsstr.replace(",", " "))
args = [float(number) for number, exponent in _args]
if d in "Mm":
@@ -706,38 +701,36 @@ class SvgPathParser:
path.add_quadratic_beziers(args, relative, True)
elif d in "Zz":
path.add_close()
-
- path.correct_endpoints();
+
+ path.correct_endpoints()
self.shapes = path.create_edges()
-
-
+
def create_faces(self, fill=True, add_wire_for_invalid_face=False):
- '''
+ """
Generate Faces from lists of Shapes.
- If shapes form a closed wire and the fill Attribute is set, we
+ If shapes form a closed wire and the fill Attribute is set, we
generate a closed Face. Otherwise we treat the shape as pure wire.
-
+
Parameters
----------
fill : Object/bool
if True or not None Faces are generated from closed shapes.
- '''
+ """
precision = svg_precision()
- cnt = -1;
+ cnt = -1
openShapes = []
self.faces = FaceTreeNode()
for sh in self.shapes:
cnt += 1
add_wire = True
wr = _make_wire(sh, precision, checkclosed=True)
- wrcpy = wr.copy();
+ wrcpy = wr.copy()
wire_reason = ""
if cnt > 0:
face_name = self.name + "_" + str(cnt)
else:
- face_name = self.name
+ face_name = self.name
-
if not fill:
wire_reason = " no-fill"
if not wr.Wires[0].isClosed():
@@ -752,37 +745,39 @@ class SvgPathParser:
res = "succeed"
else:
res = "fail"
- _wrn("Invalid Face '{}' created. Attempt to fix - {}ed."
- .format(face_name, res))
+ _wrn(
+ "Invalid Face '{}' created. Attempt to fix - {}ed.".format(
+ face_name, res
+ )
+ )
else:
add_wire = False
if not (face.Area < 10 * (_tolerance(precision) ** 2)):
self.faces.insert(face, face_name)
except:
- _wrn("Failed to make a shape from '{}'. ".format(face_name)
- + "This Path will be discarded.")
+ _wrn(
+ "Failed to make a shape from '{}'. ".format(face_name)
+ + "This Path will be discarded."
+ )
if add_wire:
if wrcpy.Length > _tolerance(precision):
- _msg("Adding wire for '{}' - reason: {}."
- .format(face_name, wire_reason))
+ _msg("Adding wire for '{}' - reason: {}.".format(face_name, wire_reason))
openShapes.append((face_name + "_w", wrcpy))
self.shapes = openShapes
-
def doCuts(self):
- ''' Exposes the FaceTreeNode.makeCuts function of the tree containing
- closed wire faces.
- This function is called after creating closed Faces with
- 'createFaces' in order to hollow faces encompassing others.
- '''
+ """Exposes the FaceTreeNode.makeCuts function of the tree containing
+ closed wire faces.
+ This function is called after creating closed Faces with
+ 'createFaces' in order to hollow faces encompassing others.
+ """
self.faces.makeCuts()
-
def getShapeList(self):
- ''' Returns the resulting list of tuples containing name and face of
- each created element.
- '''
+ """Returns the resulting list of tuples containing name and face of
+ each created element.
+ """
result = self.faces.flatten()
- result.extend(self.shapes)
+ result.extend(self.shapes)
return result
diff --git a/src/Mod/Draft/WorkingPlane.py b/src/Mod/Draft/WorkingPlane.py
index 5713f87fd4..b61a1b770a 100644
--- a/src/Mod/Draft/WorkingPlane.py
+++ b/src/Mod/Draft/WorkingPlane.py
@@ -83,9 +83,9 @@ class PlaneBase:
Note that the u, v and w vectors are not checked for validity.
"""
- def __init__(self,
- u=Vector(1, 0, 0), v=Vector(0, 1, 0), w=Vector(0, 0, 1),
- pos=Vector(0, 0, 0)):
+ def __init__(
+ self, u=Vector(1, 0, 0), v=Vector(0, 1, 0), w=Vector(0, 0, 1), pos=Vector(0, 0, 0)
+ ):
if isinstance(u, PlaneBase):
self.match(u)
@@ -297,7 +297,7 @@ class PlaneBase:
"""
if face.Surface.isPlanar() is False:
return False
- axis = face.normalAt(0,0)
+ axis = face.normalAt(0, 0)
point = edge.Vertexes[0].Point
vec = edge.Vertexes[-1].Point.sub(point)
return self.align_to_point_and_axis(point, axis, offset, axis.cross(vec))
@@ -426,44 +426,44 @@ class PlaneBase:
self.axis = Vector(axis).normalize()
ref_vec = Vector(0.0, 1.0, 0.0)
- if ((abs(axis.x) > abs(axis.y)) and (abs(axis.y) > abs(axis.z))):
- ref_vec = Vector(0.0, 0., 1.0)
+ if (abs(axis.x) > abs(axis.y)) and (abs(axis.y) > abs(axis.z)):
+ ref_vec = Vector(0.0, 0.0, 1.0)
self.u = axis.negative().cross(ref_vec)
self.u.normalize()
- self.v = DraftVecUtils.rotate(self.u, math.pi/2, self.axis)
+ self.v = DraftVecUtils.rotate(self.u, math.pi / 2, self.axis)
# projcase = "Case new"
- elif ((abs(axis.y) > abs(axis.z)) and (abs(axis.z) >= abs(axis.x))):
+ elif (abs(axis.y) > abs(axis.z)) and (abs(axis.z) >= abs(axis.x)):
ref_vec = Vector(1.0, 0.0, 0.0)
self.u = axis.negative().cross(ref_vec)
self.u.normalize()
- self.v = DraftVecUtils.rotate(self.u, math.pi/2, self.axis)
+ self.v = DraftVecUtils.rotate(self.u, math.pi / 2, self.axis)
# projcase = "Y>Z, View Y"
- elif ((abs(axis.y) >= abs(axis.x)) and (abs(axis.x) > abs(axis.z))):
- ref_vec = Vector(0.0, 0., 1.0)
+ elif (abs(axis.y) >= abs(axis.x)) and (abs(axis.x) > abs(axis.z)):
+ ref_vec = Vector(0.0, 0.0, 1.0)
self.u = axis.cross(ref_vec)
self.u.normalize()
- self.v = DraftVecUtils.rotate(self.u, math.pi/2, self.axis)
+ self.v = DraftVecUtils.rotate(self.u, math.pi / 2, self.axis)
# projcase = "ehem. XY, Case XY"
- elif ((abs(axis.x) > abs(axis.z)) and (abs(axis.z) >= abs(axis.y))):
+ elif (abs(axis.x) > abs(axis.z)) and (abs(axis.z) >= abs(axis.y)):
self.u = axis.cross(ref_vec)
self.u.normalize()
- self.v = DraftVecUtils.rotate(self.u, math.pi/2, self.axis)
+ self.v = DraftVecUtils.rotate(self.u, math.pi / 2, self.axis)
# projcase = "X>Z, View X"
- elif ((abs(axis.z) >= abs(axis.y)) and (abs(axis.y) > abs(axis.x))):
- ref_vec = Vector(1.0, 0., 0.0)
+ elif (abs(axis.z) >= abs(axis.y)) and (abs(axis.y) > abs(axis.x)):
+ ref_vec = Vector(1.0, 0.0, 0.0)
self.u = axis.cross(ref_vec)
self.u.normalize()
- self.v = DraftVecUtils.rotate(self.u, math.pi/2, self.axis)
+ self.v = DraftVecUtils.rotate(self.u, math.pi / 2, self.axis)
# projcase = "Y>X, Case YZ"
else:
self.u = axis.negative().cross(ref_vec)
self.u.normalize()
- self.v = DraftVecUtils.rotate(self.u, math.pi/2, self.axis)
+ self.v = DraftVecUtils.rotate(self.u, math.pi / 2, self.axis)
# projcase = "else"
# spat_vec = self.u.cross(self.v)
@@ -545,16 +545,18 @@ class PlaneBase:
def is_global(self):
"""Return `True` if the WP matches the global coordinate system exactly."""
- return self.u == Vector(1, 0, 0) \
- and self.v == Vector(0, 1, 0) \
- and self.axis == Vector(0, 0, 1) \
+ return (
+ self.u == Vector(1, 0, 0)
+ and self.v == Vector(0, 1, 0)
+ and self.axis == Vector(0, 0, 1)
and self.position == Vector()
+ )
def is_ortho(self):
"""Return `True` if all WP axes are parallel to a global axis."""
rot = FreeCAD.Rotation(self.u, self.v, self.axis, "ZYX")
ypr = [round(ang, 6) for ang in rot.getYawPitchRoll()]
- return all([ang%90 == 0 for ang in ypr])
+ return all([ang % 90 == 0 for ang in ypr])
def project_point(self, point, direction=None, force_projection=True):
"""Project a point onto the WP and return the global coordinates of the
@@ -575,11 +577,9 @@ class PlaneBase:
-------
Base.Vector
"""
- return DraftGeomUtils.project_point_on_plane(point,
- self.position,
- self.axis,
- direction,
- force_projection)
+ return DraftGeomUtils.project_point_on_plane(
+ point, self.position, self.axis, direction, force_projection
+ )
def set_to_top(self, offset=0):
"""Set the WP to the top position with an optional offset."""
@@ -613,15 +613,12 @@ class PlaneBase:
near multiples of 45 degrees.
"""
ypr = [round(ang, 3) for ang in rot.getYawPitchRoll()]
- if all([ang%45 == 0 for ang in ypr]):
+ if all([ang % 45 == 0 for ang in ypr]):
rot.setEulerAngles("YawPitchRoll", *ypr)
return self._axes_from_rotation(rot)
def _get_prop_list(self):
- return ["u",
- "v",
- "axis",
- "position"]
+ return ["u", "v", "axis", "position"]
class Plane(PlaneBase):
@@ -660,10 +657,14 @@ class Plane(PlaneBase):
Placeholder for a stored state.
"""
- def __init__(self,
- u=Vector(1, 0, 0), v=Vector(0, 1, 0), w=Vector(0, 0, 1),
- pos=Vector(0, 0, 0),
- weak=True):
+ def __init__(
+ self,
+ u=Vector(1, 0, 0),
+ v=Vector(0, 1, 0),
+ w=Vector(0, 0, 1),
+ pos=Vector(0, 0, 0),
+ weak=True,
+ ):
if isinstance(u, Plane):
self.match(u)
@@ -837,16 +838,20 @@ class Plane(PlaneBase):
if isinstance(geom, Part.Shape):
geom_is_shape = True
if not geom_is_shape:
- _wrn(translate(
- "draft",
- "Object without Part.Shape geometry:'{}'".format(
- obj.ObjectName)) + "\n")
+ _wrn(
+ translate(
+ "draft", "Object without Part.Shape geometry:'{}'".format(obj.ObjectName)
+ )
+ + "\n"
+ )
return False
if geom.isNull():
- _wrn(translate(
- "draft",
- "Object with null Part.Shape geometry:'{}'".format(
- obj.ObjectName)) + "\n")
+ _wrn(
+ translate(
+ "draft", "Object with null Part.Shape geometry:'{}'".format(obj.ObjectName)
+ )
+ + "\n"
+ )
return False
if obj.HasSubObjects:
shapes.extend(obj.SubObjects)
@@ -858,8 +863,7 @@ class Plane(PlaneBase):
normal = None
for n in range(len(shapes)):
if not DraftGeomUtils.is_planar(shapes[n]):
- _wrn(translate(
- "draft", "'{}' object is not planar".format(names[n])) + "\n")
+ _wrn(translate("draft", "'{}' object is not planar".format(names[n])) + "\n")
return False
if not normal:
normal = DraftGeomUtils.get_normal(shapes[n])
@@ -869,9 +873,12 @@ class Plane(PlaneBase):
if normal:
for n in range(len(shapes)):
if not DraftGeomUtils.are_coplanar(shapes[shape_ref], shapes[n]):
- _wrn(translate(
- "draft", "{} and {} are not coplanar".format(
- names[shape_ref],names[n])) + "\n")
+ _wrn(
+ translate(
+ "draft", "{} and {} are not coplanar".format(names[shape_ref], names[n])
+ )
+ + "\n"
+ )
return False
else:
# suppose all geometries are straight lines or points
@@ -879,25 +886,23 @@ class Plane(PlaneBase):
if len(points) >= 3:
poly = Part.makePolygon(points)
if not DraftGeomUtils.is_planar(poly):
- _wrn(translate(
- "draft", "All shapes must be coplanar") + "\n")
+ _wrn(translate("draft", "All shapes must be coplanar") + "\n")
return False
normal = DraftGeomUtils.get_normal(poly)
else:
normal = None
if not normal:
- _wrn(translate(
- "draft", "Selected shapes must define a plane") + "\n")
+ _wrn(translate("draft", "Selected shapes must define a plane") + "\n")
return False
# set center of mass
- ctr_mass = Vector(0,0,0)
- ctr_pts = Vector(0,0,0)
+ ctr_mass = Vector(0, 0, 0)
+ ctr_pts = Vector(0, 0, 0)
mass = 0
for shape in shapes:
if hasattr(shape, "CenterOfMass"):
- ctr_mass += shape.CenterOfMass*shape.Mass
+ ctr_mass += shape.CenterOfMass * shape.Mass
mass += shape.Mass
else:
ctr_pts += shape.Point
@@ -905,7 +910,7 @@ class Plane(PlaneBase):
ctr_mass /= mass
# all shapes are vertexes
else:
- ctr_mass = ctr_pts/len(shapes)
+ ctr_mass = ctr_pts / len(shapes)
super().align_to_point_and_axis(ctr_mass, normal, offset)
self.weak = False
@@ -970,9 +975,10 @@ class Plane(PlaneBase):
self.weak = False
if FreeCAD.GuiUp:
from draftutils.translate import translate
- if hasattr(FreeCADGui,"Snapper"):
+
+ if hasattr(FreeCADGui, "Snapper"):
FreeCADGui.Snapper.setGrid()
- if hasattr(FreeCADGui,"draftToolBar"):
+ if hasattr(FreeCADGui, "draftToolBar"):
FreeCADGui.draftToolBar.wplabel.setText(translate("draft", "Top"))
def setFront(self):
@@ -981,9 +987,10 @@ class Plane(PlaneBase):
self.weak = False
if FreeCAD.GuiUp:
from draftutils.translate import translate
- if hasattr(FreeCADGui,"Snapper"):
+
+ if hasattr(FreeCADGui, "Snapper"):
FreeCADGui.Snapper.setGrid()
- if hasattr(FreeCADGui,"draftToolBar"):
+ if hasattr(FreeCADGui, "draftToolBar"):
FreeCADGui.draftToolBar.wplabel.setText(translate("draft", "Front"))
def setSide(self):
@@ -999,9 +1006,10 @@ class Plane(PlaneBase):
self.weak = False
if FreeCAD.GuiUp:
from draftutils.translate import translate
- if hasattr(FreeCADGui,"Snapper"):
+
+ if hasattr(FreeCADGui, "Snapper"):
FreeCADGui.Snapper.setGrid()
- if hasattr(FreeCADGui,"draftToolBar"):
+ if hasattr(FreeCADGui, "draftToolBar"):
FreeCADGui.draftToolBar.wplabel.setText(translate("draft", "Side"))
def getRotation(self):
@@ -1152,15 +1160,12 @@ class Plane(PlaneBase):
data: dict
dictionary of the form:
{"u":x, "v":v, "axis":axis, "position":position, "weak":weak}
- """
+ """
super().set_parameters(data)
def _get_prop_list(self):
- return ["u",
- "v",
- "axis",
- "position",
- "weak"]
+ return ["u", "v", "axis", "position", "weak"]
+
plane = Plane
@@ -1220,13 +1225,17 @@ class PlaneGui(PlaneBase):
Dictionary that holds up to 10 stored states.
"""
- def __init__(self,
- u=Vector(1, 0, 0), v=Vector(0, 1, 0), w=Vector(0, 0, 1),
- pos=Vector(0, 0, 0),
- auto=True,
- icon=":/icons/view-axonometric.svg",
- label=QT_TRANSLATE_NOOP("draft", "Auto"),
- tip=QT_TRANSLATE_NOOP("draft", "Current working plane: Auto")):
+ def __init__(
+ self,
+ u=Vector(1, 0, 0),
+ v=Vector(0, 1, 0),
+ w=Vector(0, 0, 1),
+ pos=Vector(0, 0, 0),
+ auto=True,
+ icon=":/icons/view-axonometric.svg",
+ label=QT_TRANSLATE_NOOP("draft", "Auto"),
+ tip=QT_TRANSLATE_NOOP("draft", "Current working plane: Auto"),
+ ):
if isinstance(u, PlaneGui):
self.match(u)
@@ -1287,13 +1296,20 @@ class PlaneGui(PlaneBase):
if len(objs) != 1:
ret = False
- if all([obj[0].isNull() is False and obj[0].ShapeType in ["Edge", "Vertex"] for obj in objs]):
+ if all(
+ [
+ obj[0].isNull() is False and obj[0].ShapeType in ["Edge", "Vertex"]
+ for obj in objs
+ ]
+ ):
ret = self.align_to_edges_vertexes([obj[0] for obj in objs], offset, _hist_add)
- elif all([obj[0].isNull() is False and obj[0].ShapeType in ["Edge", "Face"] for obj in objs]):
- edges = [obj[0] for obj in objs if obj[0].ShapeType == "Edge"]
- faces = [obj[0] for obj in objs if obj[0].ShapeType == "Face"]
- if faces and edges:
- ret = self.align_to_face_and_edge(faces[0], edges[0], offset, _hist_add)
+ elif all(
+ [obj[0].isNull() is False and obj[0].ShapeType in ["Edge", "Face"] for obj in objs]
+ ):
+ edges = [obj[0] for obj in objs if obj[0].ShapeType == "Edge"]
+ faces = [obj[0] for obj in objs if obj[0].ShapeType == "Face"]
+ if faces and edges:
+ ret = self.align_to_face_and_edge(faces[0], edges[0], offset, _hist_add)
if ret is False:
_wrn(translate("draft", "Selected shapes do not define a plane"))
return ret
@@ -1310,7 +1326,7 @@ class PlaneGui(PlaneBase):
ret = self.align_to_wp_proxy(obj, offset, place * obj.Placement, _hist_add)
elif typ == "IfcBuildingStorey":
pl = FreeCAD.Placement(obj.Placement)
- pl.move(FreeCAD.Vector(0,0,obj.Elevation.Value))
+ pl.move(FreeCAD.Vector(0, 0, obj.Elevation.Value))
ret = self.align_to_wp_proxy(obj, offset, place * pl, _hist_add)
elif shape.isNull():
ret = self.align_to_obj_placement(obj, offset, place, _hist_add)
@@ -1411,10 +1427,12 @@ class PlaneGui(PlaneBase):
self.auto = False
if utils.get_type(obj) == "WorkingPlaneProxy":
self.icon = ":/icons/Draft_PlaneProxy.svg"
- elif FreeCAD.GuiUp \
- and hasattr(obj, "ViewObject") \
- and hasattr(obj.ViewObject, "Proxy") \
- and hasattr(obj.ViewObject.Proxy, "getIcon"):
+ elif (
+ FreeCAD.GuiUp
+ and hasattr(obj, "ViewObject")
+ and hasattr(obj.ViewObject, "Proxy")
+ and hasattr(obj.ViewObject.Proxy, "getIcon")
+ ):
self.icon = obj.ViewObject.Proxy.getIcon()
else:
self.icon = ":/icons/Std_Placement.svg"
@@ -1438,19 +1456,18 @@ class PlaneGui(PlaneBase):
vobj = obj.ViewObject
- if hasattr(vobj, "AutoWorkingPlane") \
- and vobj.AutoWorkingPlane is True:
+ if hasattr(vobj, "AutoWorkingPlane") and vobj.AutoWorkingPlane is True:
self.auto = True
- if hasattr(vobj, "CutView") \
- and hasattr(vobj, "AutoCutView") \
- and vobj.AutoCutView is True:
+ if hasattr(vobj, "CutView") and hasattr(vobj, "AutoCutView") and vobj.AutoCutView is True:
vobj.CutView = True
- if hasattr(vobj, "RestoreView") \
- and vobj.RestoreView is True \
- and hasattr(vobj, "ViewData") \
- and len(vobj.ViewData) >= 12:
+ if (
+ hasattr(vobj, "RestoreView")
+ and vobj.RestoreView is True
+ and hasattr(vobj, "ViewData")
+ and len(vobj.ViewData) >= 12
+ ):
vdat = vobj.ViewData
if self._view is not None:
try:
@@ -1475,14 +1492,16 @@ class PlaneGui(PlaneBase):
except Exception:
pass
- if hasattr(vobj, "RestoreState") \
- and vobj.RestoreState is True \
- and hasattr(vobj, "VisibilityMap") \
- and vobj.VisibilityMap:
+ if (
+ hasattr(vobj, "RestoreState")
+ and vobj.RestoreState is True
+ and hasattr(vobj, "VisibilityMap")
+ and vobj.VisibilityMap
+ ):
for name, vis in vobj.VisibilityMap.items():
obj = FreeCADGui.ActiveDocument.getObject(name)
if obj:
- obj.Visibility = (vis == "True")
+ obj.Visibility = vis == "True"
return True
@@ -1509,7 +1528,7 @@ class PlaneGui(PlaneBase):
elif default_wp == 3:
self.set_to_side()
- def set_to_auto(self): # Similar to Plane.reset.
+ def set_to_auto(self): # Similar to Plane.reset.
"""Set the WP to auto."""
self.auto = True
self.auto_align()
@@ -1633,9 +1652,11 @@ class PlaneGui(PlaneBase):
if self._view is not None:
try:
cam = self._view.getCameraNode()
- pos = self.project_point(Vector(cam.position.getValue().getValue()),
- direction=self._view.getViewDirection(),
- force_projection=False)
+ pos = self.project_point(
+ Vector(cam.position.getValue().getValue()),
+ direction=self._view.getViewDirection(),
+ force_projection=False,
+ )
if pos is not None:
self.position = pos
except Exception:
@@ -1647,7 +1668,9 @@ class PlaneGui(PlaneBase):
try:
default_cam_dist = abs(params.get_param_view("NewDocumentCameraScale"))
cam = self._view.getCameraNode()
- cur_cam_dist = abs(self.get_local_coords(Vector(cam.position.getValue().getValue())).z)
+ cur_cam_dist = abs(
+ self.get_local_coords(Vector(cam.position.getValue().getValue())).z
+ )
cam_dist = max(default_cam_dist, cur_cam_dist)
cam.position.setValue(self.position + DraftVecUtils.scaleTo(self.axis, cam_dist))
cam.orientation.setValue(self.get_placement().Rotation.Q)
@@ -1683,14 +1706,7 @@ class PlaneGui(PlaneBase):
return bool(self._history) and self._history["idx"] != len(self._history["data_list"]) - 1
def _get_prop_list(self):
- return ["u",
- "v",
- "axis",
- "position",
- "auto",
- "icon",
- "label",
- "tip"]
+ return ["u", "v", "axis", "position", "auto", "icon", "label", "tip"]
def _get_label(self, label):
if self.auto or self.position.isEqual(Vector(), 0):
@@ -1745,36 +1761,35 @@ class PlaneGui(PlaneBase):
return
max_len = 10 # Max. length of data_list.
- self._history["data_list"] = self._history["data_list"][(idx - (max_len - 2)):(idx + 1)]
+ self._history["data_list"] = self._history["data_list"][(idx - (max_len - 2)) : (idx + 1)]
self._history["data_list"].append(data)
self._history["idx"] = len(self._history["data_list"]) - 1
def _update_old_plane(self):
- """ Update the old DraftWorkingPlane for compatibility.
+ """Update the old DraftWorkingPlane for compatibility.
The tracker and snapper code currently still depend on it.
"""
if not hasattr(FreeCAD, "DraftWorkingPlane"):
FreeCAD.DraftWorkingPlane = Plane()
for prop in ["u", "v", "axis", "position"]:
- setattr(FreeCAD.DraftWorkingPlane,
- prop,
- self._copy_value(getattr(self, prop)))
+ setattr(FreeCAD.DraftWorkingPlane, prop, self._copy_value(getattr(self, prop)))
FreeCAD.DraftWorkingPlane.weak = self.auto
def _update_grid(self):
# Check for draftToolBar because the trackers (grid) depend on it for its colors.
- if FreeCAD.GuiUp \
- and hasattr(FreeCADGui, "draftToolBar") \
- and hasattr(FreeCADGui, "Snapper") \
- and self._view is not None:
+ if (
+ FreeCAD.GuiUp
+ and hasattr(FreeCADGui, "draftToolBar")
+ and hasattr(FreeCADGui, "Snapper")
+ and self._view is not None
+ ):
FreeCADGui.Snapper.setGrid()
FreeCADGui.Snapper.restack() # Required??
def _update_gui(self):
- if FreeCAD.GuiUp \
- and hasattr(FreeCADGui, "draftToolBar") \
- and self._view is not None:
+ if FreeCAD.GuiUp and hasattr(FreeCADGui, "draftToolBar") and self._view is not None:
from PySide import QtGui
+
button = FreeCADGui.draftToolBar.wplabel
button.setIcon(QtGui.QIcon(self.icon))
button.setText(self.label)
@@ -1800,7 +1815,9 @@ def get_working_plane(update=True):
wp = PlaneGui()
if FreeCAD.GuiUp:
- wp._view = view # Update _view before call to set_to_default, set_to_auto requires a 3D view.
+ wp._view = (
+ view # Update _view before call to set_to_default, set_to_auto requires a 3D view.
+ )
wp.set_to_default()
if view is not None:
FreeCAD.draft_working_planes[0].append(view)
diff --git a/src/Mod/Draft/draftfunctions/array.py b/src/Mod/Draft/draftfunctions/array.py
index 4222b7e953..8cb3ea65fa 100644
--- a/src/Mod/Draft/draftfunctions/array.py
+++ b/src/Mod/Draft/draftfunctions/array.py
@@ -63,52 +63,65 @@ def array(objectslist, arg1, arg2, arg3, arg4=None, arg5=None, arg6=None):
if arg6:
rectArray2(objectslist, arg1, arg2, arg3, arg4, arg5, arg6)
elif arg4:
- rectArray(objectslist, arg1,arg2, arg3, arg4)
+ rectArray(objectslist, arg1, arg2, arg3, arg4)
else:
polarArray(objectslist, arg1, arg2, arg3)
-def rectArray(objectslist,xvector,yvector,xnum,ynum):
- utils.type_check([(xvector, App.Vector),
- (yvector, App.Vector),
- (xnum,int), (ynum,int)],
- "rectArray")
- if not isinstance(objectslist,list): objectslist = [objectslist]
+def rectArray(objectslist, xvector, yvector, xnum, ynum):
+ utils.type_check(
+ [(xvector, App.Vector), (yvector, App.Vector), (xnum, int), (ynum, int)], "rectArray"
+ )
+ if not isinstance(objectslist, list):
+ objectslist = [objectslist]
for xcount in range(xnum):
- currentxvector=App.Vector(xvector).multiply(xcount)
- if not xcount==0:
- move.move(objectslist,currentxvector,True)
+ currentxvector = App.Vector(xvector).multiply(xcount)
+ if not xcount == 0:
+ move.move(objectslist, currentxvector, True)
for ycount in range(ynum):
- currentxvector=App.Vector(currentxvector)
- currentyvector=currentxvector.add(App.Vector(yvector).multiply(ycount))
- if not ycount==0:
- move.move(objectslist,currentyvector,True)
+ currentxvector = App.Vector(currentxvector)
+ currentyvector = currentxvector.add(App.Vector(yvector).multiply(ycount))
+ if not ycount == 0:
+ move.move(objectslist, currentyvector, True)
-def rectArray2(objectslist,xvector,yvector,zvector,xnum,ynum,znum):
- utils.type_check([(xvector,App.Vector), (yvector,App.Vector), (zvector,App.Vector),(xnum,int), (ynum,int),(znum,int)], "rectArray2")
- if not isinstance(objectslist,list): objectslist = [objectslist]
+def rectArray2(objectslist, xvector, yvector, zvector, xnum, ynum, znum):
+ utils.type_check(
+ [
+ (xvector, App.Vector),
+ (yvector, App.Vector),
+ (zvector, App.Vector),
+ (xnum, int),
+ (ynum, int),
+ (znum, int),
+ ],
+ "rectArray2",
+ )
+ if not isinstance(objectslist, list):
+ objectslist = [objectslist]
for xcount in range(xnum):
- currentxvector=App.Vector(xvector).multiply(xcount)
- if not xcount==0:
- move.move(objectslist,currentxvector,True)
+ currentxvector = App.Vector(xvector).multiply(xcount)
+ if not xcount == 0:
+ move.move(objectslist, currentxvector, True)
for ycount in range(ynum):
- currentxvector=App.Vector(currentxvector)
- currentyvector=currentxvector.add(App.Vector(yvector).multiply(ycount))
- if not ycount==0:
- move.move(objectslist,currentyvector,True)
+ currentxvector = App.Vector(currentxvector)
+ currentyvector = currentxvector.add(App.Vector(yvector).multiply(ycount))
+ if not ycount == 0:
+ move.move(objectslist, currentyvector, True)
for zcount in range(znum):
- currentzvector=currentyvector.add(App.Vector(zvector).multiply(zcount))
- if not zcount==0:
- move.move(objectslist,currentzvector,True)
+ currentzvector = currentyvector.add(App.Vector(zvector).multiply(zcount))
+ if not zcount == 0:
+ move.move(objectslist, currentzvector, True)
-def polarArray(objectslist,center,angle,num):
- utils.type_check([(center,App.Vector), (num,int)], "polarArray")
- if not isinstance(objectslist,list): objectslist = [objectslist]
- fraction = float(angle)/num
+def polarArray(objectslist, center, angle, num):
+ utils.type_check([(center, App.Vector), (num, int)], "polarArray")
+ if not isinstance(objectslist, list):
+ objectslist = [objectslist]
+ fraction = float(angle) / num
for i in range(num):
- currangle = fraction + (i*fraction)
- rotate.rotate(objectslist,currangle,center,copy=True)
+ currangle = fraction + (i * fraction)
+ rotate.rotate(objectslist, currangle, center, copy=True)
+
## @}
diff --git a/src/Mod/Draft/draftfunctions/cut.py b/src/Mod/Draft/draftfunctions/cut.py
index 2408c2a6bf..26c09c94a5 100644
--- a/src/Mod/Draft/draftfunctions/cut.py
+++ b/src/Mod/Draft/draftfunctions/cut.py
@@ -54,7 +54,7 @@ def cut(object1, object2):
If there is a problem and the new object can't be created.
"""
if not App.activeDocument():
- _err(translate("draft","No active document. Aborting."))
+ _err(translate("draft", "No active document. Aborting."))
return
obj = App.activeDocument().addObject("Part::Cut", "Cut")
@@ -69,4 +69,5 @@ def cut(object1, object2):
return obj
+
## @}
diff --git a/src/Mod/Draft/draftfunctions/downgrade.py b/src/Mod/Draft/draftfunctions/downgrade.py
index 463cb7145c..605d82a60e 100644
--- a/src/Mod/Draft/draftfunctions/downgrade.py
+++ b/src/Mod/Draft/draftfunctions/downgrade.py
@@ -247,7 +247,6 @@ def downgrade(objects, delete=False, force=None):
return True
return False
-
# helper functions (same as in upgrade.py)
def get_parent(obj):
@@ -311,7 +310,6 @@ def downgrade(objects, delete=False, force=None):
for newobj in new_list:
gui_utils.format_object(newobj, obj, ignore_construction=True)
-
doc = App.ActiveDocument
add_list = []
delete_list = []
@@ -347,15 +345,15 @@ def downgrade(objects, delete=False, force=None):
elif force:
# functions that work on a single object:
- single_funcs = {"explode": explode,
- "getWire": getWire,
- "shapify": _shapify}
+ single_funcs = {"explode": explode, "getWire": getWire, "shapify": _shapify}
# functions that work on multiple objects:
- multi_funcs = {"cut2": cut2,
- "splitCompounds": splitCompounds,
- "splitFaces": splitFaces,
- "splitWires": splitWires,
- "subtr": subtr}
+ multi_funcs = {
+ "cut2": cut2,
+ "splitCompounds": splitCompounds,
+ "splitFaces": splitFaces,
+ "splitWires": splitWires,
+ "subtr": subtr,
+ }
if force in single_funcs:
result = any([single_funcs[force](obj) for obj in objects])
elif force in multi_funcs:
@@ -388,21 +386,21 @@ def downgrade(objects, delete=False, force=None):
_msg(translate("draft", "Found 1 array: exploding it"))
# special case, we have one parametric object: we "de-parametrize" it
- elif len(objects) == 1 \
- and hasattr(objects[0], "Shape") \
- and (
- hasattr(objects[0], "Base")
- or hasattr(objects[0], "Profile")
- or hasattr(objects[0], "Sections")
- ):
+ elif (
+ len(objects) == 1
+ and hasattr(objects[0], "Shape")
+ and (
+ hasattr(objects[0], "Base")
+ or hasattr(objects[0], "Profile")
+ or hasattr(objects[0], "Sections")
+ )
+ ):
result = _shapify(objects[0])
if result:
_msg(translate("draft", "Found 1 parametric object: breaking its dependencies"))
# we have one multi-solids compound object: extract its solids
- elif len(objects) == 1 \
- and hasattr(objects[0], "Shape") \
- and len(solids) > 1:
+ elif len(objects) == 1 and hasattr(objects[0], "Shape") and len(solids) > 1:
result = splitCompounds(objects)
if result:
_msg(translate("draft", "Found 1 multi-solids compound: exploding it"))
@@ -423,7 +421,11 @@ def downgrade(objects, delete=False, force=None):
elif same_parent and same_parent_type != "PartDesign::Body":
result = subtr(objects)
if result:
- _msg(translate("draft", "Found several faces: subtracting them from the first one"))
+ _msg(
+ translate(
+ "draft", "Found several faces: subtracting them from the first one"
+ )
+ )
# only one face: we extract its wires
elif len(faces) > 0:
@@ -448,4 +450,5 @@ def downgrade(objects, delete=False, force=None):
gui_utils.select(add_list)
return add_list, delete_list
+
## @}
diff --git a/src/Mod/Draft/draftfunctions/draftify.py b/src/Mod/Draft/draftfunctions/draftify.py
index 8d8d14e762..465e1785a8 100644
--- a/src/Mod/Draft/draftfunctions/draftify.py
+++ b/src/Mod/Draft/draftfunctions/draftify.py
@@ -43,6 +43,7 @@ import draftmake.make_arc_3points as make_arc_3points
Part = lz.LazyLoader("Part", globals(), "Part")
DraftGeomUtils = lz.LazyLoader("DraftGeomUtils", globals(), "DraftGeomUtils")
+
def draftify(objectslist, makeblock=False, delete=True):
"""draftify(objectslist,[makeblock],[delete])
@@ -62,11 +63,11 @@ def draftify(objectslist, makeblock=False, delete=True):
If delete = False, old objects are not deleted
"""
- if not isinstance(objectslist,list):
+ if not isinstance(objectslist, list):
objectslist = [objectslist]
newobjlist = []
for obj in objectslist:
- if hasattr(obj,'Shape'):
+ if hasattr(obj, "Shape"):
for cluster in Part.sortEdges(obj.Shape.Edges):
w = Part.Wire(cluster)
nobj = draftify_shape(w)
@@ -88,11 +89,12 @@ def draftify(objectslist, makeblock=False, delete=True):
return newobjlist[0]
return newobjlist
+
def draftify_shape(shape):
nobj = None
if DraftGeomUtils.hasCurves(shape):
- if (len(shape.Edges) == 1):
+ if len(shape.Edges) == 1:
edge = shape.Edges[0]
edge_type = DraftGeomUtils.geomType(edge)
if edge_type == "Circle":
@@ -101,21 +103,24 @@ def draftify_shape(shape):
else:
first_parameter = edge.FirstParameter
last_parameter = edge.LastParameter
- points = [edge.Curve.value(first_parameter),
- edge.Curve.value((first_parameter + last_parameter)/2),
- edge.Curve.value(last_parameter)]
+ points = [
+ edge.Curve.value(first_parameter),
+ edge.Curve.value((first_parameter + last_parameter) / 2),
+ edge.Curve.value(last_parameter),
+ ]
nobj = make_arc_3points.make_arc_3points(points)
- # TODO: take into consideration trimmed curves and capture the specific
- # type of BSpline and Bezier that can be converted to a draft object.
- # elif edge_type == "BSplineCurve":
- # knots = [edge.Curve.value(p) for p in edge.Curve.getKnots()]
- # nobj = make_bspline.make_bspline(knots, closed=edge.isClosed())
- # elif edge_type == "BezierCurve":
- # nobj = make_bezcurve.make_bezcurve(edge.Curve.getPoles(),
- # closed=edge.isClosed())
+ # TODO: take into consideration trimmed curves and capture the specific
+ # type of BSpline and Bezier that can be converted to a draft object.
+ # elif edge_type == "BSplineCurve":
+ # knots = [edge.Curve.value(p) for p in edge.Curve.getKnots()]
+ # nobj = make_bspline.make_bspline(knots, closed=edge.isClosed())
+ # elif edge_type == "BezierCurve":
+ # nobj = make_bezcurve.make_bezcurve(edge.Curve.getPoles(),
+ # closed=edge.isClosed())
else:
nobj = make_wire.make_wire(shape)
return nobj
+
## @}
diff --git a/src/Mod/Draft/draftfunctions/dxf.py b/src/Mod/Draft/draftfunctions/dxf.py
index 1236c4fdef..dfca4bc1d1 100644
--- a/src/Mod/Draft/draftfunctions/dxf.py
+++ b/src/Mod/Draft/draftfunctions/dxf.py
@@ -20,8 +20,7 @@
# * USA *
# * *
# ***************************************************************************
-"""Provides functions to return the DXF representation of various shapes.
-"""
+"""Provides functions to return the DXF representation of various shapes."""
## @package dxf
# \ingroup draftfunctions
# \brief Provides functions to return the DXF representation of shapes.
@@ -44,6 +43,7 @@ TechDraw = lz.LazyLoader("TechDraw", globals(), "TechDraw")
## \addtogroup draftfunctions
# @{
+
def _get_proj(vec, plane=None):
"""Get a projection of the vector in the plane's u and v directions.
@@ -85,9 +85,9 @@ def get_dxf(obj, direction=None):
p2 = _get_proj(obj.End, plane=plane)
p3 = _get_proj(obj.Dimline, plane=plane)
result += "0\nDIMENSION\n8\n0\n62\n0\n3\nStandard\n70\n1\n"
- result += "10\n"+str(p3.x)+"\n20\n"+str(p3.y)+"\n30\n"+str(p3.z)+"\n"
- result += "13\n"+str(p1.x)+"\n23\n"+str(p1.y)+"\n33\n"+str(p1.z)+"\n"
- result += "14\n"+str(p2.x)+"\n24\n"+str(p2.y)+"\n34\n"+str(p2.z)+"\n"
+ result += "10\n" + str(p3.x) + "\n20\n" + str(p3.y) + "\n30\n" + str(p3.z) + "\n"
+ result += "13\n" + str(p1.x) + "\n23\n" + str(p1.y) + "\n33\n" + str(p1.z) + "\n"
+ result += "14\n" + str(p2.x) + "\n24\n" + str(p2.y) + "\n34\n" + str(p2.z) + "\n"
elif utils.get_type(obj) == "Annotation":
# Only for App::Annotation
@@ -104,7 +104,7 @@ def get_dxf(obj, direction=None):
result += "7\nSTANDARD\n"
count += 1
- elif hasattr(obj, 'Shape'):
+ elif hasattr(obj, "Shape"):
# TODO do this the Draft way, for ex. using polylines and rectangles
if not direction:
direction = App.Vector(0, 0, -1)
@@ -117,8 +117,7 @@ def get_dxf(obj, direction=None):
except Exception:
# TODO: trap only specific exception.
# Impossible to generate DXF from Shape? Which exception is throw?
- _wrn("get_dxf: "
- "unable to project '{}' to {}".format(obj.Label, direction))
+ _wrn("get_dxf: " "unable to project '{}' to {}".format(obj.Label, direction))
else:
result += d
else:
@@ -127,11 +126,10 @@ def get_dxf(obj, direction=None):
return result
-def getDXF(obj,
- direction=None):
+def getDXF(obj, direction=None):
"""Return DXF string of the object. DEPRECATED. Use 'get_dxf'."""
utils.use_instead("get_dxf")
- return get_dxf(obj,
- direction=direction)
+ return get_dxf(obj, direction=direction)
+
## @}
diff --git a/src/Mod/Draft/draftfunctions/extrude.py b/src/Mod/Draft/draftfunctions/extrude.py
index 970bdaa0df..421060a0c5 100644
--- a/src/Mod/Draft/draftfunctions/extrude.py
+++ b/src/Mod/Draft/draftfunctions/extrude.py
@@ -55,9 +55,10 @@ def extrude(obj, vector, solid=False):
newobj.Solid = solid
if App.GuiUp:
obj.ViewObject.Visibility = False
- gui_utils.format_object(newobj,obj)
+ gui_utils.format_object(newobj, obj)
gui_utils.select(newobj)
return newobj
+
## @}
diff --git a/src/Mod/Draft/draftfunctions/fuse.py b/src/Mod/Draft/draftfunctions/fuse.py
index 152baaf6b8..9a84e6b59c 100644
--- a/src/Mod/Draft/draftfunctions/fuse.py
+++ b/src/Mod/Draft/draftfunctions/fuse.py
@@ -49,6 +49,7 @@ def fuse(object1, object2):
return
import Part
import DraftGeomUtils
+
# testing if we have holes:
holes = False
fshape = object1.Shape.fuse(object2.Shape)
@@ -74,9 +75,10 @@ def fuse(object1, object2):
if App.GuiUp:
object1.ViewObject.Visibility = False
object2.ViewObject.Visibility = False
- gui_utils.format_object(obj,object1)
+ gui_utils.format_object(obj, object1)
gui_utils.select(obj)
return obj
+
## @}
diff --git a/src/Mod/Draft/draftfunctions/heal.py b/src/Mod/Draft/draftfunctions/heal.py
index fe7cdd1f24..47766e53b4 100644
--- a/src/Mod/Draft/draftfunctions/heal.py
+++ b/src/Mod/Draft/draftfunctions/heal.py
@@ -61,7 +61,7 @@ def heal(objlist=None, delete=True, reparent=True):
else:
print("Manual mode: Force-healing selected objects…")
- if not isinstance(objlist,list):
+ if not isinstance(objlist, list):
objlist = [objlist]
dellist = []
@@ -70,34 +70,34 @@ def heal(objlist=None, delete=True, reparent=True):
for obj in objlist:
dtype = utils.get_type(obj)
ftype = obj.TypeId
- if ftype in ["Part::FeaturePython","App::FeaturePython","Part::Part2DObjectPython"]:
+ if ftype in ["Part::FeaturePython", "App::FeaturePython", "Part::Part2DObjectPython"]:
proxy = obj.Proxy
- if hasattr(obj,"ViewObject"):
- if hasattr(obj.ViewObject,"Proxy"):
+ if hasattr(obj, "ViewObject"):
+ if hasattr(obj.ViewObject, "Proxy"):
proxy = obj.ViewObject.Proxy
- if (proxy == 1) or (dtype in ["Unknown","Part"]) or (not auto):
+ if (proxy == 1) or (dtype in ["Unknown", "Part"]) or (not auto):
got = True
dellist.append(obj.Name)
props = obj.PropertiesList
if ("Dimline" in props) and ("Start" in props):
print("Healing " + obj.Name + " of type Dimension")
- nobj = make_copy(obj,force="Dimension",reparent=reparent)
+ nobj = make_copy(obj, force="Dimension", reparent=reparent)
elif ("Height" in props) and ("Length" in props):
print("Healing " + obj.Name + " of type Rectangle")
- nobj = make_copy(obj,force="Rectangle",reparent=reparent)
+ nobj = make_copy(obj, force="Rectangle", reparent=reparent)
elif ("Points" in props) and ("Closed" in props):
if "BSpline" in obj.Name:
print("Healing " + obj.Name + " of type BSpline")
- nobj = make_copy(obj,force="BSpline",reparent=reparent)
+ nobj = make_copy(obj, force="BSpline", reparent=reparent)
else:
print("Healing " + obj.Name + " of type Wire")
- nobj = make_copy(obj,force="Wire",reparent=reparent)
+ nobj = make_copy(obj, force="Wire", reparent=reparent)
elif ("Radius" in props) and ("FirstAngle" in props):
print("Healing " + obj.Name + " of type Circle")
- nobj = make_copy(obj,force="Circle",reparent=reparent)
+ nobj = make_copy(obj, force="Circle", reparent=reparent)
elif ("DrawMode" in props) and ("FacesNumber" in props):
print("Healing " + obj.Name + " of type Polygon")
- nobj = make_copy(obj,force="Polygon",reparent=reparent)
+ nobj = make_copy(obj, force="Polygon", reparent=reparent)
else:
dellist.pop()
print("Object " + obj.Name + " is not healable")
@@ -105,10 +105,11 @@ def heal(objlist=None, delete=True, reparent=True):
if not got:
print("No object seems to need healing")
else:
- print("Healed ",len(dellist)," objects")
+ print("Healed ", len(dellist), " objects")
if dellist and delete:
for n in dellist:
App.ActiveDocument.removeObject(n)
+
## @}
diff --git a/src/Mod/Draft/draftfunctions/join.py b/src/Mod/Draft/draftfunctions/join.py
index 85a9ca81e6..6b55fa7769 100644
--- a/src/Mod/Draft/draftfunctions/join.py
+++ b/src/Mod/Draft/draftfunctions/join.py
@@ -31,7 +31,7 @@ import FreeCAD as App
import DraftVecUtils
-def join_wires(wires, joinAttempts = 0):
+def join_wires(wires, joinAttempts=0):
"""join_wires(objects): merges a set of wires where possible, if any of those
wires have a coincident start and end point"""
wires = list(wires)
@@ -58,10 +58,13 @@ def join_two_wires(wire1, wire2):
"""
wire1AbsPoints = [wire1.Placement.multVec(point) for point in wire1.Points]
wire2AbsPoints = [wire2.Placement.multVec(point) for point in wire2.Points]
- if ((DraftVecUtils.equals(wire1AbsPoints[0], wire2AbsPoints[-1])
- and DraftVecUtils.equals(wire1AbsPoints[-1], wire2AbsPoints[0]))
- or (DraftVecUtils.equals(wire1AbsPoints[0], wire2AbsPoints[0])
- and DraftVecUtils.equals(wire1AbsPoints[-1], wire2AbsPoints[-1]))):
+ if (
+ DraftVecUtils.equals(wire1AbsPoints[0], wire2AbsPoints[-1])
+ and DraftVecUtils.equals(wire1AbsPoints[-1], wire2AbsPoints[0])
+ ) or (
+ DraftVecUtils.equals(wire1AbsPoints[0], wire2AbsPoints[0])
+ and DraftVecUtils.equals(wire1AbsPoints[-1], wire2AbsPoints[-1])
+ ):
wire2AbsPoints.pop()
wire1.Closed = True
elif DraftVecUtils.equals(wire1AbsPoints[0], wire2AbsPoints[0]):
@@ -76,10 +79,9 @@ def join_two_wires(wire1, wire2):
else:
return False
wire2AbsPoints.pop(0)
- wire1.Points = ([wire1.Placement.inverse().multVec(point)
- for point in wire1AbsPoints] +
- [wire1.Placement.inverse().multVec(point)
- for point in wire2AbsPoints])
+ wire1.Points = [wire1.Placement.inverse().multVec(point) for point in wire1AbsPoints] + [
+ wire1.Placement.inverse().multVec(point) for point in wire2AbsPoints
+ ]
App.ActiveDocument.removeObject(wire2.Name)
return True
diff --git a/src/Mod/Draft/draftfunctions/mirror.py b/src/Mod/Draft/draftfunctions/mirror.py
index 21ce9aa825..add29d290b 100644
--- a/src/Mod/Draft/draftfunctions/mirror.py
+++ b/src/Mod/Draft/draftfunctions/mirror.py
@@ -80,11 +80,11 @@ def mirror(objlist, p1, p2):
"""
if not objlist:
- _err(translate("draft","No object given"))
+ _err(translate("draft", "No object given"))
return
if p1 == p2:
- _err(translate("draft","The two points are coincident"))
+ _err(translate("draft", "The two points are coincident"))
return
if not isinstance(objlist, list):
@@ -110,4 +110,5 @@ def mirror(objlist, p1, p2):
return result
+
## @}
diff --git a/src/Mod/Draft/draftfunctions/move.py b/src/Mod/Draft/draftfunctions/move.py
index fcb0ae4588..d2d169bcc0 100644
--- a/src/Mod/Draft/draftfunctions/move.py
+++ b/src/Mod/Draft/draftfunctions/move.py
@@ -92,7 +92,9 @@ def move(selection, vector, copy=False, subelements=False):
if copy:
for obj in objs:
if obj.isDerivedFrom("App::DocumentObjectGroup") and obj.Name not in newgroups:
- newgroups[obj.Name] = obj.Document.addObject(obj.TypeId, utils.get_real_name(obj.Name))
+ newgroups[obj.Name] = obj.Document.addObject(
+ obj.TypeId, utils.get_real_name(obj.Name)
+ )
for idx, obj in enumerate(objs):
newobj = None
@@ -217,7 +219,7 @@ def move_edge(obj, edge_idx, vector, global_place=None):
if utils.is_closed_edge(edge_idx, obj):
move_vertex(obj, 0, vector, global_place)
else:
- move_vertex(obj, edge_idx+1, vector, global_place)
+ move_vertex(obj, edge_idx + 1, vector, global_place)
def copy_moved_edge(obj, edge_idx, vector, global_place=None):
@@ -233,9 +235,10 @@ def copy_moved_edge(obj, edge_idx, vector, global_place=None):
if utils.is_closed_edge(edge_idx, obj):
vertex2 = glp.multVec(obj.Points[0]).add(vector)
else:
- vertex2 = glp.multVec(obj.Points[edge_idx+1]).add(vector)
+ vertex2 = glp.multVec(obj.Points[edge_idx + 1]).add(vector)
newobj = make_line.make_line(vertex1, vertex2)
gui_utils.format_object(newobj, obj)
return newobj
+
## @}
diff --git a/src/Mod/Draft/draftfunctions/offset.py b/src/Mod/Draft/draftfunctions/offset.py
index 3a9e8f227f..18271d239e 100644
--- a/src/Mod/Draft/draftfunctions/offset.py
+++ b/src/Mod/Draft/draftfunctions/offset.py
@@ -70,43 +70,51 @@ def offset(obj, delta, copy=False, bind=False, sym=False, occ=False):
"""
import Part
import DraftGeomUtils
+
newwire = None
delete = None
- if (copy is False
- and (utils.get_type(obj).startswith("Sketcher::")
- or utils.get_type(obj).startswith("Part::")
- or utils.get_type(obj).startswith("PartDesign::"))): # For PartDesign_SubShapeBinders which can reference sketches.
- print("the offset tool is currently unable to offset a non-Draft object directly - Creating a copy")
+ if copy is False and (
+ utils.get_type(obj).startswith("Sketcher::")
+ or utils.get_type(obj).startswith("Part::")
+ or utils.get_type(obj).startswith("PartDesign::")
+ ): # For PartDesign_SubShapeBinders which can reference sketches.
+ print(
+ "the offset tool is currently unable to offset a non-Draft object directly - Creating a copy"
+ )
copy = True
- def getRect(p,obj):
+ def getRect(p, obj):
"""returns length,height,placement"""
pl = obj.Placement.copy()
pl.Base = p[0]
diag = p[2].sub(p[0])
bb = p[1].sub(p[0])
bh = p[3].sub(p[0])
- nb = DraftVecUtils.project(diag,bb)
- nh = DraftVecUtils.project(diag,bh)
- if obj.Length.Value < 0: l = -nb.Length
- else: l = nb.Length
- if obj.Height.Value < 0: h = -nh.Length
- else: h = nh.Length
- return l,h,pl
+ nb = DraftVecUtils.project(diag, bb)
+ nh = DraftVecUtils.project(diag, bh)
+ if obj.Length.Value < 0:
+ l = -nb.Length
+ else:
+ l = nb.Length
+ if obj.Height.Value < 0:
+ h = -nh.Length
+ else:
+ h = nh.Length
+ return l, h, pl
- def getRadius(obj,delta):
+ def getRadius(obj, delta):
"""returns a new radius for a regular polygon"""
- an = math.pi/obj.FacesNumber
- nr = DraftVecUtils.rotate(delta,-an)
- nr.multiply(1/math.cos(an))
+ an = math.pi / obj.FacesNumber
+ nr = DraftVecUtils.rotate(delta, -an)
+ nr.multiply(1 / math.cos(an))
nr = obj.Shape.Vertexes[0].Point.add(nr)
nr = nr.sub(obj.Placement.Base)
nr = nr.Length
if obj.DrawMode == "inscribed":
return nr
else:
- return nr * math.cos(math.pi/obj.FacesNumber)
+ return nr * math.cos(math.pi / obj.FacesNumber)
newwire = None
if utils.get_type(obj) == "Circle":
@@ -117,27 +125,29 @@ def offset(obj, delta, copy=False, bind=False, sym=False, occ=False):
if sym:
d1 = App.Vector(delta).multiply(0.5)
d2 = d1.negative()
- n1 = DraftGeomUtils.offsetWire(obj.Shape,d1)
- n2 = DraftGeomUtils.offsetWire(obj.Shape,d2)
+ n1 = DraftGeomUtils.offsetWire(obj.Shape, d1)
+ n2 = DraftGeomUtils.offsetWire(obj.Shape, d2)
else:
- if isinstance(delta,float) and (len(obj.Shape.Edges) == 1):
+ if isinstance(delta, float) and (len(obj.Shape.Edges) == 1):
# circle
c = obj.Shape.Edges[0].Curve
- nc = Part.Circle(c.Center,c.Axis,delta)
+ nc = Part.Circle(c.Center, c.Axis, delta)
if len(obj.Shape.Vertexes) > 1:
- nc = Part.ArcOfCircle(nc,obj.Shape.Edges[0].FirstParameter,obj.Shape.Edges[0].LastParameter)
+ nc = Part.ArcOfCircle(
+ nc, obj.Shape.Edges[0].FirstParameter, obj.Shape.Edges[0].LastParameter
+ )
newwire = Part.Wire(nc.toShape())
p = []
else:
- newwire = DraftGeomUtils.offsetWire(obj.Shape,delta)
+ newwire = DraftGeomUtils.offsetWire(obj.Shape, delta)
if DraftGeomUtils.hasCurves(newwire) and copy:
p = []
else:
p = DraftGeomUtils.getVerts(newwire)
if occ:
- newobj = App.ActiveDocument.addObject("Part::Feature","Offset")
- newobj.Shape = DraftGeomUtils.offsetWire(obj.Shape,delta,occ=True)
- gui_utils.formatObject(newobj,obj)
+ newobj = App.ActiveDocument.addObject("Part::Feature", "Offset")
+ newobj.Shape = DraftGeomUtils.offsetWire(obj.Shape, delta, occ=True)
+ gui_utils.formatObject(newobj, obj)
if not copy:
delete = obj.Name
elif bind:
@@ -151,35 +161,36 @@ def offset(obj, delta, copy=False, bind=False, sym=False, occ=False):
if s1 and s2:
w1 = s1.Edges
w2 = s2.Edges
- w3 = Part.LineSegment(s1.Vertexes[0].Point,s2.Vertexes[0].Point).toShape()
- w4 = Part.LineSegment(s1.Vertexes[-1].Point,s2.Vertexes[-1].Point).toShape()
- newobj = App.ActiveDocument.addObject("Part::Feature","Offset")
- newobj.Shape = Part.Face(Part.Wire(w1+[w3]+w2+[w4]))
+ w3 = Part.LineSegment(s1.Vertexes[0].Point, s2.Vertexes[0].Point).toShape()
+ w4 = Part.LineSegment(s1.Vertexes[-1].Point, s2.Vertexes[-1].Point).toShape()
+ newobj = App.ActiveDocument.addObject("Part::Feature", "Offset")
+ newobj.Shape = Part.Face(Part.Wire(w1 + [w3] + w2 + [w4]))
else:
print("Draft.offset: Unable to bind wires")
else:
- newobj = App.ActiveDocument.addObject("Part::Feature","Offset")
+ newobj = App.ActiveDocument.addObject("Part::Feature", "Offset")
newobj.Shape = Part.Face(obj.Shape.Wires[0])
if not copy:
delete = obj.Name
elif copy:
newobj = None
- if sym: return None
+ if sym:
+ return None
if utils.get_type(obj) == "Wire":
if p:
newobj = make_wire(p)
newobj.Closed = obj.Closed
elif newwire:
- newobj = App.ActiveDocument.addObject("Part::Feature","Offset")
+ newobj = App.ActiveDocument.addObject("Part::Feature", "Offset")
newobj.Shape = newwire
else:
print("Draft.offset: Unable to duplicate this object")
elif utils.get_type(obj) == "Rectangle":
if p:
- length,height,plac = getRect(p,obj)
- newobj = make_rectangle(length,height,plac)
+ length, height, plac = getRect(p, obj)
+ newobj = make_rectangle(length, height, plac)
elif newwire:
- newobj = App.ActiveDocument.addObject("Part::Feature","Offset")
+ newobj = App.ActiveDocument.addObject("Part::Feature", "Offset")
newobj.Shape = newwire
else:
print("Draft.offset: Unable to duplicate this object")
@@ -192,7 +203,7 @@ def offset(obj, delta, copy=False, bind=False, sym=False, occ=False):
elif utils.get_type(obj) == "Polygon":
pl = obj.Placement
newobj = make_polygon(obj.FacesNumber)
- newobj.Radius = getRadius(obj,delta)
+ newobj.Radius = getRadius(obj, delta)
newobj.DrawMode = obj.DrawMode
newobj.Placement = pl
elif utils.get_type(obj) == "BSpline":
@@ -207,37 +218,38 @@ def offset(obj, delta, copy=False, bind=False, sym=False, occ=False):
except Part.OCCError:
pass
if (not newobj) and newwire:
- newobj = App.ActiveDocument.addObject("Part::Feature","Offset")
+ newobj = App.ActiveDocument.addObject("Part::Feature", "Offset")
newobj.Shape = newwire
if not newobj:
print("Draft.offset: Unable to create an offset")
if newobj:
- gui_utils.formatObject(newobj,obj)
+ gui_utils.formatObject(newobj, obj)
else:
newobj = None
- if sym: return None
+ if sym:
+ return None
if utils.get_type(obj) == "Wire":
if obj.Base or obj.Tool:
App.Console.PrintWarning("Warning: object history removed\n")
obj.Base = None
obj.Tool = None
- obj.Placement = App.Placement() # p points are in the global coordinate system
+ obj.Placement = App.Placement() # p points are in the global coordinate system
obj.Points = p
elif utils.get_type(obj) == "BSpline":
- #print(delta)
+ # print(delta)
obj.Points = delta
- #print("done")
+ # print("done")
elif utils.get_type(obj) == "Rectangle":
- length,height,plac = getRect(p,obj)
+ length, height, plac = getRect(p, obj)
obj.Placement = plac
obj.Length = length
obj.Height = height
elif utils.get_type(obj) == "Circle":
obj.Radius = delta
elif utils.get_type(obj) == "Polygon":
- obj.Radius = getRadius(obj,delta)
- elif utils.get_type(obj) == 'Part':
- print("unsupported object") # TODO
+ obj.Radius = getRadius(obj, delta)
+ elif utils.get_type(obj) == "Part":
+ print("unsupported object") # TODO
newobj = obj
if copy and params.get_param("selectBaseObjects"):
gui_utils.select(obj)
@@ -247,4 +259,5 @@ def offset(obj, delta, copy=False, bind=False, sym=False, occ=False):
App.ActiveDocument.removeObject(delete)
return newobj
+
## @}
diff --git a/src/Mod/Draft/draftfunctions/rotate.py b/src/Mod/Draft/draftfunctions/rotate.py
index 028c50c832..acf1931b9e 100644
--- a/src/Mod/Draft/draftfunctions/rotate.py
+++ b/src/Mod/Draft/draftfunctions/rotate.py
@@ -42,8 +42,14 @@ from draftutils import params
from draftutils import utils
-def rotate(selection, angle, center=App.Vector(0, 0, 0),
- axis=App.Vector(0, 0, 1), copy=False, subelements=False):
+def rotate(
+ selection,
+ angle,
+ center=App.Vector(0, 0, 0),
+ axis=App.Vector(0, 0, 1),
+ copy=False,
+ subelements=False,
+):
"""rotate(selection, angle, [center], [axis], [copy], [subelements])
Rotates or copies selected objects.
@@ -80,8 +86,16 @@ def rotate(selection, angle, center=App.Vector(0, 0, 0),
single object / list with 2 or more objects / empty list
The objects (or their copies).
"""
- utils.type_check([(angle, (float, int)), (center, App.Vector),
- (axis, App.Vector), (copy, bool), (subelements, bool)], "rotate")
+ utils.type_check(
+ [
+ (angle, (float, int)),
+ (center, App.Vector),
+ (axis, App.Vector),
+ (copy, bool),
+ (subelements, bool),
+ ],
+ "rotate",
+ )
if not isinstance(selection, list):
selection = [selection]
if not selection:
@@ -106,7 +120,9 @@ def rotate(selection, angle, center=App.Vector(0, 0, 0),
if copy:
for obj in objs:
if obj.isDerivedFrom("App::DocumentObjectGroup") and obj.Name not in newgroups:
- newgroups[obj.Name] = obj.Document.addObject(obj.TypeId, utils.get_real_name(obj.Name))
+ newgroups[obj.Name] = obj.Document.addObject(
+ obj.TypeId, utils.get_real_name(obj.Name)
+ )
for idx, obj in enumerate(objs):
newobj = None
@@ -230,9 +246,8 @@ def rotate_vertex(obj, vert_idx, angle, center, axis, global_place=None):
glp = global_place
points = obj.Points
points[vert_idx] = glp.inverse().multVec(
- rotate_vector_from_center(
- glp.multVec(points[vert_idx]),
- angle, axis, center))
+ rotate_vector_from_center(glp.multVec(points[vert_idx]), angle, axis, center)
+ )
obj.Points = points
@@ -245,7 +260,7 @@ def rotate_edge(obj, edge_idx, angle, center, axis, global_place=None):
if utils.is_closed_edge(edge_idx, obj):
rotate_vertex(obj, 0, angle, center, axis, global_place)
else:
- rotate_vertex(obj, edge_idx+1, angle, center, axis, global_place)
+ rotate_vertex(obj, edge_idx + 1, angle, center, axis, global_place)
def copy_rotated_edge(obj, edge_idx, angle, center, axis, global_place=None):
@@ -257,19 +272,16 @@ def copy_rotated_edge(obj, edge_idx, angle, center, axis, global_place=None):
glp = obj.getGlobalPlacement()
else:
glp = global_place
- vertex1 = rotate_vector_from_center(
- glp.multVec(obj.Points[edge_idx]),
- angle, axis, center)
+ vertex1 = rotate_vector_from_center(glp.multVec(obj.Points[edge_idx]), angle, axis, center)
if utils.is_closed_edge(edge_idx, obj):
- vertex2 = rotate_vector_from_center(
- glp.multVec(obj.Points[0]),
- angle, axis, center)
+ vertex2 = rotate_vector_from_center(glp.multVec(obj.Points[0]), angle, axis, center)
else:
vertex2 = rotate_vector_from_center(
- glp.multVec(obj.Points[edge_idx+1]),
- angle, axis, center)
+ glp.multVec(obj.Points[edge_idx + 1]), angle, axis, center
+ )
newobj = make_line.make_line(vertex1, vertex2)
gui_utils.format_object(newobj, obj)
return newobj
+
## @}
diff --git a/src/Mod/Draft/draftfunctions/scale.py b/src/Mod/Draft/draftfunctions/scale.py
index eae3c27e09..bd2553ab71 100644
--- a/src/Mod/Draft/draftfunctions/scale.py
+++ b/src/Mod/Draft/draftfunctions/scale.py
@@ -43,8 +43,7 @@ from draftutils import params
from draftutils import utils
-def scale(selection, scale, center=App.Vector(0, 0, 0),
- copy=False, clone=False, subelements=False):
+def scale(selection, scale, center=App.Vector(0, 0, 0), copy=False, clone=False, subelements=False):
"""scale(selection, scale, [center], [copy], [clone], [subelements])
Scales or copies selected objects.
@@ -82,8 +81,16 @@ def scale(selection, scale, center=App.Vector(0, 0, 0),
single object / list with 2 or more objects / empty list
The objects (or their copies).
"""
- utils.type_check([(scale, App.Vector), (center, App.Vector),
- (copy, bool), (clone, bool), (subelements, bool)], "scale")
+ utils.type_check(
+ [
+ (scale, App.Vector),
+ (center, App.Vector),
+ (copy, bool),
+ (clone, bool),
+ (subelements, bool),
+ ],
+ "scale",
+ )
sx, sy, sz = scale
if sx * sy * sz == 0:
raise ValueError("Zero component in scale vector")
@@ -98,9 +105,13 @@ def scale(selection, scale, center=App.Vector(0, 0, 0),
if subelements:
return _scale_subelements(selection, scale, center, copy)
else:
- objs, parent_places, sel_info = utils._modifiers_process_selection(selection, (copy or clone), scale=True)
+ objs, parent_places, sel_info = utils._modifiers_process_selection(
+ selection, (copy or clone), scale=True
+ )
else:
- objs = utils._modifiers_filter_objects(utils._modifiers_get_group_contents(selection), (copy or clone), scale=True)
+ objs = utils._modifiers_filter_objects(
+ utils._modifiers_get_group_contents(selection), (copy or clone), scale=True
+ )
parent_places = None
sel_info = None
@@ -113,7 +124,9 @@ def scale(selection, scale, center=App.Vector(0, 0, 0),
if copy or clone:
for obj in objs:
if obj.isDerivedFrom("App::DocumentObjectGroup") and obj.Name not in newgroups:
- newgroups[obj.Name] = obj.Document.addObject(obj.TypeId, utils.get_real_name(obj.Name))
+ newgroups[obj.Name] = obj.Document.addObject(
+ obj.TypeId, utils.get_real_name(obj.Name)
+ )
for idx, obj in enumerate(objs):
newobj = None
@@ -174,7 +187,9 @@ def scale(selection, scale, center=App.Vector(0, 0, 0),
continue
if sx == sy == sz:
newobj = make_clone.make_clone(obj, forcedraft=True)
- newobj.Placement.Base = scale_vector_from_center(newobj.Placement.Base, scale, center)
+ newobj.Placement.Base = scale_vector_from_center(
+ newobj.Placement.Base, scale, center
+ )
newobj.Scale = scale
else:
if parent_place.isIdentity():
@@ -221,10 +236,10 @@ def scale(selection, scale, center=App.Vector(0, 0, 0),
else:
pla = parent_place * obj.Placement
pts = [
- App.Vector (0.0, 0.0, 0.0),
- App.Vector (obj.Length.Value, 0.0, 0.0),
- App.Vector (obj.Length.Value, obj.Height.Value, 0.0),
- App.Vector (0.0, obj.Height.Value, 0.0)
+ App.Vector(0.0, 0.0, 0.0),
+ App.Vector(obj.Length.Value, 0.0, 0.0),
+ App.Vector(obj.Length.Value, obj.Height.Value, 0.0),
+ App.Vector(0.0, obj.Height.Value, 0.0),
]
pts = [pla.multVec(p) for p in pts]
pts = [scale_vector_from_center(p, scale, center) for p in pts]
@@ -232,7 +247,7 @@ def scale(selection, scale, center=App.Vector(0, 0, 0),
x_vec = pts[1] - pts[0]
y_vec = pts[3] - pts[0]
ang = x_vec.getAngle(y_vec)
- if math.isclose(ang % math.pi/2, math.pi/4, abs_tol=1e-6):
+ if math.isclose(ang % math.pi / 2, math.pi / 4, abs_tol=1e-6):
if copy:
newobj = make_copy.make_copy(obj)
newobj.Placement = pla
@@ -275,6 +290,7 @@ def scale(selection, scale, center=App.Vector(0, 0, 0),
if create_non_parametric:
import Part
+
if parent_place.isIdentity():
pla = obj.Placement
else:
@@ -288,6 +304,7 @@ def scale(selection, scale, center=App.Vector(0, 0, 0),
if App.GuiUp:
if utils.get_type(obj) in ("Circle", "Ellipse"):
from draftviewproviders.view_base import ViewProviderDraft
+
ViewProviderDraft(newobj.ViewObject)
else:
newobj.ViewObject.Proxy = 0
@@ -384,7 +401,7 @@ def scale_edge(obj, edge_idx, scale, center, global_place=None):
if utils.is_closed_edge(edge_idx, obj):
scale_vertex(obj, 0, scale, center, global_place)
else:
- scale_vertex(obj, edge_idx+1, scale, center, global_place)
+ scale_vertex(obj, edge_idx + 1, scale, center, global_place)
def copy_scaled_edge(obj, edge_idx, scale, center, global_place=None):
@@ -400,9 +417,10 @@ def copy_scaled_edge(obj, edge_idx, scale, center, global_place=None):
if utils.is_closed_edge(edge_idx, obj):
vertex2 = scale_vector_from_center(glp.multVec(obj.Points[0]), scale, center)
else:
- vertex2 = scale_vector_from_center(glp.multVec(obj.Points[edge_idx+1]), scale, center)
+ vertex2 = scale_vector_from_center(glp.multVec(obj.Points[edge_idx + 1]), scale, center)
newobj = make_line.make_line(vertex1, vertex2)
gui_utils.format_object(newobj, obj)
return newobj
+
## @}
diff --git a/src/Mod/Draft/draftfunctions/split.py b/src/Mod/Draft/draftfunctions/split.py
index db8231e626..b14179e579 100644
--- a/src/Mod/Draft/draftfunctions/split.py
+++ b/src/Mod/Draft/draftfunctions/split.py
@@ -30,6 +30,7 @@
from draftmake import make_copy
from draftutils import utils
+
def split(wire, newPoint, edgeIndex):
if utils.get_type(wire) != "Wire":
return None
@@ -44,8 +45,10 @@ def split_closed_wire(wire, edgeIndex):
if edgeIndex == len(wire.Points):
new.Points = [wire.Points[0], wire.Points[-1]]
else:
- new.Points = [wire.Points[edgeIndex-1], wire.Points[edgeIndex]]
- wire.Points = list(reversed(wire.Points[0:edgeIndex])) + list(reversed(wire.Points[edgeIndex:]))
+ new.Points = [wire.Points[edgeIndex - 1], wire.Points[edgeIndex]]
+ wire.Points = list(reversed(wire.Points[0:edgeIndex])) + list(
+ reversed(wire.Points[edgeIndex:])
+ )
return new
diff --git a/src/Mod/Draft/draftfunctions/svg.py b/src/Mod/Draft/draftfunctions/svg.py
index fd40e32d71..3f5fff1cf0 100644
--- a/src/Mod/Draft/draftfunctions/svg.py
+++ b/src/Mod/Draft/draftfunctions/svg.py
@@ -21,8 +21,7 @@
# * USA *
# * *
# ***************************************************************************
-"""Provides functions to return the SVG representation of various shapes.
-"""
+"""Provides functions to return the SVG representation of various shapes."""
## @package svg
# \ingroup draftfunctions
# \brief Provides functions to return the SVG representation of shapes.
@@ -67,7 +66,7 @@ def get_line_style(line_style, scale):
style = style.split(",")
try:
# scale dashes
- style = ",".join([str(float(d)/scale) for d in style])
+ style = ",".join([str(float(d) / scale) for d in style])
# print("lstyle ", style)
except Exception:
# TODO: trap only specific exception; what is the problem?
@@ -91,7 +90,7 @@ def get_pattern(pat):
if pat in patterns:
return patterns[pat][0]
- return ''
+ return ""
def getPattern(pat):
@@ -100,8 +99,7 @@ def getPattern(pat):
return get_pattern(pat)
-def get_arrow(obj,
- arrowtype, point, arrowsize, color, linewidth, angle=0):
+def get_arrow(obj, arrowtype, point, arrowsize, color, linewidth, angle=0):
"""Get the SVG representation from an arrow."""
svg = ""
vobj = _get_view_object(obj)
@@ -110,54 +108,52 @@ def get_arrow(obj,
return svg
_cx_cy_r = 'cx="{}" cy="{}" r="{}"'.format(point.x, point.y, arrowsize)
- _rotate = 'rotate({},{},{})'.format(math.degrees(angle),
- point.x, point.y)
- _transl = 'translate({},{})'.format(point.x, point.y)
- _scale = 'scale({size},{size})'.format(size=arrowsize)
+ _rotate = "rotate({},{},{})".format(math.degrees(angle), point.x, point.y)
+ _transl = "translate({},{})".format(point.x, point.y)
+ _scale = "scale({size},{size})".format(size=arrowsize)
_style = 'style="stroke-miterlimit:4;stroke-dasharray:none;stroke-linecap:square"'
if arrowtype == "Circle":
- svg += '\n'
+ svg += "/>\n"
elif arrowtype == "Dot":
- svg += '\n'
+ svg += "/>\n"
elif arrowtype == "Arrow":
- svg += '\n'
+ svg += "/>\n"
elif arrowtype == "Tick":
- svg += '\n'
+ svg += "/>\n"
elif arrowtype == "Tick-2":
- svg += '\n'
+ svg += "/>\n"
elif arrowtype == "None":
svg += ""
else:
@@ -174,20 +170,17 @@ def get_arrow(obj,
return svg
-def getArrow(obj,
- arrowtype, point, arrowsize, color, linewidth, angle=0):
+def getArrow(obj, arrowtype, point, arrowsize, color, linewidth, angle=0):
"""Get the SVG representation from an arrow. DEPRECATED."""
utils.use_instead("get_arrow")
- return get_arrow(obj,
- arrowtype, point, arrowsize, color, linewidth, angle)
+ return get_arrow(obj, arrowtype, point, arrowsize, color, linewidth, angle)
def get_overshoot(point, shootsize, color, linewidth, angle=0):
"""Get the SVG representation of a dimension line overshoot."""
- svg = '\n'
+ svg += "/>\n"
return svg
@@ -205,54 +198,59 @@ def getOvershoot(point, shootsize, color, linewidth, angle=0):
return get_overshoot(point, shootsize, color, linewidth, angle)
-def format_point(coords, action='L'):
+def format_point(coords, action="L"):
"""Return a string with a formatted point."""
return "{action}{x},{y}".format(x=coords.x, y=coords.y, action=action)
-def _svg_shape(svg, obj, plane,
- fillstyle, pathdata, stroke, linewidth, lstyle):
+def _svg_shape(svg, obj, plane, fillstyle, pathdata, stroke, linewidth, lstyle):
"""Return the SVG representation of a Part.Shape."""
if "#" in fillstyle:
fill = fillstyle
elif fillstyle == "shape color":
fill = "#888888"
- elif fillstyle in ("none",None):
+ elif fillstyle in ("none", None):
fill = "none"
else:
- fill = 'url(#' + fillstyle + ')'
+ fill = "url(#" + fillstyle + ")"
- svg += get_path(obj, plane,
- fill, pathdata, stroke, linewidth, lstyle,
- fill_opacity=None,
- edges=obj.Edges, pathname="")
+ svg += get_path(
+ obj,
+ plane,
+ fill,
+ pathdata,
+ stroke,
+ linewidth,
+ lstyle,
+ fill_opacity=None,
+ edges=obj.Edges,
+ pathname="",
+ )
return svg
-def _svg_dimension(obj, plane, scale, linewidth, fontsize,
- stroke, tstroke, pointratio, techdraw, rotation):
+def _svg_dimension(
+ obj, plane, scale, linewidth, fontsize, stroke, tstroke, pointratio, techdraw, rotation
+):
"""Return the SVG representation of a linear dimension."""
if not App.GuiUp:
- _wrn("'{}': SVG can only be generated "
- "in GUI mode".format(obj.Label))
+ _wrn("'{}': SVG can only be generated " "in GUI mode".format(obj.Label))
return ""
vobj = _get_view_object(obj)
if not hasattr(vobj, "Proxy") or not vobj.Proxy:
- _err("'{}': doesn't have Proxy, "
- "SVG cannot be generated".format(obj.Label))
+ _err("'{}': doesn't have Proxy, " "SVG cannot be generated".format(obj.Label))
return ""
prx = vobj.Proxy
if not hasattr(prx, "p1"):
- _err("'{}': doesn't have points, "
- "SVG cannot be generated".format(obj.Label))
+ _err("'{}': doesn't have points, " "SVG cannot be generated".format(obj.Label))
return ""
ts = len(prx.string) * vobj.FontSize.Value / 4.0
- rm = (prx.p3 - prx.p2).Length/2.0 - ts
+ rm = (prx.p3 - prx.p2).Length / 2.0 - ts
_diff32 = prx.p3 - prx.p2
_diff23 = prx.p2 - prx.p3
@@ -274,7 +272,7 @@ def _svg_dimension(obj, plane, scale, linewidth, fontsize,
angle = -DraftVecUtils.angle(get_proj(rv, plane))
# angle = -DraftVecUtils.angle(p3.sub(p2))
- svg = ''
+ svg = ""
nolines = False
if hasattr(vobj, "ShowLine"):
if not vobj.ShowLine:
@@ -282,12 +280,12 @@ def _svg_dimension(obj, plane, scale, linewidth, fontsize,
# drawing lines
if not nolines:
- svg += ' math.pi/2:
- tangle = tangle-math.pi
+ if tangle > math.pi / 2:
+ tangle = tangle - math.pi
# elif (tangle <= -math.pi/2) or (tangle > math.pi/2):
# tangle = tangle + math.pi
@@ -297,28 +295,28 @@ def _svg_dimension(obj, plane, scale, linewidth, fontsize,
# " text: ", prx.string)
if abs(tangle + math.radians(rotation)) < 0.0001:
tangle += math.pi
- _v = App.Vector(0, 2.0/scale, 0)
+ _v = App.Vector(0, 2.0 / scale, 0)
_rot = DraftVecUtils.rotate(_v, tangle)
tbase = tbase + _rot
if not nolines:
- svg += 'd="M ' + str(p1.x) + ' ' + str(p1.y) + ' '
- svg += 'L ' + str(p2.x) + ' ' + str(p2.y) + ' '
- svg += 'L ' + str(p3.x) + ' ' + str(p3.y) + ' '
- svg += 'L ' + str(p4.x) + ' ' + str(p4.y) + '" '
+ svg += 'd="M ' + str(p1.x) + " " + str(p1.y) + " "
+ svg += "L " + str(p2.x) + " " + str(p2.y) + " "
+ svg += "L " + str(p3.x) + " " + str(p3.y) + " "
+ svg += "L " + str(p4.x) + " " + str(p4.y) + '" '
else:
tangle = 0
if rotation != 0:
tangle = -math.radians(rotation)
- tbase = tbase + App.Vector(0, -2.0/scale, 0)
+ tbase = tbase + App.Vector(0, -2.0 / scale, 0)
if not nolines:
- svg += 'd="M ' + str(p1.x) + ' ' + str(p1.y) + ' '
- svg += 'L ' + str(p2.x) + ' ' + str(p2.y) + ' '
- svg += 'L ' + str(p2a.x) + ' ' + str(p2a.y) + ' '
- svg += 'M ' + str(p2b.x) + ' ' + str(p2b.y) + ' '
- svg += 'L ' + str(p3.x) + ' ' + str(p3.y) + ' '
- svg += 'L ' + str(p4.x) + ' ' + str(p4.y) + '" '
+ svg += 'd="M ' + str(p1.x) + " " + str(p1.y) + " "
+ svg += "L " + str(p2.x) + " " + str(p2.y) + " "
+ svg += "L " + str(p2a.x) + " " + str(p2a.y) + " "
+ svg += "M " + str(p2b.x) + " " + str(p2b.y) + " "
+ svg += "L " + str(p3.x) + " " + str(p3.y) + " "
+ svg += "L " + str(p4.x) + " " + str(p4.y) + '" '
if not nolines:
svg += 'fill="none" stroke="'
@@ -326,66 +324,78 @@ def _svg_dimension(obj, plane, scale, linewidth, fontsize,
svg += 'stroke-width="' + str(linewidth) + ' px" '
svg += 'style="stroke-width:' + str(linewidth)
svg += ';stroke-miterlimit:4;stroke-dasharray:none;stroke-linecap:square" '
- svg += 'freecad:basepoint1="'+str(p1.x)+' '+str(p1.y)+'" '
- svg += 'freecad:basepoint2="'+str(p4.x)+' '+str(p4.y)+'" '
- svg += 'freecad:dimpoint="'+str(p2.x)+' '+str(p2.y)+'"'
- svg += '/>\n'
+ svg += 'freecad:basepoint1="' + str(p1.x) + " " + str(p1.y) + '" '
+ svg += 'freecad:basepoint2="' + str(p4.x) + " " + str(p4.y) + '" '
+ svg += 'freecad:dimpoint="' + str(p2.x) + " " + str(p2.y) + '"'
+ svg += "/>\n"
# drawing dimension and extension lines overshoots
if hasattr(vobj, "DimOvershoot") and vobj.DimOvershoot.Value:
- shootsize = vobj.DimOvershoot.Value/pointratio
- svg += get_overshoot(p2, shootsize, stroke,
- linewidth, angle)
- svg += get_overshoot(p3, shootsize, stroke,
- linewidth, angle + math.pi)
+ shootsize = vobj.DimOvershoot.Value / pointratio
+ svg += get_overshoot(p2, shootsize, stroke, linewidth, angle)
+ svg += get_overshoot(p3, shootsize, stroke, linewidth, angle + math.pi)
if hasattr(vobj, "ExtOvershoot") and vobj.ExtOvershoot.Value:
- shootsize = vobj.ExtOvershoot.Value/pointratio
+ shootsize = vobj.ExtOvershoot.Value / pointratio
shootangle = -DraftVecUtils.angle(p1 - p2)
- svg += get_overshoot(p2, shootsize, stroke,
- linewidth, shootangle)
- svg += get_overshoot(p3, shootsize, stroke,
- linewidth, shootangle)
+ svg += get_overshoot(p2, shootsize, stroke, linewidth, shootangle)
+ svg += get_overshoot(p3, shootsize, stroke, linewidth, shootangle)
# drawing arrows
- if hasattr(vobj, "ArrowTypeStart") \
- and hasattr(vobj, "ArrowTypeEnd") \
- and hasattr(vobj, "ArrowSizeStart") \
- and hasattr(vobj, "ArrowSizeEnd"):
+ if (
+ hasattr(vobj, "ArrowTypeStart")
+ and hasattr(vobj, "ArrowTypeEnd")
+ and hasattr(vobj, "ArrowSizeStart")
+ and hasattr(vobj, "ArrowSizeEnd")
+ ):
if getattr(vobj, "FlipArrows", False):
angle = angle + math.pi
if getattr(vobj, "FlipText", False):
angle = angle + math.pi
- svg += get_arrow(obj,
- vobj.ArrowTypeStart,
- p2,
- vobj.ArrowSizeStart.Value/pointratio,
- stroke,
- linewidth,
- angle)
+ svg += get_arrow(
+ obj,
+ vobj.ArrowTypeStart,
+ p2,
+ vobj.ArrowSizeStart.Value / pointratio,
+ stroke,
+ linewidth,
+ angle,
+ )
- svg += get_arrow(obj,
- vobj.ArrowTypeEnd,
- p3,
- vobj.ArrowSizeEnd.Value/pointratio,
- stroke,
- linewidth,
- angle + math.pi)
+ svg += get_arrow(
+ obj,
+ vobj.ArrowTypeEnd,
+ p3,
+ vobj.ArrowSizeEnd.Value / pointratio,
+ stroke,
+ linewidth,
+ angle + math.pi,
+ )
# drawing text
- svg += svgtext.get_text(plane, techdraw,
- tstroke, fontsize, vobj.FontName,
- tangle, tbase, prx.string)
+ svg += svgtext.get_text(
+ plane, techdraw, tstroke, fontsize, vobj.FontName, tangle, tbase, prx.string
+ )
return svg
-def get_svg(obj,
- scale=1, linewidth=0.35, fontsize=12,
- fillstyle="shape color", direction=None, linestyle=None,
- color=None, linespacing=None, techdraw=False, rotation=0,
- fillspaces=False, override=True):
+def get_svg(
+ obj,
+ scale=1,
+ linewidth=0.35,
+ fontsize=12,
+ fillstyle="shape color",
+ direction=None,
+ linestyle=None,
+ color=None,
+ linespacing=None,
+ techdraw=False,
+ rotation=0,
+ fillspaces=False,
+ override=True,
+):
"""Return a string containing an SVG representation of the object.
Paramaeters
@@ -434,17 +444,22 @@ def get_svg(obj,
"""
# If this is a group, recursively call this function to gather
# all the SVG strings from the contents of the group.
- if (obj.isDerivedFrom("App::DocumentObjectGroup")
- or utils.get_type(obj) in ["Layer", "BuildingPart", "IfcGroup"]
- or obj.isDerivedFrom("App::LinkGroup")
- or (obj.isDerivedFrom("App::Link")
- and obj.LinkedObject.isDerivedFrom("App::DocumentObjectGroup"))):
+ if (
+ obj.isDerivedFrom("App::DocumentObjectGroup")
+ or utils.get_type(obj) in ["Layer", "BuildingPart", "IfcGroup"]
+ or obj.isDerivedFrom("App::LinkGroup")
+ or (
+ obj.isDerivedFrom("App::Link")
+ and obj.LinkedObject.isDerivedFrom("App::DocumentObjectGroup")
+ )
+ ):
hidden_doc = None
- if (obj.isDerivedFrom("App::LinkGroup")
- or (obj.isDerivedFrom("App::Link")
- and obj.LinkedObject.isDerivedFrom("App::DocumentObjectGroup"))):
+ if obj.isDerivedFrom("App::LinkGroup") or (
+ obj.isDerivedFrom("App::Link")
+ and obj.LinkedObject.isDerivedFrom("App::DocumentObjectGroup")
+ ):
if obj.Placement.isIdentity():
if obj.isDerivedFrom("App::LinkGroup"):
group = obj.ElementList
@@ -467,11 +482,21 @@ def get_svg(obj,
svg = ""
for child in group:
- svg += get_svg(child,
- scale, linewidth, fontsize,
- fillstyle, direction, linestyle,
- color, linespacing, techdraw,
- rotation, fillspaces, override)
+ svg += get_svg(
+ child,
+ scale,
+ linewidth,
+ fontsize,
+ fillstyle,
+ direction,
+ linestyle,
+ color,
+ linespacing,
+ techdraw,
+ rotation,
+ fillspaces,
+ override,
+ )
if hidden_doc is not None:
try:
@@ -492,11 +517,21 @@ def get_svg(obj,
new.Placement = obj.Placement * new.Placement
else:
new.Placement = obj.Placement
- svg = get_svg(new,
- scale, linewidth, fontsize,
- fillstyle, direction, linestyle,
- color, linespacing, techdraw,
- rotation, fillspaces, override)
+ svg = get_svg(
+ new,
+ scale,
+ linewidth,
+ fontsize,
+ fillstyle,
+ direction,
+ linestyle,
+ color,
+ linespacing,
+ techdraw,
+ rotation,
+ fillspaces,
+ override,
+ )
try:
App.closeDocument(hidden_doc.Name)
except:
@@ -507,7 +542,7 @@ def get_svg(obj,
pathdata = []
svg = ""
- linewidth = float(linewidth)/scale
+ linewidth = float(linewidth) / scale
if not override:
if vobj is not None and hasattr(vobj, "LineWidth"):
if hasattr(vobj.LineWidth, "Value"):
@@ -516,9 +551,9 @@ def get_svg(obj,
lw = vobj.LineWidth
linewidth = lw * linewidth
- fontsize = (float(fontsize)/scale)/2
+ fontsize = (float(fontsize) / scale) / 2
if linespacing:
- linespacing = float(linespacing)/scale
+ linespacing = float(linespacing) / scale
else:
linespacing = 0.5
@@ -532,9 +567,9 @@ def get_svg(obj,
if isinstance(direction, App.Vector):
if direction != App.Vector(0, 0, 0):
plane = WorkingPlane.PlaneBase()
- plane.align_to_point_and_axis_svg(App.Vector(0, 0, 0),
- direction.negative().negative(),
- 0)
+ plane.align_to_point_and_axis_svg(
+ App.Vector(0, 0, 0), direction.negative().negative(), 0
+ )
else:
raise ValueError("'direction' cannot be: Vector(0, 0, 0)")
elif isinstance(direction, WorkingPlane.PlaneBase):
@@ -573,13 +608,14 @@ def get_svg(obj,
pass
elif isinstance(obj, Part.Shape):
- svg = _svg_shape(svg, obj, plane,
- fillstyle, pathdata, stroke, linewidth, lstyle)
+ svg = _svg_shape(svg, obj, plane, fillstyle, pathdata, stroke, linewidth, lstyle)
- elif (utils.get_type(obj) in ["Dimension", "LinearDimension"]
- or (utils.get_type(obj) == "IfcAnnotation" and obj.ObjectType == "DIMENSION")):
- svg = _svg_dimension(obj, plane, scale, linewidth, fontsize,
- stroke, tstroke, pointratio, techdraw, rotation)
+ elif utils.get_type(obj) in ["Dimension", "LinearDimension"] or (
+ utils.get_type(obj) == "IfcAnnotation" and obj.ObjectType == "DIMENSION"
+ ):
+ svg = _svg_dimension(
+ obj, plane, scale, linewidth, fontsize, stroke, tstroke, pointratio, techdraw, rotation
+ )
elif utils.get_type(obj) == "AngularDimension":
if not App.GuiUp:
@@ -593,50 +629,79 @@ def get_svg(obj,
# drawing arc
fill = "none"
if vobj.DisplayMode == "World":
- svg += get_path(obj, plane,
- fill, pathdata, stroke, linewidth,
- lstyle, fill_opacity=None,
- edges=[prx.circle])
+ svg += get_path(
+ obj,
+ plane,
+ fill,
+ pathdata,
+ stroke,
+ linewidth,
+ lstyle,
+ fill_opacity=None,
+ edges=[prx.circle],
+ )
else:
if hasattr(prx, "circle1"):
- svg += get_path(obj, plane,
- fill, pathdata, stroke, linewidth,
- lstyle, fill_opacity=None,
- edges=[prx.circle1])
- svg += get_path(obj, plane,
- fill, pathdata, stroke, linewidth,
- lstyle, fill_opacity=None,
- edges=[prx.circle2])
+ svg += get_path(
+ obj,
+ plane,
+ fill,
+ pathdata,
+ stroke,
+ linewidth,
+ lstyle,
+ fill_opacity=None,
+ edges=[prx.circle1],
+ )
+ svg += get_path(
+ obj,
+ plane,
+ fill,
+ pathdata,
+ stroke,
+ linewidth,
+ lstyle,
+ fill_opacity=None,
+ edges=[prx.circle2],
+ )
else:
- svg += get_path(obj, plane,
- fill, pathdata, stroke, linewidth,
- lstyle, fill_opacity=None,
- edges=[prx.circle])
+ svg += get_path(
+ obj,
+ plane,
+ fill,
+ pathdata,
+ stroke,
+ linewidth,
+ lstyle,
+ fill_opacity=None,
+ edges=[prx.circle],
+ )
# drawing arrows
- if hasattr(vobj, "ArrowTypeStart") \
- and hasattr(vobj, "ArrowTypeEnd") \
- and hasattr(vobj, "ArrowSizeStart") \
- and hasattr(vobj, "ArrowSizeEnd"):
+ if (
+ hasattr(vobj, "ArrowTypeStart")
+ and hasattr(vobj, "ArrowTypeEnd")
+ and hasattr(vobj, "ArrowSizeStart")
+ and hasattr(vobj, "ArrowSizeEnd")
+ ):
p2 = get_proj(prx.p2, plane)
p3 = get_proj(prx.p3, plane)
- arrowsizestart = vobj.ArrowSizeStart.Value/pointratio
+ arrowsizestart = vobj.ArrowSizeStart.Value / pointratio
halfstartarrowlength = 2 * arrowsizestart
- startarrowangle = 2 * math.asin(halfstartarrowlength / prx.circle.Curve.Radius)
- arrowsizeend = vobj.ArrowSizeEnd.Value/pointratio
+ startarrowangle = 2 * math.asin(
+ halfstartarrowlength / prx.circle.Curve.Radius
+ )
+ arrowsizeend = vobj.ArrowSizeEnd.Value / pointratio
halfendarrowlength = 2 * arrowsizeend
endarrowangle = 2 * math.asin(halfendarrowlength / prx.circle.Curve.Radius)
- if hasattr(vobj, "FlipArrows") \
- and vobj.FlipArrows:
+ if hasattr(vobj, "FlipArrows") and vobj.FlipArrows:
startarrowangle = -startarrowangle
endarrowangle = -endarrowangle
- _v1a = prx.circle.valueAt(prx.circle.FirstParameter
- + startarrowangle)
+ _v1a = prx.circle.valueAt(prx.circle.FirstParameter + startarrowangle)
_v1b = prx.circle.valueAt(prx.circle.FirstParameter)
- _v2a = prx.circle.valueAt(prx.circle.LastParameter
- - endarrowangle)
+ _v2a = prx.circle.valueAt(prx.circle.LastParameter - endarrowangle)
_v2b = prx.circle.valueAt(prx.circle.LastParameter)
u1 = get_proj(_v1a - _v1b, plane)
@@ -644,49 +709,36 @@ def get_svg(obj,
angle1 = -DraftVecUtils.angle(u1)
angle2 = -DraftVecUtils.angle(u2)
- svg += get_arrow(obj,
- vobj.ArrowTypeStart,
- p2,
- arrowsizestart,
- stroke,
- linewidth,
- angle1)
- svg += get_arrow(obj,
- vobj.ArrowTypeEnd,
- p3,
- arrowsizeend,
- stroke,
- linewidth,
- angle2)
+ svg += get_arrow(
+ obj, vobj.ArrowTypeStart, p2, arrowsizestart, stroke, linewidth, angle1
+ )
+ svg += get_arrow(
+ obj, vobj.ArrowTypeEnd, p3, arrowsizeend, stroke, linewidth, angle2
+ )
# drawing text
if vobj.DisplayMode == "World":
- _diff = (prx.circle.LastParameter
- - prx.circle.FirstParameter)
- t = prx.circle.tangentAt(prx.circle.FirstParameter
- + _diff/2.0)
+ _diff = prx.circle.LastParameter - prx.circle.FirstParameter
+ t = prx.circle.tangentAt(prx.circle.FirstParameter + _diff / 2.0)
t = get_proj(t, plane)
tangle = -DraftVecUtils.angle(t)
- if (tangle <= -math.pi/2) or (tangle > math.pi/2):
+ if (tangle <= -math.pi / 2) or (tangle > math.pi / 2):
tangle = tangle + math.pi
- _diff = (prx.circle.LastParameter
- - prx.circle.FirstParameter)
- _va = prx.circle.valueAt(prx.circle.FirstParameter
- + _diff/2.0)
+ _diff = prx.circle.LastParameter - prx.circle.FirstParameter
+ _va = prx.circle.valueAt(prx.circle.FirstParameter + _diff / 2.0)
tbase = get_proj(_va, plane)
- _v = App.Vector(0, 2.0/scale, 0)
+ _v = App.Vector(0, 2.0 / scale, 0)
tbase = tbase + DraftVecUtils.rotate(_v, tangle)
# print(tbase)
else:
tangle = 0
tbase = get_proj(prx.tbase, plane)
- svg += svgtext.get_text(plane, techdraw,
- tstroke, fontsize,
- vobj.FontName,
- tangle, tbase, prx.string)
+ svg += svgtext.get_text(
+ plane, techdraw, tstroke, fontsize, vobj.FontName, tangle, tbase, prx.string
+ )
elif utils.get_type(obj) == "Label":
@@ -699,48 +751,59 @@ def get_svg(obj,
# Some Labels may have no Line property
# Draw multisegment line
proj_points = list(map(lambda x: get_proj(x, plane), obj.Points))
- path_dir_list = [format_point(proj_points[0], action='M')]
+ path_dir_list = [format_point(proj_points[0], action="M")]
path_dir_list += map(format_point, proj_points[1:])
path_dir_str = " ".join(path_dir_list)
- svg_path = ''
+ svg_path += "/>"
svg += svg_path
# Draw arrow.
# We are different here from 3D view
# if Line is set to 'off', no arrow is drawn
- if hasattr(vobj, "ArrowTypeStart") \
- and (hasattr(vobj, "ArrowSizeStart") \
- and len(obj.Points) > 1):
+ if hasattr(vobj, "ArrowTypeStart") and (
+ hasattr(vobj, "ArrowSizeStart") and len(obj.Points) > 1
+ ):
last_segment = App.Vector(obj.Points[-1] - obj.Points[-2])
_v = get_proj(last_segment, plane)
angle = -DraftVecUtils.angle(_v) + math.pi
- svg += get_arrow(obj,
- vobj.ArrowTypeStart,
- proj_points[-1],
- vobj.ArrowSizeStart.Value/pointratio,
- stroke,
- linewidth,
- angle)
+ svg += get_arrow(
+ obj,
+ vobj.ArrowTypeStart,
+ proj_points[-1],
+ vobj.ArrowSizeStart.Value / pointratio,
+ stroke,
+ linewidth,
+ angle,
+ )
fontname = vobj.FontName
position = get_proj(obj.Placement.Base, plane)
rotation = obj.Placement.Rotation
justification = vobj.Justification
text = obj.Text
- svg += svgtext.get_text(plane, techdraw,
- tstroke, fontsize, fontname,
- rotation, position, text,
- linespacing, justification)
+ svg += svgtext.get_text(
+ plane,
+ techdraw,
+ tstroke,
+ fontsize,
+ fontname,
+ rotation,
+ position,
+ text,
+ linespacing,
+ justification,
+ )
- elif (utils.get_type(obj) in ["Annotation", "DraftText", "Text"]
- or (utils.get_type(obj) == "IfcAnnotation" and obj.ObjectType == "TEXT")):
+ elif utils.get_type(obj) in ["Annotation", "DraftText", "Text"] or (
+ utils.get_type(obj) == "IfcAnnotation" and obj.ObjectType == "TEXT"
+ ):
# returns an svg representation of a document annotation
if not App.GuiUp:
_wrn("Export of texts to SVG is only available in GUI mode")
@@ -757,10 +820,7 @@ def get_svg(obj,
t = obj.Text
j = vobj.Justification
- svg += svgtext.get_text(plane, techdraw,
- tstroke, fontsize, n,
- r, p, t,
- linespacing, j)
+ svg += svgtext.get_text(plane, techdraw, tstroke, fontsize, n, r, p, t, linespacing, j)
elif utils.get_type(obj) == "Axis":
# returns the SVG representation of an Arch Axis system
@@ -769,45 +829,61 @@ def get_svg(obj,
if App.GuiUp:
fn = vobj.FontName
- fill = 'none'
- rad = vobj.BubbleSize.Value/2
+ fill = "none"
+ rad = vobj.BubbleSize.Value / 2
n = 0
for e in obj.Shape.Edges:
- svg += get_path(obj, plane,
- fill, pathdata, stroke, linewidth, lstyle,
- fill_opacity=None,
- edges=[e])
+ svg += get_path(
+ obj,
+ plane,
+ fill,
+ pathdata,
+ stroke,
+ linewidth,
+ lstyle,
+ fill_opacity=None,
+ edges=[e],
+ )
for t in vobj.Proxy.getTextData():
- pos = t[1].add(App.Vector(0,-fontsize/2,0))
- svg += svgtext.get_text(plane, techdraw,
- tstroke, fontsize, fn,
- 0.0, pos, t[0],
- 1.0, "center")
+ pos = t[1].add(App.Vector(0, -fontsize / 2, 0))
+ svg += svgtext.get_text(
+ plane, techdraw, tstroke, fontsize, fn, 0.0, pos, t[0], 1.0, "center"
+ )
for b in vobj.Proxy.getShapeData():
- if hasattr(b,"Curve") and isinstance(b.Curve,Part.Circle):
- svg += get_circle(plane,
- fill, stroke, linewidth, "none",
- b)
+ if hasattr(b, "Curve") and isinstance(b.Curve, Part.Circle):
+ svg += get_circle(plane, fill, stroke, linewidth, "none", b)
else:
sfill = stroke
- svg += get_path(obj, plane,
- sfill, pathdata, stroke, linewidth, "none",
- fill_opacity=None,
- edges=b.Edges)
+ svg += get_path(
+ obj,
+ plane,
+ sfill,
+ pathdata,
+ stroke,
+ linewidth,
+ "none",
+ fill_opacity=None,
+ edges=b.Edges,
+ )
elif utils.get_type(obj) == "Pipe":
fill = stroke
if obj.Base and obj.Diameter:
- svg += get_path(obj, plane,
- fill, pathdata, stroke, linewidth, lstyle,
- fill_opacity=None,
- edges=obj.Base.Shape.Edges)
+ svg += get_path(
+ obj,
+ plane,
+ fill,
+ pathdata,
+ stroke,
+ linewidth,
+ lstyle,
+ fill_opacity=None,
+ edges=obj.Base.Shape.Edges,
+ )
for f in obj.Shape.Faces:
if len(f.Edges) == 1:
if isinstance(f.Edges[0].Curve, Part.Circle):
- svg += get_circle(plane,
- fill, stroke, linewidth, lstyle,
- f.Edges[0])
+ svg += get_circle(plane, fill, stroke, linewidth, lstyle, f.Edges[0])
elif utils.get_type(obj) == "Rebar":
fill = "none"
@@ -822,10 +898,9 @@ def get_svg(obj,
wire = basewire.copy()
wire.Placement = placement.multiply(basewire.Placement)
wires.append(wire)
- svg += get_path(obj, plane,
- fill, pathdata, stroke, linewidth, lstyle,
- fill_opacity=None,
- wires=wires)
+ svg += get_path(
+ obj, plane, fill, pathdata, stroke, linewidth, lstyle, fill_opacity=None, wires=wires
+ )
elif utils.get_type(obj) == "PipeConnector":
pass
@@ -843,16 +918,22 @@ def get_svg(obj,
obj.Proxy.getArea(obj, notouch=True)
if hasattr(obj.Proxy, "face"):
# setting fill
- if App.GuiUp and hasattr(vobj,"ShapeColor"):
- fill = utils.get_rgb(vobj.ShapeColor,
- testbw=False)
+ if App.GuiUp and hasattr(vobj, "ShapeColor"):
+ fill = utils.get_rgb(vobj.ShapeColor, testbw=False)
fill_opacity = 1 - vobj.Transparency / 100.0
else:
fill = "#888888"
- svg += get_path(obj, plane,
- fill, pathdata, stroke, linewidth,
- lstyle, fill_opacity=fill_opacity,
- wires=[obj.Proxy.face.OuterWire])
+ svg += get_path(
+ obj,
+ plane,
+ fill,
+ pathdata,
+ stroke,
+ linewidth,
+ lstyle,
+ fill_opacity=fill_opacity,
+ wires=[obj.Proxy.face.OuterWire],
+ )
c = utils.get_rgb(vobj.TextColor)
n = vobj.FontName
a = 0
@@ -861,10 +942,10 @@ def get_svg(obj,
t1 = vobj.Proxy.text1.string.getValues()
t2 = vobj.Proxy.text2.string.getValues()
- scale = vobj.FirstLine.Value/vobj.FontSize.Value
+ scale = vobj.FirstLine.Value / vobj.FontSize.Value
f1 = fontsize * scale
- if round(plane.axis.getAngle(App.Vector(0,0,1)),2) not in [0,3.14]:
+ if round(plane.axis.getAngle(App.Vector(0, 0, 1)), 2) not in [0, 3.14]:
# if not in XY view, place the label at center
p2 = obj.Shape.CenterOfMass
else:
@@ -875,23 +956,31 @@ def get_svg(obj,
lspc = App.Vector(_h)
p1 = p2 + lspc
j = vobj.TextAlign
- t3 = svgtext.get_text(plane, techdraw,
- c, f1, n,
- a, get_proj(p1, plane), t1,
- linespacing, j, flip=True)
+ t3 = svgtext.get_text(
+ plane, techdraw, c, f1, n, a, get_proj(p1, plane), t1, linespacing, j, flip=True
+ )
svg += t3
if t2:
ofs = App.Vector(0, -lspc.Length, 0)
if a:
Z = App.Vector(0, 0, 1)
ofs = App.Rotation(Z, -rotation).multVec(ofs)
- t4 = svgtext.get_text(plane, techdraw,
- c, fontsize, n,
- a, get_proj(p1, plane).add(ofs), t2,
- linespacing, j, flip=True)
+ t4 = svgtext.get_text(
+ plane,
+ techdraw,
+ c,
+ fontsize,
+ n,
+ a,
+ get_proj(p1, plane).add(ofs),
+ t2,
+ linespacing,
+ j,
+ flip=True,
+ )
svg += t4
- elif hasattr(obj, 'Shape'):
+ elif hasattr(obj, "Shape"):
# In the past we tested for a Part Feature
# elif obj.isDerivedFrom('Part::Feature'):
#
@@ -899,7 +988,7 @@ def get_svg(obj,
# test for a 'Shape'. All Part::Features should have a Shape,
# and App::Links can have one as well.
if obj.Shape.isNull():
- return ''
+ return ""
fill_opacity = 1
# setting fill
@@ -911,21 +1000,20 @@ def get_svg(obj,
m = None
if m != "Wireframe":
- if (fillstyle == "shape color") and hasattr(vobj,"ShapeColor"):
- fill = utils.get_rgb(vobj.ShapeColor,
- testbw=False)
+ if (fillstyle == "shape color") and hasattr(vobj, "ShapeColor"):
+ fill = utils.get_rgb(vobj.ShapeColor, testbw=False)
fill_opacity = 1 - vobj.Transparency / 100.0
- elif fillstyle in ("none",None):
+ elif fillstyle in ("none", None):
fill = "none"
else:
- fill = 'url(#'+fillstyle+')'
+ fill = "url(#" + fillstyle + ")"
svg += get_pattern(fillstyle)
else:
fill = "none"
else:
fill = "#888888"
else:
- fill = 'none'
+ fill = "none"
if len(obj.Shape.Vertexes) > 1:
wiredEdges = []
@@ -934,81 +1022,115 @@ def get_svg(obj,
# place outer wire first
wires = [f.OuterWire]
wires.extend([w for w in f.Wires if w.hashCode() != f.OuterWire.hashCode()])
- svg += get_path(obj, plane,
- fill, pathdata, stroke, linewidth, lstyle,
- fill_opacity=fill_opacity,
- wires=f.Wires,
- pathname='%s_f%04d' % (obj.Name, i))
+ svg += get_path(
+ obj,
+ plane,
+ fill,
+ pathdata,
+ stroke,
+ linewidth,
+ lstyle,
+ fill_opacity=fill_opacity,
+ wires=f.Wires,
+ pathname="%s_f%04d" % (obj.Name, i),
+ )
wiredEdges.extend(f.Edges)
else:
for i, w in enumerate(obj.Shape.Wires):
- svg += get_path(obj, plane,
- fill, pathdata, stroke, linewidth, lstyle,
- fill_opacity=fill_opacity,
- edges=w.Edges,
- pathname='%s_w%04d' % (obj.Name, i))
+ svg += get_path(
+ obj,
+ plane,
+ fill,
+ pathdata,
+ stroke,
+ linewidth,
+ lstyle,
+ fill_opacity=fill_opacity,
+ edges=w.Edges,
+ pathname="%s_w%04d" % (obj.Name, i),
+ )
wiredEdges.extend(w.Edges)
if len(wiredEdges) != len(obj.Shape.Edges):
- fill = 'none' # Required if obj has a face. Edges processed here have no face.
+ fill = "none" # Required if obj has a face. Edges processed here have no face.
for i, e in enumerate(obj.Shape.Edges):
if DraftGeomUtils.findEdge(e, wiredEdges) is None:
- svg += get_path(obj, plane,
- fill, pathdata, stroke, linewidth,
- lstyle, fill_opacity=fill_opacity,
- edges=[e],
- pathname='%s_nwe%04d' % (obj.Name, i))
+ svg += get_path(
+ obj,
+ plane,
+ fill,
+ pathdata,
+ stroke,
+ linewidth,
+ lstyle,
+ fill_opacity=fill_opacity,
+ edges=[e],
+ pathname="%s_nwe%04d" % (obj.Name, i),
+ )
else:
# closed circle or spline
if obj.Shape.Edges:
if isinstance(obj.Shape.Edges[0].Curve, Part.Circle):
- svg = get_circle(plane,
- fill, stroke, linewidth, lstyle,
- obj.Shape.Edges[0])
+ svg = get_circle(plane, fill, stroke, linewidth, lstyle, obj.Shape.Edges[0])
else:
- svg = get_path(obj, plane,
- fill, pathdata, stroke, linewidth, lstyle,
- fill_opacity=fill_opacity,
- edges=obj.Shape.Edges)
+ svg = get_path(
+ obj,
+ plane,
+ fill,
+ pathdata,
+ stroke,
+ linewidth,
+ lstyle,
+ fill_opacity=fill_opacity,
+ edges=obj.Shape.Edges,
+ )
- if App.GuiUp \
- and hasattr(vobj, "ArrowTypeStart") \
- and hasattr(vobj, "ArrowTypeEnd") \
- and hasattr(vobj, "ArrowSizeStart") \
- and hasattr(vobj, "ArrowSizeEnd") \
- and len(obj.Shape.Vertexes) > 1:
+ if (
+ App.GuiUp
+ and hasattr(vobj, "ArrowTypeStart")
+ and hasattr(vobj, "ArrowTypeEnd")
+ and hasattr(vobj, "ArrowSizeStart")
+ and hasattr(vobj, "ArrowSizeEnd")
+ and len(obj.Shape.Vertexes) > 1
+ ):
# Draft_Wire
p1 = get_proj(obj.Shape.Vertexes[0].Point, plane)
p2 = get_proj(obj.Shape.Vertexes[1].Point, plane)
- svg += get_arrow(obj,
- vobj.ArrowTypeStart,
- p1,
- vobj.ArrowSizeStart.Value/pointratio,
- stroke,
- linewidth,
- -DraftVecUtils.angle(p2 - p1))
+ svg += get_arrow(
+ obj,
+ vobj.ArrowTypeStart,
+ p1,
+ vobj.ArrowSizeStart.Value / pointratio,
+ stroke,
+ linewidth,
+ -DraftVecUtils.angle(p2 - p1),
+ )
p1 = get_proj(obj.Shape.Vertexes[-1].Point, plane)
p2 = get_proj(obj.Shape.Vertexes[-2].Point, plane)
- svg += get_arrow(obj,
- vobj.ArrowTypeEnd,
- p1,
- vobj.ArrowSizeEnd.Value/pointratio,
- stroke,
- linewidth,
- -DraftVecUtils.angle(p2 - p1))
+ svg += get_arrow(
+ obj,
+ vobj.ArrowTypeEnd,
+ p1,
+ vobj.ArrowSizeEnd.Value / pointratio,
+ stroke,
+ linewidth,
+ -DraftVecUtils.angle(p2 - p1),
+ )
# techdraw expects bottom-to-top coordinates
if techdraw:
- svg = '\n ' + svg + '\n'
+ svg = '\n ' + svg + "\n"
return svg
def _get_view_object(obj):
- if obj.isDerivedFrom("App::Link") \
- and hasattr(obj, "ViewObject") \
- and hasattr(obj.ViewObject, "OverrideMaterial") \
- and not obj.ViewObject.OverrideMaterial \
- and hasattr(obj.LinkedObject, "ViewObject"):
+ if (
+ obj.isDerivedFrom("App::Link")
+ and hasattr(obj, "ViewObject")
+ and hasattr(obj.ViewObject, "OverrideMaterial")
+ and not obj.ViewObject.OverrideMaterial
+ and hasattr(obj.LinkedObject, "ViewObject")
+ ):
return obj.LinkedObject.ViewObject
if hasattr(obj, "ViewObject"):
return obj.ViewObject
@@ -1026,21 +1148,38 @@ def get_print_color(obj):
return None
-def getSVG(obj,
- scale=1, linewidth=0.35, fontsize=12,
- fillstyle="shape color", direction=None,
- linestyle=None,
- color=None, linespacing=None,
- techdraw=False, rotation=0,
- fillSpaces=False, override=True):
+def getSVG(
+ obj,
+ scale=1,
+ linewidth=0.35,
+ fontsize=12,
+ fillstyle="shape color",
+ direction=None,
+ linestyle=None,
+ color=None,
+ linespacing=None,
+ techdraw=False,
+ rotation=0,
+ fillSpaces=False,
+ override=True,
+):
"""Return SVG string of the object. DEPRECATED. Use 'get_svg'."""
utils.use_instead("get_svg")
- return get_svg(obj,
- scale=scale, linewidth=linewidth, fontsize=fontsize,
- fillstyle=fillstyle, direction=direction,
- linestyle=linestyle,
- color=color, linespacing=linespacing,
- techdraw=techdraw, rotation=rotation,
- fillspaces=fillSpaces, override=override)
+ return get_svg(
+ obj,
+ scale=scale,
+ linewidth=linewidth,
+ fontsize=fontsize,
+ fillstyle=fillstyle,
+ direction=direction,
+ linestyle=linestyle,
+ color=color,
+ linespacing=linespacing,
+ techdraw=techdraw,
+ rotation=rotation,
+ fillspaces=fillSpaces,
+ override=override,
+ )
+
## @}
diff --git a/src/Mod/Draft/draftfunctions/svgshapes.py b/src/Mod/Draft/draftfunctions/svgshapes.py
index efe62186ef..d588f23c0c 100644
--- a/src/Mod/Draft/draftfunctions/svgshapes.py
+++ b/src/Mod/Draft/draftfunctions/svgshapes.py
@@ -21,8 +21,7 @@
# * USA *
# * *
# ***************************************************************************
-"""Provides functions to return the SVG representation of some shapes.
-"""
+"""Provides functions to return the SVG representation of some shapes."""
## @package svgshapes
# \ingroup draftfunctions
# \brief Provides functions to return the SVG representation of some shapes.
@@ -95,21 +94,21 @@ def get_discretized(edge, plane):
if pieces == 0:
pieces = 10
- d = int(edge.Length/pieces)
+ d = int(edge.Length / pieces)
if d == 0:
d = 1
edata = ""
for i in range(d + 1):
_length = edge.LastParameter - edge.FirstParameter
- _point = edge.FirstParameter + float(i)/d * _length
+ _point = edge.FirstParameter + float(i) / d * _length
_vec = edge.valueAt(_point)
v = get_proj(_vec, plane)
if not edata:
- edata += 'M ' + str(v.x) + ' ' + str(v.y) + ' '
+ edata += "M " + str(v.x) + " " + str(v.y) + " "
else:
- edata += 'L ' + str(v.x) + ' ' + str(v.y) + ' '
+ edata += "L " + str(v.x) + " " + str(v.y) + " "
return edata
@@ -120,9 +119,9 @@ def getDiscretized(edge, plane):
return get_discretized(edge, plane)
-def _get_path_circ_ellipse(plane, edge, verts, edata,
- iscircle, isellipse,
- fill, stroke, linewidth, lstyle):
+def _get_path_circ_ellipse(
+ plane, edge, verts, edata, iscircle, isellipse, fill, stroke, linewidth, lstyle
+):
"""Get the edge data from a path that is a circle or ellipse."""
if plane:
drawing_plane_normal = plane.axis
@@ -166,9 +165,7 @@ def _get_path_circ_ellipse(plane, edge, verts, edata,
if not done:
if len(edge.Vertexes) == 1 and iscircle:
# Complete circle not only arc
- svg = get_circle(plane,
- fill, stroke, linewidth, lstyle,
- edge)
+ svg = get_circle(plane, fill, stroke, linewidth, lstyle, edge)
# If it's a circle we will return the final SVG string,
# otherwise it will process the `edata` further
return "svg", svg
@@ -180,9 +177,8 @@ def _get_path_circ_ellipse(plane, edge, verts, edata,
# return svg
# Difference in angles
- _diff = (center.LastParameter - center.FirstParameter)/2.0
- endpoints = [get_proj(center.value(_diff), plane),
- get_proj(verts[-1].Point, plane)]
+ _diff = (center.LastParameter - center.FirstParameter) / 2.0
+ endpoints = [get_proj(center.value(_diff), plane), get_proj(verts[-1].Point, plane)]
else:
endpoints = [get_proj(verts[-1].Point, plane)]
@@ -213,16 +209,15 @@ def _get_path_circ_ellipse(plane, edge, verts, edata,
# between tangents
_diff = edge.LastParameter - edge.FirstParameter
t1 = edge.tangentAt(edge.FirstParameter)
- t2 = edge.tangentAt(edge.FirstParameter + _diff/10)
+ t2 = edge.tangentAt(edge.FirstParameter + _diff / 10)
flag_sweep = DraftVecUtils.angle(t1, t2, drawing_plane_normal) < 0
for v in endpoints:
- edata += ('A {} {} {} '
- '{} {} '
- '{} {} '.format(rx, ry, rot,
- int(flag_large_arc),
- int(flag_sweep),
- v.x, v.y))
+ edata += (
+ "A {} {} {} "
+ "{} {} "
+ "{} {} ".format(rx, ry, rot, int(flag_large_arc), int(flag_sweep), v.x, v.y)
+ )
return "edata", edata
@@ -232,7 +227,7 @@ def _get_path_bspline(plane, edge, edata):
bspline = edge.Curve.toBSpline(edge.FirstParameter, edge.LastParameter)
if bspline.Degree > 3 or bspline.isRational():
try:
- bspline = bspline.approximateBSpline(0.05, 50, 3, 'C0')
+ bspline = bspline.approximateBSpline(0.05, 50, 3, "C0")
except RuntimeError:
_wrn("Debug: unable to approximate bspline from edge")
@@ -242,30 +237,30 @@ def _get_path_bspline(plane, edge, edata):
_wrn("Bezier segment of degree > 3")
raise AssertionError
elif bezierseg.Degree == 1:
- edata += 'L '
+ edata += "L "
elif bezierseg.Degree == 2:
- edata += 'Q '
+ edata += "Q "
elif bezierseg.Degree == 3:
- edata += 'C '
+ edata += "C "
for pole in bezierseg.getPoles()[1:]:
v = get_proj(pole, plane)
- edata += '{} {} '.format(v.x, v.y)
+ edata += "{} {} ".format(v.x, v.y)
else:
- _msg("Debug: one edge (hash {}) "
- "has been discretized "
- "with parameter 0.1".format(edge.hashCode()))
+ _msg(
+ "Debug: one edge (hash {}) "
+ "has been discretized "
+ "with parameter 0.1".format(edge.hashCode())
+ )
for linepoint in bspline.discretize(0.1)[1:]:
v = get_proj(linepoint, plane)
- edata += 'L {} {} '.format(v.x, v.y)
+ edata += "L {} {} ".format(v.x, v.y)
return edata
-def get_circle(plane,
- fill, stroke, linewidth, lstyle,
- edge):
+def get_circle(plane, fill, stroke, linewidth, lstyle, edge):
"""Get the SVG representation from a circular edge."""
cen = get_proj(edge.Curve.Center, plane)
rad = edge.Curve.Radius
@@ -277,7 +272,7 @@ def get_circle(plane,
if round(edge.Curve.Axis.getAngle(drawing_plane_normal), 2) in [0, 3.14]:
# Perpendicular projection: circle
- svg = '\n'
+ svg += "stroke-width:{};".format(linewidth)
+ svg += "stroke-miterlimit:4;"
+ svg += "stroke-dasharray:{};".format(lstyle)
+ svg += "stroke-linecap:square;"
+ svg += "fill:{}".format(fill) + '"'
+ svg += "/>\n"
return svg
-def getCircle(plane,
- fill, stroke, linewidth, lstyle,
- edge):
+def getCircle(plane, fill, stroke, linewidth, lstyle, edge):
"""Get the SVG representation from a circular edge."""
utils.use_instead("get_circle")
return get_circle(plane, fill, stroke, linewidth, lstyle, edge)
-def get_ellipse(plane,
- fill, stroke, linewidth, lstyle,
- edge):
+def get_ellipse(plane, fill, stroke, linewidth, lstyle, edge):
"""Get the SVG representation from an elliptical edge."""
cen = get_proj(edge.Curve.Center, plane)
mir = edge.Curve.MinorRadius
mar = edge.Curve.MajorRadius
- svg = '\n'
+ svg += "stroke-width:{};".format(linewidth)
+ svg += "stroke-miterlimit:4;"
+ svg += "stroke-dasharray:{};".format(lstyle)
+ svg += "stroke-linecap:square;"
+ svg += "fill:{}".format(fill) + '"'
+ svg += "/>\n"
return svg
-def getEllipse(plane,
- fill, stroke, linewidth, lstyle,
- edge):
+def getEllipse(plane, fill, stroke, linewidth, lstyle, edge):
"""Get the SVG representation from an elliptical edge. DEPRECATED."""
utils.use_instead("get_ellipse")
return get_ellipse(plane, fill, stroke, linewidth, lstyle, edge)
-def get_path(obj, plane,
- fill, pathdata, stroke, linewidth, lstyle,
- fill_opacity=None,
- edges=[], wires=[], pathname=None):
+def get_path(
+ obj,
+ plane,
+ fill,
+ pathdata,
+ stroke,
+ linewidth,
+ lstyle,
+ fill_opacity=None,
+ edges=[],
+ wires=[],
+ pathname=None,
+):
"""Get the SVG representation from an object's edges or wires.
TODO: the `edges` and `wires` must not default to empty list `[]`
@@ -382,28 +380,27 @@ def get_path(obj, plane,
if len(_edges) > 1:
last_pt = verts[-1].Point
nextverts = _edges[1].Vertexes
- if (last_pt - nextverts[0].Point).Length > 1e-6 \
- and (last_pt - nextverts[-1].Point).Length > 1e-6:
+ if (last_pt - nextverts[0].Point).Length > 1e-6 and (
+ last_pt - nextverts[-1].Point
+ ).Length > 1e-6:
verts.reverse()
v = get_proj(verts[0].Point, plane)
- edata += 'M {} {} '.format(v.x, v.y)
+ edata += "M {} {} ".format(v.x, v.y)
else:
previousverts = verts
verts = edge.Vertexes
if (verts[0].Point - previousverts[-1].Point).Length > 1e-6:
verts.reverse()
if (verts[0].Point - previousverts[-1].Point).Length > 1e-6:
- raise ValueError('edges not ordered')
+ raise ValueError("edges not ordered")
iscircle = DraftGeomUtils.geomType(edge) == "Circle"
isellipse = DraftGeomUtils.geomType(edge) == "Ellipse"
if iscircle or isellipse:
- _type, data = _get_path_circ_ellipse(plane, edge, verts,
- edata,
- iscircle, isellipse,
- fill, stroke,
- linewidth, lstyle)
+ _type, data = _get_path_circ_ellipse(
+ plane, edge, verts, edata, iscircle, isellipse, fill, stroke, linewidth, lstyle
+ )
if _type == "svg":
# final svg string already calculated, so just return it
return data
@@ -412,14 +409,14 @@ def get_path(obj, plane,
edata = data
elif DraftGeomUtils.geomType(edge) == "Line":
v = get_proj(verts[-1].Point, plane)
- edata += 'L {} {} '.format(v.x, v.y)
+ edata += "L {} {} ".format(v.x, v.y)
else:
# If it's not a circle nor ellipse nor straight line
# convert the curve to BSpline
edata = _get_path_bspline(plane, edge, edata)
- if fill != 'none':
- edata += 'Z '
+ if fill != "none":
+ edata += "Z "
if edata in pathdata:
# do not draw a path on another identical path
@@ -432,29 +429,48 @@ def get_path(obj, plane,
svg += 'stroke="{}" '.format(stroke)
svg += 'stroke-width="{} px" '.format(linewidth)
svg += 'style="'
- svg += 'stroke-width:{};'.format(linewidth)
- svg += 'stroke-miterlimit:4;'
- svg += 'stroke-dasharray:{};'.format(lstyle)
- svg += 'stroke-linecap:square;'
- svg += 'fill:{};'.format(fill)
+ svg += "stroke-width:{};".format(linewidth)
+ svg += "stroke-miterlimit:4;"
+ svg += "stroke-dasharray:{};".format(lstyle)
+ svg += "stroke-linecap:square;"
+ svg += "fill:{};".format(fill)
# fill_opacity must be a number, but if it's `None` it is omitted
if fill_opacity is not None:
- svg += 'fill-opacity:{};'.format(fill_opacity)
+ svg += "fill-opacity:{};".format(fill_opacity)
svg += 'fill-rule: evenodd"'
- svg += '/>\n'
+ svg += "/>\n"
return svg
-def getPath(obj, plane,
- fill, pathdata, stroke, linewidth, lstyle,
- fill_opacity,
- edges=[], wires=[], pathname=None):
+def getPath(
+ obj,
+ plane,
+ fill,
+ pathdata,
+ stroke,
+ linewidth,
+ lstyle,
+ fill_opacity,
+ edges=[],
+ wires=[],
+ pathname=None,
+):
"""Get the SVG representation from a path. DEPRECATED."""
utils.use_instead("get_path")
- return get_path(obj, plane,
- fill, pathdata, stroke, linewidth, lstyle,
- fill_opacity,
- edges=edges, wires=wires, pathname=pathname)
+ return get_path(
+ obj,
+ plane,
+ fill,
+ pathdata,
+ stroke,
+ linewidth,
+ lstyle,
+ fill_opacity,
+ edges=edges,
+ wires=wires,
+ pathname=pathname,
+ )
+
## @}
diff --git a/src/Mod/Draft/draftfunctions/svgtext.py b/src/Mod/Draft/draftfunctions/svgtext.py
index dfb8b537dc..e2e3ae0c9e 100644
--- a/src/Mod/Draft/draftfunctions/svgtext.py
+++ b/src/Mod/Draft/draftfunctions/svgtext.py
@@ -36,9 +36,7 @@ import draftutils.utils as utils
# @{
-def _get_text_techdraw(text, tcolor, fontsize, anchor,
- align, fontname, angle, base,
- linespacing):
+def _get_text_techdraw(text, tcolor, fontsize, anchor, align, fontname, angle, base, linespacing):
"""Return the SVG representation of text for TechDraw display.
`text` is a list of textual elements; they are iterated, styled,
@@ -56,28 +54,23 @@ def _get_text_techdraw(text, tcolor, fontsize, anchor,
_t = _t.replace("<", "<")
t = _t.replace(">", ">")
- svg += '\n'
+ svg += ">\n"
svg += t
- svg += '\n'
+ svg += "\n"
return svg
-def _get_text_header(tcolor, fontsize, anchor, align,
- fontname, angle, base, flip):
+def _get_text_header(tcolor, fontsize, anchor, align, fontname, angle, base, flip):
"""Return the initial tag with style options.
The text must be added after this tag, and then must be closed.
@@ -86,37 +79,43 @@ def _get_text_header(tcolor, fontsize, anchor, align,
...
"""
- svg = '\n'
+ svg += ">\n"
return svg
-def get_text(plane, techdraw,
- tcolor, fontsize, fontname,
- angle, base, text,
- linespacing=0.5, align="center", flip=True):
+def get_text(
+ plane,
+ techdraw,
+ tcolor,
+ fontsize,
+ fontname,
+ angle,
+ base,
+ text,
+ linespacing=0.5,
+ align="center",
+ flip=True,
+):
"""Get the SVG representation of a textual element."""
if isinstance(angle, App.Rotation):
if not plane:
@@ -129,14 +128,14 @@ def get_text(plane, techdraw,
angle = -angle.Angle
else:
angle = angle.Angle
- elif abs(plane.axis.getAngle(angle.Axis) - math.pi/2) < 0.001:
+ elif abs(plane.axis.getAngle(angle.Axis) - math.pi / 2) < 0.001:
# text is perpendicular to view, so it shouldn't appear
return ""
else:
# Compute an X vector
- vec = App.Vector(1,0,0)
- vec = angle.multVec(App.Vector(1,0,0))
- angle = DraftVecUtils.angle(vec,plane.u)
+ vec = App.Vector(1, 0, 0)
+ vec = angle.multVec(App.Vector(1, 0, 0))
+ angle = DraftVecUtils.angle(vec, plane.u)
# text should be a list of strings separated by a newline
if not isinstance(text, list):
@@ -154,9 +153,9 @@ def get_text(plane, techdraw,
# in an individual tag.
# text[0]
# text[1]
- svg = _get_text_techdraw(text, tcolor, fontsize, anchor,
- align, fontname, angle, base,
- linespacing)
+ svg = _get_text_techdraw(
+ text, tcolor, fontsize, anchor, align, fontname, angle, base, linespacing
+ )
else:
# If the SVG is not for TechDraw, and there is a single item
# in the text list, place it in a single tag.
@@ -167,8 +166,7 @@ def get_text(plane, techdraw,
# text[0]
# text[1]
#
- svg = _get_text_header(tcolor, fontsize, anchor, align,
- fontname, angle, base, flip)
+ svg = _get_text_header(tcolor, fontsize, anchor, align, fontname, angle, base, flip)
if len(text) == 1:
_t = text[0].replace("&", "&").replace("<", "<")
@@ -176,25 +174,34 @@ def get_text(plane, techdraw,
else:
for i in range(len(text)):
if i == 0:
- svg += ''
+ svg += ""
else:
svg += ''.format(linespacing)
_t = text[i].replace("&", "&").replace("<", "<")
svg += _t.replace(">", ">")
- svg += '\n'
- svg += '\n'
+ svg += "\n"
+ svg += "\n"
return svg
-def getText(plane, techdraw,
- tcolor, fontsize, fontname,
- angle, base, text,
- linespacing=0.5, align="center", flip=True):
+def getText(
+ plane,
+ techdraw,
+ tcolor,
+ fontsize,
+ fontname,
+ angle,
+ base,
+ text,
+ linespacing=0.5,
+ align="center",
+ flip=True,
+):
"""Get the SVG representation of a textual element. DEPRECATED."""
utils.use_instead("get_text")
- return get_text(plane, techdraw,
- tcolor, fontsize, fontname,
- angle, base, text,
- linespacing, align, flip)
+ return get_text(
+ plane, techdraw, tcolor, fontsize, fontname, angle, base, text, linespacing, align, flip
+ )
+
## @}
diff --git a/src/Mod/Draft/draftfunctions/upgrade.py b/src/Mod/Draft/draftfunctions/upgrade.py
index 79cc7449ff..06196eaa02 100644
--- a/src/Mod/Draft/draftfunctions/upgrade.py
+++ b/src/Mod/Draft/draftfunctions/upgrade.py
@@ -220,8 +220,9 @@ def upgrade(objects, delete=False, force=None):
new_area = new_face.Area
new_cen = new_face.CenterOfMass
for old_area, old_cen, old_color in old_data:
- if math.isclose(new_area, old_area, abs_tol=1e-7) \
- and new_cen.isEqual(old_cen, 1e-7):
+ if math.isclose(new_area, old_area, abs_tol=1e-7) and new_cen.isEqual(
+ old_cen, 1e-7
+ ):
new_colors.append(old_color)
break
newobj.ViewObject.DiffuseColor = new_colors
@@ -316,8 +317,11 @@ def upgrade(objects, delete=False, force=None):
for cluster in sorted_edges:
for edge in cluster:
print("Curve: {}".format(edge.Curve))
- print("first: {}, last: {}".format(edge.Vertexes[0].Point,
- edge.Vertexes[-1].Point))
+ print(
+ "first: {}, last: {}".format(
+ edge.Vertexes[0].Point, edge.Vertexes[-1].Point
+ )
+ )
wires = [Part.Wire(cluster) for cluster in sorted_edges]
except Part.OCCError:
return False
@@ -349,7 +353,6 @@ def upgrade(objects, delete=False, force=None):
delete_list.append(obj)
return True
-
# helper functions (same as in downgrade.py)
def get_parent(obj):
@@ -413,7 +416,6 @@ def upgrade(objects, delete=False, force=None):
for newobj in new_list:
gui_utils.format_object(newobj, obj, ignore_construction=True)
-
doc = App.ActiveDocument
add_list = []
delete_list = []
@@ -476,17 +478,21 @@ def upgrade(objects, delete=False, force=None):
result = turnToParts(meshes)
else:
# functions that work on a single object:
- single_funcs = {"closeWire": closeWire,
- "draftify": _draftify,
- "makeSketchFace": makeSketchFace,
- "makeSolid": makeSolid}
+ single_funcs = {
+ "closeWire": closeWire,
+ "draftify": _draftify,
+ "makeSketchFace": makeSketchFace,
+ "makeSolid": makeSolid,
+ }
# functions that work on multiple objects:
- multi_funcs = {"joinFaces": joinFaces,
- "makeCompound": makeCompound,
- "makeFaces": makeFaces,
- "makeFusion": makeFusion,
- "makeShell": makeShell,
- "makeWires": makeWires}
+ multi_funcs = {
+ "joinFaces": joinFaces,
+ "makeCompound": makeCompound,
+ "makeFaces": makeFaces,
+ "makeFusion": makeFusion,
+ "makeShell": makeShell,
+ "makeWires": makeWires,
+ }
if force in single_funcs:
result = any([single_funcs[force](obj) for obj in objects])
elif force in multi_funcs:
@@ -536,39 +542,55 @@ def upgrade(objects, delete=False, force=None):
_msg(translate("draft", "Found 1 solidifiable object: solidifying it"))
# we have exactly 2 objects: we fuse them
- elif len(objects) == 2 \
- and not faces_coplanarity \
- and same_parent \
- and same_parent_type != "PartDesign::Body":
+ elif (
+ len(objects) == 2
+ and not faces_coplanarity
+ and same_parent
+ and same_parent_type != "PartDesign::Body"
+ ):
result = makeFusion(objects)
if result:
_msg(translate("draft", "Found 2 objects: fusing them"))
# we have many separate faces: we try to make a shell or compound
- elif len(objects) > 1 \
- and len(faces) > 1 \
- and same_parent \
- and same_parent_type != "PartDesign::Body":
+ elif (
+ len(objects) > 1
+ and len(faces) > 1
+ and same_parent
+ and same_parent_type != "PartDesign::Body"
+ ):
result = makeShell(objects)
if result:
- _msg(translate(
- "draft",
- "Found several objects: creating a " + result.Shape.ShapeType
- ))
+ _msg(
+ translate(
+ "draft", "Found several objects: creating a " + result.Shape.ShapeType
+ )
+ )
# we have faces: we try to join them if they are coplanar
elif len(objects) == 1 and len(faces) > 1 and faces_coplanarity:
result = joinFaces(objects)
if result:
- _msg(translate("draft", "Found object with several coplanar faces: refining them"))
+ _msg(
+ translate(
+ "draft", "Found object with several coplanar faces: refining them"
+ )
+ )
# only one object: if not parametric, we "draftify" it
- elif len(objects) == 1 \
- and not objects[0].isDerivedFrom("Part::Part2DObjectPython") \
- and not utils.get_type(objects[0]) in ["BezCurve", "BSpline", "Wire"]:
+ elif (
+ len(objects) == 1
+ and not objects[0].isDerivedFrom("Part::Part2DObjectPython")
+ and not utils.get_type(objects[0]) in ["BezCurve", "BSpline", "Wire"]
+ ):
result = _draftify(objects[0])
if result:
- _msg(translate("draft", "Found 1 non-parametric object: replacing it with a Draft object"))
+ _msg(
+ translate(
+ "draft",
+ "Found 1 non-parametric object: replacing it with a Draft object",
+ )
+ )
# in the following cases there are no faces
elif not faces:
@@ -579,7 +601,11 @@ def upgrade(objects, delete=False, force=None):
if len(objects) == 1 and objects[0].isDerivedFrom("Sketcher::SketchObject"):
result = makeSketchFace(objects[0])
if result:
- _msg(translate("draft", "Found 1 closed sketch object: creating a face from it"))
+ _msg(
+ translate(
+ "draft", "Found 1 closed sketch object: creating a face from it"
+ )
+ )
# only closed wires
else:
result = makeFaces(objects)
@@ -594,7 +620,11 @@ def upgrade(objects, delete=False, force=None):
else:
result = makeCompound(objects)
if result:
- _msg(translate("draft", "Found several non-treatable objects: creating compound"))
+ _msg(
+ translate(
+ "draft", "Found several non-treatable objects: creating compound"
+ )
+ )
# special case, we have only one open wire. We close it, unless it has only 1 edge!
elif len(objects) == 1 and len(openwires) == 1:
@@ -603,16 +633,23 @@ def upgrade(objects, delete=False, force=None):
_msg(translate("draft", "Found 1 open wire: closing it"))
# only one object: if not parametric, we "draftify" it
- elif len(objects) == 1 \
- and len(edges) == 1 \
- and not objects[0].isDerivedFrom("Part::Part2DObjectPython") \
- and not utils.get_type(objects[0]) in ["BezCurve", "BSpline", "Wire"]:
+ elif (
+ len(objects) == 1
+ and len(edges) == 1
+ and not objects[0].isDerivedFrom("Part::Part2DObjectPython")
+ and not utils.get_type(objects[0]) in ["BezCurve", "BSpline", "Wire"]
+ ):
edge_type = DraftGeomUtils.geomType(objects[0].Shape.Edges[0])
# currently only support Line and Circle
if edge_type in ("Line", "Circle"):
result = _draftify(objects[0])
if result:
- _msg(translate("draft", "Found 1 non-parametric object: replacing it with a Draft object"))
+ _msg(
+ translate(
+ "draft",
+ "Found 1 non-parametric object: replacing it with a Draft object",
+ )
+ )
# only points, no edges
elif not edges and len(objects) > 1:
@@ -637,4 +674,5 @@ def upgrade(objects, delete=False, force=None):
gui_utils.select(add_list)
return add_list, delete_list
+
## @}
diff --git a/src/Mod/Draft/draftgeoutils/arcs.py b/src/Mod/Draft/draftgeoutils/arcs.py
index c27766e767..8963cbefd0 100644
--- a/src/Mod/Draft/draftgeoutils/arcs.py
+++ b/src/Mod/Draft/draftgeoutils/arcs.py
@@ -74,7 +74,7 @@ def isClockwise(edge, ref=None):
# if that axis points "the wrong way" from the reference, we invert it
if not ref:
ref = App.Vector(0, 0, 1)
- if n.getAngle(ref) > math.pi/2:
+ if n.getAngle(ref) > math.pi / 2:
n = n.negative()
if DraftVecUtils.angle(v1, v2, n) < 0:
@@ -92,9 +92,9 @@ def isWideAngle(edge):
return False
r = edge.Curve.Radius
- total = 2*r*math.pi
+ total = 2 * r * math.pi
- if edge.Length > total/2:
+ if edge.Length > total / 2:
return True
return False
@@ -106,7 +106,7 @@ def arcFrom2Pts(firstPt, lastPt, center, axis=None):
radius2 = lastPt.sub(center).Length
# (PREC = 4 = same as Part Module), Is it possible?
- if round(radius1-radius2, 4) != 0:
+ if round(radius1 - radius2, 4) != 0:
return None
thirdPt = App.Vector(firstPt.sub(center).add(lastPt).sub(center))
@@ -141,7 +141,7 @@ def arcFromSpline(edge):
# 2-point arc
p1 = edge.Vertexes[0].Point
p2 = edge.Vertexes[-1].Point
- ml = edge.Length/2
+ ml = edge.Length / 2
p3 = edge.valueAt(ml)
try:
return Part.Arc(p1, p3, p2).toShape()
@@ -162,4 +162,5 @@ def arcFromSpline(edge):
print("couldn't make a circle out of this edge")
return None
+
## @}
diff --git a/src/Mod/Draft/draftgeoutils/circle_inversion.py b/src/Mod/Draft/draftgeoutils/circle_inversion.py
index c48436109a..f413ba758b 100644
--- a/src/Mod/Draft/draftgeoutils/circle_inversion.py
+++ b/src/Mod/Draft/draftgeoutils/circle_inversion.py
@@ -84,9 +84,7 @@ def polarInversion(circle, edge):
print("debug: circleInversionPole bad parameters! Must be a circle.")
return None
- nearest = circle.Curve.Center.add(findDistance(circle.Curve.Center,
- edge,
- False))
+ nearest = circle.Curve.Center.add(findDistance(circle.Curve.Center, edge, False))
if nearest:
inversionPole = pointInversion(circle, nearest)
if inversionPole:
@@ -117,8 +115,7 @@ def circleInversion(circle, circle2):
pointOnCircle2 = App.Vector.add(cen2, App.Vector(rad2, 0, 0))
invPointOnCircle2 = pointInversion(circle, pointOnCircle2)
- return Part.Circle(invCen2,
- NORM,
- DraftVecUtils.dist(invCen2, invPointOnCircle2))
+ return Part.Circle(invCen2, NORM, DraftVecUtils.dist(invCen2, invPointOnCircle2))
+
## @}
diff --git a/src/Mod/Draft/draftgeoutils/circles.py b/src/Mod/Draft/draftgeoutils/circles.py
index d5dac2aaf4..d995ef4fad 100644
--- a/src/Mod/Draft/draftgeoutils/circles.py
+++ b/src/Mod/Draft/draftgeoutils/circles.py
@@ -65,18 +65,18 @@ def getCircleFromSpline(edge):
# get 2 points
p1 = edge.Curve.value(0)
- p2 = edge.Curve.value(math.pi/2)
+ p2 = edge.Curve.value(math.pi / 2)
# get 2 tangents
t1 = edge.Curve.tangent(0)[0]
- t2 = edge.Curve.tangent(math.pi/2)[0]
+ t2 = edge.Curve.tangent(math.pi / 2)[0]
# get normal
n = p1.cross(p2)
if DraftVecUtils.isNull(n):
return None
# get rays
- r1 = DraftVecUtils.rotate(t1, math.pi/2, n)
- r2 = DraftVecUtils.rotate(t2, math.pi/2, n)
+ r1 = DraftVecUtils.rotate(t1, math.pi / 2, n)
+ r2 = DraftVecUtils.rotate(t2, math.pi / 2, n)
# get center (intersection of rays)
i = findIntersection(p1, p1.add(r1), p2, p2.add(r2), True, True)
if not i:
@@ -116,10 +116,8 @@ def circlefrom1Line2Points(edge, p1, p2):
x = DraftVecUtils.crossproduct(vec(p1_p2))
x.normalize()
perp_mid = App.Vector.add(mid, x)
- cen1 = findIntersection(edg(projectedCen1, perpCen1),
- edg(mid, perp_mid), True, True)
- cen2 = findIntersection(edg(projectedCen2, perpCen2),
- edg(mid, perp_mid), True, True)
+ cen1 = findIntersection(edg(projectedCen1, perpCen1), edg(mid, perp_mid), True, True)
+ cen2 = findIntersection(edg(projectedCen2, perpCen2), edg(mid, perp_mid), True, True)
circles = []
if cen1:
@@ -157,8 +155,9 @@ def circleFrom2LinesRadius(edge1, edge2, radius):
intsec = intsec[0]
bis12 = angleBisection(edge1, edge2)
- bis21 = Part.LineSegment(bis12.Vertexes[0].Point,
- DraftVecUtils.rotate(vec(bis12), math.pi/2.0))
+ bis21 = Part.LineSegment(
+ bis12.Vertexes[0].Point, DraftVecUtils.rotate(vec(bis12), math.pi / 2.0)
+ )
ang12 = abs(DraftVecUtils.angle(vec(edge1), vec(edge2)))
ang21 = math.pi - ang12
dist12 = radius / math.sin(ang12 * 0.5)
@@ -185,10 +184,9 @@ def circleFrom3LineTangents(edge1, edge2, edge3):
It calculates up to 6 possible centers.
"""
+
def rot(ed):
- geo = Part.LineSegment(v1(ed),
- v1(ed).add(DraftVecUtils.rotate(vec(ed),
- math.pi/2)))
+ geo = Part.LineSegment(v1(ed), v1(ed).add(DraftVecUtils.rotate(vec(ed), math.pi / 2)))
return geo.toShape()
bis12 = angleBisection(edge1, edge2)
@@ -273,7 +271,7 @@ def circleFromPointLineRadius(point, edge, radius):
else:
normPoint = point.add(findDistance(point, edge, False))
normDist = DraftVecUtils.dist(normPoint, point)
- dist = math.sqrt(radius**2 - (radius - normDist)**2)
+ dist = math.sqrt(radius**2 - (radius - normDist) ** 2)
centerNormVec = DraftVecUtils.scaleTo(point.sub(normPoint), radius)
edgeDir = edge.Vertexes[0].Point.sub(normPoint)
edgeDir.normalize()
@@ -311,7 +309,7 @@ def circleFrom2PointsRadius(p1, p2, radius):
dist_p1p2 = DraftVecUtils.dist(p1, p2)
mid = findMidpoint(p1_p2)
- if dist_p1p2 == 2*radius:
+ if dist_p1p2 == 2 * radius:
circle = Part.Circle(mid, NORM, radius)
if circle:
return [circle]
@@ -322,7 +320,7 @@ def circleFrom2PointsRadius(p1, p2, radius):
_dir.normalize()
perpDir = _dir.cross(App.Vector(0, 0, 1))
perpDir.normalize()
- dist = math.sqrt(radius**2 - (dist_p1p2 / 2.0)**2)
+ dist = math.sqrt(radius**2 - (dist_p1p2 / 2.0) ** 2)
cen1 = App.Vector.add(mid, App.Vector(perpDir).multiply(dist))
cen2 = App.Vector.add(mid, App.Vector(perpDir).multiply(-dist))
@@ -346,16 +344,14 @@ def findHomotheticCenterOfCircles(circle1, circle2):
http://en.wikipedia.org/wiki/Homothetic_center
http://mathworld.wolfram.com/HomotheticCenter.html
"""
- if (geomType(circle1) == "Circle" and geomType(circle2) == "Circle"):
+ if geomType(circle1) == "Circle" and geomType(circle2) == "Circle":
print("debug: findHomotheticCenterOfCircles bad parameters!")
return None
- if DraftVecUtils.equals(circle1.Curve.Center,
- circle2.Curve.Center):
+ if DraftVecUtils.equals(circle1.Curve.Center, circle2.Curve.Center):
return None
- cen1_cen2 = Part.LineSegment(circle1.Curve.Center,
- circle2.Curve.Center).toShape()
+ cen1_cen2 = Part.LineSegment(circle1.Curve.Center, circle2.Curve.Center).toShape()
cenDir = vec(cen1_cen2)
cenDir.normalize()
@@ -364,18 +360,17 @@ def findHomotheticCenterOfCircles(circle1, circle2):
perpCenDir.normalize()
# Get point on first circle
- p1 = App.Vector.add(circle1.Curve.Center,
- App.Vector(perpCenDir).multiply(circle1.Curve.Radius))
+ p1 = App.Vector.add(circle1.Curve.Center, App.Vector(perpCenDir).multiply(circle1.Curve.Radius))
centers = []
# Calculate inner homothetic center
# Get point on second circle
- p2_inner = App.Vector.add(circle1.Curve.Center,
- App.Vector(perpCenDir).multiply(-circle1.Curve.Radius))
- hCenterInner = DraftVecUtils.intersect(circle1.Curve.Center,
- circle2.Curve.Center,
- p1, p2_inner,
- True, True)
+ p2_inner = App.Vector.add(
+ circle1.Curve.Center, App.Vector(perpCenDir).multiply(-circle1.Curve.Radius)
+ )
+ hCenterInner = DraftVecUtils.intersect(
+ circle1.Curve.Center, circle2.Curve.Center, p1, p2_inner, True, True
+ )
if hCenterInner:
centers.append(hCenterInner)
@@ -383,12 +378,12 @@ def findHomotheticCenterOfCircles(circle1, circle2):
# have different radii
if circle1.Curve.Radius != circle2.Curve.Radius:
# Get point on second circle
- p2_outer = App.Vector.add(circle1.Curve.Center,
- App.Vector(perpCenDir).multiply(circle1.Curve.Radius))
- hCenterOuter = DraftVecUtils.intersect(circle1.Curve.Center,
- circle2.Curve.Center,
- p1, p2_outer,
- True, True)
+ p2_outer = App.Vector.add(
+ circle1.Curve.Center, App.Vector(perpCenDir).multiply(circle1.Curve.Radius)
+ )
+ hCenterOuter = DraftVecUtils.intersect(
+ circle1.Curve.Center, circle2.Curve.Center, p1, p2_outer, True, True
+ )
if hCenterOuter:
centers.append(hCenterOuter)
@@ -473,9 +468,11 @@ def findRadicalCenter(circle1, circle2, circle3):
--------
findRadicalAxis
"""
- if (geomType(circle1) != "Circle"
- or geomType(circle2) != "Circle"
- or geomType(circle3) != "Circle"):
+ if (
+ geomType(circle1) != "Circle"
+ or geomType(circle2) != "Circle"
+ or geomType(circle3) != "Circle"
+ ):
print("debug: findRadicalCenter bad parameters! Must be circles.")
return None
@@ -494,4 +491,5 @@ def findRadicalCenter(circle1, circle2, circle3):
# No radical center could be calculated.
return None
+
## @}
diff --git a/src/Mod/Draft/draftgeoutils/circles_apollonius.py b/src/Mod/Draft/draftgeoutils/circles_apollonius.py
index e1f975b4f9..c8b270d9ee 100644
--- a/src/Mod/Draft/draftgeoutils/circles_apollonius.py
+++ b/src/Mod/Draft/draftgeoutils/circles_apollonius.py
@@ -68,9 +68,11 @@ def outerSoddyCircle(circle1, circle2, circle3):
Either Creative Commons Attribution 3.0, the MIT license,
or the GNU Lesser General License LGPL.
"""
- if (geomType(circle1) != "Circle"
- or geomType(circle2) != "Circle"
- or geomType(circle3) != "Circle"):
+ if (
+ geomType(circle1) != "Circle"
+ or geomType(circle2) != "Circle"
+ or geomType(circle3) != "Circle"
+ ):
print("debug: outerSoddyCircle bad parameters! Must be circles.")
return None
@@ -93,7 +95,7 @@ def outerSoddyCircle(circle1, circle2, circle3):
q2 = (k2 + 0j) * (B.x + B.y * 1j)
q3 = (k3 + 0j) * (C.x + C.y * 1j)
- temp = ((q1 * q2) + (q2 * q3) + (q3 * q1))
+ temp = (q1 * q2) + (q2 * q3) + (q3 * q1)
q4 = q1 + q2 + q3 - ((2 + 0j) * cmath.sqrt(temp))
z = q4 / (k4 + 0j)
@@ -121,9 +123,11 @@ def innerSoddyCircle(circle1, circle2, circle3):
Converted to python by Martin Buerbaum 2009
http://www.randelshofer.ch/treeviz/
"""
- if (geomType(circle1) != "Circle"
- and geomType(circle2) != "Circle"
- and geomType(circle3) != "Circle"):
+ if (
+ geomType(circle1) != "Circle"
+ and geomType(circle2) != "Circle"
+ and geomType(circle3) != "Circle"
+ ):
print("debug: innerSoddyCircle bad parameters! Must be circles.")
return None
@@ -146,13 +150,13 @@ def innerSoddyCircle(circle1, circle2, circle3):
q2 = (k2 + 0j) * (B.x + B.y * 1j)
q3 = (k3 + 0j) * (C.x + C.y * 1j)
- temp = ((q1 * q2) + (q2 * q3) + (q3 * q1))
+ temp = (q1 * q2) + (q2 * q3) + (q3 * q1)
q4 = q1 + q2 + q3 + ((2 + 0j) * cmath.sqrt(temp))
z = q4 / (k4 + 0j)
# If the formula is not solvable, we return no circle.
- if (not z or not (1 / k4)):
+ if not z or not (1 / k4):
return None
X = z.real
@@ -186,9 +190,11 @@ def circleFrom3CircleTangents(circle1, circle2, circle3):
inversion pole and the radical center) with the circle.
* This gives us all the tangent points.
"""
- if (geomType(circle1) != "Circle"
- and geomType(circle2) != "Circle"
- and geomType(circle3) == "Circle"):
+ if (
+ geomType(circle1) != "Circle"
+ and geomType(circle2) != "Circle"
+ and geomType(circle3) == "Circle"
+ ):
print("debug: circleFrom3CircleTangents bad input! Must be circles")
return None
@@ -222,4 +228,5 @@ def circleFrom3CircleTangents(circle1, circle2, circle3):
# Some circles are inside each other or an error has occurred.
return None
+
## @}
diff --git a/src/Mod/Draft/draftgeoutils/circles_incomplete.py b/src/Mod/Draft/draftgeoutils/circles_incomplete.py
index e410e0bb66..2498f141bc 100644
--- a/src/Mod/Draft/draftgeoutils/circles_incomplete.py
+++ b/src/Mod/Draft/draftgeoutils/circles_incomplete.py
@@ -57,11 +57,13 @@ import FreeCAD
from draftutils.messages import _wrn
from draftgeoutils.general import geomType
-from draftgeoutils.circles import (circlefrom2Lines1Point,
- circleFrom2LinesRadius,
- circlefrom1Line2Points,
- circleFromPointLineRadius,
- circleFrom3LineTangents)
+from draftgeoutils.circles import (
+ circlefrom2Lines1Point,
+ circleFrom2LinesRadius,
+ circlefrom1Line2Points,
+ circleFromPointLineRadius,
+ circleFrom3LineTangents,
+)
from draftgeoutils.circles_apollonius import circleFrom3CircleTangents
@@ -81,24 +83,28 @@ def circleFrom2tan1pt(tan1, tan2, point):
The tangents should be edges, and they may be either straight line edges
or circular edges, so four combinations are possible.
"""
- if (geomType(tan1) == "Line"
- and geomType(tan2) == "Line"
- and isinstance(point, FreeCAD.Vector)):
+ if geomType(tan1) == "Line" and geomType(tan2) == "Line" and isinstance(point, FreeCAD.Vector):
return circlefrom2Lines1Point(tan1, tan2, point)
- elif (geomType(tan1) == "Circle"
- and geomType(tan2) == "Line"
- and isinstance(point, FreeCAD.Vector)):
+ elif (
+ geomType(tan1) == "Circle"
+ and geomType(tan2) == "Line"
+ and isinstance(point, FreeCAD.Vector)
+ ):
return circlefromCircleLinePoint(tan1, tan2, point)
- elif (geomType(tan2) == "Circle"
- and geomType(tan1) == "Line"
- and isinstance(point, FreeCAD.Vector)):
+ elif (
+ geomType(tan2) == "Circle"
+ and geomType(tan1) == "Line"
+ and isinstance(point, FreeCAD.Vector)
+ ):
return circlefromCircleLinePoint(tan2, tan1, point)
- elif (geomType(tan2) == "Circle"
- and geomType(tan1) == "Circle"
- and isinstance(point, FreeCAD.Vector)):
+ elif (
+ geomType(tan2) == "Circle"
+ and geomType(tan1) == "Circle"
+ and isinstance(point, FreeCAD.Vector)
+ ):
return circlefrom2Circles1Point(tan2, tan1, point)
@@ -142,14 +148,18 @@ def circleFrom1tan2pt(tan1, p1, p2):
The tangents should be edges, and they may be either straight line edges
or circular edges, so two combinations are possible.
"""
- if (geomType(tan1) == "Line"
- and isinstance(p1, FreeCAD.Vector)
- and isinstance(p2, FreeCAD.Vector)):
+ if (
+ geomType(tan1) == "Line"
+ and isinstance(p1, FreeCAD.Vector)
+ and isinstance(p2, FreeCAD.Vector)
+ ):
return circlefrom1Line2Points(tan1, p1, p2)
- elif (geomType(tan1) == "Circle"
- and isinstance(p1, FreeCAD.Vector)
- and isinstance(p2, FreeCAD.Vector)):
+ elif (
+ geomType(tan1) == "Circle"
+ and isinstance(p1, FreeCAD.Vector)
+ and isinstance(p2, FreeCAD.Vector)
+ ):
return circlefrom1Circle2Points(tan1, p1, p2)
@@ -187,13 +197,13 @@ def circleFrom3tan(tan1, tan2, tan3):
The tangents should be edges, and they may be either straight line edges
or circular edges, so eight combinations are possible.
"""
- tan1IsLine = (geomType(tan1) == "Line")
- tan2IsLine = (geomType(tan2) == "Line")
- tan3IsLine = (geomType(tan3) == "Line")
+ tan1IsLine = geomType(tan1) == "Line"
+ tan2IsLine = geomType(tan2) == "Line"
+ tan3IsLine = geomType(tan3) == "Line"
- tan1IsCircle = (geomType(tan1) == "Circle")
- tan2IsCircle = (geomType(tan2) == "Circle")
- tan3IsCircle = (geomType(tan3) == "Circle")
+ tan1IsCircle = geomType(tan1) == "Circle"
+ tan2IsCircle = geomType(tan2) == "Circle"
+ tan3IsCircle = geomType(tan3) == "Circle"
if tan1IsLine and tan2IsLine and tan3IsLine:
return circleFrom3LineTangents(tan1, tan2, tan3)
@@ -219,4 +229,5 @@ def circleFrom3tan(tan1, tan2, tan3):
elif tan1IsCircle and tan2IsCircle and tan3IsLine:
return circleFrom2Circle1Lines(tan1, tan2, tan3)
+
## @}
diff --git a/src/Mod/Draft/draftgeoutils/cuboids.py b/src/Mod/Draft/draftgeoutils/cuboids.py
index 833e46634c..7eb5216e2a 100644
--- a/src/Mod/Draft/draftgeoutils/cuboids.py
+++ b/src/Mod/Draft/draftgeoutils/cuboids.py
@@ -43,9 +43,7 @@ def isCubic(shape):
and all angles are 90 degrees between its edges.
"""
# first we try fast methods
- if (len(shape.Vertexes) != 8
- or len(shape.Faces) != 6
- or len(shape.Edges) != 12):
+ if len(shape.Vertexes) != 8 or len(shape.Faces) != 6 or len(shape.Edges) != 12:
return False
for e in shape.Edges:
@@ -60,10 +58,10 @@ def isCubic(shape):
for i in range(4):
e1 = vec(f.Edges[i])
if i < 3:
- e2 = vec(f.Edges[i+1])
+ e2 = vec(f.Edges[i + 1])
else:
e2 = vec(f.Edges[0])
- rpi = [0.0, round(math.pi/2, precision())]
+ rpi = [0.0, round(math.pi / 2, precision())]
if round(e1.getAngle(e2), precision()) not in rpi:
return False
@@ -109,7 +107,7 @@ def getCubicDimensions(shape):
# getting height
vz = None
- rpi = round(math.pi/2, precision())
+ rpi = round(math.pi / 2, precision())
for i in range(1, 6):
for e in shape.Faces[i].Edges:
if basepoint in [e.Vertexes[0].Point, e.Vertexes[1].Point]:
@@ -128,9 +126,12 @@ def getCubicDimensions(shape):
mat.rotateY(rotY)
mat.rotateZ(rotZ)
- return [App.Placement(mat),
- round(vx.Length, precision()),
- round(vy.Length, precision()),
- round(vz.Length, precision())]
+ return [
+ App.Placement(mat),
+ round(vx.Length, precision()),
+ round(vy.Length, precision()),
+ round(vz.Length, precision()),
+ ]
+
## @}
diff --git a/src/Mod/Draft/draftgeoutils/edges.py b/src/Mod/Draft/draftgeoutils/edges.py
index c7ba1b2e5a..eb27be1a6e 100644
--- a/src/Mod/Draft/draftgeoutils/edges.py
+++ b/src/Mod/Draft/draftgeoutils/edges.py
@@ -44,10 +44,8 @@ def findEdge(anEdge, aList):
"""Return True if edge is found in list of edges."""
for e in range(len(aList)):
if str(anEdge.Curve) == str(aList[e].Curve):
- if DraftVecUtils.equals(anEdge.Vertexes[0].Point,
- aList[e].Vertexes[0].Point):
- if DraftVecUtils.equals(anEdge.Vertexes[-1].Point,
- aList[e].Vertexes[-1].Point):
+ if DraftVecUtils.equals(anEdge.Vertexes[0].Point, aList[e].Vertexes[0].Point):
+ if DraftVecUtils.equals(anEdge.Vertexes[-1].Point, aList[e].Vertexes[-1].Point):
return e
return None
@@ -75,19 +73,15 @@ def orientEdge(edge, normal=None, make_arc=False):
if angle:
edge.rotate(base, axis, angle)
if isinstance(edge.Curve, Part.Line):
- return Part.LineSegment(edge.Curve,
- edge.FirstParameter,
- edge.LastParameter)
+ return Part.LineSegment(edge.Curve, edge.FirstParameter, edge.LastParameter)
elif make_arc and isinstance(edge.Curve, Part.Circle) and not edge.Closed:
- return Part.ArcOfCircle(edge.Curve,
- edge.FirstParameter,
- edge.LastParameter,
- edge.Curve.Axis.z > 0)
+ return Part.ArcOfCircle(
+ edge.Curve, edge.FirstParameter, edge.LastParameter, edge.Curve.Axis.z > 0
+ )
elif make_arc and isinstance(edge.Curve, Part.Ellipse) and not edge.Closed:
- return Part.ArcOfEllipse(edge.Curve,
- edge.FirstParameter,
- edge.LastParameter,
- edge.Curve.Axis.z > 0)
+ return Part.ArcOfEllipse(
+ edge.Curve, edge.FirstParameter, edge.LastParameter, edge.Curve.Axis.z > 0
+ )
return edge.Curve
@@ -98,15 +92,13 @@ def isSameLine(e1, e2):
if not isinstance(e2.Curve, Part.LineSegment):
return False
- if (DraftVecUtils.equals(e1.Vertexes[0].Point,
- e2.Vertexes[0].Point)
- and DraftVecUtils.equals(e1.Vertexes[-1].Point,
- e2.Vertexes[-1].Point)):
+ if DraftVecUtils.equals(e1.Vertexes[0].Point, e2.Vertexes[0].Point) and DraftVecUtils.equals(
+ e1.Vertexes[-1].Point, e2.Vertexes[-1].Point
+ ):
return True
- elif (DraftVecUtils.equals(e1.Vertexes[-1].Point,
- e2.Vertexes[0].Point)
- and DraftVecUtils.equals(e1.Vertexes[0].Point,
- e2.Vertexes[-1].Point)):
+ elif DraftVecUtils.equals(e1.Vertexes[-1].Point, e2.Vertexes[0].Point) and DraftVecUtils.equals(
+ e1.Vertexes[0].Point, e2.Vertexes[-1].Point
+ ):
return True
return False
@@ -114,15 +106,15 @@ def isSameLine(e1, e2):
def is_line(bspline):
"""Return True if the given BSpline curve is a straight line."""
-# previous implementation may fail for a multipole straight spline due
-# a second order error in tolerance, which introduce a difference of 1e-14
-# in the values of the tangents. Also, may fail on a periodic spline.
-# step = bspline.LastParameter/10
-# b = bspline.tangent(0)
-#
-# for i in range(10):
-# if bspline.tangent(i * step) != b:
-# return False
+ # previous implementation may fail for a multipole straight spline due
+ # a second order error in tolerance, which introduce a difference of 1e-14
+ # in the values of the tangents. Also, may fail on a periodic spline.
+ # step = bspline.LastParameter/10
+ # b = bspline.tangent(0)
+ #
+ # for i in range(10):
+ # if bspline.tangent(i * step) != b:
+ # return False
start_point = bspline.StartPoint
end_point = bspline.EndPoint
@@ -133,7 +125,6 @@ def is_line(bspline):
return False
-
def invert(shape):
"""Return an inverted copy of the edge or wire contained in the shape."""
if shape.ShapeType == "Wire":
@@ -144,17 +135,13 @@ def invert(shape):
if len(shape.Vertexes) == 1:
return shape
if geomType(shape) == "Line":
- return Part.LineSegment(shape.Vertexes[-1].Point,
- shape.Vertexes[0].Point).toShape()
+ return Part.LineSegment(shape.Vertexes[-1].Point, shape.Vertexes[0].Point).toShape()
elif geomType(shape) == "Circle":
mp = findMidpoint(shape)
- return Part.Arc(shape.Vertexes[-1].Point,
- mp,
- shape.Vertexes[0].Point).toShape()
+ return Part.Arc(shape.Vertexes[-1].Point, mp, shape.Vertexes[0].Point).toShape()
elif geomType(shape) in ["BSplineCurve", "BezierCurve"]:
if isLine(shape.Curve):
- return Part.LineSegment(shape.Vertexes[-1].Point,
- shape.Vertexes[0].Point).toShape()
+ return Part.LineSegment(shape.Vertexes[-1].Point, shape.Vertexes[0].Point).toShape()
print("DraftGeomUtils.invert: unable to invert", shape.Curve)
return shape
@@ -168,7 +155,7 @@ def findMidpoint(edge):
if edge.Length == 0:
return None
else:
- return edge.valueAt(edge.Curve.parameterAtDistance(edge.Length/2, edge.FirstParameter))
+ return edge.valueAt(edge.Curve.parameterAtDistance(edge.Length / 2, edge.FirstParameter))
def getTangent(edge, from_point=None):
@@ -180,8 +167,7 @@ def getTangent(edge, from_point=None):
if geomType(edge) == "Line":
return vec(edge)
- elif (geomType(edge) == "BSplineCurve"
- or geomType(edge) == "BezierCurve"):
+ elif geomType(edge) == "BSplineCurve" or geomType(edge) == "BezierCurve":
if not from_point:
return None
cp = edge.Curve.parameter(from_point)
@@ -199,7 +185,7 @@ def getTangent(edge, from_point=None):
def get_referenced_edges(property_value):
"""Return the Edges referenced by the value of a App:PropertyLink, App::PropertyLinkList,
- App::PropertyLinkSub or App::PropertyLinkSubList property."""
+ App::PropertyLinkSub or App::PropertyLinkSubList property."""
edges = []
if not isinstance(property_value, list):
property_value = [property_value]
@@ -219,6 +205,7 @@ def get_referenced_edges(property_value):
edges.append(object.Shape.Edges[edge_number])
return edges
+
# compatibility layer
isLine = is_line
diff --git a/src/Mod/Draft/draftgeoutils/faces.py b/src/Mod/Draft/draftgeoutils/faces.py
index 06469daa11..d5c2c38cd3 100644
--- a/src/Mod/Draft/draftgeoutils/faces.py
+++ b/src/Mod/Draft/draftgeoutils/faces.py
@@ -48,8 +48,10 @@ def concatenate(shape):
wires = [Part.Wire(edges) for edges in sorted_edges]
face = Part.makeFace(wires, "Part::FaceMakerBullseye")
except Base.FreeCADError:
- print("DraftGeomUtils: Fails to join faces into one. "
- + "The precision of the faces would be insufficient")
+ print(
+ "DraftGeomUtils: Fails to join faces into one. "
+ + "The precision of the faces would be insufficient"
+ )
return shape
else:
if not wires[0].isClosed():
@@ -106,6 +108,7 @@ def is_coplanar(faces, tol=-1):
return True
+
isCoplanar = is_coplanar
@@ -122,10 +125,8 @@ def bind(w1, w2, per_segment=False):
def create_face(w1, w2):
try:
- w3 = Part.LineSegment(w1.Vertexes[0].Point,
- w2.Vertexes[0].Point).toShape()
- w4 = Part.LineSegment(w1.Vertexes[-1].Point,
- w2.Vertexes[-1].Point).toShape()
+ w3 = Part.LineSegment(w1.Vertexes[0].Point, w2.Vertexes[0].Point).toShape()
+ w4 = Part.LineSegment(w1.Vertexes[-1].Point, w2.Vertexes[-1].Point).toShape()
except Part.OCCError:
print("DraftGeomUtils: unable to bind wires")
return None
@@ -138,12 +139,10 @@ def bind(w1, w2, per_segment=False):
print("DraftGeomUtils: unable to bind wires")
return None
- if (per_segment
- and len(w1.Edges) > 1
- and len(w1.Edges) == len(w2.Edges)):
+ if per_segment and len(w1.Edges) > 1 and len(w1.Edges) == len(w2.Edges):
faces = []
faces_list = []
- for (edge1, edge2) in zip(w1.Edges, w2.Edges):
+ for edge1, edge2 in zip(w1.Edges, w2.Edges):
# Find touching edges due to ArchWall Align in opposite
# directions, and/or opposite edge orientations.
#
@@ -181,32 +180,40 @@ def bind(w1, w2, per_segment=False):
# 1) there are only 2 series, connecting would return invalid shape
# 2) 1st series of faces happens to be [], i.e. 1st edge pairs touch
#
- if w1.isClosed() and w2.isClosed() \
- and len(faces_list) > 1 and faces_list[0]:
- faces_list[0].extend(faces) # TODO: To be reviewed, 'afterthought' on 2025.3.29, seems by 'extend', faces in 1st and last faces are not in sequential order
+ if w1.isClosed() and w2.isClosed() and len(faces_list) > 1 and faces_list[0]:
+ faces_list[0].extend(
+ faces
+ ) # TODO: To be reviewed, 'afterthought' on 2025.3.29, seems by 'extend', faces in 1st and last faces are not in sequential order
else:
faces_list.append(faces) # Break into separate list
from collections import Counter
+
if faces_list:
faces_fused_list = []
for faces in faces_list:
dir = []
countDir = None
for f in faces:
- dir.append(f.normalAt(0,0).z)
+ dir.append(f.normalAt(0, 0).z)
countDir = Counter(dir)
l = len(faces)
m = max(countDir.values()) # max(countDir, key=countDir.get)
if m != l:
- print("DraftGeomUtils: Problem, the direction of " + str(l-m) + " out of " + str(l) + " segment is reversed, please check!")
- if len(faces) > 1 :
+ print(
+ "DraftGeomUtils: Problem, the direction of "
+ + str(l - m)
+ + " out of "
+ + str(l)
+ + " segment is reversed, please check!"
+ )
+ if len(faces) > 1:
# Below not good if a face is self-intersecting or reversed
- #faces_fused = faces[0].fuse(faces[1:]).removeSplitter().Faces[0]
+ # faces_fused = faces[0].fuse(faces[1:]).removeSplitter().Faces[0]
rf = faces[0]
for f in faces[1:]:
rf = rf.fuse(f).removeSplitter().Faces[0]
- #rf = rf.fuse(f) # Not working
- #rf = rf.removeSplitter().Faces[0] # Not working
+ # rf = rf.fuse(f) # Not working
+ # rf = rf.removeSplitter().Faces[0] # Not working
faces_fused_list.append(rf)
# faces might be empty list [], see above; skip if empty
elif faces:
@@ -217,19 +224,25 @@ def bind(w1, w2, per_segment=False):
dir = []
countDir = None
for f in faces:
- dir.append(f.normalAt(0,0).z)
+ dir.append(f.normalAt(0, 0).z)
countDir = Counter(dir)
l = len(faces)
m = max(countDir.values()) # max(countDir, key=countDir.get)
if m != l:
- print("DraftGeomUtils: Problem, the direction of " + str(l-m) + " out of " + str(l) + " segment is reversed, please check!")
+ print(
+ "DraftGeomUtils: Problem, the direction of "
+ + str(l - m)
+ + " out of "
+ + str(l)
+ + " segment is reversed, please check!"
+ )
# Below not good if a face is self-intersecting or reversed
- #return faces[0].fuse(faces[1:]).removeSplitter().Faces[0]
+ # return faces[0].fuse(faces[1:]).removeSplitter().Faces[0]
rf = faces[0]
for f in faces[1:]:
rf = rf.fuse(f).removeSplitter().Faces[0]
- #rf = rf.fuse(f) # Not working
- #rf = rf.removeSplitter().Faces[0] # Not working
+ # rf = rf.fuse(f) # Not working
+ # rf = rf.removeSplitter().Faces[0] # Not working
return rf
elif w1.isClosed() and w2.isClosed():
@@ -385,4 +398,5 @@ def removeSplitter(shape):
return None
+
## @}
diff --git a/src/Mod/Draft/draftgeoutils/fillets.py b/src/Mod/Draft/draftgeoutils/fillets.py
index 2ab56ebf31..af7260628c 100644
--- a/src/Mod/Draft/draftgeoutils/fillets.py
+++ b/src/Mod/Draft/draftgeoutils/fillets.py
@@ -54,14 +54,13 @@ def fillet(lEdges, r, chamfer=False):
The dictionary contains edges with keys 'Arc' and 'Line'.
"""
if not existingCurveType:
- existingCurveType = {'Line': [],
- 'Arc': []}
+ existingCurveType = {"Line": [], "Arc": []}
if issubclass(type(edge.Curve), Part.LineSegment):
- existingCurveType['Line'] += [edge]
+ existingCurveType["Line"] += [edge]
elif issubclass(type(edge.Curve), Part.Line):
- existingCurveType['Line'] += [edge]
+ existingCurveType["Line"] += [edge]
elif issubclass(type(edge.Curve), Part.Circle):
- existingCurveType['Arc'] += [edge]
+ existingCurveType["Arc"] += [edge]
else:
raise ValueError("Edge's curve must be either Line or Arc")
return existingCurveType
@@ -93,7 +92,7 @@ def fillet(lEdges, r, chamfer=False):
else:
lVertexes = [rndEdges[0].Vertexes[0], rndEdges[0].Vertexes[-1], rndEdges[1].Vertexes[0]]
- if len(curveType['Line']) == 2:
+ if len(curveType["Line"]) == 2:
# Deals with 2-line-edges lists
U1 = lVertexes[0].Point.sub(lVertexes[1].Point)
U1.normalize()
@@ -104,14 +103,12 @@ def fillet(lEdges, r, chamfer=False):
alpha = U1.getAngle(U2)
# Edges have same direction
- if (round(alpha, precision()) == 0
- or round(alpha - math.pi, precision()) == 0):
- print("DraftGeomUtils.fillet: Warning: "
- "edges have same direction. Did nothing")
+ if round(alpha, precision()) == 0 or round(alpha - math.pi, precision()) == 0:
+ print("DraftGeomUtils.fillet: Warning: " "edges have same direction. Did nothing")
return rndEdges
- dToCenter = r / math.sin(alpha/2.0)
- dToTangent = (dToCenter**2-r**2)**(0.5)
+ dToCenter = r / math.sin(alpha / 2.0)
+ dToTangent = (dToCenter**2 - r**2) ** (0.5)
dirVect = App.Vector(U1)
dirVect.scale(dToTangent, dToTangent, dToTangent)
arcPt1 = lVertexes[1].Point.add(dirVect)
@@ -126,8 +123,7 @@ def fillet(lEdges, r, chamfer=False):
arcPt3 = lVertexes[1].Point.add(dirVect)
if (dToTangent > rndEdges[0].Length) or (dToTangent > rndEdges[1].Length):
- print("DraftGeomUtils.fillet: Error: radius value ", r,
- " is too high")
+ print("DraftGeomUtils.fillet: Error: radius value ", r, " is too high")
return rndEdges
if chamfer:
@@ -139,19 +135,17 @@ def fillet(lEdges, r, chamfer=False):
# fillet consumes entire first edge
rndEdges.pop(0)
else:
- rndEdges[0] = Part.Edge(Part.LineSegment(lVertexes[0].Point,
- arcPt1))
+ rndEdges[0] = Part.Edge(Part.LineSegment(lVertexes[0].Point, arcPt1))
if lVertexes[2].Point != arcPt3:
# fillet does not consume entire second edge
- rndEdges += [Part.Edge(Part.LineSegment(arcPt3,
- lVertexes[2].Point))]
+ rndEdges += [Part.Edge(Part.LineSegment(arcPt3, lVertexes[2].Point))]
return rndEdges
- elif len(curveType['Arc']) == 1:
+ elif len(curveType["Arc"]) == 1:
# Deals with lists containing an arc and a line
- if rndEdges[0] in curveType['Arc']:
+ if rndEdges[0] in curveType["Arc"]:
lineEnd = lVertexes[2]
arcEnd = lVertexes[0]
arcFirst = True
@@ -159,10 +153,10 @@ def fillet(lEdges, r, chamfer=False):
lineEnd = lVertexes[0]
arcEnd = lVertexes[2]
arcFirst = False
- arcCenter = curveType['Arc'][0].Curve.Center
- arcRadius = curveType['Arc'][0].Curve.Radius
- arcAxis = curveType['Arc'][0].Curve.Axis
- arcLength = curveType['Arc'][0].Length
+ arcCenter = curveType["Arc"][0].Curve.Center
+ arcRadius = curveType["Arc"][0].Curve.Radius
+ arcAxis = curveType["Arc"][0].Curve.Axis
+ arcLength = curveType["Arc"][0].Length
U1 = lineEnd.Point.sub(lVertexes[1].Point)
U1.normalize()
@@ -183,20 +177,19 @@ def fillet(lEdges, r, chamfer=False):
if round(projCenter, precision()) > 0:
newRadius = arcRadius - r
- elif (round(projCenter, precision()) < 0
- or (round(projCenter, precision()) == 0 and U1.dot(T) > 0)):
+ elif round(projCenter, precision()) < 0 or (
+ round(projCenter, precision()) == 0 and U1.dot(T) > 0
+ ):
newRadius = arcRadius + r
else:
- print("DraftGeomUtils.fillet: Warning: "
- "edges are already tangent. Did nothing")
+ print("DraftGeomUtils.fillet: Warning: " "edges are already tangent. Did nothing")
return rndEdges
toNewCent = newRadius**2 - dCenterToLine**2
if toNewCent > 0:
- toNewCent = abs(abs(projCenter) - toNewCent**(0.5))
+ toNewCent = abs(abs(projCenter) - toNewCent ** (0.5))
else:
- print("DraftGeomUtils.fillet: Error: radius value ", r,
- " is too high")
+ print("DraftGeomUtils.fillet: Error: radius value ", r, " is too high")
return rndEdges
U1.scale(toNewCent, toNewCent, toNewCent)
@@ -232,9 +225,8 @@ def fillet(lEdges, r, chamfer=False):
toCenter.scale(-1, -1, -1)
delLength = arcRadius * V[0].sub(arcCenter).getAngle(toCenter)
- if delLength > arcLength or toNewCent > curveType['Line'][0].Length:
- print("DraftGeomUtils.fillet: Error: radius value ", r,
- " is too high")
+ if delLength > arcLength or toNewCent > curveType["Line"][0].Length:
+ print("DraftGeomUtils.fillet: Error: radius value ", r, " is too high")
return rndEdges
arcAsEdge = arcFrom2Pts(V[-arcFirst], V[-myTrick], arcCenter, arcAxis)
@@ -245,26 +237,29 @@ def fillet(lEdges, r, chamfer=False):
rndEdges[not arcFirst] = arcAsEdge
rndEdges[arcFirst] = lineAsEdge
if chamfer:
- rndEdges[1:1] = [Part.Edge(Part.LineSegment(arcPt[- arcFirst],
- arcPt[- myTrick]))]
+ rndEdges[1:1] = [Part.Edge(Part.LineSegment(arcPt[-arcFirst], arcPt[-myTrick]))]
else:
- rndEdges[1:1] = [Part.Edge(Part.Arc(arcPt[- arcFirst],
- arcPt[1],
- arcPt[- myTrick]))]
+ rndEdges[1:1] = [Part.Edge(Part.Arc(arcPt[-arcFirst], arcPt[1], arcPt[-myTrick]))]
return rndEdges
- elif len(curveType['Arc']) == 2:
+ elif len(curveType["Arc"]) == 2:
# Deals with lists of 2 arc-edges
- (arcCenter, arcRadius,
- arcAxis, arcLength,
- toCenter, T, newRadius) = [], [], [], [], [], [], []
+ (arcCenter, arcRadius, arcAxis, arcLength, toCenter, T, newRadius) = (
+ [],
+ [],
+ [],
+ [],
+ [],
+ [],
+ [],
+ )
for i in range(2):
- arcCenter += [curveType['Arc'][i].Curve.Center]
- arcRadius += [curveType['Arc'][i].Curve.Radius]
- arcAxis += [curveType['Arc'][i].Curve.Axis]
- arcLength += [curveType['Arc'][i].Length]
+ arcCenter += [curveType["Arc"][i].Curve.Center]
+ arcRadius += [curveType["Arc"][i].Curve.Radius]
+ arcAxis += [curveType["Arc"][i].Curve.Axis]
+ arcLength += [curveType["Arc"][i].Length]
toCenter += [arcCenter[i].sub(lVertexes[1].Point)]
T += [arcAxis[0].cross(toCenter[0])]
@@ -272,7 +267,7 @@ def fillet(lEdges, r, chamfer=False):
CentToCent = toCenter[1].sub(toCenter[0])
dCentToCent = CentToCent.Length
- sameDirection = (arcAxis[0].dot(arcAxis[1]) > 0)
+ sameDirection = arcAxis[0].dot(arcAxis[1]) > 0
TcrossT = T[0].cross(T[1])
if sameDirection:
@@ -286,8 +281,7 @@ def fillet(lEdges, r, chamfer=False):
newRadius += [arcRadius[0] + r]
newRadius += [arcRadius[1] + r]
else:
- print("DraftGeomUtils.fillet: Warning: "
- "edges are already tangent. Did nothing")
+ print("DraftGeomUtils.fillet: Warning: " "edges are already tangent. Did nothing")
return rndEdges
elif not sameDirection:
@@ -305,24 +299,22 @@ def fillet(lEdges, r, chamfer=False):
newRadius += [arcRadius[0] + r]
newRadius += [arcRadius[1] - r]
else:
- print("DraftGeomUtils.fillet: Warning: "
- "arcs are coincident. Did nothing")
+ print("DraftGeomUtils.fillet: Warning: " "arcs are coincident. Did nothing")
return rndEdges
else:
- print("DraftGeomUtils.fillet: Warning: "
- "edges are already tangent. Did nothing")
+ print("DraftGeomUtils.fillet: Warning: " "edges are already tangent. Did nothing")
return rndEdges
- if (newRadius[0] + newRadius[1] < dCentToCent
- or newRadius[0] - newRadius[1] > dCentToCent
- or newRadius[1] - newRadius[0] > dCentToCent):
- print("DraftGeomUtils.fillet: Error: radius value ", r,
- " is too high")
+ if (
+ newRadius[0] + newRadius[1] < dCentToCent
+ or newRadius[0] - newRadius[1] > dCentToCent
+ or newRadius[1] - newRadius[0] > dCentToCent
+ ):
+ print("DraftGeomUtils.fillet: Error: radius value ", r, " is too high")
return rndEdges
- x = ((dCentToCent**2 + newRadius[0]**2 - newRadius[1]**2)
- / (2*dCentToCent))
- y = (newRadius[0]**2 - x**2)**(0.5)
+ x = (dCentToCent**2 + newRadius[0] ** 2 - newRadius[1] ** 2) / (2 * dCentToCent)
+ y = (newRadius[0] ** 2 - x**2) ** (0.5)
CentToCent.normalize()
toCenter[0].normalize()
@@ -336,8 +328,7 @@ def fillet(lEdges, r, chamfer=False):
CentToCent.scale(x, x, x)
normVect.scale(y, y, y)
newCent = arcCenter[0].add(CentToCent.add(normVect))
- CentToNewCent = [newCent.sub(arcCenter[0]),
- newCent.sub(arcCenter[1])]
+ CentToNewCent = [newCent.sub(arcCenter[0]), newCent.sub(arcCenter[1])]
for i in range(2):
CentToNewCent[i].normalize()
@@ -357,24 +348,19 @@ def fillet(lEdges, r, chamfer=False):
arcAsEdge = []
for i in range(2):
toCenter[i].scale(-1, -1, -1)
- delLength = (arcRadius[i]
- * arcPt[-i].sub(arcCenter[i]).getAngle(toCenter[i]))
+ delLength = arcRadius[i] * arcPt[-i].sub(arcCenter[i]).getAngle(toCenter[i])
if delLength > arcLength[i]:
- print("DraftGeomUtils.fillet: Error: radius value ", r,
- " is too high")
+ print("DraftGeomUtils.fillet: Error: radius value ", r, " is too high")
return rndEdges
V = [arcPt[-i], lVertexes[-i].Point]
- arcAsEdge += [arcFrom2Pts(V[i-1], V[-i],
- arcCenter[i], arcAxis[i])]
+ arcAsEdge += [arcFrom2Pts(V[i - 1], V[-i], arcCenter[i], arcAxis[i])]
rndEdges[0] = arcAsEdge[0]
rndEdges[1] = arcAsEdge[1]
if chamfer:
rndEdges[1:1] = [Part.Edge(Part.LineSegment(arcPt[0], arcPt[2]))]
else:
- rndEdges[1:1] = [Part.Edge(Part.Arc(arcPt[0],
- arcPt[1],
- arcPt[2]))]
+ rndEdges[1:1] = [Part.Edge(Part.Arc(arcPt[0], arcPt[1], arcPt[2]))]
return rndEdges
@@ -390,7 +376,7 @@ def filletWire(aWire, r, chamfer=False):
filEdges = [edges[0]]
for i in range(len(edges) - 1):
- result = fillet([filEdges[-1], edges[i+1]], r, chamfer)
+ result = fillet([filEdges[-1], edges[i + 1]], r, chamfer)
if len(result) > 2:
filEdges[-1:] = result[0:3]
else:
@@ -404,4 +390,5 @@ def filletWire(aWire, r, chamfer=False):
return Part.Wire(filEdges)
+
## @}
diff --git a/src/Mod/Draft/draftgeoutils/general.py b/src/Mod/Draft/draftgeoutils/general.py
index 0323c54852..2a624b9f1e 100644
--- a/src/Mod/Draft/draftgeoutils/general.py
+++ b/src/Mod/Draft/draftgeoutils/general.py
@@ -59,7 +59,7 @@ def precision():
return precisionInt
-def vec(edge, use_orientation = False):
+def vec(edge, use_orientation=False):
"""Return a vector from an edge or a Part.LineSegment.
If use_orientation is True, it takes into account the edges orientation.
@@ -114,8 +114,7 @@ def isNull(something):
else:
return False
elif isinstance(something, App.Placement):
- if (something.Base == App.Vector(0, 0, 0)
- and something.Rotation.Q == (0, 0, 0, 1)):
+ if something.Base == App.Vector(0, 0, 0) and something.Rotation.Q == (0, 0, 0, 1):
return True
else:
return False
@@ -148,6 +147,7 @@ def isAligned(edge, axis="x"):
The axis can be 'x', 'y' or 'z'.
"""
+
def is_same(a, b):
return round(a, precision()) == round(b, precision())
@@ -193,12 +193,9 @@ def getQuad(face):
v2 = vec(face.Edges[1])
v3 = vec(face.Edges[2])
v4 = vec(face.Edges[3])
- angles90 = [round(math.pi*0.5, precision()),
- round(math.pi*1.5, precision())]
+ angles90 = [round(math.pi * 0.5, precision()), round(math.pi * 1.5, precision())]
- angles180 = [0,
- round(math.pi, precision()),
- round(math.pi*2, precision())]
+ angles180 = [0, round(math.pi, precision()), round(math.pi * 2, precision())]
for ov in [v2, v3, v4]:
if not (round(v1.getAngle(ov), precision()) in angles90 + angles180):
return None
@@ -267,7 +264,7 @@ def geomType(edge):
return "Ellipse"
else:
return "Unknown"
- except Exception: # catch all errors, no only TypeError
+ except Exception: # catch all errors, no only TypeError
return "Unknown"
@@ -319,10 +316,10 @@ def getBoundaryAngles(angle, alist):
negs = False
for i in range(len(alist)):
if alist[i] < 0:
- alist[i] = 2*math.pi + alist[i]
+ alist[i] = 2 * math.pi + alist[i]
negs = True
if angle < 0:
- angle = 2*math.pi + angle
+ angle = 2 * math.pi + angle
negs = True
lower = None
@@ -350,11 +347,12 @@ def getBoundaryAngles(angle, alist):
higher = a
if higher is None:
- higher = 2*math.pi
+ higher = 2 * math.pi
for a in alist:
if a < higher:
higher = a
return lower, higher
+
## @}
diff --git a/src/Mod/Draft/draftgeoutils/geo_arrays.py b/src/Mod/Draft/draftgeoutils/geo_arrays.py
index a39c29a1a2..5b8ee53d2e 100644
--- a/src/Mod/Draft/draftgeoutils/geo_arrays.py
+++ b/src/Mod/Draft/draftgeoutils/geo_arrays.py
@@ -48,7 +48,7 @@ Part = lz.LazyLoader("Part", globals(), "Part")
def print_places(places, title="Places"):
"""Print a vector with a title."""
- _msg(12*"-")
+ _msg(12 * "-")
_msg(title)
for i in places:
_msg("{}".format(i))
@@ -87,8 +87,7 @@ def get_twisted_placements(path, count=15, rot_factor=0.25):
"""Get the placements of the twisted array elements."""
count = max(count, 1)
- (norm, edge,
- step, inc) = get_init_values(path, count)
+ (norm, edge, step, inc) = get_init_values(path, count)
increment = 0
places = []
@@ -111,24 +110,18 @@ def get_twisted_placements(path, count=15, rot_factor=0.25):
def get_twisted_array_shape(base, path, count=15, rot_factor=0.25):
"""Get the twisted array shape as a compound."""
- places, _ = get_twisted_placements(path,
- count=count,
- rot_factor=rot_factor)
+ places, _ = get_twisted_placements(path, count=count, rot_factor=rot_factor)
shapes, _ = create_frames(base, places)
shape = Part.makeCompound(shapes)
return shape
-def get_twisted_bridge_shape(base, path, count=15, rot_factor=0.25,
- width=100,
- thickness=10):
+def get_twisted_bridge_shape(base, path, count=15, rot_factor=0.25, width=100, thickness=10):
"""Get the twisted bridge array shape as a compound."""
compound = list()
- places, _ = get_twisted_placements(path,
- count=count,
- rot_factor=rot_factor)
+ places, _ = get_twisted_placements(path, count=count, rot_factor=rot_factor)
# print_places(places)
shapes, profiles = create_frames(base, places)
@@ -175,7 +168,7 @@ def make_walkway(path, width=100, thickness=10):
"""Construct the walkway of the twisted bridge array."""
spine = path.Shape.Edges[0]
- half_size = width/2
+ half_size = width / 2
offset_height = thickness
norm1 = App.Vector(0, 0, 1)
@@ -187,8 +180,7 @@ def make_walkway(path, width=100, thickness=10):
place.Rotation = App.Rotation(binorm1, norm1, tan1)
place.move(v1 - App.Vector(0, 0, 3 * offset_height))
- plane = Part.makePlane(width, thickness,
- App.Vector(-half_size, -2 * offset_height, 0))
+ plane = Part.makePlane(width, thickness, App.Vector(-half_size, -2 * offset_height, 0))
face = Part.Face(plane)
face.Placement = place.multiply(face.Placement)
@@ -197,4 +189,5 @@ def make_walkway(path, width=100, thickness=10):
return sweep
+
## @}
diff --git a/src/Mod/Draft/draftgeoutils/geometry.py b/src/Mod/Draft/draftgeoutils/geometry.py
index 1c24d0738f..b53b917394 100644
--- a/src/Mod/Draft/draftgeoutils/geometry.py
+++ b/src/Mod/Draft/draftgeoutils/geometry.py
@@ -111,8 +111,7 @@ def findDistance(point, edge, strict=False):
if strict:
s1 = newpoint.sub(edge[0])
s2 = newpoint.sub(edge[1])
- if (s1.Length <= segment.Length
- and s2.Length <= segment.Length):
+ if s1.Length <= segment.Length and s2.Length <= segment.Length:
return dist
else:
return None
@@ -131,14 +130,13 @@ def findDistance(point, edge, strict=False):
newpoint = point.add(dist)
- if (dist.Length == 0):
+ if dist.Length == 0:
return None
if strict:
s1 = newpoint.sub(edge.Vertexes[0].Point)
s2 = newpoint.sub(edge.Vertexes[-1].Point)
- if (s1.Length <= segment.Length
- and s2.Length <= segment.Length):
+ if s1.Length <= segment.Length and s2.Length <= segment.Length:
return dist
else:
return None
@@ -170,7 +168,7 @@ def findDistance(point, edge, strict=False):
ang1 = DraftVecUtils.angle(ve1.sub(center))
ang2 = DraftVecUtils.angle(ve2.sub(center))
angpt = DraftVecUtils.angle(newpoint.sub(center))
- if ang1 >= ang2: # Arc does not cross the 9 o'clock point.
+ if ang1 >= ang2: # Arc does not cross the 9 o'clock point.
if ang1 >= angpt and angpt >= ang2:
return dist
else:
@@ -182,15 +180,13 @@ def findDistance(point, edge, strict=False):
else:
return dist
- elif (geomType(edge) == "BSplineCurve"
- or geomType(edge) == "BezierCurve"):
+ elif geomType(edge) == "BSplineCurve" or geomType(edge) == "BezierCurve":
try:
pr = edge.Curve.parameter(point)
np = edge.Curve.value(pr)
dist = np.sub(point)
except Part.OCCError:
- print("DraftGeomUtils: Unable to get curve parameter "
- "for point ", point)
+ print("DraftGeomUtils: Unable to get curve parameter " "for point ", point)
return None
else:
return dist
@@ -263,7 +259,9 @@ def get_shape_normal(shape):
if not is_straight_line(shape):
return None
start_edge = shape.Edges[0]
- x_vec = start_edge.tangentAt(start_edge.FirstParameter) # Return vector is in global coordinate
+ x_vec = start_edge.tangentAt(
+ start_edge.FirstParameter
+ ) # Return vector is in global coordinate
local_x_vec = shape_rot.inverted().multVec(x_vec) #
local_rot = App.Rotation(local_x_vec, App.Vector(0, 1, 0), App.Vector(0, 0, 1), "XZY")
# see https://blog.freecad.org/2023/01/16/the-rotation-api-in-freecad/ for App.Rotation(vecx, vecy, vecz, string)
@@ -275,7 +273,7 @@ def get_shape_normal(shape):
# Now, check the normal direction of the plane (plane.Axis).
# The final deduced normal should be 'in the direction' of the z-direction of the shape's placement,
# if plane.Axis is in the 'opposite' direction of the Z direction of the shape's placement, reverse it.
- if normal.getAngle(shape_normal) > math.pi/2:
+ if normal.getAngle(shape_normal) > math.pi / 2:
normal = normal.negative()
return normal
@@ -392,8 +390,8 @@ def is_straight_line(shape, tol=-1):
dir_start_edge = start_edge.tangentAt(start_edge.FirstParameter)
point_start_edge = start_edge.firstVertex().Point
- #set tolerance
- if tol <=0:
+ # set tolerance
+ if tol <= 0:
err = shape.globalTolerance(tol)
else:
err = tol
@@ -405,8 +403,8 @@ def is_straight_line(shape, tol=-1):
# check if edge is curve or no parallel to start_edge
# because sin(x) = x + O(x**3), for small angular deflection it's
# enough use the cross product of directions (or dot with a normal)
- if (abs(edge.Length - first_point.distanceToPoint(last_point)) > err
-
+ if (
+ abs(edge.Length - first_point.distanceToPoint(last_point)) > err
# https://forum.freecad.org/viewtopic.php?p=726101#p726101
# Shape with parallel edges but not colinear used to return True
# by this function, below line added fixes this bug.
@@ -423,9 +421,9 @@ def is_straight_line(shape, tol=-1):
# ./draftfunctions/upgrade.py
# ./draftgeoutils/geometry.py
# ./draftmake/make_wire.py
- or first_point.distanceToLine(point_start_edge, dir_start_edge) > err \
- #
- or dir_start_edge.cross(dir_edge).Length > err):
+ or first_point.distanceToLine(point_start_edge, dir_start_edge) > err #
+ or dir_start_edge.cross(dir_edge).Length > err
+ ):
return False
return True
@@ -446,8 +444,8 @@ def are_coplanar(shape_a, shape_b, tol=-1):
plane_a = find_plane(shape_a, tol)
plane_b = find_plane(shape_b, tol)
- #set tolerance
- if tol <=0:
+ # set tolerance
+ if tol <= 0:
err = 1e-7
else:
err = tol
@@ -456,8 +454,7 @@ def are_coplanar(shape_a, shape_b, tol=-1):
normal_a = plane_a.Axis
normal_b = plane_b.Axis
proj = plane_a.projectPoint(plane_b.Position)
- if (normal_a.cross(normal_b).Length > err
- or plane_b.Position.sub(proj).Length > err):
+ if normal_a.cross(normal_b).Length > err or plane_b.Position.sub(proj).Length > err:
return False
else:
return True
@@ -502,8 +499,8 @@ def get_spline_surface_normal(shape, tol=-1):
if len(shape.Faces) == 0:
return None
- #set tolerance
- if tol <=0:
+ # set tolerance
+ if tol <= 0:
err = shape.globalTolerance(tol)
else:
err = tol
@@ -515,8 +512,8 @@ def get_spline_surface_normal(shape, tol=-1):
# find bounds of first_surf
u0, u1, v0, v1 = first_surf.bounds()
- u = (u0 + u1)/2
- v = (v0 + v1)/2
+ u = (u0 + u1) / 2
+ v = (v0 + v1) / 2
first_normal = first_surf.normal(u, v)
# check if all faces are planar and parallel
for face in shape.Faces:
@@ -524,8 +521,8 @@ def get_spline_surface_normal(shape, tol=-1):
if not surf.isPlanar(tol):
return None
u0, u1, v0, v1 = surf.bounds()
- u = (u0 + u1)/2
- v = (v0 + v1)/2
+ u = (u0 + u1) / 2
+ v = (v0 + v1) / 2
surf_normal = surf.normal(u, v)
if first_normal.cross(surf_normal).Length > err:
return None
@@ -534,6 +531,7 @@ def get_spline_surface_normal(shape, tol=-1):
return normal
+
def find_plane(shape, tol=-1):
"""Find the plane containing the shape if possible.
Use this function as a workaround due Part.Shape.findPlane
@@ -832,13 +830,13 @@ def project_point_on_plane(point, base, normal, direction=None, force_projection
return point - delta_ax_proj / cos * direction
-#compatibility layer
+# compatibility layer
getSplineNormal = get_spline_normal
getNormal = get_normal
-isPlanar = is_planar
+isPlanar = is_planar
## @}
diff --git a/src/Mod/Draft/draftgeoutils/intersections.py b/src/Mod/Draft/draftgeoutils/intersections.py
index 844c4a2567..25ed99a739 100644
--- a/src/Mod/Draft/draftgeoutils/intersections.py
+++ b/src/Mod/Draft/draftgeoutils/intersections.py
@@ -41,10 +41,9 @@ Part = lz.LazyLoader("Part", globals(), "Part")
# @{
-def findIntersection(edge1, edge2,
- infinite1=False, infinite2=False,
- ex1=False, ex2=False,
- dts=True, findAll=False):
+def findIntersection(
+ edge1, edge2, infinite1=False, infinite2=False, ex1=False, ex2=False, dts=True, findAll=False
+):
"""Return a list containing the intersection points of 2 edges.
You can also feed 4 points instead of `edge1` and `edge2`.
@@ -86,12 +85,13 @@ def findIntersection(edge1, edge2,
list
A list of intersection points
"""
+
def getLineIntersections(pt1, pt2, pt3, pt4, infinite1, infinite2):
if pt1:
# first check if we don't already have coincident endpoints
if pt1 in [pt3, pt4]:
return [pt1]
- elif (pt2 in [pt3, pt4]):
+ elif pt2 in [pt3, pt4]:
return [pt2]
norm1 = pt2.sub(pt1).cross(pt3.sub(pt1))
norm2 = pt2.sub(pt4).cross(pt3.sub(pt4))
@@ -121,9 +121,11 @@ def findIntersection(edge1, edge2,
norm3 = vec1.cross(vec2)
denom = norm3.x + norm3.y + norm3.z
if not DraftVecUtils.isNull(norm3) and denom != 0:
- k = ((pt3.z - pt1.z) * (vec2.x - vec2.y)
- + (pt3.y - pt1.y) * (vec2.z - vec2.x)
- + (pt3.x - pt1.x) * (vec2.y - vec2.z))/denom
+ k = (
+ (pt3.z - pt1.z) * (vec2.x - vec2.y)
+ + (pt3.y - pt1.y) * (vec2.z - vec2.x)
+ + (pt3.x - pt1.x) * (vec2.y - vec2.z)
+ ) / denom
vec1.scale(k, k, k)
intp = pt1.add(vec1)
@@ -142,19 +144,27 @@ def findIntersection(edge1, edge2,
tol = pow(10, -precision())
# First, check bound boxes
- if (isinstance(edge1, Part.Edge) and isinstance(edge2, Part.Edge)
- and (not infinite1) and (not infinite2)):
+ if (
+ isinstance(edge1, Part.Edge)
+ and isinstance(edge2, Part.Edge)
+ and (not infinite1)
+ and (not infinite2)
+ ):
bb1 = edge1.BoundBox
bb1.enlarge(tol) # enlarge one box to account for rounding errors
if not bb1.intersect(edge2.BoundBox):
return [] # bound boxes don't intersect
# First, try to use Shape.section if possible
- if dts \
- and ((isinstance(edge1, Part.Edge) and isinstance(edge2, (Part.Edge, Part.Face)))
- or (isinstance(edge1, (Part.Edge, Part.Face)) and isinstance(edge2, Part.Edge))) \
- and (not infinite1) \
- and (not infinite2):
+ if (
+ dts
+ and (
+ (isinstance(edge1, Part.Edge) and isinstance(edge2, (Part.Edge, Part.Face)))
+ or (isinstance(edge1, (Part.Edge, Part.Face)) and isinstance(edge2, Part.Edge))
+ )
+ and (not infinite1)
+ and (not infinite2)
+ ):
return [v.Point for v in edge1.section((edge2), tol).Vertexes]
pt1 = None
@@ -171,14 +181,20 @@ def findIntersection(edge1, edge2,
elif (geomType(edge1) == "Line") and (geomType(edge2) == "Line"):
# we have 2 straight lines
- pt1, pt2, pt3, pt4 = [edge1.Vertexes[0].Point,
- edge1.Vertexes[1].Point,
- edge2.Vertexes[0].Point,
- edge2.Vertexes[1].Point]
+ pt1, pt2, pt3, pt4 = [
+ edge1.Vertexes[0].Point,
+ edge1.Vertexes[1].Point,
+ edge2.Vertexes[0].Point,
+ edge2.Vertexes[1].Point,
+ ]
return getLineIntersections(pt1, pt2, pt3, pt4, infinite1, infinite2)
- elif ((geomType(edge1) == "Circle") and (geomType(edge2) == "Line")
- or (geomType(edge1) == "Line") and (geomType(edge2) == "Circle")):
+ elif (
+ (geomType(edge1) == "Circle")
+ and (geomType(edge2) == "Line")
+ or (geomType(edge1) == "Line")
+ and (geomType(edge2) == "Circle")
+ ):
# deals with an arc or circle and a line
edges = [edge1, edge2]
@@ -218,7 +234,7 @@ def findIntersection(edge1, edge2,
toLine = pt1.sub(center).add(onLine)
if toLine.Length < arc.Curve.Radius:
- dOnLine = (arc.Curve.Radius**2 - toLine.Length**2)**(0.5)
+ dOnLine = (arc.Curve.Radius**2 - toLine.Length**2) ** (0.5)
onLine = App.Vector(dirVec)
onLine.scale(dOnLine, dOnLine, dOnLine)
int += [center.add(toLine).add(onLine)]
@@ -240,10 +256,9 @@ def findIntersection(edge1, edge2,
return []
dToPlane = center.sub(pt1).dot(toPlane)
toPlane = App.Vector(pt1)
- toPlane.scale(dToPlane/d, dToPlane/d, dToPlane/d)
+ toPlane.scale(dToPlane / d, dToPlane / d, dToPlane / d)
ptOnPlane = toPlane.add(pt1)
- if round(ptOnPlane.sub(center).Length - arc.Curve.Radius,
- precision()) == 0:
+ if round(ptOnPlane.sub(center).Length - arc.Curve.Radius, precision()) == 0:
int = [ptOnPlane]
else:
return []
@@ -277,9 +292,11 @@ def findIntersection(edge1, edge2,
dc2c = c2c.Length
if not DraftVecUtils.isNull(c2c):
c2c.normalize()
- if (round(rad1 + rad2 - dc2c, precision()) < 0
- or round(rad1 - dc2c - rad2, precision()) > 0
- or round(rad2 - dc2c - rad1, precision()) > 0):
+ if (
+ round(rad1 + rad2 - dc2c, precision()) < 0
+ or round(rad1 - dc2c - rad2, precision()) > 0
+ or round(rad2 - dc2c - rad1, precision()) > 0
+ ):
return []
else:
norm = c2c.cross(axis1)
@@ -288,8 +305,8 @@ def findIntersection(edge1, edge2,
if DraftVecUtils.isNull(norm):
x = 0
else:
- x = (dc2c**2 + rad1**2 - rad2**2) / (2*dc2c)
- y = abs(rad1**2 - x**2)**(0.5)
+ x = (dc2c**2 + rad1**2 - rad2**2) / (2 * dc2c)
+ y = abs(rad1**2 - x**2) ** (0.5)
c2c.scale(x, x, x)
if round(y, precision()) != 0:
norm.scale(y, y, y)
@@ -307,14 +324,13 @@ def findIntersection(edge1, edge2,
V = axis1.cross(U)
dToPlane = c2c.dot(axis2)
d = V.add(cent1).dot(axis2)
- V.scale(dToPlane/d, dToPlane/d, dToPlane/d)
+ V.scale(dToPlane / d, dToPlane / d, dToPlane / d)
PtOn2Planes = V.add(cent1)
planeIntersectionVector = U.add(PtOn2Planes)
- intTemp = findIntersection(planeIntersectionVector,
- edge1, True, True)
+ intTemp = findIntersection(planeIntersectionVector, edge1, True, True)
int = []
for pt in intTemp:
- if round(pt.sub(cent2).Length-rad2, precision()) == 0:
+ if round(pt.sub(cent2).Length - rad2, precision()) == 0:
int += [pt]
if infinite1 is False:
@@ -328,8 +344,10 @@ def findIntersection(edge1, edge2,
return int
else:
- print("DraftGeomUtils: Unsupported curve type: "
- "(" + str(edge1.Curve) + ", " + str(edge2.Curve) + ")")
+ print(
+ "DraftGeomUtils: Unsupported curve type: "
+ "(" + str(edge1.Curve) + ", " + str(edge2.Curve) + ")"
+ )
return []
@@ -344,10 +362,11 @@ def wiresIntersect(wire1, wire2):
return True
return False
+
def connect(edges, closed=False, wireNedge=False):
"""Connect the edges in the given list by their intersections."""
- inters_list = [] # List of intersections (with the previous edge).
+ inters_list = [] # List of intersections (with the previous edge).
for i, curr in enumerate(edges):
if i > 0:
prev = edges[i - 1]
@@ -357,14 +376,15 @@ def connect(edges, closed=False, wireNedge=False):
inters_list.append(None)
continue
- curr_inters_list = (findIntersection(prev, curr, True, True))
+ curr_inters_list = findIntersection(prev, curr, True, True)
if len(curr_inters_list) == 0:
inters_list.append(None)
elif len(curr_inters_list) == 1:
inters_list.append(curr_inters_list[0])
else:
- inters = curr_inters_list[DraftVecUtils.closest(curr.Vertexes[0].Point,
- curr_inters_list)]
+ inters = curr_inters_list[
+ DraftVecUtils.closest(curr.Vertexes[0].Point, curr_inters_list)
+ ]
inters_list.append(inters)
new_edges_full = []
@@ -418,9 +438,7 @@ def connect(edges, closed=False, wireNedge=False):
except Part.OCCError:
print("DraftGeomUtils.connect: unable to connect edges")
for edge in new_edges:
- print(edge.Curve, " ",
- edge.Vertexes[0].Point, " ",
- edge.Vertexes[-1].Point)
+ print(edge.Curve, " ", edge.Vertexes[0].Point, " ", edge.Vertexes[-1].Point)
return None
@@ -450,4 +468,5 @@ def angleBisection(edge1, edge2):
return Part.LineSegment(origin, origin.add(direction)).toShape()
+
## @}
diff --git a/src/Mod/Draft/draftgeoutils/linear_algebra.py b/src/Mod/Draft/draftgeoutils/linear_algebra.py
index 0a83b4692b..c14a27b3ba 100644
--- a/src/Mod/Draft/draftgeoutils/linear_algebra.py
+++ b/src/Mod/Draft/draftgeoutils/linear_algebra.py
@@ -52,10 +52,10 @@ def linearFromPoints(p1, p2):
return None
line = {}
- line['dx'] = (p2.x - p1.x)
- line['dy'] = (p2.y - p1.y)
- line['slope'] = line['dy'] / line['dx']
- line['offset'] = p1.y - line['slope'] * p1.x
+ line["dx"] = p2.x - p1.x
+ line["dy"] = p2.y - p1.y
+ line["slope"] = line["dy"] / line["dx"]
+ line["offset"] = p1.y - line["slope"] * p1.x
return line
@@ -65,7 +65,7 @@ def determinant(mat, n):
It recursively expands the minors.
"""
matTemp = [[0.0, 0.0, 0.0], [0.0, 0.0, 0.0], [0.0, 0.0, 0.0]]
- if (n > 1):
+ if n > 1:
if n == 2:
d = mat[0][0] * mat[1][1] - mat[1][0] * mat[0][1]
else:
@@ -77,12 +77,12 @@ def determinant(mat, n):
for j in range(n):
if j == j1:
continue
- matTemp[i-1][j2] = mat[i][j]
+ matTemp[i - 1][j2] = mat[i][j]
j2 += 1
- d += ((-1.0)**(1.0 + j1 + 1.0)
- * mat[0][j1] * determinant(matTemp, n-1))
+ d += (-1.0) ** (1.0 + j1 + 1.0) * mat[0][j1] * determinant(matTemp, n - 1)
return d
else:
return 0
+
## @}
diff --git a/src/Mod/Draft/draftgeoutils/offsets.py b/src/Mod/Draft/draftgeoutils/offsets.py
index e09ba1ddec..564d22e4e1 100644
--- a/src/Mod/Draft/draftgeoutils/offsets.py
+++ b/src/Mod/Draft/draftgeoutils/offsets.py
@@ -80,9 +80,7 @@ def pocket2d(shape, offset):
if len(innerWire.Edges) == 1:
e = innerWire.Edges[0]
if isinstance(e.Curve, Part.Circle):
- e = Part.makeCircle(e.Curve.Radius + offset,
- e.Curve.Center,
- e.Curve.Axis)
+ e = Part.makeCircle(e.Curve.Radius + offset, e.Curve.Center, e.Curve.Axis)
i = Part.Wire(e)
if i.Wires:
# print("offsetting island ", innerWire, " : ", i.Wires)
@@ -108,12 +106,14 @@ def pocket2d(shape, offset):
else:
a = w.BoundBox
b = ow.BoundBox
- if ((a.XMin <= b.XMin)
- and (a.YMin <= b.YMin)
- and (a.ZMin <= b.ZMin)
- and (a.XMax >= b.XMax)
- and (a.YMax >= b.YMax)
- and (a.ZMax >= b.ZMax)):
+ if (
+ (a.XMin <= b.XMin)
+ and (a.YMin <= b.YMin)
+ and (a.ZMin <= b.ZMin)
+ and (a.XMax >= b.XMax)
+ and (a.YMax >= b.YMax)
+ and (a.ZMax >= b.ZMax)
+ ):
# print("this wire is bigger than "
# "the outer wire")
offsetWires[j] = None
@@ -151,8 +151,7 @@ def offset(edge, vector, trim=False):
Part.Shape
The offset shape
"""
- if (not isinstance(edge, Part.Shape)
- or not isinstance(vector, App.Vector)):
+ if not isinstance(edge, Part.Shape) or not isinstance(vector, App.Vector):
return None
if geomType(edge) == "Line":
@@ -165,27 +164,34 @@ def offset(edge, vector, trim=False):
curve = Part.Circle(edge.Curve)
curve.Radius = App.Vector.add(rad, vector).Length
if trim:
- return Part.ArcOfCircle(curve,
- edge.FirstParameter,
- edge.LastParameter).toShape()
+ return Part.ArcOfCircle(curve, edge.FirstParameter, edge.LastParameter).toShape()
elif geomType(edge) == "Ellipse":
rad = edge.Vertexes[0].Point.sub(edge.Curve.Center)
curve = edge.Curve.copy()
if vector.getAngle(rad) < 1:
- curve.MajorRadius = curve.MajorRadius+vector.Length
- curve.MinorRadius = curve.MinorRadius+vector.Length
+ curve.MajorRadius = curve.MajorRadius + vector.Length
+ curve.MinorRadius = curve.MinorRadius + vector.Length
else:
- curve.MajorRadius = curve.MajorRadius-vector.Length
- curve.MinorRadius = curve.MinorRadius-vector.Length
+ curve.MajorRadius = curve.MajorRadius - vector.Length
+ curve.MinorRadius = curve.MinorRadius - vector.Length
return curve.toShape()
else:
return None
-def offsetWire(wire, dvec, bind=False, occ=False,
- widthList=None, offsetMode=None, alignList=[],
- normal=None, basewireOffset=0, wireNedge=False):
- # normal=None, basewireOffset=0):
+def offsetWire(
+ wire,
+ dvec,
+ bind=False,
+ occ=False,
+ widthList=None,
+ offsetMode=None,
+ alignList=[],
+ normal=None,
+ basewireOffset=0,
+ wireNedge=False,
+):
+ # normal=None, basewireOffset=0):
"""Offset the wire along the given vector.
Parameters
@@ -244,8 +250,7 @@ def offsetWire(wire, dvec, bind=False, occ=False,
edges = [wire]
closed = wire.isClosed()
else:
- print("Either Part.Wire or Part.Edges should be provided, "
- "returning None")
+ print("Either Part.Wire or Part.Edges should be provided, " "returning None")
return None
# For sketch with a number of wires, getNormal() may result
@@ -291,15 +296,15 @@ def offsetWire(wire, dvec, bind=False, occ=False,
# Check the direction / offset of starting edge
firstDir = None
try:
- if alignListC[0] == 'Left':
+ if alignListC[0] == "Left":
firstDir = 1
- firstAlign = 'Left'
- elif alignListC[0] == 'Right':
+ firstAlign = "Left"
+ elif alignListC[0] == "Right":
firstDir = -1
- firstAlign = 'Right'
- elif alignListC[0] == 'Center':
+ firstAlign = "Right"
+ elif alignListC[0] == "Center":
firstDir = 1
- firstAlign = 'Center'
+ firstAlign = "Center"
except IndexError:
# Should no longer happen for ArchWall
# as aligns are 'filled in' by ArchWall
@@ -312,7 +317,7 @@ def offsetWire(wire, dvec, bind=False, occ=False,
# ('legacy/backward-compatible' mode)
if not firstDir:
# need to test against Part.Circle, not Part.ArcOfCircle
- if isinstance(e.Curve, (Part.Circle,Part.Ellipse)):
+ if isinstance(e.Curve, (Part.Circle, Part.Ellipse)):
v0 = e.tangentAt(e.FirstParameter).cross(norm)
else:
v0 = vec(e).cross(norm)
@@ -324,17 +329,17 @@ def offsetWire(wire, dvec, bind=False, occ=False,
if v0.isEqual(v1, 0.0001):
# "Left Offset" (Left Align or 'left offset' in Centre Align)
firstDir = 1
- firstAlign = 'Left'
- alignListC.append('Left')
+ firstAlign = "Left"
+ alignListC.append("Left")
elif v0.isEqual(v1.negative(), 0.0001):
# "Right Offset" (Right Align or 'right offset' in Centre Align)
firstDir = -1
- firstAlign = 'Right'
- alignListC.append('Right')
+ firstAlign = "Right"
+ alignListC.append("Right")
else:
print(" something wrong with firstDir ")
- firstAlign = 'Left'
- alignListC.append('Left')
+ firstAlign = "Left"
+ alignListC.append("Left")
if not isinstance(basewireOffset, list):
basewireOffset = [basewireOffset]
@@ -357,9 +362,9 @@ def offsetWire(wire, dvec, bind=False, occ=False,
# record current edge's Orientation, and set Delta
if i != 0: # else:
# TODO Should also calculate 1st edge direction above
- if isinstance(curredge.Curve, (Part.Circle,Part.Ellipse)):
- # Seems Circle/Ellipse (1 geometry) would be sorted in 1 list,
- # so i=0; should not happen here in fact (i != 0). 2024.8.25.
+ if isinstance(curredge.Curve, (Part.Circle, Part.Ellipse)):
+ # Seems Circle/Ellipse (1 geometry) would be sorted in 1 list,
+ # so i=0; should not happen here in fact (i != 0). 2024.8.25.
delta = curredge.tangentAt(curredge.FirstParameter).cross(norm)
else:
delta = vec(curredge).cross(norm)
@@ -396,31 +401,31 @@ def offsetWire(wire, dvec, bind=False, occ=False,
# Consider individual edge Align direction
# - ArchWall should now always provide alignList
if i == 0:
- if alignListC[0] == 'Center':
- delta = DraftVecUtils.scaleTo(delta, delta.Length/2)
+ if alignListC[0] == "Center":
+ delta = DraftVecUtils.scaleTo(delta, delta.Length / 2)
# No need to do anything for 'Left' and 'Right' as original dvec
# have set both the direction and amount of offset correct
# elif alignListC[i] == 'Left': #elif alignListC[i] == 'Right':
if i != 0:
try:
- if alignListC[i] == 'Left':
+ if alignListC[i] == "Left":
curDir = 1
- curAlign = 'Left'
- elif alignListC[i] == 'Right':
+ curAlign = "Left"
+ elif alignListC[i] == "Right":
curDir = -1
- curAlign = 'Right'
+ curAlign = "Right"
delta = delta.negative()
- elif alignListC[i] == 'Center':
+ elif alignListC[i] == "Center":
curDir = 1
- curAlign = 'Center'
- delta = DraftVecUtils.scaleTo(delta, delta.Length/2)
+ curAlign = "Center"
+ delta = DraftVecUtils.scaleTo(delta, delta.Length / 2)
except IndexError:
curDir = firstDir
curAlign = firstAlign
- if firstAlign == 'Right':
+ if firstAlign == "Right":
delta = delta.negative()
- elif firstAlign == 'Center':
- delta = DraftVecUtils.scaleTo(delta, delta.Length/2)
+ elif firstAlign == "Center":
+ delta = DraftVecUtils.scaleTo(delta, delta.Length / 2)
# Consider whether generating the 'offset wire' or the 'base wire'
if offsetMode is None:
@@ -430,16 +435,16 @@ def offsetWire(wire, dvec, bind=False, occ=False,
# This is a xor
if (curOrientation == firstOrientation) != (curDir == firstDir):
- if curAlign in ['Left', 'Right']:
+ if curAlign in ["Left", "Right"]:
# ArchWall has an Offset properties for user to offset
# the basewire before creating the base profile of wall
# (not applicable to 'Center' align)
if currOffset:
delta = DraftVecUtils.scaleTo(delta, currOffset)
- nedge = offset(curredge,delta,trim=True)
+ nedge = offset(curredge, delta, trim=True)
else:
nedge = curredge
- elif curAlign == 'Center':
+ elif curAlign == "Center":
delta = delta.negative()
nedge = offset(curredge, delta, trim=True)
else:
@@ -449,32 +454,32 @@ def offsetWire(wire, dvec, bind=False, occ=False,
# the basewire before creating the base profile of wall
# (not applicable to 'Center' align)
if currOffset:
- if curAlign in ['Left', 'Right']:
- delta = DraftVecUtils.scaleTo(delta,
- delta.Length + currOffset)
+ if curAlign in ["Left", "Right"]:
+ delta = DraftVecUtils.scaleTo(delta, delta.Length + currOffset)
nedge = offset(curredge, delta, trim=True)
# TODO arc always in counter-clockwise directinon
# ... ( not necessarily 'reversed')
if curOrientation == "Reversed":
- if not isinstance(curredge.Curve, (Part.Circle,Part.Ellipse)):
+ if not isinstance(curredge.Curve, (Part.Circle, Part.Ellipse)):
# assume straight line, reverse it
nedge = Part.Edge(nedge.Vertexes[1], nedge.Vertexes[0])
elif nedge.isClosed():
pass
else:
- midParameter = nedge.FirstParameter + (nedge.LastParameter - nedge.FirstParameter)/2
+ midParameter = (
+ nedge.FirstParameter + (nedge.LastParameter - nedge.FirstParameter) / 2
+ )
midOfArc = nedge.valueAt(midParameter)
- nedge = Part.ArcOfCircle(nedge.Vertexes[1].Point,
- midOfArc,
- nedge.Vertexes[0].Point).toShape()
+ nedge = Part.ArcOfCircle(
+ nedge.Vertexes[1].Point, midOfArc, nedge.Vertexes[0].Point
+ ).toShape()
# TODO any better solution than to calculate midpoint
# of arc to reverse?
elif offsetMode in ["BasewireMode"]:
- if (not (curOrientation == firstOrientation)
- != (curDir == firstDir)):
- if curAlign in ['Left', 'Right']:
+ if not (curOrientation == firstOrientation) != (curDir == firstDir):
+ if curAlign in ["Left", "Right"]:
# ArchWall has an Offset properties for user to offset
# the basewire before creating the base profile of wall
# (not applicable to 'Center' align)
@@ -483,32 +488,33 @@ def offsetWire(wire, dvec, bind=False, occ=False,
nedge = offset(curredge, delta, trim=True)
else:
nedge = curredge
- elif curAlign == 'Center':
+ elif curAlign == "Center":
delta = delta.negative()
nedge = offset(curredge, delta, trim=True)
else:
- if curAlign in ['Left', 'Right']:
+ if curAlign in ["Left", "Right"]:
# ArchWall has an Offset properties for user to offset
# the basewire before creating the base profile of wall
# (not applicable to 'Center' align)
if currOffset:
- delta = DraftVecUtils.scaleTo(delta,
- delta.Length + currOffset)
+ delta = DraftVecUtils.scaleTo(delta, delta.Length + currOffset)
nedge = offset(curredge, delta, trim=True)
- elif curAlign == 'Center':
+ elif curAlign == "Center":
nedge = offset(curredge, delta, trim=True)
if curOrientation == "Reversed":
- if not isinstance(curredge.Curve, (Part.Circle,Part.Ellipse)):
+ if not isinstance(curredge.Curve, (Part.Circle, Part.Ellipse)):
# assume straight line, reverse it
nedge = Part.Edge(nedge.Vertexes[1], nedge.Vertexes[0])
elif nedge.isClosed():
pass
else:
- midParameter = nedge.FirstParameter + (nedge.LastParameter - nedge.FirstParameter)/2
+ midParameter = (
+ nedge.FirstParameter + (nedge.LastParameter - nedge.FirstParameter) / 2
+ )
midOfArc = nedge.valueAt(midParameter)
- nedge = Part.ArcOfCircle(nedge.Vertexes[1].Point,
- midOfArc,
- nedge.Vertexes[0].Point).toShape()
+ nedge = Part.ArcOfCircle(
+ nedge.Vertexes[1].Point, midOfArc, nedge.Vertexes[0].Point
+ ).toShape()
# TODO any better solution than to calculate midpoint
# of arc to reverse?
else:
@@ -523,7 +529,7 @@ def offsetWire(wire, dvec, bind=False, occ=False,
if len(edges) > 1:
# TODO May phase out wire if bind() can do without it later and do with
# only connectEdges so no need bind() to find 'touching edges' there
- wire,connectEdgesF,connectEdges = connect(nedges,closed,wireNedge=True)
+ wire, connectEdgesF, connectEdges = connect(nedges, closed, wireNedge=True)
else:
# TODO May phase out wire if bind() can do without it later and do with
# only connectEdges so no need bind() to find 'touching edges' there
@@ -531,19 +537,18 @@ def offsetWire(wire, dvec, bind=False, occ=False,
connectEdgesF = connectEdges = nedges # nedges[0]
if bind and not closed:
- e1 = Part.LineSegment(edges[0].Vertexes[0].Point,
- wire[0].Vertexes[0].Point).toShape()
- e2 = Part.LineSegment(edges[-1].Vertexes[-1].Point,
- wire[-1].Vertexes[-1].Point).toShape()
- #nedges[-1].Vertexes[-1].Point).toShape()
+ e1 = Part.LineSegment(edges[0].Vertexes[0].Point, wire[0].Vertexes[0].Point).toShape()
+ e2 = Part.LineSegment(edges[-1].Vertexes[-1].Point, wire[-1].Vertexes[-1].Point).toShape()
+ # nedges[-1].Vertexes[-1].Point).toShape()
alledges = edges.extend(nedges) # TODO nedges is a wire or are edges?
alledges = alledges.extend([e1, e2])
w = Part.Wire(alledges)
return w
else:
if wireNedge:
- return (wire,connectEdgesF,connectEdges,nedges)
+ return (wire, connectEdgesF, connectEdges, nedges)
else:
return wire
+
## @}
diff --git a/src/Mod/Draft/draftgeoutils/sort_edges.py b/src/Mod/Draft/draftgeoutils/sort_edges.py
index 9f9e0c7eab..3862f86e04 100644
--- a/src/Mod/Draft/draftgeoutils/sort_edges.py
+++ b/src/Mod/Draft/draftgeoutils/sort_edges.py
@@ -142,10 +142,10 @@ def sortEdgesOld(lEdges, aVertex=None):
linstances = [] # lists the instances of aVertex
for i in range(len(inEdges)):
for j in range(2):
- if aVertex.Point == inEdges[i].Vertexes[j-1].Point:
+ if aVertex.Point == inEdges[i].Vertexes[j - 1].Point:
instance = inEdges[i]
count += 1
- linstances += [i, j-1, instance]
+ linstances += [i, j - 1, instance]
return [count] + linstances
if len(lEdges) < 2:
@@ -158,18 +158,22 @@ def sortEdgesOld(lEdges, aVertex=None):
return lEdges
else:
if geomType(result[3]) == "Line":
- return [Part.LineSegment(aVertex.Point,
- result[3].Vertexes[0].Point).toShape()]
+ return [
+ Part.LineSegment(aVertex.Point, result[3].Vertexes[0].Point).toShape()
+ ]
elif geomType(result[3]) == "Circle":
mp = findMidpoint(result[3])
- return [Part.Arc(aVertex.Point,
- mp,
- result[3].Vertexes[0].Point).toShape()]
- elif (geomType(result[3]) == "BSplineCurve"
- or geomType(result[3]) == "BezierCurve"):
+ return [Part.Arc(aVertex.Point, mp, result[3].Vertexes[0].Point).toShape()]
+ elif (
+ geomType(result[3]) == "BSplineCurve"
+ or geomType(result[3]) == "BezierCurve"
+ ):
if isLine(result[3].Curve):
- return [Part.LineSegment(aVertex.Point,
- result[3].Vertexes[0].Point).toShape()]
+ return [
+ Part.LineSegment(
+ aVertex.Point, result[3].Vertexes[0].Point
+ ).toShape()
+ ]
else:
return lEdges
else:
@@ -177,12 +181,11 @@ def sortEdgesOld(lEdges, aVertex=None):
olEdges = [] # ol stands for ordered list
if aVertex is None:
- for i in range(len(lEdges)*2):
- if len(lEdges[i/2].Vertexes) > 1:
- result = lookfor(lEdges[i/2].Vertexes[i % 2], lEdges)
+ for i in range(len(lEdges) * 2):
+ if len(lEdges[i / 2].Vertexes) > 1:
+ result = lookfor(lEdges[i / 2].Vertexes[i % 2], lEdges)
if result[0] == 1: # Have we found an end ?
- olEdges = sortEdgesOld(lEdges,
- result[3].Vertexes[result[2]])
+ olEdges = sortEdgesOld(lEdges, result[3].Vertexes[result[2]])
return olEdges
# if the wire is closed there is no end so choose 1st Vertex
# print("closed wire, starting from ",lEdges[0].Vertexes[0].Point)
@@ -192,8 +195,7 @@ def sortEdgesOld(lEdges, aVertex=None):
result = lookfor(aVertex, lEdges)
if result[0] != 0:
del lEdges[result[1]]
- _next = sortEdgesOld(lEdges,
- result[3].Vertexes[-((-result[2])^1)])
+ _next = sortEdgesOld(lEdges, result[3].Vertexes[-((-result[2]) ^ 1)])
# print("result ", result[3].Vertexes[0].Point, " ",
# result[3].Vertexes[1].Point, " compared to ",aVertex.Point)
if aVertex.Point == result[3].Vertexes[0].Point:
@@ -202,20 +204,17 @@ def sortEdgesOld(lEdges, aVertex=None):
else:
# print("inverting", result[3].Curve)
if geomType(result[3]) == "Line":
- newedge = Part.LineSegment(aVertex.Point,
- result[3].Vertexes[0].Point).toShape()
+ newedge = Part.LineSegment(aVertex.Point, result[3].Vertexes[0].Point).toShape()
olEdges += [newedge] + _next
elif geomType(result[3]) == "Circle":
mp = findMidpoint(result[3])
- newedge = Part.Arc(aVertex.Point,
- mp,
- result[3].Vertexes[0].Point).toShape()
+ newedge = Part.Arc(aVertex.Point, mp, result[3].Vertexes[0].Point).toShape()
olEdges += [newedge] + _next
- elif (geomType(result[3]) == "BSplineCurve"
- or geomType(result[3]) == "BezierCurve"):
+ elif geomType(result[3]) == "BSplineCurve" or geomType(result[3]) == "BezierCurve":
if isLine(result[3].Curve):
- newedge = Part.LineSegment(aVertex.Point,
- result[3].Vertexes[0].Point).toShape()
+ newedge = Part.LineSegment(
+ aVertex.Point, result[3].Vertexes[0].Point
+ ).toShape()
olEdges += [newedge] + _next
else:
olEdges += [result[3]] + _next
@@ -225,4 +224,5 @@ def sortEdgesOld(lEdges, aVertex=None):
else:
return []
+
## @}
diff --git a/src/Mod/Draft/draftgeoutils/wires.py b/src/Mod/Draft/draftgeoutils/wires.py
index 751f29de52..cdda3a87e7 100644
--- a/src/Mod/Draft/draftgeoutils/wires.py
+++ b/src/Mod/Draft/draftgeoutils/wires.py
@@ -59,17 +59,13 @@ def findWiresOld2(edgeslist):
return False
if len(e2.Vertexes) < 2:
return False
- if DraftVecUtils.equals(e1.Vertexes[0].Point,
- e2.Vertexes[0].Point):
+ if DraftVecUtils.equals(e1.Vertexes[0].Point, e2.Vertexes[0].Point):
return True
- if DraftVecUtils.equals(e1.Vertexes[0].Point,
- e2.Vertexes[-1].Point):
+ if DraftVecUtils.equals(e1.Vertexes[0].Point, e2.Vertexes[-1].Point):
return True
- if DraftVecUtils.equals(e1.Vertexes[-1].Point,
- e2.Vertexes[0].Point):
+ if DraftVecUtils.equals(e1.Vertexes[-1].Point, e2.Vertexes[0].Point):
return True
- if DraftVecUtils.equals(e1.Vertexes[-1].Point,
- e2.Vertexes[-1].Point):
+ if DraftVecUtils.equals(e1.Vertexes[-1].Point, e2.Vertexes[-1].Point):
return True
return False
@@ -119,12 +115,12 @@ def findWiresOld(edges):
Find connected edges in the list.
"""
- raise DeprecationWarning("This function shouldn't be called anymore. "
- "Use findWires() instead")
+ raise DeprecationWarning(
+ "This function shouldn't be called anymore. " "Use findWires() instead"
+ )
def verts(shape):
- return [shape.Vertexes[0].Point,
- shape.Vertexes[-1].Point]
+ return [shape.Vertexes[0].Point, shape.Vertexes[-1].Point]
def group(shapes):
shapesIn = shapes[:]
@@ -138,8 +134,7 @@ def findWiresOld(edges):
for v in verts(s):
for i in range(len(shapesOut)):
if clean and (v in verts(shapesOut[i])):
- shapesOut[i] = Part.Wire(shapesOut[i].Edges
- + s.Edges)
+ shapesOut[i] = Part.Wire(shapesOut[i].Edges + s.Edges)
changed = True
clean = False
if clean:
@@ -184,6 +179,7 @@ def superWire(edgeslist, closed=False):
Forces a wire between edges that don't necessarily
have coincident endpoints. If closed=True, the wire will always be closed.
"""
+
def median(v1, v2):
vd = v2.sub(v1)
vd.scale(0.5, 0.5, 0.5)
@@ -209,7 +205,7 @@ def superWire(edgeslist, closed=False):
else:
_next = None
else:
- _next = edges[i+1]
+ _next = edges[i + 1]
print(i, prev, curr, _next)
@@ -290,7 +286,7 @@ def rebaseWire(wire, vidx=0):
return wire
# This can be done in one step
- return Part.Wire(wire.Edges[vidx-1:] + wire.Edges[:vidx-1])
+ return Part.Wire(wire.Edges[vidx - 1 :] + wire.Edges[: vidx - 1])
def removeInterVertices(wire):
@@ -348,8 +344,7 @@ def cleanProjection(shape, tessellate=True, seglength=0.05):
newedges.append(e)
elif typ in ["BSplineCurve", "BezierCurve"]:
if isLine(e.Curve):
- line = Part.LineSegment(e.Vertexes[0].Point,
- e.Vertexes[-1].Point)
+ line = Part.LineSegment(e.Vertexes[0].Point, e.Vertexes[-1].Point)
newedges.append(line)
elif tessellate:
newedges.append(Part.Wire(curvetowire(e, seglength)))
@@ -387,6 +382,7 @@ def tessellateProjection(shape, seglen):
return Part.makeCompound(newedges)
+
def get_placement_perpendicular_to_wire(wire):
"""Return the placement whose base is the wire's first vertex and it's z axis aligned to the wire's tangent."""
pl = App.Placement()
@@ -399,7 +395,9 @@ def get_placement_perpendicular_to_wire(wire):
zaxis = first_edge.tangentAt(first_edge.LastParameter)
pl.Rotation = App.Rotation(App.Vector(1, 0, 0), App.Vector(0, 0, 1), zaxis, "ZYX")
else:
- App.Console.PrintError("debug: get_placement_perpendicular_to_wire called with a zero-length wire.\n")
+ App.Console.PrintError(
+ "debug: get_placement_perpendicular_to_wire called with a zero-length wire.\n"
+ )
return pl
@@ -410,27 +408,33 @@ def get_extended_wire(wire, offset_start, offset_end):
get_extended_wire(wire, 0.0, 100.0) -> returns a copy of the wire extended by 100 mm after it's last vertex
"""
if min(offset_start, offset_end, offset_start + offset_end) <= -wire.Length:
- App.Console.PrintError("debug: get_extended_wire error, wire's length insufficient for trimming.\n")
+ App.Console.PrintError(
+ "debug: get_extended_wire error, wire's length insufficient for trimming.\n"
+ )
return wire
- if offset_start < 0: # Trim the wire from the first vertex
+ if offset_start < 0: # Trim the wire from the first vertex
offset_start = -offset_start
out_edges = []
for edge in wire.OrderedEdges:
- if offset_start >= edge.Length: # Remove entire edge
+ if offset_start >= edge.Length: # Remove entire edge
offset_start -= edge.Length
- elif round(offset_start, precision()) > 0: # Split edge, to remove the required length
+ elif round(offset_start, precision()) > 0: # Split edge, to remove the required length
if edge.Orientation == "Forward":
new_edge = edge.split(edge.getParameterByLength(offset_start)).OrderedEdges[1]
else:
- new_edge = edge.split(edge.getParameterByLength(edge.Length - offset_start)).OrderedEdges[0]
- new_edge.Placement = edge.Placement # Strangely, edge.split discards the placement and orientation
+ new_edge = edge.split(
+ edge.getParameterByLength(edge.Length - offset_start)
+ ).OrderedEdges[0]
+ new_edge.Placement = (
+ edge.Placement
+ ) # Strangely, edge.split discards the placement and orientation
new_edge.Orientation = edge.Orientation
out_edges.append(new_edge)
offset_start = 0
- else: # Keep the remaining entire edges
+ else: # Keep the remaining entire edges
out_edges.append(edge)
wire = Part.Wire(out_edges)
- elif offset_start > 0: # Extend the first edge along its normal
+ elif offset_start > 0: # Extend the first edge along its normal
first_edge = wire.OrderedEdges[0]
if first_edge.Orientation == "Forward":
start, end = first_edge.FirstParameter, first_edge.LastParameter
@@ -438,31 +442,39 @@ def get_extended_wire(wire, offset_start, offset_end):
else:
start, end = first_edge.LastParameter, first_edge.FirstParameter
vec = -first_edge.tangentAt(start).multiply(offset_start)
- if geomType(first_edge) == "Line": # Replace first edge with the extended new edge
- new_edge = Part.LineSegment(first_edge.valueAt(start).sub(vec), first_edge.valueAt(end)).toShape()
+ if geomType(first_edge) == "Line": # Replace first edge with the extended new edge
+ new_edge = Part.LineSegment(
+ first_edge.valueAt(start).sub(vec), first_edge.valueAt(end)
+ ).toShape()
wire = Part.Wire([new_edge] + wire.OrderedEdges[1:])
- else: # Add a straight edge before the first vertex
- new_edge = Part.LineSegment(first_edge.valueAt(start).sub(vec), first_edge.valueAt(start)).toShape()
+ else: # Add a straight edge before the first vertex
+ new_edge = Part.LineSegment(
+ first_edge.valueAt(start).sub(vec), first_edge.valueAt(start)
+ ).toShape()
wire = Part.Wire([new_edge] + wire.OrderedEdges)
- if offset_end < 0: # Trim the wire from the last vertex
+ if offset_end < 0: # Trim the wire from the last vertex
offset_end = -offset_end
out_edges = []
for edge in reversed(wire.OrderedEdges):
- if offset_end >= edge.Length: # Remove entire edge
+ if offset_end >= edge.Length: # Remove entire edge
offset_end -= edge.Length
- elif round(offset_end, precision()) > 0: # Split edge, to remove the required length
+ elif round(offset_end, precision()) > 0: # Split edge, to remove the required length
if edge.Orientation == "Forward":
- new_edge = edge.split(edge.getParameterByLength(edge.Length - offset_end)).OrderedEdges[0]
+ new_edge = edge.split(
+ edge.getParameterByLength(edge.Length - offset_end)
+ ).OrderedEdges[0]
else:
new_edge = edge.split(edge.getParameterByLength(offset_end)).OrderedEdges[1]
- new_edge.Placement = edge.Placement # Strangely, edge.split discards the placement and orientation
+ new_edge.Placement = (
+ edge.Placement
+ ) # Strangely, edge.split discards the placement and orientation
new_edge.Orientation = edge.Orientation
out_edges.insert(0, new_edge)
offset_end = 0
- else: # Keep the remaining entire edges
+ else: # Keep the remaining entire edges
out_edges.insert(0, edge)
wire = Part.Wire(out_edges)
- elif offset_end > 0: # Extend the last edge along its normal
+ elif offset_end > 0: # Extend the last edge along its normal
last_edge = wire.OrderedEdges[-1]
if last_edge.Orientation == "Forward":
start, end = last_edge.FirstParameter, last_edge.LastParameter
@@ -470,12 +482,17 @@ def get_extended_wire(wire, offset_start, offset_end):
else:
start, end = last_edge.LastParameter, last_edge.FirstParameter
vec = -last_edge.tangentAt(end).multiply(offset_end)
- if geomType(last_edge) == "Line": # Replace last edge with the extended new edge
- new_edge = Part.LineSegment(last_edge.valueAt(start), last_edge.valueAt(end).add(vec)).toShape()
+ if geomType(last_edge) == "Line": # Replace last edge with the extended new edge
+ new_edge = Part.LineSegment(
+ last_edge.valueAt(start), last_edge.valueAt(end).add(vec)
+ ).toShape()
wire = Part.Wire(wire.OrderedEdges[:-1] + [new_edge])
- else: # Add a straight edge after the last vertex
- new_edge = Part.LineSegment(last_edge.valueAt(end), last_edge.valueAt(end).add(vec)).toShape()
+ else: # Add a straight edge after the last vertex
+ new_edge = Part.LineSegment(
+ last_edge.valueAt(end), last_edge.valueAt(end).add(vec)
+ ).toShape()
wire = Part.Wire(wire.OrderedEdges + [new_edge])
return wire
+
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_annotationstyleeditor.py b/src/Mod/Draft/draftguitools/gui_annotationstyleeditor.py
index c7d801da1c..ec64a56496 100644
--- a/src/Mod/Draft/draftguitools/gui_annotationstyleeditor.py
+++ b/src/Mod/Draft/draftguitools/gui_annotationstyleeditor.py
@@ -63,7 +63,9 @@ class AnnotationStyleEditor(gui_base.GuiCommandSimplest):
"""
def __init__(self):
- super(AnnotationStyleEditor, self).__init__(name=translate("draft","Annotation Style Editor"))
+ super(AnnotationStyleEditor, self).__init__(
+ name=translate("draft", "Annotation Style Editor")
+ )
self.doc = None
self.styles = {}
self.renamed = {}
@@ -72,11 +74,14 @@ class AnnotationStyleEditor(gui_base.GuiCommandSimplest):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': ":icons/Draft_Annotation_Style.svg",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_AnnotationStyleEditor",
- "Annotation Styles"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_AnnotationStyleEditor",
- "Opens an editor to manage or create annotation styles")}
+ return {
+ "Pixmap": ":icons/Draft_Annotation_Style.svg",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_AnnotationStyleEditor", "Annotation Styles"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_AnnotationStyleEditor",
+ "Opens an editor to manage or create annotation styles",
+ ),
+ }
def Activated(self):
"""Execute when the command is called.
@@ -99,9 +104,9 @@ class AnnotationStyleEditor(gui_base.GuiCommandSimplest):
# center the dialog over FreeCAD window
mw = Gui.getMainWindow()
- self.form.move(mw.frameGeometry().topLeft()
- + mw.rect().center()
- - self.form.rect().center())
+ self.form.move(
+ mw.frameGeometry().topLeft() + mw.rect().center() - self.form.rect().center()
+ )
# set icons
self.form.setWindowIcon(QtGui.QIcon(":/icons/Draft_Annotation_Style.svg"))
@@ -156,8 +161,7 @@ class AnnotationStyleEditor(gui_base.GuiCommandSimplest):
strvalue = json.dumps(value)
except Exception:
print("debug: unable to serialize this:", value)
- if ("Draft_Style_" + key in meta
- and meta["Draft_Style_" + key] != strvalue):
+ if "Draft_Style_" + key in meta and meta["Draft_Style_" + key] != strvalue:
changedstyles.append(key)
meta["Draft_Style_" + key] = strvalue
@@ -184,7 +188,10 @@ class AnnotationStyleEditor(gui_base.GuiCommandSimplest):
if vobj.AnnotationStyle in self.renamed:
# the style has been renamed
# temporarily add the new style and switch to it
- vobj.AnnotationStyle = [vobj.AnnotationStyle, self.renamed[vobj.AnnotationStyle]]
+ vobj.AnnotationStyle = [
+ vobj.AnnotationStyle,
+ self.renamed[vobj.AnnotationStyle],
+ ]
vobj.AnnotationStyle = self.renamed[vobj.AnnotationStyle]
if vobj.AnnotationStyle in styles:
if vobj.AnnotationStyle in changedstyles:
@@ -210,21 +217,25 @@ class AnnotationStyleEditor(gui_base.GuiCommandSimplest):
self.form.pushButtonRename.setEnabled(False)
elif index == 1:
# Add new... entry
- reply = QtWidgets.QInputDialog.getText(None,
- translate("draft", "New Style"),
- translate("draft", "Style name"))
+ reply = QtWidgets.QInputDialog.getText(
+ None, translate("draft", "New Style"), translate("draft", "Style name")
+ )
if reply[1]:
# OK or Enter pressed
name = reply[0].strip()
if name == "":
- QtWidgets.QMessageBox.information(None,
- translate("draft", "Style name required"),
- translate("draft", "No style name specified"))
+ QtWidgets.QMessageBox.information(
+ None,
+ translate("draft", "Style name required"),
+ translate("draft", "No style name specified"),
+ )
self.form.comboBoxStyles.setCurrentIndex(0)
elif name in self.styles:
- QtWidgets.QMessageBox.information(None,
- translate("draft", "Style exists"),
- translate("draft", "This style name already exists"))
+ QtWidgets.QMessageBox.information(
+ None,
+ translate("draft", "Style exists"),
+ translate("draft", "This style name already exists"),
+ )
self.form.comboBoxStyles.setCurrentIndex(0)
else:
# create new style from current editor values
@@ -251,11 +262,13 @@ class AnnotationStyleEditor(gui_base.GuiCommandSimplest):
style = self.form.comboBoxStyles.itemText(index)
if self.get_style_users(style):
- reply = QtWidgets.QMessageBox.question(None,
- translate("draft", "Style in use"),
- translate("draft", "This style is used by some objects in this document. Proceed?"),
- QtWidgets.QMessageBox.Yes | QtWidgets.QMessageBox.No,
- QtWidgets.QMessageBox.No)
+ reply = QtWidgets.QMessageBox.question(
+ None,
+ translate("draft", "Style in use"),
+ translate("draft", "This style is used by some objects in this document. Proceed?"),
+ QtWidgets.QMessageBox.Yes | QtWidgets.QMessageBox.No,
+ QtWidgets.QMessageBox.No,
+ )
if reply == QtWidgets.QMessageBox.No:
return
@@ -277,18 +290,22 @@ class AnnotationStyleEditor(gui_base.GuiCommandSimplest):
index = self.form.comboBoxStyles.currentIndex()
style = self.form.comboBoxStyles.itemText(index)
- reply = QtWidgets.QInputDialog.getText(None,
- translate("draft", "Rename Style"),
- translate("draft", "New name"),
- QtWidgets.QLineEdit.Normal,
- style)
+ reply = QtWidgets.QInputDialog.getText(
+ None,
+ translate("draft", "Rename Style"),
+ translate("draft", "New name"),
+ QtWidgets.QLineEdit.Normal,
+ style,
+ )
if reply[1]:
# OK or Enter pressed
newname = reply[0]
if newname in self.styles:
- reply = QtWidgets.QMessageBox.information(None,
- translate("draft", "Style exists"),
- translate("draft", "This style name already exists"))
+ reply = QtWidgets.QMessageBox.information(
+ None,
+ translate("draft", "Style exists"),
+ translate("draft", "This style name already exists"),
+ )
else:
self.form.comboBoxStyles.setItemText(index, newname)
value = self.styles[style]
@@ -301,9 +318,10 @@ class AnnotationStyleEditor(gui_base.GuiCommandSimplest):
"""Import styles from a json file."""
filename = QtWidgets.QFileDialog.getOpenFileName(
QtWidgets.QApplication.activeWindow(),
- translate("draft","Open Styles File"),
+ translate("draft", "Open Styles File"),
None,
- translate("draft","JSON files (*.json *.JSON)"))
+ translate("draft", "JSON files (*.json *.JSON)"),
+ )
if filename and filename[0]:
nstyles = {}
with open(filename[0]) as f:
@@ -314,20 +332,21 @@ class AnnotationStyleEditor(gui_base.GuiCommandSimplest):
for style in self.styles.keys():
if self.form.comboBoxStyles.findText(style) == -1:
self.form.comboBoxStyles.addItem(style)
- self.fill_editor(self.current_style) # The current style may have changed.
+ self.fill_editor(self.current_style) # The current style may have changed.
print("Styles updated from " + filename[0])
def on_export(self):
"""Export styles to a json file."""
filename = QtWidgets.QFileDialog.getSaveFileName(
QtWidgets.QApplication.activeWindow(),
- translate("draft","Save Styles File"),
+ translate("draft", "Save Styles File"),
None,
- translate("draft","JSON file (*.json)"))
+ translate("draft", "JSON file (*.json)"),
+ )
if filename and filename[0]:
self.update_style()
- with open(filename[0],"w") as f:
- json.dump(self.styles,f,indent=4)
+ with open(filename[0], "w") as f:
+ json.dump(self.styles, f, indent=4)
print("Styles saved to " + filename[0])
def fill_editor(self, style=None):
@@ -414,6 +433,6 @@ class AnnotationStyleEditor(gui_base.GuiCommandSimplest):
return users
-Gui.addCommand('Draft_AnnotationStyleEditor', AnnotationStyleEditor())
+Gui.addCommand("Draft_AnnotationStyleEditor", AnnotationStyleEditor())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_arcs.py b/src/Mod/Draft/draftguitools/gui_arcs.py
index 3eae3114e6..26a3aa0e15 100644
--- a/src/Mod/Draft/draftguitools/gui_arcs.py
+++ b/src/Mod/Draft/draftguitools/gui_arcs.py
@@ -58,10 +58,14 @@ class Arc(gui_base_original.Creator):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_Arc",
- "Accel": "A, R",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Arc", "Arc"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Arc", "Creates a circular arc from a center point and a radius")}
+ return {
+ "Pixmap": "Draft_Arc",
+ "Accel": "A, R",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Arc", "Arc"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Arc", "Creates a circular arc from a center point and a radius"
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -149,8 +153,7 @@ class Arc(gui_base_original.Creator):
self.point, ctrlPoint, info = gui_tool_utils.getPoint(self, arg)
# this is to make sure radius is what you see on screen
if self.center and DraftVecUtils.dist(self.point, self.center) > 0:
- viewdelta = DraftVecUtils.project(self.point.sub(self.center),
- self.wp.axis)
+ viewdelta = DraftVecUtils.project(self.point.sub(self.center), self.wp.axis)
if not DraftVecUtils.isNull(viewdelta):
self.point = self.point.add(viewdelta.negative())
if self.step == 0: # choose center
@@ -164,16 +167,16 @@ class Arc(gui_base_original.Creator):
self.ui.switchUi(False)
elif self.step == 1: # choose radius
if len(self.tangents) == 2:
- cir = DraftGeomUtils.circleFrom2tan1pt(self.tangents[0],
- self.tangents[1],
- self.point)
+ cir = DraftGeomUtils.circleFrom2tan1pt(
+ self.tangents[0], self.tangents[1], self.point
+ )
_c = DraftGeomUtils.findClosestCircle(self.point, cir)
self.center = _c.Center
self.arctrack.setCenter(self.center)
elif self.tangents and self.tanpoints:
- cir = DraftGeomUtils.circleFrom1tan2pt(self.tangents[0],
- self.tanpoints[0],
- self.point)
+ cir = DraftGeomUtils.circleFrom1tan2pt(
+ self.tangents[0], self.tanpoints[0], self.point
+ )
_c = DraftGeomUtils.findClosestCircle(self.point, cir)
self.center = _c.Center
self.arctrack.setCenter(self.center)
@@ -181,19 +184,21 @@ class Arc(gui_base_original.Creator):
if not self.altdown:
self.altdown = True
if info:
- ob = self.doc.getObject(info['Object'])
- num = int(info['Component'].lstrip('Edge')) - 1
+ ob = self.doc.getObject(info["Object"])
+ num = int(info["Component"].lstrip("Edge")) - 1
ed = ob.Shape.Edges[num]
if len(self.tangents) == 2:
- cir = DraftGeomUtils.circleFrom3tan(self.tangents[0],
- self.tangents[1],
- ed)
+ cir = DraftGeomUtils.circleFrom3tan(
+ self.tangents[0], self.tangents[1], ed
+ )
cl = DraftGeomUtils.findClosestCircle(self.point, cir)
self.center = cl.Center
self.rad = cl.Radius
self.arctrack.setCenter(self.center)
else:
- self.rad = self.center.add(DraftGeomUtils.findDistance(self.center, ed).sub(self.center)).Length
+ self.rad = self.center.add(
+ DraftGeomUtils.findDistance(self.center, ed).sub(self.center)
+ ).Length
else:
self.rad = DraftVecUtils.dist(self.point, self.center)
else:
@@ -205,23 +210,31 @@ class Arc(gui_base_original.Creator):
self.linetrack.p1(self.center)
self.linetrack.p2(self.point)
self.linetrack.on()
- elif (self.step == 2): # choose first angle
+ elif self.step == 2: # choose first angle
currentrad = DraftVecUtils.dist(self.point, self.center)
if currentrad != 0:
- angle = DraftVecUtils.angle(self.wp.u, self.point.sub(self.center), self.wp.axis)
+ angle = DraftVecUtils.angle(
+ self.wp.u, self.point.sub(self.center), self.wp.axis
+ )
else:
angle = 0
- self.linetrack.p2(DraftVecUtils.scaleTo(self.point.sub(self.center), self.rad).add(self.center))
+ self.linetrack.p2(
+ DraftVecUtils.scaleTo(self.point.sub(self.center), self.rad).add(self.center)
+ )
self.ui.setRadiusValue(math.degrees(angle), unit="Angle")
self.firstangle = angle
else:
# choose second angle
currentrad = DraftVecUtils.dist(self.point, self.center)
if currentrad != 0:
- angle = DraftVecUtils.angle(self.wp.u, self.point.sub(self.center), self.wp.axis)
+ angle = DraftVecUtils.angle(
+ self.wp.u, self.point.sub(self.center), self.wp.axis
+ )
else:
angle = 0
- self.linetrack.p2(DraftVecUtils.scaleTo(self.point.sub(self.center), self.rad).add(self.center))
+ self.linetrack.p2(
+ DraftVecUtils.scaleTo(self.point.sub(self.center), self.rad).add(self.center)
+ )
self.updateAngle(angle)
self.ui.setRadiusValue(math.degrees(self.angle), unit="Angle")
self.arctrack.setApertureAngle(self.angle)
@@ -234,14 +247,14 @@ class Arc(gui_base_original.Creator):
if self.step == 0: # choose center
if not self.support:
gui_tool_utils.getSupport(arg)
- (self.point,
- ctrlPoint, info) = gui_tool_utils.getPoint(self, arg)
+ (self.point, ctrlPoint, info) = gui_tool_utils.getPoint(self, arg)
if gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key()):
- snapped = self.view.getObjectInfo((arg["Position"][0],
- arg["Position"][1]))
+ snapped = self.view.getObjectInfo(
+ (arg["Position"][0], arg["Position"][1])
+ )
if snapped:
- ob = self.doc.getObject(snapped['Object'])
- num = int(snapped['Component'].lstrip('Edge')) - 1
+ ob = self.doc.getObject(snapped["Object"])
+ num = int(snapped["Component"].lstrip("Edge")) - 1
ed = ob.Shape.Edges[num]
self.tangents.append(ed)
if len(self.tangents) == 2:
@@ -259,8 +272,9 @@ class Arc(gui_base_original.Creator):
self.node = [self.point]
self.arctrack.setCenter(self.center)
self.linetrack.p1(self.center)
- self.linetrack.p2(self.view.getPoint(arg["Position"][0],
- arg["Position"][1]))
+ self.linetrack.p2(
+ self.view.getPoint(arg["Position"][0], arg["Position"][1])
+ )
self.arctrack.on()
self.ui.radiusUi()
self.step = 1
@@ -283,9 +297,9 @@ class Arc(gui_base_original.Creator):
elif self.step == 2: # choose first angle
self.ui.labelRadius.setText(translate("draft", "Aperture angle"))
self.ui.radiusValue.setToolTip(translate("draft", "Aperture angle"))
- ang_offset = DraftVecUtils.angle(self.wp.u,
- self.arctrack.getDeviation(),
- self.wp.axis)
+ ang_offset = DraftVecUtils.angle(
+ self.wp.u, self.arctrack.getDeviation(), self.wp.axis
+ )
self.arctrack.setStartAngle(self.firstangle - ang_offset)
self.step = 3
_toolmsg(translate("draft", "Pick aperture"))
@@ -305,37 +319,39 @@ class Arc(gui_base_original.Creator):
if params.get_param("UsePartPrimitives"):
# Insert a Part::Primitive object
_base = DraftVecUtils.toString(self.center)
- _cmd = 'FreeCAD.ActiveDocument.'
+ _cmd = "FreeCAD.ActiveDocument."
_cmd += 'addObject("Part::Circle", "Circle")'
- _cmd_list = ['circle = ' + _cmd,
- 'circle.Radius = ' + str(self.rad),
- 'pl = FreeCAD.Placement()',
- 'pl.Rotation.Q = ' + rot,
- 'pl.Base = ' + _base,
- 'circle.Placement = pl',
- 'Draft.autogroup(circle)',
- 'Draft.select(circle)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Circle (Part)"),
- _cmd_list)
+ _cmd_list = [
+ "circle = " + _cmd,
+ "circle.Radius = " + str(self.rad),
+ "pl = FreeCAD.Placement()",
+ "pl.Rotation.Q = " + rot,
+ "pl.Base = " + _base,
+ "circle.Placement = pl",
+ "Draft.autogroup(circle)",
+ "Draft.select(circle)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Circle (Part)"), _cmd_list)
else:
# Insert a Draft circle
_base = DraftVecUtils.toString(self.center)
- _cmd = 'Draft.make_circle'
- _cmd += '('
- _cmd += 'radius=' + str(self.rad) + ', '
- _cmd += 'placement=pl, '
- _cmd += 'face=' + fil + ', '
- _cmd += 'support=' + sup
- _cmd += ')'
- _cmd_list = ['pl=FreeCAD.Placement()',
- 'pl.Rotation.Q=' + rot,
- 'pl.Base=' + _base,
- 'circle = ' + _cmd,
- 'Draft.autogroup(circle)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Circle"),
- _cmd_list)
+ _cmd = "Draft.make_circle"
+ _cmd += "("
+ _cmd += "radius=" + str(self.rad) + ", "
+ _cmd += "placement=pl, "
+ _cmd += "face=" + fil + ", "
+ _cmd += "support=" + sup
+ _cmd += ")"
+ _cmd_list = [
+ "pl=FreeCAD.Placement()",
+ "pl.Rotation.Q=" + rot,
+ "pl.Base=" + _base,
+ "circle = " + _cmd,
+ "Draft.autogroup(circle)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Circle"), _cmd_list)
except Exception:
_err("Draft: error delaying commit")
else:
@@ -352,41 +368,43 @@ class Arc(gui_base_original.Creator):
if params.get_param("UsePartPrimitives"):
# Insert a Part::Primitive object
_base = DraftVecUtils.toString(self.center)
- _cmd = 'FreeCAD.ActiveDocument.'
+ _cmd = "FreeCAD.ActiveDocument."
_cmd += 'addObject("Part::Circle", "Circle")'
- _cmd_list = ['circle = ' + _cmd,
- 'circle.Radius = ' + str(self.rad),
- 'circle.Angle1 = ' + str(sta),
- 'circle.Angle2 = ' + str(end),
- 'pl = FreeCAD.Placement()',
- 'pl.Rotation.Q = ' + rot,
- 'pl.Base = ' + _base,
- 'circle.Placement = pl',
- 'Draft.autogroup(circle)',
- 'Draft.select(circle)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Arc (Part)"),
- _cmd_list)
+ _cmd_list = [
+ "circle = " + _cmd,
+ "circle.Radius = " + str(self.rad),
+ "circle.Angle1 = " + str(sta),
+ "circle.Angle2 = " + str(end),
+ "pl = FreeCAD.Placement()",
+ "pl.Rotation.Q = " + rot,
+ "pl.Base = " + _base,
+ "circle.Placement = pl",
+ "Draft.autogroup(circle)",
+ "Draft.select(circle)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Arc (Part)"), _cmd_list)
else:
# Insert a Draft circle
_base = DraftVecUtils.toString(self.center)
- _cmd = 'Draft.make_circle'
- _cmd += '('
- _cmd += 'radius=' + str(self.rad) + ', '
- _cmd += 'placement=pl, '
- _cmd += 'face=' + fil + ', '
- _cmd += 'startangle=' + str(sta) + ', '
- _cmd += 'endangle=' + str(end) + ', '
- _cmd += 'support=' + sup
- _cmd += ')'
- _cmd_list = ['pl = FreeCAD.Placement()',
- 'pl.Rotation.Q = ' + rot,
- 'pl.Base = ' + _base,
- 'circle = ' + _cmd,
- 'Draft.autogroup(circle)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Arc"),
- _cmd_list)
+ _cmd = "Draft.make_circle"
+ _cmd += "("
+ _cmd += "radius=" + str(self.rad) + ", "
+ _cmd += "placement=pl, "
+ _cmd += "face=" + fil + ", "
+ _cmd += "startangle=" + str(sta) + ", "
+ _cmd += "endangle=" + str(end) + ", "
+ _cmd += "support=" + sup
+ _cmd += ")"
+ _cmd_list = [
+ "pl = FreeCAD.Placement()",
+ "pl.Rotation.Q = " + rot,
+ "pl.Base = " + _base,
+ "circle = " + _cmd,
+ "Draft.autogroup(circle)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Arc"), _cmd_list)
except Exception:
_err("Draft: error delaying commit")
@@ -420,18 +438,14 @@ class Arc(gui_base_original.Creator):
if self.step == 1:
self.rad = rad
if len(self.tangents) == 2:
- cir = DraftGeomUtils.circleFrom2tan1rad(self.tangents[0],
- self.tangents[1],
- rad)
+ cir = DraftGeomUtils.circleFrom2tan1rad(self.tangents[0], self.tangents[1], rad)
if self.center:
_c = DraftGeomUtils.findClosestCircle(self.center, cir)
self.center = _c.Center
else:
self.center = cir[-1].Center
elif self.tangents and self.tanpoints:
- cir = DraftGeomUtils.circleFrom1tan1pt1rad(self.tangents[0],
- self.tanpoints[0],
- rad)
+ cir = DraftGeomUtils.circleFrom1tan1pt1rad(self.tangents[0], self.tanpoints[0], rad)
if self.center:
_c = DraftGeomUtils.findClosestCircle(self.center, cir)
self.center = _c.Center
@@ -453,9 +467,7 @@ class Arc(gui_base_original.Creator):
self.ui.labelRadius.setText(translate("draft", "Aperture angle"))
self.ui.radiusValue.setToolTip(translate("draft", "Aperture angle"))
self.firstangle = math.radians(rad)
- ang_offset = DraftVecUtils.angle(self.wp.u,
- self.arctrack.getDeviation(),
- self.wp.axis)
+ ang_offset = DraftVecUtils.angle(self.wp.u, self.arctrack.getDeviation(), self.wp.axis)
self.arctrack.setStartAngle(self.firstangle - ang_offset)
self.step = 3
self.ui.radiusValue.setText("")
@@ -470,28 +482,24 @@ class Arc(gui_base_original.Creator):
def get_hints(self):
if self.step == 0:
- hints = [
- Gui.InputHint(translate("draft", "%1 pick center"), Gui.UserInput.MouseLeft)
- ]
+ hints = [Gui.InputHint(translate("draft", "%1 pick center"), Gui.UserInput.MouseLeft)]
elif self.step == 1:
- hints = [
- Gui.InputHint(translate("draft", "%1 pick radius"), Gui.UserInput.MouseLeft)
- ]
+ hints = [Gui.InputHint(translate("draft", "%1 pick radius"), Gui.UserInput.MouseLeft)]
elif self.step == 2:
hints = [
Gui.InputHint(translate("draft", "%1 pick start angle"), Gui.UserInput.MouseLeft)
]
else:
- hints = [
- Gui.InputHint(translate("draft", "%1 pick aperture"), Gui.UserInput.MouseLeft)
- ]
- return hints \
- + gui_tool_utils._get_hint_xyz_constrain() \
- + gui_tool_utils._get_hint_mod_constrain() \
+ hints = [Gui.InputHint(translate("draft", "%1 pick aperture"), Gui.UserInput.MouseLeft)]
+ return (
+ hints
+ + gui_tool_utils._get_hint_xyz_constrain()
+ + gui_tool_utils._get_hint_mod_constrain()
+ gui_tool_utils._get_hint_mod_snap()
+ )
-Gui.addCommand('Draft_Arc', Arc())
+Gui.addCommand("Draft_Arc", Arc())
class Arc_3Points(gui_base.GuiCommandBase):
@@ -502,10 +510,14 @@ class Arc_3Points(gui_base.GuiCommandBase):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_Arc_3Points",
- "Accel": "A, T",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Arc_3Points", "Arc From 3 Points"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Arc_3Points", "Creates a circular arc from 3 points")}
+ return {
+ "Pixmap": "Draft_Arc_3Points",
+ "Accel": "A, T",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Arc_3Points", "Arc From 3 Points"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Arc_3Points", "Creates a circular arc from 3 points"
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -521,13 +533,14 @@ class Arc_3Points(gui_base.GuiCommandBase):
# with the indicated callbacks: one for when the user clicks
# on the 3D view, and another for when the user moves the pointer.
import WorkingPlane
+
WorkingPlane.get_working_plane()
- Gui.Snapper.getPoint(callback=self.getPoint,
- movecallback=self.drawArc)
+ Gui.Snapper.getPoint(callback=self.getPoint, movecallback=self.drawArc)
Gui.Snapper.ui.sourceCmd = self
- Gui.Snapper.ui.setTitle(title=translate("draft", "Arc From 3 Points"),
- icon="Draft_Arc_3Points")
+ Gui.Snapper.ui.setTitle(
+ title=translate("draft", "Arc From 3 Points"), icon="Draft_Arc_3Points"
+ )
Gui.Snapper.ui.continueCmd.show()
self.update_hints()
@@ -567,12 +580,13 @@ class Arc_3Points(gui_base.GuiCommandBase):
# the arc tracker to show the preview of the final curve.
if len(self.points) == 2:
self.tracker.on()
- Gui.Snapper.getPoint(last=self.points[-1],
- callback=self.getPoint,
- movecallback=self.drawArc)
+ Gui.Snapper.getPoint(
+ last=self.points[-1], callback=self.getPoint, movecallback=self.drawArc
+ )
Gui.Snapper.ui.sourceCmd = self
- Gui.Snapper.ui.setTitle(title=translate("draft", "Arc From 3 Points"),
- icon="Draft_Arc_3Points")
+ Gui.Snapper.ui.setTitle(
+ title=translate("draft", "Arc From 3 Points"), icon="Draft_Arc_3Points"
+ )
Gui.Snapper.ui.continueCmd.show()
self.update_hints()
@@ -590,9 +604,11 @@ class Arc_3Points(gui_base.GuiCommandBase):
_cmd += ", placement=pl"
_cmd += ", primitive=" + str(params.get_param("UsePartPrimitives"))
_cmd += ")"
- _cmd_list = ["pl = WorkingPlane.get_working_plane().get_placement()",
- "circle = " + _cmd,
- "Draft.autogroup(circle)"]
+ _cmd_list = [
+ "pl = WorkingPlane.get_working_plane().get_placement()",
+ "circle = " + _cmd,
+ "Draft.autogroup(circle)",
+ ]
if params.get_param("UsePartPrimitives"):
_cmd_list.append("Draft.select(circle)")
_cmd_list.append("FreeCAD.ActiveDocument.recompute()")
@@ -615,9 +631,7 @@ class Arc_3Points(gui_base.GuiCommandBase):
"""
if len(self.points) == 2:
if point.sub(self.points[1]).Length > 0.001:
- self.tracker.setBy3Points(self.points[0],
- self.points[1],
- point)
+ self.tracker.setBy3Points(self.points[0], self.points[1], point)
def finish(self, cont=False):
"""Terminate the operation.
@@ -646,14 +660,16 @@ class Arc_3Points(gui_base.GuiCommandBase):
hints = [
Gui.InputHint(translate("draft", "%1 pick third point"), Gui.UserInput.MouseLeft)
]
- return hints \
- + gui_tool_utils._get_hint_xyz_constrain() \
- + gui_tool_utils._get_hint_mod_constrain() \
+ return (
+ hints
+ + gui_tool_utils._get_hint_xyz_constrain()
+ + gui_tool_utils._get_hint_mod_constrain()
+ gui_tool_utils._get_hint_mod_snap()
+ )
Draft_Arc_3Points = Arc_3Points
-Gui.addCommand('Draft_Arc_3Points', Arc_3Points())
+Gui.addCommand("Draft_Arc_3Points", Arc_3Points())
class ArcGroup:
@@ -661,18 +677,22 @@ class ArcGroup:
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"MenuText": QT_TRANSLATE_NOOP("Draft_ArcTools", "Arc Tools"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_ArcTools", "Tools to create various types of circular arcs")}
+ return {
+ "MenuText": QT_TRANSLATE_NOOP("Draft_ArcTools", "Arc Tools"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_ArcTools", "Tools to create various types of circular arcs"
+ ),
+ }
def GetCommands(self):
"""Return a tuple of commands in the group."""
- return ('Draft_Arc', 'Draft_Arc_3Points')
+ return ("Draft_Arc", "Draft_Arc_3Points")
def IsActive(self):
"""Return True when this command should be available."""
return bool(gui_utils.get_3d_view())
-Gui.addCommand('Draft_ArcTools', ArcGroup())
+Gui.addCommand("Draft_ArcTools", ArcGroup())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_arrays.py b/src/Mod/Draft/draftguitools/gui_arrays.py
index c98e5c399e..ced33555b1 100644
--- a/src/Mod/Draft/draftguitools/gui_arrays.py
+++ b/src/Mod/Draft/draftguitools/gui_arrays.py
@@ -53,24 +53,35 @@ class ArrayGroup:
def GetCommands(self):
"""Tuple of array commands."""
- return ("Draft_OrthoArray",
- "Draft_PolarArray", "Draft_CircularArray",
- "Draft_PathArray", "Draft_PathLinkArray",
- "Draft_PointArray", "Draft_PointLinkArray",
- "Draft_PathTwistedArray", "Draft_PathTwistedLinkArray")
+ return (
+ "Draft_OrthoArray",
+ "Draft_PolarArray",
+ "Draft_CircularArray",
+ "Draft_PathArray",
+ "Draft_PathLinkArray",
+ "Draft_PointArray",
+ "Draft_PointLinkArray",
+ "Draft_PathTwistedArray",
+ "Draft_PathTwistedLinkArray",
+ )
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_Array",
- "MenuText": QT_TRANSLATE_NOOP("Draft_ArrayTools", "Array Tools"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_ArrayTools", "Tools to create various types of arrays, including rectangular, polar, circular, path, and point arrays")}
+ return {
+ "Pixmap": "Draft_Array",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_ArrayTools", "Array Tools"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_ArrayTools",
+ "Tools to create various types of arrays, including rectangular, polar, circular, path, and point arrays",
+ ),
+ }
def IsActive(self):
"""Return True when this command should be available."""
return bool(gui_utils.get_3d_view())
-Gui.addCommand('Draft_ArrayTools', ArrayGroup())
+Gui.addCommand("Draft_ArrayTools", ArrayGroup())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_base.py b/src/Mod/Draft/draftguitools/gui_base.py
index abd9860093..f842fdfa90 100644
--- a/src/Mod/Draft/draftguitools/gui_base.py
+++ b/src/Mod/Draft/draftguitools/gui_base.py
@@ -90,7 +90,7 @@ class GuiCommandSimplest:
Also update the `doc` attribute.
"""
self.doc = App.activeDocument()
- _toolmsg("{}".format(16*"-"))
+ _toolmsg("{}".format(16 * "-"))
_toolmsg("GuiCommand: {}".format(self.featureName))
@@ -170,7 +170,7 @@ class GuiCommandBase:
if params.get_param("showPlaneTracker"):
self.planetrack = trackers.PlaneTracker()
- _toolmsg("{}".format(16*"-"))
+ _toolmsg("{}".format(16 * "-"))
_toolmsg("GuiCommand: {}".format(self.featureName))
def update_hints(self):
@@ -218,4 +218,5 @@ class GuiCommandBase:
"""
self.commit_list.append((name, func))
+
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_base_original.py b/src/Mod/Draft/draftguitools/gui_base_original.py
index 3d1e6a448e..617410989d 100644
--- a/src/Mod/Draft/draftguitools/gui_base_original.py
+++ b/src/Mod/Draft/draftguitools/gui_base_original.py
@@ -132,7 +132,7 @@ class DraftTool:
if hasattr(Gui, "Snapper"):
Gui.Snapper.setTrackers()
- _toolmsg("{}".format(16*"-"))
+ _toolmsg("{}".format(16 * "-"))
_toolmsg("GuiCommand: {}".format(self.featureName))
# update hints after the tool is fully initialized
@@ -231,18 +231,18 @@ class DraftTool:
# Support object
if self.support and params.get_param("useSupport"):
- sup = 'FreeCAD.ActiveDocument.getObject'
+ sup = "FreeCAD.ActiveDocument.getObject"
sup += '("{}")'.format(self.support.Name)
else:
- sup = 'None'
+ sup = "None"
# Contents of self.node
- points = '['
+ points = "["
for n in self.node:
if len(points) > 1:
- points += ', '
+ points += ", "
points += DraftVecUtils.toString(n)
- points += ']'
+ points += "]"
# Make face
if self.ui:
@@ -293,4 +293,6 @@ class Modifier(DraftTool):
super().Activated(name, is_subtool)
# call _save to sync with _restore called in finish method
self.wp._save()
+
+
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_beziers.py b/src/Mod/Draft/draftguitools/gui_beziers.py
index bb44e1224b..f459708172 100644
--- a/src/Mod/Draft/draftguitools/gui_beziers.py
+++ b/src/Mod/Draft/draftguitools/gui_beziers.py
@@ -61,19 +61,24 @@ class BezCurve(gui_lines.Line):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_BezCurve",
- "Accel": "B, Z",
- "MenuText": QT_TRANSLATE_NOOP("Draft_BezCurve", "Bézier Curve"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_BezCurve", "Creates an n-degree Bézier curve. The more points, the higher the degree.")}
+ return {
+ "Pixmap": "Draft_BezCurve",
+ "Accel": "B, Z",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_BezCurve", "Bézier Curve"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_BezCurve",
+ "Creates an n-degree Bézier curve. The more points, the higher the degree.",
+ ),
+ }
def Activated(self):
"""Execute when the command is called.
Activate the specific Bézier curve tracker.
"""
- super().Activated(name="BezCurve",
- icon="Draft_BezCurve",
- task_title=translate("draft", "Bézier Curve"))
+ super().Activated(
+ name="BezCurve", icon="Draft_BezCurve", task_title=translate("draft", "Bézier Curve")
+ )
if self.doc:
self.bezcurvetrack = trackers.bezcurveTracker()
@@ -131,7 +136,7 @@ class BezCurve(gui_lines.Line):
# by placing ends close to each other
# with tol = Draft tolerance
# old code has been to insensitive
- if (self.point-self.node[0]).Length < utils.tolerance():
+ if (self.point - self.node[0]).Length < utils.tolerance():
self.undolast()
self.finish(cont=None, closed=True)
@@ -158,13 +163,16 @@ class BezCurve(gui_lines.Line):
def updateShape(self, pts):
"""Create shape for display during creation process."""
import Part
+
edges = []
if len(pts) >= 2: # allow lower degree segment
poles = pts[1:]
else:
poles = []
if self.degree:
- segpoleslst = [poles[x:x+self.degree] for x in range(0, len(poles), (self.degree or 1))]
+ segpoleslst = [
+ poles[x : x + self.degree] for x in range(0, len(poles), (self.degree or 1))
+ ]
else:
segpoleslst = [pts]
startpoint = pts[0]
@@ -201,19 +209,20 @@ class BezCurve(gui_lines.Line):
try:
rot, sup, pts, fil = self.getStrings()
Gui.addModule("Draft")
- _cmd = 'Draft.make_bezcurve'
- _cmd += '('
- _cmd += 'points, '
- _cmd += 'closed=' + str(closed) + ', '
- _cmd += 'support=' + sup + ', '
- _cmd += 'degree=' + str(self.degree)
- _cmd += ')'
- _cmd_list = ['points = ' + pts,
- 'bez = ' + _cmd,
- 'Draft.autogroup(bez)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Bézier Curve"),
- _cmd_list)
+ _cmd = "Draft.make_bezcurve"
+ _cmd += "("
+ _cmd += "points, "
+ _cmd += "closed=" + str(closed) + ", "
+ _cmd += "support=" + sup + ", "
+ _cmd += "degree=" + str(self.degree)
+ _cmd += ")"
+ _cmd_list = [
+ "points = " + pts,
+ "bez = " + _cmd,
+ "Draft.autogroup(bez)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Bézier Curve"), _cmd_list)
except Exception:
_err("Draft: error delaying commit")
@@ -228,7 +237,7 @@ class BezCurve(gui_lines.Line):
self.Activated()
-Gui.addCommand('Draft_BezCurve', BezCurve())
+Gui.addCommand("Draft_BezCurve", BezCurve())
class CubicBezCurve(gui_lines.Line):
@@ -249,10 +258,15 @@ class CubicBezCurve(gui_lines.Line):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_CubicBezCurve",
- # "Accel": "B, Z",
- "MenuText": QT_TRANSLATE_NOOP("Draft_CubicBezCurve", "Cubic Bézier Curve"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_CubicBezCurve", "Creates a Bézier curve made of 2nd degree (quadratic) and 3rd degree (cubic) segments. Clicking and dragging allows to define segments.\nControl points and properties of each knot can be edited after creation.")}
+ return {
+ "Pixmap": "Draft_CubicBezCurve",
+ # "Accel": "B, Z",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_CubicBezCurve", "Cubic Bézier Curve"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_CubicBezCurve",
+ "Creates a Bézier curve made of 2nd degree (quadratic) and 3rd degree (cubic) segments. Clicking and dragging allows to define segments.\nControl points and properties of each knot can be edited after creation.",
+ ),
+ }
def Activated(self):
"""Execute when the command is called.
@@ -262,9 +276,11 @@ class CubicBezCurve(gui_lines.Line):
self.old_EnableSelection = params.get_param_view("EnableSelection")
params.set_param_view("EnableSelection", False)
- super().Activated(name="CubicBezCurve",
- icon="Draft_CubicBezCurve",
- task_title=translate("draft", "Cubic Bézier Curve"))
+ super().Activated(
+ name="CubicBezCurve",
+ icon="Draft_CubicBezCurve",
+ task_title=translate("draft", "Cubic Bézier Curve"),
+ )
if self.doc:
self.bezcurvetrack = trackers.bezcurveTracker()
@@ -291,14 +307,13 @@ class CubicBezCurve(gui_lines.Line):
if (len(self.node) - 1) % self.degree == 0 and len(self.node) > 2:
prevctrl = 2 * self.node[-1] - self.point
# Existing points + this pointer position
- self.bezcurvetrack.update(self.node[0:-2]
- + [prevctrl]
- + [self.node[-1]]
- + [self.point], degree=self.degree)
+ self.bezcurvetrack.update(
+ self.node[0:-2] + [prevctrl] + [self.node[-1]] + [self.point],
+ degree=self.degree,
+ )
else:
# Existing points + this pointer position
- self.bezcurvetrack.update(self.node
- + [self.point], degree=self.degree)
+ self.bezcurvetrack.update(self.node + [self.point], degree=self.degree)
gui_tool_utils.redraw3DView()
return
if arg["Type"] != "SoMouseButtonEvent":
@@ -394,6 +409,7 @@ class CubicBezCurve(gui_lines.Line):
def updateShape(self, pts):
"""Create shape for display during creation process."""
import Part
+
# Not quite right. draws 1 big bez. sb segmented
edges = []
@@ -403,7 +419,9 @@ class CubicBezCurve(gui_lines.Line):
poles = []
if self.degree:
- segpoleslst = [poles[x:x+self.degree] for x in range(0, len(poles), (self.degree or 1))]
+ segpoleslst = [
+ poles[x : x + self.degree] for x in range(0, len(poles), (self.degree or 1))
+ ]
else:
segpoleslst = [pts]
@@ -450,19 +468,20 @@ class CubicBezCurve(gui_lines.Line):
# to be committed through the `draftutils.todo.ToDo` class.
rot, sup, pts, fil = self.getStrings()
Gui.addModule("Draft")
- _cmd = 'Draft.make_bezcurve'
- _cmd += '('
- _cmd += 'points, '
- _cmd += 'closed=' + str(closed) + ', '
- _cmd += 'support=' + sup + ', '
- _cmd += 'degree=' + str(self.degree)
- _cmd += ')'
- _cmd_list = ['points = ' + pts,
- 'bez = ' + _cmd,
- 'Draft.autogroup(bez)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Bézier Curve"),
- _cmd_list)
+ _cmd = "Draft.make_bezcurve"
+ _cmd += "("
+ _cmd += "points, "
+ _cmd += "closed=" + str(closed) + ", "
+ _cmd += "support=" + sup + ", "
+ _cmd += "degree=" + str(self.degree)
+ _cmd += ")"
+ _cmd_list = [
+ "points = " + pts,
+ "bez = " + _cmd,
+ "Draft.autogroup(bez)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Bézier Curve"), _cmd_list)
except Exception:
_err("Draft: error delaying commit")
@@ -478,17 +497,21 @@ class CubicBezCurve(gui_lines.Line):
def get_hints(self):
if len(self.node) < 2:
- return [Gui.InputHint(
- translate("draft", "%1 click and drag to define first point and knot"),
- Gui.UserInput.MouseLeft
- )]
- return [Gui.InputHint(
- translate("draft", "%1 click and drag to define next point and knot"),
- Gui.UserInput.MouseLeft
- )]
+ return [
+ Gui.InputHint(
+ translate("draft", "%1 click and drag to define first point and knot"),
+ Gui.UserInput.MouseLeft,
+ )
+ ]
+ return [
+ Gui.InputHint(
+ translate("draft", "%1 click and drag to define next point and knot"),
+ Gui.UserInput.MouseLeft,
+ )
+ ]
-Gui.addCommand('Draft_CubicBezCurve', CubicBezCurve())
+Gui.addCommand("Draft_CubicBezCurve", CubicBezCurve())
class BezierGroup:
@@ -496,18 +519,22 @@ class BezierGroup:
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"MenuText": QT_TRANSLATE_NOOP("Draft_BezierTools", "Bézier Tools"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_BezierTools", "Tools to create various types of Bézier curves")}
+ return {
+ "MenuText": QT_TRANSLATE_NOOP("Draft_BezierTools", "Bézier Tools"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_BezierTools", "Tools to create various types of Bézier curves"
+ ),
+ }
def GetCommands(self):
"""Return a tuple of commands in the group."""
- return ('Draft_CubicBezCurve', 'Draft_BezCurve')
+ return ("Draft_CubicBezCurve", "Draft_BezCurve")
def IsActive(self):
"""Return True when this command should be available."""
return bool(gui_utils.get_3d_view())
-Gui.addCommand('Draft_BezierTools', BezierGroup())
+Gui.addCommand("Draft_BezierTools", BezierGroup())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_circles.py b/src/Mod/Draft/draftguitools/gui_circles.py
index 536e7583ab..3989d7a362 100644
--- a/src/Mod/Draft/draftguitools/gui_circles.py
+++ b/src/Mod/Draft/draftguitools/gui_circles.py
@@ -75,12 +75,14 @@ class Circle(gui_arcs.Arc):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_Circle',
- 'Accel': "C, I",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Circle", "Circle"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Circle", "Creates a circle (full circular arc)")}
+ return {
+ "Pixmap": "Draft_Circle",
+ "Accel": "C, I",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Circle", "Circle"),
+ "ToolTip": QT_TRANSLATE_NOOP("Draft_Circle", "Creates a circle (full circular arc)"),
+ }
-Gui.addCommand('Draft_Circle', Circle())
+Gui.addCommand("Draft_Circle", Circle())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_circulararray.py b/src/Mod/Draft/draftguitools/gui_circulararray.py
index ae579c260c..d694e3872f 100644
--- a/src/Mod/Draft/draftguitools/gui_circulararray.py
+++ b/src/Mod/Draft/draftguitools/gui_circulararray.py
@@ -51,9 +51,14 @@ class CircularArray(gui_base.GuiCommandBase):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_CircularArray",
- "MenuText": QT_TRANSLATE_NOOP("Draft_CircularArray", "Circular Array"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_CircularArray", "Creates copies of the selected object in a radial pattern with 1 or more circular layers")}
+ return {
+ "Pixmap": "Draft_CircularArray",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_CircularArray", "Circular Array"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_CircularArray",
+ "Creates copies of the selected object in a radial pattern with 1 or more circular layers",
+ ),
+ }
def Activated(self):
"""Execute when the command is called.
@@ -65,10 +70,8 @@ class CircularArray(gui_base.GuiCommandBase):
self.location = coin.SoLocation2Event.getClassTypeId()
self.mouse_event = coin.SoMouseButtonEvent.getClassTypeId()
- self.callback_move = \
- self.view.addEventCallbackPivy(self.location, self.move)
- self.callback_click = \
- self.view.addEventCallbackPivy(self.mouse_event, self.click)
+ self.callback_move = self.view.addEventCallbackPivy(self.location, self.move)
+ self.callback_click = self.view.addEventCallbackPivy(self.mouse_event, self.click)
self.ui = task_circulararray.TaskPanelCircularArray()
# The calling class (this one) is saved in the object
@@ -99,8 +102,10 @@ class CircularArray(gui_base.GuiCommandBase):
"""
if event_cb:
event = event_cb.getEvent()
- if (event.getState() != coin.SoMouseButtonEvent.DOWN
- or event.getButton() != coin.SoMouseButtonEvent.BUTTON1):
+ if (
+ event.getState() != coin.SoMouseButtonEvent.DOWN
+ or event.getButton() != coin.SoMouseButtonEvent.BUTTON1
+ ):
return
if self.ui and self.point:
# The accept function of the interface
@@ -128,6 +133,6 @@ class CircularArray(gui_base.GuiCommandBase):
self.finish()
-Gui.addCommand('Draft_CircularArray', CircularArray())
+Gui.addCommand("Draft_CircularArray", CircularArray())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_clone.py b/src/Mod/Draft/draftguitools/gui_clone.py
index 7ca25edc0f..1fd9a5d072 100644
--- a/src/Mod/Draft/draftguitools/gui_clone.py
+++ b/src/Mod/Draft/draftguitools/gui_clone.py
@@ -66,10 +66,12 @@ class Clone(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_Clone",
- "Accel": "C, L",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Clone", "Clone"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Clone", "Creates a clone of the selected objects")}
+ return {
+ "Pixmap": "Draft_Clone",
+ "Accel": "C, L",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Clone", "Clone"),
+ "ToolTip": QT_TRANSLATE_NOOP("Draft_Clone", "Creates a clone of the selected objects"),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -121,6 +123,6 @@ class Clone(gui_base_original.Modifier):
Draft_Clone = Clone
-Gui.addCommand('Draft_Clone', Clone())
+Gui.addCommand("Draft_Clone", Clone())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_dimension_ops.py b/src/Mod/Draft/draftguitools/gui_dimension_ops.py
index d4ed46dadd..5b717fa853 100644
--- a/src/Mod/Draft/draftguitools/gui_dimension_ops.py
+++ b/src/Mod/Draft/draftguitools/gui_dimension_ops.py
@@ -52,24 +52,26 @@ class FlipDimension(gui_base.GuiCommandNeedsSelection):
"""
def __init__(self):
- super(Draft_FlipDimension, self).__init__(name=translate("draft","Flip Dimension"))
+ super(Draft_FlipDimension, self).__init__(name=translate("draft", "Flip Dimension"))
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_FlipDimension',
- 'MenuText': QT_TRANSLATE_NOOP("Draft_FlipDimension",
- "Flip Dimension"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_FlipDimension",
- "Flips the normal direction of the selected dimensions (linear, radial, angular).\nIf other objects are selected they are ignored.")}
+ return {
+ "Pixmap": "Draft_FlipDimension",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_FlipDimension", "Flip Dimension"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_FlipDimension",
+ "Flips the normal direction of the selected dimensions (linear, radial, angular).\nIf other objects are selected they are ignored.",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
super(Draft_FlipDimension, self).Activated()
for o in Gui.Selection.getSelection():
- if utils.get_type(o) in ("Dimension",
- "LinearDimension", "AngularDimension"):
+ if utils.get_type(o) in ("Dimension", "LinearDimension", "AngularDimension"):
self.doc.openTransaction("Flip dimension")
_cmd = "App.activeDocument()." + o.Name + ".Normal"
_cmd += " = "
@@ -80,6 +82,6 @@ class FlipDimension(gui_base.GuiCommandNeedsSelection):
Draft_FlipDimension = FlipDimension
-Gui.addCommand('Draft_FlipDimension', FlipDimension())
+Gui.addCommand("Draft_FlipDimension", FlipDimension())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_dimensions.py b/src/Mod/Draft/draftguitools/gui_dimensions.py
index c244858d59..0d694f0517 100644
--- a/src/Mod/Draft/draftguitools/gui_dimensions.py
+++ b/src/Mod/Draft/draftguitools/gui_dimensions.py
@@ -74,7 +74,7 @@ class Dimension(gui_base_original.Creator):
def __init__(self):
super().__init__()
self.max = 2
- self.chain = None # Last chain's leg in ChainMode
+ self.chain = None # Last chain's leg in ChainMode
self.contMode = None
self.dir = None
self.featureName = "Dimension"
@@ -82,10 +82,15 @@ class Dimension(gui_base_original.Creator):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_Dimension',
- 'Accel': "D, I",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Dimension", "Dimension"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Dimension", "Creates a linear dimension for a straight edge, a circular edge, or 2 picked points, or an angular dimension for 2 straight edges")}
+ return {
+ "Pixmap": "Draft_Dimension",
+ "Accel": "D, I",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Dimension", "Dimension"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Dimension",
+ "Creates a linear dimension for a straight edge, a circular edge, or 2 picked points, or an angular dimension for 2 straight edges",
+ ),
+ }
def Activated(self, dir_vec=None):
"""Execute when the command is called."""
@@ -123,9 +128,11 @@ class Dimension(gui_base_original.Creator):
def set_selection(self):
"""Fill the nodes according to the selected geometry."""
sel = Gui.Selection.getSelectionEx()
- if (len(sel) == 1
- and len(sel[0].SubElementNames) == 1
- and "Edge" in sel[0].SubElementNames[0]):
+ if (
+ len(sel) == 1
+ and len(sel[0].SubElementNames) == 1
+ and "Edge" in sel[0].SubElementNames[0]
+ ):
# The selection is just a single `Edge`
sel_object = sel[0]
edge = sel_object.SubObjects[0]
@@ -137,8 +144,7 @@ class Dimension(gui_base_original.Creator):
self.indices.append(n)
if DraftGeomUtils.geomType(edge) == "Line":
- self.node.extend([edge.Vertexes[0].Point,
- edge.Vertexes[1].Point])
+ self.node.extend([edge.Vertexes[0].Point, edge.Vertexes[1].Point])
# Iterate over the vertices of the parent `Object`;
# when the vertices match those of the selected `edge`
@@ -151,11 +157,10 @@ class Dimension(gui_base_original.Creator):
if v.Point == edge.Vertexes[1].Point:
v2 = i
- if v1 is not None and v2 is not None: # note that v1 or v2 can be zero
+ if v1 is not None and v2 is not None: # note that v1 or v2 can be zero
self.link = [sel_object.Object, v1, v2]
elif DraftGeomUtils.geomType(edge) == "Circle":
- self.node.extend([edge.Curve.Center,
- edge.Vertexes[0].Point])
+ self.node.extend([edge.Curve.Center, edge.Vertexes[0].Point])
self.edges = [edge]
self.arcmode = "diameter"
self.link = [sel_object.Object, n]
@@ -172,10 +177,9 @@ class Dimension(gui_base_original.Creator):
super().finish()
def angle_dimension_normal(self, edge1, edge2):
- rot = App.Rotation(DraftGeomUtils.vec(edge1),
- DraftGeomUtils.vec(edge2),
- self.wp.axis,
- "XYZ")
+ rot = App.Rotation(
+ DraftGeomUtils.vec(edge1), DraftGeomUtils.vec(edge2), self.wp.axis, "XYZ"
+ )
norm = rot.multVec(App.Vector(0, 0, 1))
vnorm = gui_utils.get_3d_view().getViewDirection()
if vnorm.getAngle(norm) < math.pi / 2:
@@ -188,36 +192,38 @@ class Dimension(gui_base_original.Creator):
ang2 = math.degrees(self.angledata[0])
norm = self.angle_dimension_normal(self.edges[0], self.edges[1])
- _cmd = 'Draft.make_angular_dimension'
- _cmd += '('
- _cmd += 'center=' + DraftVecUtils.toString(self.center) + ', '
- _cmd += 'angles='
- _cmd += '['
- _cmd += str(ang1) + ', '
+ _cmd = "Draft.make_angular_dimension"
+ _cmd += "("
+ _cmd += "center=" + DraftVecUtils.toString(self.center) + ", "
+ _cmd += "angles="
+ _cmd += "["
+ _cmd += str(ang1) + ", "
_cmd += str(ang2)
- _cmd += '], '
- _cmd += 'dim_line=' + DraftVecUtils.toString(self.node[-1]) + ', '
- _cmd += 'normal=' + DraftVecUtils.toString(norm)
- _cmd += ')'
- _cmd_list = ['_dim_ = ' + _cmd,
- 'Draft.autogroup(_dim_)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Dimension"),
- _cmd_list)
+ _cmd += "], "
+ _cmd += "dim_line=" + DraftVecUtils.toString(self.node[-1]) + ", "
+ _cmd += "normal=" + DraftVecUtils.toString(norm)
+ _cmd += ")"
+ _cmd_list = [
+ "_dim_ = " + _cmd,
+ "Draft.autogroup(_dim_)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Dimension"), _cmd_list)
def create_linear_dimension(self):
"""Create a simple linear dimension, not linked to an edge."""
- _cmd = 'Draft.make_linear_dimension'
- _cmd += '('
- _cmd += DraftVecUtils.toString(self.node[0]) + ', '
- _cmd += DraftVecUtils.toString(self.node[1]) + ', '
- _cmd += 'dim_line=' + DraftVecUtils.toString(self.node[2])
- _cmd += ')'
- _cmd_list = ['_dim_ = ' + _cmd,
- 'Draft.autogroup(_dim_)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Dimension"),
- _cmd_list)
+ _cmd = "Draft.make_linear_dimension"
+ _cmd += "("
+ _cmd += DraftVecUtils.toString(self.node[0]) + ", "
+ _cmd += DraftVecUtils.toString(self.node[1]) + ", "
+ _cmd += "dim_line=" + DraftVecUtils.toString(self.node[2])
+ _cmd += ")"
+ _cmd_list = [
+ "_dim_ = " + _cmd,
+ "Draft.autogroup(_dim_)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Dimension"), _cmd_list)
def create_linear_dimension_obj(self, direction=None):
"""Create a linear dimension linked to an edge.
@@ -230,41 +236,40 @@ class Dimension(gui_base_original.Creator):
with 1, that is, `Vertex1`.
Therefore the value in `link` has to be incremented by 1.
"""
- _cmd = 'Draft.make_linear_dimension_obj'
- _cmd += '('
- _cmd += 'FreeCAD.ActiveDocument.' + self.link[0].Name + ', '
- _cmd += 'i1=' + str(self.link[1] + 1) + ', '
- _cmd += 'i2=' + str(self.link[2] + 1) + ', '
- _cmd += 'dim_line=' + DraftVecUtils.toString(self.node[2])
- _cmd += ')'
- _cmd_list = ['_dim_ = ' + _cmd]
+ _cmd = "Draft.make_linear_dimension_obj"
+ _cmd += "("
+ _cmd += "FreeCAD.ActiveDocument." + self.link[0].Name + ", "
+ _cmd += "i1=" + str(self.link[1] + 1) + ", "
+ _cmd += "i2=" + str(self.link[2] + 1) + ", "
+ _cmd += "dim_line=" + DraftVecUtils.toString(self.node[2])
+ _cmd += ")"
+ _cmd_list = ["_dim_ = " + _cmd]
dir_u = DraftVecUtils.toString(self.wp.u)
dir_v = DraftVecUtils.toString(self.wp.v)
if direction == "X":
- _cmd_list += ['_dim_.Direction = ' + dir_u]
+ _cmd_list += ["_dim_.Direction = " + dir_u]
elif direction == "Y":
- _cmd_list += ['_dim_.Direction = ' + dir_v]
+ _cmd_list += ["_dim_.Direction = " + dir_v]
- _cmd_list += ['Draft.autogroup(_dim_)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Dimension"),
- _cmd_list)
+ _cmd_list += ["Draft.autogroup(_dim_)", "FreeCAD.ActiveDocument.recompute()"]
+ self.commit(translate("draft", "Create Dimension"), _cmd_list)
def create_radial_dimension_obj(self):
"""Create a radial dimension linked to a circular edge."""
- _cmd = 'Draft.make_radial_dimension_obj'
- _cmd += '('
- _cmd += 'FreeCAD.ActiveDocument.' + self.link[0].Name + ', '
- _cmd += 'index=' + str(self.link[1] + 1) + ', '
+ _cmd = "Draft.make_radial_dimension_obj"
+ _cmd += "("
+ _cmd += "FreeCAD.ActiveDocument." + self.link[0].Name + ", "
+ _cmd += "index=" + str(self.link[1] + 1) + ", "
_cmd += 'mode="' + str(self.arcmode) + '", '
- _cmd += 'dim_line=' + DraftVecUtils.toString(self.node[2])
- _cmd += ')'
- _cmd_list = ['_dim_ = ' + _cmd,
- 'Draft.autogroup(_dim_)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Dimension"),
- _cmd_list)
+ _cmd += "dim_line=" + DraftVecUtils.toString(self.node[2])
+ _cmd += ")"
+ _cmd_list = [
+ "_dim_ = " + _cmd,
+ "Draft.autogroup(_dim_)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Dimension"), _cmd_list)
def createObject(self):
"""Create the actual object in the current document."""
@@ -325,23 +330,23 @@ class Dimension(gui_base_original.Creator):
shift = gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_constrain_key())
if self.arcmode or self.point2:
gui_tool_utils.setMod(arg, gui_tool_utils.get_mod_constrain_key(), False)
- (self.point,
- ctrlPoint, self.info) = gui_tool_utils.getPoint(self, arg,
- noTracker=(len(self.node)>0))
- if (gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key())
- or self.selectmode) and (len(self.node) < 3):
+ (self.point, ctrlPoint, self.info) = gui_tool_utils.getPoint(
+ self, arg, noTracker=(len(self.node) > 0)
+ )
+ if (
+ gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key()) or self.selectmode
+ ) and (len(self.node) < 3):
self.dimtrack.off()
if not self.altdown:
self.altdown = True
self.ui.switchUi(True)
if hasattr(Gui, "Snapper"):
Gui.Snapper.setSelectMode(True)
- snapped = self.view.getObjectInfo((arg["Position"][0],
- arg["Position"][1]))
+ snapped = self.view.getObjectInfo((arg["Position"][0], arg["Position"][1]))
if snapped:
- ob = self.doc.getObject(snapped['Object'])
- if "Edge" in snapped['Component']:
- num = int(snapped['Component'].lstrip('Edge')) - 1
+ ob = self.doc.getObject(snapped["Object"])
+ if "Edge" in snapped["Component"]:
+ num = int(snapped["Component"].lstrip("Edge")) - 1
ed = ob.Shape.Edges[num]
v1 = ed.Vertexes[0].Point
v2 = ed.Vertexes[-1].Point
@@ -367,11 +372,9 @@ class Dimension(gui_base_original.Creator):
a = self.arctrack.getAngle(self.point)
pair = DraftGeomUtils.getBoundaryAngles(a, self.angles)
if not (pair[0] < a < pair[1]):
- self.angledata = [4 * math.pi - pair[0],
- 2 * math.pi - pair[1]]
+ self.angledata = [4 * math.pi - pair[0], 2 * math.pi - pair[1]]
else:
- self.angledata = [2 * math.pi - pair[0],
- 2 * math.pi - pair[1]]
+ self.angledata = [2 * math.pi - pair[0], 2 * math.pi - pair[1]]
self.arctrack.setStartAngle(self.angledata[0])
self.arctrack.setEndAngle(self.angledata[1])
if self.altdown:
@@ -380,8 +383,7 @@ class Dimension(gui_base_original.Creator):
if hasattr(Gui, "Snapper"):
Gui.Snapper.setSelectMode(False)
if self.node and self.dir and len(self.node) < 2:
- _p = DraftVecUtils.project(self.point.sub(self.node[0]),
- self.dir)
+ _p = DraftVecUtils.project(self.point.sub(self.node[0]), self.dir)
self.point = self.node[0].add(_p)
if len(self.node) == 2:
if self.arcmode and self.edges:
@@ -418,8 +420,7 @@ class Dimension(gui_base_original.Creator):
# self.point2 = None
# update the dimline
if self.node and not self.arcmode:
- self.dimtrack.update(self.node
- + [self.point] + [self.chain])
+ self.dimtrack.update(self.node + [self.point] + [self.chain])
gui_tool_utils.redraw3DView()
elif arg["Type"] == "SoMouseButtonEvent":
if (arg["State"] == "DOWN") and (arg["Button"] == "BUTTON1"):
@@ -427,13 +428,15 @@ class Dimension(gui_base_original.Creator):
self.ui.redraw()
if (not self.node) and (not self.support):
gui_tool_utils.getSupport(arg)
- if (gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key())
- or self.selectmode) and (len(self.node) < 3):
+ if (
+ gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key())
+ or self.selectmode
+ ) and (len(self.node) < 3):
# print("snapped: ",self.info)
if self.info:
- ob = self.doc.getObject(self.info['Object'])
- if 'Edge' in self.info['Component']:
- num = int(self.info['Component'].lstrip('Edge')) - 1
+ ob = self.doc.getObject(self.info["Object"])
+ if "Edge" in self.info["Component"]:
+ num = int(self.info["Component"].lstrip("Edge")) - 1
ed = ob.Shape.Edges[num]
v1 = ed.Vertexes[0].Point
v2 = ed.Vertexes[-1].Point
@@ -461,26 +464,37 @@ class Dimension(gui_base_original.Creator):
self.edges.append(ed)
# self.node now has the 4 endpoints
self.node.extend([v1, v2])
- c = DraftGeomUtils.findIntersection(self.node[0],
- self.node[1],
- self.node[2],
- self.node[3],
- True, True)
+ c = DraftGeomUtils.findIntersection(
+ self.node[0],
+ self.node[1],
+ self.node[2],
+ self.node[3],
+ True,
+ True,
+ )
if c:
# print("centers:",c)
self.center = c[0]
self.arctrack.setCenter(self.center)
- self.arctrack.normal = self.angle_dimension_normal(self.edges[0], self.edges[1])
+ self.arctrack.normal = self.angle_dimension_normal(
+ self.edges[0], self.edges[1]
+ )
self.arctrack.on()
for e in self.edges:
- if e.Length < 0.00003: # Edge must be long enough for the tolerance of 0.00001mm to make sense.
+ if (
+ e.Length < 0.00003
+ ): # Edge must be long enough for the tolerance of 0.00001mm to make sense.
_msg(translate("draft", "Edge too short!"))
self.finish()
return
for i in [0, 1]:
pt = e.Vertexes[i].Point
- if pt.isEqual(self.center, 0.00001): # A relatively high tolerance is required.
- pt = e.Vertexes[i - 1].Point # Use the other point instead.
+ if pt.isEqual(
+ self.center, 0.00001
+ ): # A relatively high tolerance is required.
+ pt = e.Vertexes[
+ i - 1
+ ].Point # Use the other point instead.
self.angles.append(self.arctrack.getAngle(pt))
self.link = [self.link[0], ob]
else:
@@ -545,27 +559,27 @@ class Dimension(gui_base_original.Creator):
if not self.proj_point1 or not self.proj_point2:
self.proj_point1 = self.wp.project_point(self.node[0])
self.proj_point2 = self.wp.project_point(self.node[1])
- proj_u= self.wp.u.dot(self.proj_point2 - self.proj_point1)
- proj_v= self.wp.v.dot(self.proj_point2 - self.proj_point1)
+ proj_u = self.wp.u.dot(self.proj_point2 - self.proj_point1)
+ proj_v = self.wp.v.dot(self.proj_point2 - self.proj_point1)
active_view = Gui.ActiveDocument.ActiveView
cursor = active_view.getCursorPos()
cursor_point = active_view.getPoint(cursor)
self.point = self.wp.project_point(cursor_point)
if not self.force:
- ref_point = self.point - (self.proj_point2 + self.proj_point1)*1/2
+ ref_point = self.point - (self.proj_point2 + self.proj_point1) * 1 / 2
ref_angle = abs(ref_point.getAngle(self.wp.u))
- if (ref_angle > math.pi/4) and (ref_angle <= 0.75*math.pi):
+ if (ref_angle > math.pi / 4) and (ref_angle <= 0.75 * math.pi):
self.force = 2
else:
self.force = 1
if self.force == 1:
self.node[0] = self.proj_point1
- self.node[1] = self.proj_point1 + self.wp.v*proj_v
+ self.node[1] = self.proj_point1 + self.wp.v * proj_v
elif self.force == 2:
self.node[0] = self.proj_point1
- self.node[1] = self.proj_point1 + self.wp.u*proj_u
+ self.node[1] = self.proj_point1 + self.wp.u * proj_u
-Gui.addCommand('Draft_Dimension', Dimension())
+Gui.addCommand("Draft_Dimension", Dimension())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_downgrade.py b/src/Mod/Draft/draftguitools/gui_downgrade.py
index 9d10fa8a75..167a779498 100644
--- a/src/Mod/Draft/draftguitools/gui_downgrade.py
+++ b/src/Mod/Draft/draftguitools/gui_downgrade.py
@@ -53,10 +53,15 @@ class Downgrade(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_Downgrade',
- 'Accel': "D, N",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Downgrade", "Downgrade"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Downgrade", "Downgrades the selected objects into simpler shapes.\nThe result of the operation depends on the types of objects, which may be downgraded several times in a row.\nFor example, a 3D solid is deconstructed into separate faces, wires, and then edges. Faces can also be subtracted.")}
+ return {
+ "Pixmap": "Draft_Downgrade",
+ "Accel": "D, N",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Downgrade", "Downgrade"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Downgrade",
+ "Downgrades the selected objects into simpler shapes.\nThe result of the operation depends on the types of objects, which may be downgraded several times in a row.\nFor example, a 3D solid is deconstructed into separate faces, wires, and then edges. Faces can also be subtracted.",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -76,18 +81,16 @@ class Downgrade(gui_base_original.Modifier):
self.end_callbacks(self.call)
if Gui.Selection.getSelection():
Gui.addModule("Draft")
- _cmd = 'Draft.downgrade'
- _cmd += '('
- _cmd += 'FreeCADGui.Selection.getSelection(), '
- _cmd += 'delete=True'
- _cmd += ')'
- _cmd_list = ['_objs_ = ' + _cmd,
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Downgrade"),
- _cmd_list)
+ _cmd = "Draft.downgrade"
+ _cmd += "("
+ _cmd += "FreeCADGui.Selection.getSelection(), "
+ _cmd += "delete=True"
+ _cmd += ")"
+ _cmd_list = ["_objs_ = " + _cmd, "FreeCAD.ActiveDocument.recompute()"]
+ self.commit(translate("draft", "Downgrade"), _cmd_list)
self.finish()
-Gui.addCommand('Draft_Downgrade', Downgrade())
+Gui.addCommand("Draft_Downgrade", Downgrade())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_draft2sketch.py b/src/Mod/Draft/draftguitools/gui_draft2sketch.py
index ba6c1491b2..9a94832a7b 100644
--- a/src/Mod/Draft/draftguitools/gui_draft2sketch.py
+++ b/src/Mod/Draft/draftguitools/gui_draft2sketch.py
@@ -53,9 +53,14 @@ class Draft2Sketch(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_Draft2Sketch',
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Draft2Sketch", "Draft to Sketch"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Draft2Sketch", "Converts bidirectionally between Draft objects and sketches.\nMultiple selected Draft objects are converted into a single sketch.\nHowever, a single sketch with disconnected traces is converted into several individual Draft objects.")}
+ return {
+ "Pixmap": "Draft_Draft2Sketch",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Draft2Sketch", "Draft to Sketch"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Draft2Sketch",
+ "Converts bidirectionally between Draft objects and sketches.\nMultiple selected Draft objects are converted into a single sketch.\nHowever, a single sketch with disconnected traces is converted into several individual Draft objects.",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -80,8 +85,9 @@ class Draft2Sketch(gui_base_original.Modifier):
for obj in sel:
if obj.isDerivedFrom("Sketcher::SketchObject"):
allDraft = False
- elif (obj.isDerivedFrom("Part::Part2DObjectPython")
- or obj.isDerivedFrom("Part::Feature")):
+ elif obj.isDerivedFrom("Part::Part2DObjectPython") or obj.isDerivedFrom(
+ "Part::Feature"
+ ):
allSketches = False
else:
allDraft = False
@@ -95,10 +101,8 @@ class Draft2Sketch(gui_base_original.Modifier):
_cmd += "FreeCADGui.Selection.getSelection(), "
_cmd += "autoconstraints=True"
_cmd += ")"
- _cmd_list = ['sk = ' + _cmd,
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Convert to Sketch"),
- _cmd_list)
+ _cmd_list = ["sk = " + _cmd, "FreeCAD.ActiveDocument.recompute()"]
+ self.commit(translate("draft", "Convert to Sketch"), _cmd_list)
elif allSketches:
n = 0
_cmd_list = list()
@@ -111,9 +115,8 @@ class Draft2Sketch(gui_base_original.Modifier):
_cmd_list.append("df" + str(n) + " = " + _cmd)
n += 1
- _cmd_list.append('FreeCAD.ActiveDocument.recompute()')
- self.commit(translate("draft", "Convert to Draft"),
- _cmd_list)
+ _cmd_list.append("FreeCAD.ActiveDocument.recompute()")
+ self.commit(translate("draft", "Convert to Draft"), _cmd_list)
else:
_cmd_list = list()
n = 0
@@ -132,20 +135,20 @@ class Draft2Sketch(gui_base_original.Modifier):
if obj.isDerivedFrom("Sketcher::SketchObject"):
_cmd_list.append("obj" + str(n) + " = " + _cmd_df)
- elif (obj.isDerivedFrom("Part::Part2DObjectPython")
- or obj.isDerivedFrom("Part::Feature")):
+ elif obj.isDerivedFrom("Part::Part2DObjectPython") or obj.isDerivedFrom(
+ "Part::Feature"
+ ):
_cmd_list.append("obj" + str(n) + " = " + _cmd_sk)
- #elif obj.isDerivedFrom("Part::Feature"):
+ # elif obj.isDerivedFrom("Part::Feature"):
# # if (len(obj.Shape.Wires) == 1
# # or len(obj.Shape.Edges) == 1):
# _cmd_list.append("obj" + str(n) + " = " + _cmd_sk)
n += 1
- _cmd_list.append('FreeCAD.ActiveDocument.recompute()')
- self.commit(translate("draft", "Convert Draft/Sketch"),
- _cmd_list)
+ _cmd_list.append("FreeCAD.ActiveDocument.recompute()")
+ self.commit(translate("draft", "Convert Draft/Sketch"), _cmd_list)
self.finish()
-Gui.addCommand('Draft_Draft2Sketch', Draft2Sketch())
+Gui.addCommand("Draft_Draft2Sketch", Draft2Sketch())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_edit.py b/src/Mod/Draft/draftguitools/gui_edit.py
index fcae555760..f3ca6f2a9a 100644
--- a/src/Mod/Draft/draftguitools/gui_edit.py
+++ b/src/Mod/Draft/draftguitools/gui_edit.py
@@ -26,8 +26,9 @@
# \brief Provides GUI tools to start the edit mode of different objects.
__title__ = "FreeCAD Draft Edit Tool"
-__author__ = ("Yorik van Havre, Werner Mayer, Martin Burbaum, Ken Cline, "
- "Dmitry Chigrin, Carlo Pavan")
+__author__ = (
+ "Yorik van Havre, Werner Mayer, Martin Burbaum, Ken Cline, " "Dmitry Chigrin, Carlo Pavan"
+)
__url__ = "https://www.freecad.org"
## \addtogroup draftguitools
@@ -55,15 +56,15 @@ from draftguitools import gui_trackers as trackers
COLORS = {
"default": utils.get_rgba_tuple(params.get_param("snapcolor"))[:3],
- "black": (0., 0., 0.),
- "white": (1., 1., 1.),
- "grey": (.5, .5, .5),
- "red": (1., 0., 0.),
- "green": (0., 1., 0.),
- "blue": (0., 0., 1.),
- "yellow": (1., 1., 0.),
- "cyan": (0., 1., 1.),
- "magenta": (1., 0., 1.)
+ "black": (0.0, 0.0, 0.0),
+ "white": (1.0, 1.0, 1.0),
+ "grey": (0.5, 0.5, 0.5),
+ "red": (1.0, 0.0, 0.0),
+ "green": (0.0, 1.0, 0.0),
+ "blue": (0.0, 0.0, 1.0),
+ "yellow": (1.0, 1.0, 0.0),
+ "cyan": (0.0, 1.0, 1.0),
+ "magenta": (1.0, 0.0, 1.0),
}
@@ -198,7 +199,7 @@ class Edit(gui_base_original.Modifier):
super().__init__()
"""Initialize Draft_Edit Command."""
self.running = False
- self.trackers = {'object': []}
+ self.trackers = {"object": []}
self.overNode = None # preselected node with mouseover
self.edited_objects = []
self.obj = None
@@ -218,7 +219,7 @@ class Edit(gui_base_original.Modifier):
self.max_objects = 5
self.pick_radius = 20
- self.alt_edit_mode = 0 # default edit mode for objects
+ self.alt_edit_mode = 0 # default edit mode for objects
# preview
self.ghost = None
@@ -226,40 +227,43 @@ class Edit(gui_base_original.Modifier):
# setup gui_tools for every supported object
self.gui_tools_repository = GuiToolsRepository()
- self.gui_tools_repository.add('Wire', edit_draft.DraftWireGuiTools())
- self.gui_tools_repository.add('BSpline', edit_draft.DraftBSplineGuiTools())
- self.gui_tools_repository.add('BezCurve', edit_draft.DraftBezCurveGuiTools())
- self.gui_tools_repository.add('Circle', edit_draft.DraftCircleGuiTools())
- self.gui_tools_repository.add('Rectangle', edit_draft.DraftRectangleGuiTools())
- self.gui_tools_repository.add('Polygon', edit_draft.DraftPolygonGuiTools())
- self.gui_tools_repository.add('Ellipse', edit_draft.DraftEllipseGuiTools())
- self.gui_tools_repository.add('Dimension', edit_draft.DraftDimensionGuiTools()) # Backward compatibility
- self.gui_tools_repository.add('LinearDimension', edit_draft.DraftDimensionGuiTools())
- self.gui_tools_repository.add('Label', edit_draft.DraftLabelGuiTools())
+ self.gui_tools_repository.add("Wire", edit_draft.DraftWireGuiTools())
+ self.gui_tools_repository.add("BSpline", edit_draft.DraftBSplineGuiTools())
+ self.gui_tools_repository.add("BezCurve", edit_draft.DraftBezCurveGuiTools())
+ self.gui_tools_repository.add("Circle", edit_draft.DraftCircleGuiTools())
+ self.gui_tools_repository.add("Rectangle", edit_draft.DraftRectangleGuiTools())
+ self.gui_tools_repository.add("Polygon", edit_draft.DraftPolygonGuiTools())
+ self.gui_tools_repository.add("Ellipse", edit_draft.DraftEllipseGuiTools())
+ self.gui_tools_repository.add(
+ "Dimension", edit_draft.DraftDimensionGuiTools()
+ ) # Backward compatibility
+ self.gui_tools_repository.add("LinearDimension", edit_draft.DraftDimensionGuiTools())
+ self.gui_tools_repository.add("Label", edit_draft.DraftLabelGuiTools())
- self.gui_tools_repository.add('Wall', edit_arch.ArchWallGuiTools())
- self.gui_tools_repository.add('Window', edit_arch.ArchWindowGuiTools())
- self.gui_tools_repository.add('Structure', edit_arch.ArchStructureGuiTools())
- self.gui_tools_repository.add('Space', edit_arch.ArchSpaceGuiTools())
- self.gui_tools_repository.add('PanelCut', edit_arch.ArchPanelCutGuiTools())
- self.gui_tools_repository.add('PanelSheet', edit_arch.ArchPanelSheetGuiTools())
+ self.gui_tools_repository.add("Wall", edit_arch.ArchWallGuiTools())
+ self.gui_tools_repository.add("Window", edit_arch.ArchWindowGuiTools())
+ self.gui_tools_repository.add("Structure", edit_arch.ArchStructureGuiTools())
+ self.gui_tools_repository.add("Space", edit_arch.ArchSpaceGuiTools())
+ self.gui_tools_repository.add("PanelCut", edit_arch.ArchPanelCutGuiTools())
+ self.gui_tools_repository.add("PanelSheet", edit_arch.ArchPanelSheetGuiTools())
- self.gui_tools_repository.add('Part::Line', edit_part.PartLineGuiTools())
- self.gui_tools_repository.add('Part::Box', edit_part.PartBoxGuiTools())
- self.gui_tools_repository.add('Part::Cylinder', edit_part.PartCylinderGuiTools())
- self.gui_tools_repository.add('Part::Cone', edit_part.PartConeGuiTools())
- self.gui_tools_repository.add('Part::Sphere', edit_part.PartSphereGuiTools())
-
- self.gui_tools_repository.add('Sketcher::SketchObject', edit_sketcher.SketcherSketchObjectGuiTools())
+ self.gui_tools_repository.add("Part::Line", edit_part.PartLineGuiTools())
+ self.gui_tools_repository.add("Part::Box", edit_part.PartBoxGuiTools())
+ self.gui_tools_repository.add("Part::Cylinder", edit_part.PartCylinderGuiTools())
+ self.gui_tools_repository.add("Part::Cone", edit_part.PartConeGuiTools())
+ self.gui_tools_repository.add("Part::Sphere", edit_part.PartSphereGuiTools())
+ self.gui_tools_repository.add(
+ "Sketcher::SketchObject", edit_sketcher.SketcherSketchObjectGuiTools()
+ )
def GetResources(self):
- return {'Pixmap': 'Draft_Edit',
- 'Accel': "D, E",
- 'MenuText': QtCore.QT_TRANSLATE_NOOP("Draft_Edit", "Edit"),
- 'ToolTip': QtCore.QT_TRANSLATE_NOOP("Draft_Edit", "Edits the active object")
- }
-
+ return {
+ "Pixmap": "Draft_Edit",
+ "Accel": "D, E",
+ "MenuText": QtCore.QT_TRANSLATE_NOOP("Draft_Edit", "Edit"),
+ "ToolTip": QtCore.QT_TRANSLATE_NOOP("Draft_Edit", "Edits the active object"),
+ }
# -------------------------------------------------------------------------
# MAIN FUNCTIONS
@@ -286,12 +290,9 @@ class Edit(gui_base_original.Modifier):
self.proceed()
else:
self.ui.selectUi(on_close_call=self.finish)
- App.Console.PrintMessage(translate("draft",
- "Select a Draft object to edit")
- + "\n")
+ App.Console.PrintMessage(translate("draft", "Select a Draft object to edit") + "\n")
self.register_selection_callback()
-
def proceed(self):
"""this method set the editTrackers"""
self.unregister_selection_callback()
@@ -312,7 +313,6 @@ class Edit(gui_base_original.Modifier):
self.register_editing_callbacks()
-
def numericInput(self, numx, numy, numz):
"""Execute callback by the toolbar to activate the update function.
@@ -322,7 +322,6 @@ class Edit(gui_base_original.Modifier):
self.endEditing(self.obj, self.editing, App.Vector(numx, numy, numz))
App.ActiveDocument.recompute()
-
def finish(self, cont=False):
"""Terminate Edit Tool."""
self.unregister_selection_callback()
@@ -341,6 +340,7 @@ class Edit(gui_base_original.Modifier):
self.running = False
# delay resetting edit mode otherwise it doesn't happen
from PySide import QtCore
+
QtCore.QTimer.singleShot(0, self.reset_edit)
def reset_edit(self):
@@ -375,14 +375,17 @@ class Edit(gui_base_original.Modifier):
self.render_manager = self.view.getViewer().getSoRenderManager()
if self._keyPressedCB is None:
self._keyPressedCB = self.view.addEventCallbackPivy(
- coin.SoKeyboardEvent.getClassTypeId(), self.keyPressed)
+ coin.SoKeyboardEvent.getClassTypeId(), self.keyPressed
+ )
if self._mouseMovedCB is None:
self._mouseMovedCB = self.view.addEventCallbackPivy(
- coin.SoLocation2Event.getClassTypeId(), self.mouseMoved)
+ coin.SoLocation2Event.getClassTypeId(), self.mouseMoved
+ )
if self._mousePressedCB is None:
self._mousePressedCB = self.view.addEventCallbackPivy(
- coin.SoMouseButtonEvent.getClassTypeId(), self.mousePressed)
- #App.Console.PrintMessage("Draft edit callbacks registered \n")
+ coin.SoMouseButtonEvent.getClassTypeId(), self.mousePressed
+ )
+ # App.Console.PrintMessage("Draft edit callbacks registered \n")
def unregister_editing_callbacks(self):
"""
@@ -390,14 +393,20 @@ class Edit(gui_base_original.Modifier):
"""
try:
if self._keyPressedCB:
- self.view.removeEventCallbackSWIG(coin.SoKeyboardEvent.getClassTypeId(), self._keyPressedCB)
- #App.Console.PrintMessage("Draft edit keyboard callback unregistered \n")
+ self.view.removeEventCallbackSWIG(
+ coin.SoKeyboardEvent.getClassTypeId(), self._keyPressedCB
+ )
+ # App.Console.PrintMessage("Draft edit keyboard callback unregistered \n")
if self._mouseMovedCB:
- self.view.removeEventCallbackSWIG(coin.SoLocation2Event.getClassTypeId(), self._mouseMovedCB)
- #App.Console.PrintMessage("Draft edit location callback unregistered \n")
+ self.view.removeEventCallbackSWIG(
+ coin.SoLocation2Event.getClassTypeId(), self._mouseMovedCB
+ )
+ # App.Console.PrintMessage("Draft edit location callback unregistered \n")
if self._mousePressedCB:
- self.view.removeEventCallbackSWIG(coin.SoMouseButtonEvent.getClassTypeId(), self._mousePressedCB)
- #App.Console.PrintMessage("Draft edit mouse button callback unregistered \n")
+ self.view.removeEventCallbackSWIG(
+ coin.SoMouseButtonEvent.getClassTypeId(), self._mousePressedCB
+ )
+ # App.Console.PrintMessage("Draft edit mouse button callback unregistered \n")
except RuntimeError:
# the view has been deleted already
pass
@@ -420,7 +429,9 @@ class Edit(gui_base_original.Modifier):
self.finish()
if key == 101: # "e"
self.display_tracker_menu(event)
- if key == 65535 and Gui.Selection.getSelection() is None: # BUG: delete key activate Std::Delete command at the same time!
+ if (
+ key == 65535 and Gui.Selection.getSelection() is None
+ ): # BUG: delete key activate Std::Delete command at the same time!
print("DELETE PRESSED\n")
self.delPoint(event)
@@ -429,9 +440,9 @@ class Edit(gui_base_original.Modifier):
mouse button event handler, calls: startEditing, endEditing, addPoint, delPoint
"""
event = event_callback.getEvent()
- if (event.getState() == coin.SoMouseButtonEvent.DOWN and
- event.getButton() == event.BUTTON1
- ):#left click
+ if (
+ event.getState() == coin.SoMouseButtonEvent.DOWN and event.getButton() == event.BUTTON1
+ ): # left click
if not event.wasAltDown():
if self.editing is None:
@@ -474,13 +485,11 @@ class Edit(gui_base_original.Modifier):
def startEditing(self, obj, node_idx):
"""Start editing selected EditNode."""
- self.obj = obj # this is still needed to handle preview
+ self.obj = obj # this is still needed to handle preview
if obj is None:
return
- App.Console.PrintMessage(obj.Name
- + ": editing node number "
- + str(node_idx) + "\n")
+ App.Console.PrintMessage(obj.Name + ": editing node number " + str(node_idx) + "\n")
self.ui.lineUi(title=translate("draft", "Edit Node"), icon="Draft_Edit")
self.ui.continueCmd.hide()
@@ -500,7 +509,7 @@ class Edit(gui_base_original.Modifier):
orthoConstrain = False
if event.wasShiftDown() == 1:
orthoConstrain = True
- snappedPos = Gui.Snapper.snap((pos[0],pos[1]),self.node[-1], constrain=orthoConstrain)
+ snappedPos = Gui.Snapper.snap((pos[0], pos[1]), self.node[-1], constrain=orthoConstrain)
self.trackers[self.obj.Name][self.editing].set(snappedPos)
self.ui.displayPoint(snappedPos, self.node[-1], mask=Gui.Snapper.affinity)
if self.ghost:
@@ -526,7 +535,6 @@ class Edit(gui_base_original.Modifier):
self.showTrackers()
gui_tool_utils.redraw_3d_view()
-
# -------------------------------------------------------------------------
# EDIT TRACKERS functions
# -------------------------------------------------------------------------
@@ -539,14 +547,16 @@ class Edit(gui_base_original.Modifier):
_wrn = translate("draft", "No edit point found for selected object")
App.Console.PrintWarning(_wrn + "\n")
# do not finish if some trackers are still present
- if self.trackers == {'object': []}:
+ if self.trackers == {"object": []}:
self.finish()
return
self.trackers[obj.Name] = []
if obj.Name in self.trackers:
self.removeTrackers(obj)
for ep in range(len(points)):
- self.trackers[obj.Name].append(trackers.editTracker(pos=points[ep], name=obj.Name, idx=ep))
+ self.trackers[obj.Name].append(
+ trackers.editTracker(pos=points[ep], name=obj.Name, idx=ep)
+ )
def resetTrackers(self, obj):
"""Reset Edit Trackers and set them again."""
@@ -557,28 +567,28 @@ class Edit(gui_base_original.Modifier):
# in future move tracker definition to DraftTrackers
size = params.get_param_view("MarkerSize")
knotmarkers = (
- Gui.getMarkerIndex("DIAMOND_FILLED", size), # sharp
- Gui.getMarkerIndex("SQUARE_FILLED", size), # tangent
- Gui.getMarkerIndex("HOURGLASS_FILLED", size) # symmetric
+ Gui.getMarkerIndex("DIAMOND_FILLED", size), # sharp
+ Gui.getMarkerIndex("SQUARE_FILLED", size), # tangent
+ Gui.getMarkerIndex("HOURGLASS_FILLED", size), # symmetric
)
- polemarker = Gui.getMarkerIndex("CIRCLE_FILLED", size) # pole
+ polemarker = Gui.getMarkerIndex("CIRCLE_FILLED", size) # pole
self.trackers[obj.Name] = []
cont = obj.Continuity
firstknotcont = cont[-1] if (obj.Closed and cont) else 0
- pointswithmarkers = [(obj.Shape.Edges[0].Curve.
- getPole(1),knotmarkers[firstknotcont])]
+ pointswithmarkers = [(obj.Shape.Edges[0].Curve.getPole(1), knotmarkers[firstknotcont])]
for edgeindex, edge in enumerate(obj.Shape.Edges):
poles = edge.Curve.getPoles()
- pointswithmarkers.extend([(point,polemarker) for point in poles[1:-1]])
- if not obj.Closed or len(obj.Shape.Edges) > edgeindex +1:
+ pointswithmarkers.extend([(point, polemarker) for point in poles[1:-1]])
+ if not obj.Closed or len(obj.Shape.Edges) > edgeindex + 1:
knotmarkeri = cont[edgeindex] if len(cont) > edgeindex else 0
- pointswithmarkers.append((poles[-1],knotmarkers[knotmarkeri]))
+ pointswithmarkers.append((poles[-1], knotmarkers[knotmarkeri]))
for index, pwm in enumerate(pointswithmarkers):
p, marker = pwm
p = obj.Placement.inverse().multVec(p)
p = obj.getGlobalPlacement().multVec(p)
- self.trackers[obj.Name].append(trackers.editTracker(p, obj.Name,
- index, obj.ViewObject.LineColor, marker=marker))
+ self.trackers[obj.Name].append(
+ trackers.editTracker(p, obj.Name, index, obj.ViewObject.LineColor, marker=marker)
+ )
def removeTrackers(self, obj=None):
"""Remove Edit Trackers.
@@ -593,7 +603,7 @@ class Edit(gui_base_original.Modifier):
for key in self.trackers:
for t in self.trackers[key]:
t.finalize()
- self.trackers = {'object': []}
+ self.trackers = {"object": []}
else:
key = obj.Name
if key in self.trackers:
@@ -690,7 +700,8 @@ class Edit(gui_base_original.Modifier):
if actions is None:
return
- for (label, callback) in actions:
+ for label, callback in actions:
+
def wrapper(callback=callback):
callback()
self.resetTrackers(obj)
@@ -700,16 +711,14 @@ class Edit(gui_base_original.Modifier):
self.tracker_menu.popup(Gui.getMainWindow().cursor().pos())
- QtCore.QObject.connect(self.tracker_menu,
- QtCore.SIGNAL("triggered(QAction *)"),
- self.evaluate_menu_action)
-
+ QtCore.QObject.connect(
+ self.tracker_menu, QtCore.SIGNAL("triggered(QAction *)"), self.evaluate_menu_action
+ )
def evaluate_menu_action(self, action):
callback = action.data()
callback()
-
# -------------------------------------------------------------------------
# EDIT OBJECT TOOLS
#
@@ -718,8 +727,7 @@ class Edit(gui_base_original.Modifier):
# -------------------------------------------------------------------------
def getEditPoints(self, obj):
- """Return a list of App.Vectors according to the given object edit nodes.
- """
+ """Return a list of App.Vectors according to the given object edit nodes."""
eps = None
obj_gui_tools = self.get_obj_gui_tools(obj)
@@ -731,7 +739,6 @@ class Edit(gui_base_original.Modifier):
else:
return None
-
def update(self, obj, nodeIndex, v):
"""Apply the App.Vector to the modified point and update obj."""
v = self.localize_vector(obj, v)
@@ -744,35 +751,33 @@ class Edit(gui_base_original.Modifier):
except AttributeError as err:
pass
-
def update_object(self, obj, nodeIndex, v):
- """Update the object according to the given modified editpoint.
- """
+ """Update the object according to the given modified editpoint."""
obj_gui_tools = self.get_obj_gui_tools(obj)
if obj_gui_tools:
- eps = obj_gui_tools.update_object_from_edit_points(obj, nodeIndex, v, self.alt_edit_mode)
+ eps = obj_gui_tools.update_object_from_edit_points(
+ obj, nodeIndex, v, self.alt_edit_mode
+ )
obj.recompute()
-
# -------------------------------------------------------------------------
# UTILS
# -------------------------------------------------------------------------
def has_obj_gui_tools(self, obj):
- """ Check if the object has the GuiTools to provide information to edit it.
- """
- if (hasattr(obj, 'obj_gui_tools') or
- (hasattr(obj, 'Proxy') and hasattr(obj.Proxy, 'obj_gui_tools')) or
- (utils.get_type(obj) in self.gui_tools_repository.keys()) ):
+ """Check if the object has the GuiTools to provide information to edit it."""
+ if (
+ hasattr(obj, "obj_gui_tools")
+ or (hasattr(obj, "Proxy") and hasattr(obj.Proxy, "obj_gui_tools"))
+ or (utils.get_type(obj) in self.gui_tools_repository.keys())
+ ):
return True
else:
return False
-
def get_obj_gui_tools(self, obj):
- """ Retrieve the obj_gui_tools to support Draft Edit.
- """
+ """Retrieve the obj_gui_tools to support Draft Edit."""
try:
obj_gui_tools = obj.obj_gui_tools
except AttributeError:
@@ -785,14 +790,13 @@ class Edit(gui_base_original.Modifier):
obj_gui_tools = None
return obj_gui_tools
-
def getObjsFromSelection(self):
"""Evaluate selection and return a valid object to edit.
#to be used for app link support
for selobj in Gui.Selection.getSelectionEx('', 0):
- for sub in selobj.SubElementNames:
+ for sub in selobj.SubElementNames:
obj = selobj.Object
obj_matrix = selobj.Object.getSubObject(sub, retType=4)
"""
@@ -811,20 +815,16 @@ class Edit(gui_base_original.Modifier):
App.Console.PrintWarning(obj.Name + _wrn + "\n")
return self.edited_objects
-
def format_objects_for_editing(self, objs):
- """Change objects style during editing mode.
- """
+ """Change objects style during editing mode."""
for obj in objs:
obj_gui_tools = self.get_obj_gui_tools(obj)
if obj_gui_tools:
self.objs_formats[obj.Name] = obj_gui_tools.get_object_style(obj)
obj_gui_tools.set_object_editing_style(obj)
-
def deformat_objects_after_editing(self, objs):
- """Restore objects style during editing mode.
- """
+ """Restore objects style during editing mode."""
for obj in objs:
if utils.is_deleted(obj):
continue
@@ -832,11 +832,9 @@ class Edit(gui_base_original.Modifier):
if obj_gui_tools:
obj_gui_tools.restore_object_style(obj, self.objs_formats[obj.Name])
-
def get_specific_object_info(self, obj, pos):
- """Return info of a specific object at a given position.
- """
- selobjs = self.view.getObjectsInfo((pos[0],pos[1]))
+ """Return info of a specific object at a given position."""
+ selobjs = self.view.getObjectsInfo((pos[0], pos[1]))
if not selobjs:
return
for info in selobjs:
@@ -852,7 +850,7 @@ class Edit(gui_base_original.Modifier):
If object is one of the edited objects (self.edited_objects).
"""
- selobjs = self.view.getObjectsInfo((pos[0],pos[1]))
+ selobjs = self.view.getObjectsInfo((pos[0], pos[1]))
if not selobjs:
return
for info in selobjs:
@@ -913,8 +911,10 @@ class Edit(gui_base_original.Modifier):
path = point.getPath()
length = path.getLength()
point = path.getNode(length - 2)
- #import DraftTrackers
- if hasattr(point,"subElementName") and 'EditNode' in str(point.subElementName.getValue()):
+ # import DraftTrackers
+ if hasattr(point, "subElementName") and "EditNode" in str(
+ point.subElementName.getValue()
+ ):
return point
return None
@@ -928,16 +928,16 @@ class Edit(gui_base_original.Modifier):
return None
-
-class GuiToolsRepository():
- """ This object provide a repository to collect all the specific objects
+class GuiToolsRepository:
+ """This object provide a repository to collect all the specific objects
editing tools.
"""
+
def __init__(self):
- self.obj_gui_tools = {}
+ self.obj_gui_tools = {}
def get(self, obj_type):
- return self.obj_gui_tools[obj_type]
+ return self.obj_gui_tools[obj_type]
def add(self, type, gui_tools):
self.obj_gui_tools[type] = gui_tools
@@ -946,7 +946,6 @@ class GuiToolsRepository():
return self.obj_gui_tools.keys()
-
-Gui.addCommand('Draft_Edit', Edit())
+Gui.addCommand("Draft_Edit", Edit())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_edit_arch_objects.py b/src/Mod/Draft/draftguitools/gui_edit_arch_objects.py
index 2ddcd0a02f..0b175b34bc 100644
--- a/src/Mod/Draft/draftguitools/gui_edit_arch_objects.py
+++ b/src/Mod/Draft/draftguitools/gui_edit_arch_objects.py
@@ -26,8 +26,9 @@
# \brief Provides support functions to edit Arch objects.
__title__ = "FreeCAD Draft Edit Tool"
-__author__ = ("Yorik van Havre, Werner Mayer, Martin Burbaum, Ken Cline, "
- "Dmitry Chigrin, Carlo Pavan")
+__author__ = (
+ "Yorik van Havre, Werner Mayer, Martin Burbaum, Ken Cline, " "Dmitry Chigrin, Carlo Pavan"
+)
__url__ = "https://www.freecad.org"
## \addtogroup draftguitools
@@ -42,7 +43,6 @@ import draftutils.utils as utils
from draftguitools.gui_edit_base_object import GuiTools
-
class ArchWallGuiTools(GuiTools):
def __init__(self):
@@ -61,13 +61,13 @@ class ArchWallGuiTools(GuiTools):
return editpoints
def update_object_from_edit_points(self, obj, node_idx, v, alt_edit_mode=0):
- ''' if node_idx == 0:
+ """if node_idx == 0:
edit_arch.updateWall(obj, node_idx, v)
elif node_idx > 0:
if obj.Base:
if utils.get_type(obj.Base) in ["Wire", "Circle", "Rectangle",
"Polygon", "Sketch"]:
- self.update(obj.Base, node_idx - 1, v)'''
+ self.update(obj.Base, node_idx - 1, v)"""
if node_idx == 0:
vz = DraftVecUtils.project(v, App.Vector(0, 0, 1))
if vz.Length > 0:
@@ -86,9 +86,13 @@ class ArchWindowGuiTools(GuiTools):
normal = obj.Normal
angle = normal.getAngle(App.Vector(1, 0, 0))
editpoints.append(pos)
- editpoints.append(App.Vector(pos.x + float(obj.Width) * math.cos(angle-math.pi / 2.0),
- pos.y + float(obj.Width) * math.sin(angle-math.pi / 2.0),
- pos.z))
+ editpoints.append(
+ App.Vector(
+ pos.x + float(obj.Width) * math.cos(angle - math.pi / 2.0),
+ pos.y + float(obj.Width) * math.sin(angle - math.pi / 2.0),
+ pos.z,
+ )
+ )
editpoints.append(App.Vector(pos.x, pos.y, h))
return editpoints
@@ -127,9 +131,7 @@ class ArchStructureGuiTools(GuiTools):
obj.Nodes = nodes
def get_object_style(self, obj):
- return (obj.ViewObject.DisplayMode,
- obj.ViewObject.NodeSize,
- obj.ViewObject.ShowNodes)
+ return (obj.ViewObject.DisplayMode, obj.ViewObject.NodeSize, obj.ViewObject.ShowNodes)
def set_object_editing_style(self, obj):
obj.ViewObject.DisplayMode = "Wireframe"
@@ -195,6 +197,7 @@ class ArchPanelSheetGuiTools(GuiTools):
if node_idx == 0:
obj.TagPosition = v
else:
- obj.Group[node_idx-1].Placement.Base = v
+ obj.Group[node_idx - 1].Placement.Base = v
+
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_edit_base_object.py b/src/Mod/Draft/draftguitools/gui_edit_base_object.py
index d5d37822ce..6c58f3bf08 100644
--- a/src/Mod/Draft/draftguitools/gui_edit_base_object.py
+++ b/src/Mod/Draft/draftguitools/gui_edit_base_object.py
@@ -24,7 +24,7 @@
# \brief Provides support functions to edit Arch objects.
__title__ = "FreeCAD Draft Edit Tool"
-__author__ = ("Carlo Pavan")
+__author__ = "Carlo Pavan"
__url__ = "https://www.freecad.org"
## \addtogroup draftguitools
@@ -32,8 +32,7 @@ __url__ = "https://www.freecad.org"
class GuiTools:
- """ Base class for object editing tools
- """
+ """Base class for object editing tools"""
def __init__(self):
pass
@@ -62,7 +61,7 @@ class GuiTools:
pass
def get_edit_point_context_menu(self, edit_command, obj, node_idx):
- """ Get the context menu associated to edit points (user is over an editpoint)
+ """Get the context menu associated to edit points (user is over an editpoint)
Return a list of tuples containing menu labels and associated functions:
return [
@@ -77,7 +76,7 @@ class GuiTools:
pass
def get_edit_obj_context_menu(self, edit_command, obj, position):
- """ Get the context menu associated to edited object (user is over the object)
+ """Get the context menu associated to edited object (user is over the object)
Return a list of tuples containing menu labels and associated functions:
return [
@@ -106,4 +105,5 @@ class GuiTools:
def update_preview_object(self, edit_command, obj, node_idx, v):
pass
+
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_edit_draft_objects.py b/src/Mod/Draft/draftguitools/gui_edit_draft_objects.py
index 2a39673d69..4dfb811344 100644
--- a/src/Mod/Draft/draftguitools/gui_edit_draft_objects.py
+++ b/src/Mod/Draft/draftguitools/gui_edit_draft_objects.py
@@ -38,8 +38,9 @@ TODO: Abstract the code that handles the preview and move the object specific
# \brief Provides support functions to edit Draft objects.
__title__ = "FreeCAD Draft Edit Tool"
-__author__ = ("Yorik van Havre, Werner Mayer, Martin Burbaum, Ken Cline, "
- "Dmitry Chigrin, Carlo Pavan")
+__author__ = (
+ "Yorik van Havre, Werner Mayer, Martin Burbaum, Ken Cline, " "Dmitry Chigrin, Carlo Pavan"
+)
__url__ = "https://www.freecad.org"
## \addtogroup draftguitools
@@ -58,7 +59,6 @@ import draftguitools.gui_trackers as trackers
from draftguitools.gui_edit_base_object import GuiTools
-
class DraftWireGuiTools(GuiTools):
def __init__(self):
@@ -72,8 +72,8 @@ class DraftWireGuiTools(GuiTools):
def update_object_from_edit_points(self, obj, node_idx, v, alt_edit_mode=0):
pts = obj.Points
- tol = 0.001 # TODO : Use default precision
- if (node_idx == 0 and (v - pts[-1]).Length < tol ):
+ tol = 0.001 # TODO : Use default precision
+ if node_idx == 0 and (v - pts[-1]).Length < tol:
# DNC: user moved first point over last point -> Close curve
obj.Closed = True
pts[0] = v
@@ -88,14 +88,13 @@ class DraftWireGuiTools(GuiTools):
return
elif v in pts:
# DNC: checks if point enter is equal to other, this could cause a OCC problem
- _err = translate("draft", "This object does not support possible "
- "coincident points")
+ _err = translate("draft", "This object does not support possible " "coincident points")
App.Console.PrintMessage(_err + "\n")
return
# TODO: Make consistent operation with trackers and open wires
# See: https://forum.freecad.org/viewtopic.php?f=23&t=56661
- #if obj.Closed:
+ # if obj.Closed:
# # DNC: project the new point to the plane of the face if present
# if hasattr(obj.Shape, "normalAt"):
# normal = obj.Shape.normalAt(0,0)
@@ -118,16 +117,14 @@ class DraftWireGuiTools(GuiTools):
]
def get_open_close_menu_text(self, obj):
- """This function is overridden in the DraftBSplineGuiTools class.
- """
+ """This function is overridden in the DraftBSplineGuiTools class."""
if obj.Closed:
return translate("draft", "Open Wire")
else:
return translate("draft", "Close Wire")
def get_reverse_menu_text(self, obj):
- """This function is overridden in the DraftBSplineGuiTools class.
- """
+ """This function is overridden in the DraftBSplineGuiTools class."""
return translate("draft", "Reverse Wire")
def init_preview_object(self, obj):
@@ -142,13 +139,12 @@ class DraftWireGuiTools(GuiTools):
edit_command.ghost.updateFromPointlist(pointList)
def add_point(self, edit_command, obj, pos):
- """Add point to obj.
- """
- info, newPoint = edit_command.get_specific_object_info(obj,pos)
+ """Add point to obj."""
+ info, newPoint = edit_command.get_specific_object_info(obj, pos)
if not info:
return
- if not 'Edge' in info["Component"]:
+ if not "Edge" in info["Component"]:
return
edgeIndex = int(info["Component"][4:])
@@ -214,9 +210,8 @@ class DraftBSplineGuiTools(DraftWireGuiTools):
edit_command.ghost.update(pointList)
def add_point(self, edit_command, obj, pos):
- """Add point to obj.
- """
- info, global_pt = edit_command.get_specific_object_info(obj,pos)
+ """Add point to obj."""
+ info, global_pt = edit_command.get_specific_object_info(obj, pos)
pt = edit_command.localize_vector(obj, global_pt)
if not info or (pt is None):
@@ -231,7 +226,7 @@ class DraftBSplineGuiTools(DraftWireGuiTools):
uPoints = curve.getKnots()
for i in range(len(uPoints) - 1):
- if ( uNewPoint > uPoints[i] ) and ( uNewPoint < uPoints[i+1] ):
+ if (uNewPoint > uPoints[i]) and (uNewPoint < uPoints[i + 1]):
pts.insert(i + 1, pt)
break
# DNC: fix: add points to last segment if curve is closed
@@ -264,9 +259,9 @@ class DraftRectangleGuiTools(GuiTools):
if node_idx == 0:
obj.Placement.Base = obj.Placement.multVec(v)
elif node_idx == 1:
- obj.Length = DraftVecUtils.project(v, App.Vector(1,0,0)).Length
+ obj.Length = DraftVecUtils.project(v, App.Vector(1, 0, 0)).Length
elif node_idx == 2:
- obj.Height = DraftVecUtils.project(v, App.Vector(0,1,0)).Length
+ obj.Height = DraftVecUtils.project(v, App.Vector(0, 1, 0)).Length
class DraftCircleGuiTools(GuiTools):
@@ -291,12 +286,12 @@ class DraftCircleGuiTools(GuiTools):
editpoints.append(App.Vector(0, 0, 0))
if obj.FirstAngle == obj.LastAngle:
# obj is a circle
- editpoints.append(App.Vector(obj.Radius,0,0))
+ editpoints.append(App.Vector(obj.Radius, 0, 0))
else:
# obj is an arc
- editpoints.append(self.getArcStart(obj))#First endpoint
- editpoints.append(self.getArcEnd(obj))#Second endpoint
- editpoints.append(self.getArcMid(obj))#Midpoint
+ editpoints.append(self.getArcStart(obj)) # First endpoint
+ editpoints.append(self.getArcEnd(obj)) # Second endpoint
+ editpoints.append(self.getArcMid(obj)) # Midpoint
return editpoints
def update_object_from_edit_points(self, obj, node_idx, v, alt_edit_mode=0):
@@ -311,6 +306,7 @@ class DraftCircleGuiTools(GuiTools):
# obj is an arc
if alt_edit_mode == 0:
import Part
+
if node_idx == 0:
# center point
p1 = self.getArcStart(obj)
@@ -322,9 +318,8 @@ class DraftCircleGuiTools(GuiTools):
obj.Placement.Base = obj.Placement.multVec(p0)
else:
- """ Edit arc by 3 points.
- """
- v= obj.Placement.multVec(v)
+ """Edit arc by 3 points."""
+ v = obj.Placement.multVec(v)
p1 = obj.Placement.multVec(self.getArcStart(obj))
p2 = obj.Placement.multVec(self.getArcMid(obj))
p3 = obj.Placement.multVec(self.getArcEnd(obj))
@@ -336,8 +331,9 @@ class DraftCircleGuiTools(GuiTools):
elif node_idx == 2: # second point
p3 = v
- arc=Part.ArcOfCircle(p1, p2, p3)
+ arc = Part.ArcOfCircle(p1, p2, p3)
import Part
+
s = arc.toShape()
# Part.show(s) DEBUG
p0 = arc.Location
@@ -354,7 +350,7 @@ class DraftCircleGuiTools(GuiTools):
if node_idx == 0:
obj.Placement.Base = obj.Placement.multVec(v)
else:
- dangle = math.degrees(math.atan2(v[1],v[0]))
+ dangle = math.degrees(math.atan2(v[1], v[0]))
if node_idx == 1:
obj.FirstAngle = dangle
elif node_idx == 2:
@@ -362,25 +358,36 @@ class DraftCircleGuiTools(GuiTools):
elif node_idx == 3:
obj.Radius = v.Length
-
def get_edit_point_context_menu(self, edit_command, obj, node_idx):
actions = None
if obj.FirstAngle != obj.LastAngle:
if node_idx == 0: # user is over arc start point
return [
- (translate("draft", "Move Arc"), lambda: self.handle_move_arc(edit_command, obj, node_idx)),
+ (
+ translate("draft", "Move Arc"),
+ lambda: self.handle_move_arc(edit_command, obj, node_idx),
+ ),
]
elif node_idx == 1: # user is over arc start point
return [
- (translate("draft", "Set First Angle"), lambda: self.handle_set_first_angle(edit_command, obj, node_idx)),
+ (
+ translate("draft", "Set First Angle"),
+ lambda: self.handle_set_first_angle(edit_command, obj, node_idx),
+ ),
]
elif node_idx == 2: # user is over arc end point
return [
- (translate("draft", "Set Last Angle"), lambda: self.handle_set_last_angle(edit_command, obj, node_idx)),
+ (
+ translate("draft", "Set Last Angle"),
+ lambda: self.handle_set_last_angle(edit_command, obj, node_idx),
+ ),
]
elif node_idx == 3: # user is over arc mid point
return [
- (translate("draft", "Set Radius"), lambda: self.handle_set_radius(edit_command, obj, node_idx)),
+ (
+ translate("draft", "Set Radius"),
+ lambda: self.handle_set_radius(edit_command, obj, node_idx),
+ ),
]
def handle_move_arc(self, edit_command, obj, node_idx):
@@ -429,9 +436,13 @@ class DraftCircleGuiTools(GuiTools):
# center point
p1 = edit_command.localize_vector(obj, obj.Shape.Vertexes[0].Point)
p2 = edit_command.localize_vector(obj, obj.Shape.Vertexes[1].Point)
- p0 = DraftVecUtils.project(edit_command.localize_vector(obj, v),
- edit_command.localize_vector(obj, (self.getArcMid(obj, global_placement=True))))
- edit_command.ghost.autoinvert=False
+ p0 = DraftVecUtils.project(
+ edit_command.localize_vector(obj, v),
+ edit_command.localize_vector(
+ obj, (self.getArcMid(obj, global_placement=True))
+ ),
+ )
+ edit_command.ghost.autoinvert = False
edit_command.ghost.setRadius(p1.sub(p0).Length)
edit_command.ghost.setStartPoint(obj.Shape.Vertexes[1].Point)
edit_command.ghost.setEndPoint(obj.Shape.Vertexes[0].Point)
@@ -442,12 +453,12 @@ class DraftCircleGuiTools(GuiTools):
p2 = self.getArcMid(obj, global_placement=True)
p3 = self.getArcEnd(obj, global_placement=True)
if node_idx == 1:
- p1=v
+ p1 = v
elif node_idx == 3:
- p2=v
+ p2 = v
elif node_idx == 2:
- p3=v
- edit_command.ghost.setBy3Points(p1,p2,p3)
+ p3 = v
+ edit_command.ghost.setBy3Points(p1, p2, p3)
elif edit_command.alt_edit_mode == 1:
# edit by center radius angles
edit_command.ghost.setStartAngle(math.radians(obj.FirstAngle))
@@ -461,27 +472,23 @@ class DraftCircleGuiTools(GuiTools):
elif node_idx == 3:
edit_command.ghost.setRadius(edit_command.localize_vector(obj, v).Length)
-
- def getArcStart(self, obj, global_placement=False):#Returns object midpoint
+ def getArcStart(self, obj, global_placement=False): # Returns object midpoint
if utils.get_type(obj) == "Circle":
return self.pointOnCircle(obj, obj.FirstAngle, global_placement)
-
- def getArcEnd(self, obj, global_placement=False):#Returns object midpoint
+ def getArcEnd(self, obj, global_placement=False): # Returns object midpoint
if utils.get_type(obj) == "Circle":
return self.pointOnCircle(obj, obj.LastAngle, global_placement)
-
- def getArcMid(self, obj, global_placement=False):#Returns object midpoint
+ def getArcMid(self, obj, global_placement=False): # Returns object midpoint
if utils.get_type(obj) == "Circle":
if obj.LastAngle > obj.FirstAngle:
midAngle = obj.FirstAngle + (obj.LastAngle - obj.FirstAngle) / 2.0
else:
midAngle = obj.FirstAngle + (obj.LastAngle - obj.FirstAngle) / 2.0
- midAngle += App.Units.Quantity(180,App.Units.Angle)
+ midAngle += App.Units.Quantity(180, App.Units.Angle)
return self.pointOnCircle(obj, midAngle, global_placement)
-
def pointOnCircle(self, obj, angle, global_placement=False):
if utils.get_type(obj) == "Circle":
px = obj.Radius * math.cos(math.radians(angle))
@@ -492,7 +499,6 @@ class DraftCircleGuiTools(GuiTools):
return p
return None
-
def arcInvert(self, obj):
obj.FirstAngle, obj.LastAngle = obj.LastAngle, obj.FirstAngle
obj.recompute()
@@ -533,12 +539,14 @@ class DraftPolygonGuiTools(GuiTools):
def get_edit_points(self, obj):
editpoints = []
editpoints.append(App.Vector(0, 0, 0))
- if obj.DrawMode == 'inscribed':
+ if obj.DrawMode == "inscribed":
editpoints.append(obj.Placement.inverse().multVec(obj.Shape.Vertexes[0].Point))
else:
- editpoints.append(obj.Placement.inverse().multVec((obj.Shape.Vertexes[0].Point +
- obj.Shape.Vertexes[1].Point) / 2
- ))
+ editpoints.append(
+ obj.Placement.inverse().multVec(
+ (obj.Shape.Vertexes[0].Point + obj.Shape.Vertexes[1].Point) / 2
+ )
+ )
return editpoints
def update_object_from_edit_points(self, obj, node_idx, v, alt_edit_mode=0):
@@ -589,13 +597,15 @@ class DraftLabelGuiTools(GuiTools):
# If StraightDistance == 0.0, editpoint 1 is exactly on editpoint 0 => Move slightly editpoint 1 to allow selection of editpoint 0
editpoints[1] = 0.9 * editpoints[1] + 0.1 * editpoints[2]
else:
- pass # TODO : support custom direction with any number of points
+ pass # TODO : support custom direction with any number of points
return editpoints
def update_object_from_edit_points(self, obj, node_idx, v, alt_edit_mode=0):
if obj.StraightDirection != "Custom":
if node_idx == 0:
- vector_p1_p2 = obj.Placement.inverse().multVec(obj.Points[1]) - obj.Placement.inverse().multVec(v)
+ vector_p1_p2 = obj.Placement.inverse().multVec(
+ obj.Points[1]
+ ) - obj.Placement.inverse().multVec(v)
if obj.StraightDirection == "Horizontal":
if round(vector_p1_p2.y, utils.precision()) == 0.0:
obj.StraightDistance = vector_p1_p2.x
@@ -604,7 +614,9 @@ class DraftLabelGuiTools(GuiTools):
obj.StraightDistance = vector_p1_p2.y
obj.Placement.Base = v
elif node_idx == 1:
- vector_p1_p2 = obj.Placement.inverse().multVec(v) - obj.Placement.inverse().multVec(obj.Placement.Base)
+ vector_p1_p2 = obj.Placement.inverse().multVec(v) - obj.Placement.inverse().multVec(
+ obj.Placement.Base
+ )
if obj.StraightDirection == "Horizontal":
if round(vector_p1_p2.y, utils.precision()) == 0.0:
obj.StraightDistance = vector_p1_p2.x
@@ -618,7 +630,7 @@ class DraftLabelGuiTools(GuiTools):
elif node_idx == 2:
obj.TargetPoint = v
else:
- pass # TODO : support custom direction with any number of points
+ pass # TODO : support custom direction with any number of points
class DraftBezCurveGuiTools(GuiTools):
@@ -626,25 +638,25 @@ class DraftBezCurveGuiTools(GuiTools):
def __init__(self):
pass
-
def get_edit_points(self, obj):
editpoints = []
for p in obj.Points:
editpoints.append(p)
return editpoints
-
def update_object_from_edit_points(self, obj, node_idx, v, alt_edit_mode=0):
pts = obj.Points
# DNC: check for coincident startpoint/endpoint to auto close the curve
tol = 0.001
- if ( ( node_idx == 0 ) and ( (v - pts[-1]).Length < tol) ) or (
- node_idx == len(pts) - 1 ) and ( (v - pts[0]).Length < tol):
+ if (
+ ((node_idx == 0) and ((v - pts[-1]).Length < tol))
+ or (node_idx == len(pts) - 1)
+ and ((v - pts[0]).Length < tol)
+ ):
obj.Closed = True
# DNC: checks if point enter is equal to other, this could cause a OCC problem
if v in pts:
- _err = translate("draft", "This object does not support possible "
- "coincident points")
+ _err = translate("draft", "This object does not support possible " "coincident points")
App.Console.PrintMessage(_err + "\n")
return
@@ -652,20 +664,25 @@ class DraftBezCurveGuiTools(GuiTools):
if obj.Closed:
# check that the new point lies on the plane of the wire
- if hasattr(obj.Shape,"normalAt"):
- normal = obj.Shape.normalAt(0,0)
+ if hasattr(obj.Shape, "normalAt"):
+ normal = obj.Shape.normalAt(0, 0)
point_on_plane = obj.Shape.Vertexes[0].Point
v.projectToPlane(point_on_plane, normal)
pts[node_idx] = v
obj.Points = pts
-
def get_edit_point_context_menu(self, edit_command, obj, node_idx):
return [
(translate("draft", "Delete Point"), lambda: self.delete_point(obj, node_idx)),
(translate("draft", "Make Sharp"), lambda: self.smoothBezPoint(obj, node_idx, "Sharp")),
- (translate("draft", "Make Tangent"), lambda: self.smoothBezPoint(obj, node_idx, "Tangent")),
- (translate("draft", "Make Symmetric"), lambda: self.smoothBezPoint(obj, node_idx, "Symmetric")),
+ (
+ translate("draft", "Make Tangent"),
+ lambda: self.smoothBezPoint(obj, node_idx, "Tangent"),
+ ),
+ (
+ translate("draft", "Make Symmetric"),
+ lambda: self.smoothBezPoint(obj, node_idx, "Symmetric"),
+ ),
]
def get_edit_obj_context_menu(self, edit_command, obj, position):
@@ -686,74 +703,75 @@ class DraftBezCurveGuiTools(GuiTools):
def update_preview_object(self, edit_command, obj, node_idx, v):
plist = edit_command.globalize_vectors(obj, obj.Points)
- pointList = self.recomputePointsBezier(obj,plist,node_idx,v,obj.Degree,moveTrackers=False)
+ pointList = self.recomputePointsBezier(
+ obj, plist, node_idx, v, obj.Degree, moveTrackers=False
+ )
edit_command.ghost.update(pointList, obj.Degree)
- def recomputePointsBezier(self, obj, pts, idx, v,
- degree, moveTrackers=False):
+ def recomputePointsBezier(self, obj, pts, idx, v, degree, moveTrackers=False):
"""
(object, Points as list, nodeIndex as Int, App.Vector of new point, moveTrackers as Bool)
return the new point list, applying the App.Vector to the given index point
"""
# DNC: allows one to close the curve by placing ends close to each other
tol = 0.001
- if ( ( idx == 0 ) and ( (v - pts[-1]).Length < tol) ) or (
- idx == len(pts) - 1 ) and ( (v - pts[0]).Length < tol):
+ if (
+ ((idx == 0) and ((v - pts[-1]).Length < tol))
+ or (idx == len(pts) - 1)
+ and ((v - pts[0]).Length < tol)
+ ):
obj.Closed = True
# DNC: fix error message if edited point coincides with one of the existing points
- #if ( v in pts ) == False:
+ # if ( v in pts ) == False:
knot = None
ispole = idx % degree
- if ispole == 0: #knot
+ if ispole == 0: # knot
if degree >= 3:
- if idx >= 1: #move left pole
+ if idx >= 1: # move left pole
knotidx = idx if idx < len(pts) else 0
- pts[idx-1] = pts[idx-1] + v - pts[knotidx]
- #if moveTrackers: # trackers are reset after editing
+ pts[idx - 1] = pts[idx - 1] + v - pts[knotidx]
+ # if moveTrackers: # trackers are reset after editing
# self.trackers[obj.Name][idx-1].set(pts[idx-1])
- if idx < len(pts)-1: #move right pole
- pts[idx+1] = pts[idx+1] + v - pts[idx]
- #if moveTrackers:
+ if idx < len(pts) - 1: # move right pole
+ pts[idx + 1] = pts[idx + 1] + v - pts[idx]
+ # if moveTrackers:
# self.trackers[obj.Name][idx+1].set(pts[idx+1])
- if idx == 0 and obj.Closed: # move last pole
- pts[-1] = pts [-1] + v -pts[idx]
- #if moveTrackers:
+ if idx == 0 and obj.Closed: # move last pole
+ pts[-1] = pts[-1] + v - pts[idx]
+ # if moveTrackers:
# self.trackers[obj.Name][-1].set(pts[-1])
- elif ispole == 1 and (idx >=2 or obj.Closed): #right pole
- knot = idx -1
+ elif ispole == 1 and (idx >= 2 or obj.Closed): # right pole
+ knot = idx - 1
changep = idx - 2 # -1 in case of closed curve
- elif ispole == degree-1 and idx <= len(pts)-3: # left pole
+ elif ispole == degree - 1 and idx <= len(pts) - 3: # left pole
knot = idx + 1
changep = idx + 2
- elif ispole == degree-1 and obj.Closed and idx == len(pts)-1: #last pole
+ elif ispole == degree - 1 and obj.Closed and idx == len(pts) - 1: # last pole
knot = 0
changep = 1
if knot is not None: # we need to modify the opposite pole
segment = int(knot / degree) - 1
cont = obj.Continuity[segment] if len(obj.Continuity) > segment else 0
- if cont == 1: #tangent
- pts[changep] = obj.Proxy.modifytangentpole(pts[knot],
- v,pts[changep])
- #if moveTrackers:
+ if cont == 1: # tangent
+ pts[changep] = obj.Proxy.modifytangentpole(pts[knot], v, pts[changep])
+ # if moveTrackers:
# self.trackers[obj.Name][changep].set(pts[changep])
- elif cont == 2: #symmetric
- pts[changep] = obj.Proxy.modifysymmetricpole(pts[knot],v)
- #if moveTrackers:
+ elif cont == 2: # symmetric
+ pts[changep] = obj.Proxy.modifysymmetricpole(pts[knot], v)
+ # if moveTrackers:
# self.trackers[obj.Name][changep].set(pts[changep])
pts[idx] = v
return pts # returns the list of new points, taking into account knot continuity
-
- def smoothBezPoint(self, obj, point, style='Symmetric'):
- """called when changing the continuity of a knot
- """
- style2cont = {'Sharp':0,'Tangent':1,'Symmetric':2}
+ def smoothBezPoint(self, obj, point, style="Symmetric"):
+ """called when changing the continuity of a knot"""
+ style2cont = {"Sharp": 0, "Tangent": 1, "Symmetric": 2}
if point is None:
return
if not (utils.get_type(obj) == "BezCurve"):
@@ -763,95 +781,96 @@ class DraftBezCurveGuiTools(GuiTools):
if deg < 2:
return
if point % deg != 0: # point is a pole
- if deg >=3: # allow one to select poles
- if (point % deg == 1) and (point > 2 or obj.Closed): #right pole
- knot = point -1
+ if deg >= 3: # allow one to select poles
+ if (point % deg == 1) and (point > 2 or obj.Closed): # right pole
+ knot = point - 1
keepp = point
- changep = point -2
- elif point < len(pts) -3 and point % deg == deg -1: #left pole
- knot = point +1
+ changep = point - 2
+ elif point < len(pts) - 3 and point % deg == deg - 1: # left pole
+ knot = point + 1
keepp = point
- changep = point +2
- elif point == len(pts)-1 and obj.Closed: #last pole
+ changep = point + 2
+ elif point == len(pts) - 1 and obj.Closed: # last pole
# if the curve is closed the last pole has the last
# index in the points lists
knot = 0
keepp = point
changep = 1
else:
- App.Console.PrintWarning(translate("draft",
- "Cannot change knot belonging to pole %d"%point)
- + "\n")
+ App.Console.PrintWarning(
+ translate("draft", "Cannot change knot belonging to pole %d" % point) + "\n"
+ )
return
if knot:
- if style == 'Tangent':
- pts[changep] = obj.Proxy.modifytangentpole(pts[knot],
- pts[keepp],pts[changep])
- elif style == 'Symmetric':
- pts[changep] = obj.Proxy.modifysymmetricpole(pts[knot],
- pts[keepp])
- else: #sharp
- pass #
+ if style == "Tangent":
+ pts[changep] = obj.Proxy.modifytangentpole(
+ pts[knot], pts[keepp], pts[changep]
+ )
+ elif style == "Symmetric":
+ pts[changep] = obj.Proxy.modifysymmetricpole(pts[knot], pts[keepp])
+ else: # sharp
+ pass #
else:
- App.Console.PrintWarning(translate("draft",
- "Selection is not a knot")
- + "\n")
+ App.Console.PrintWarning(translate("draft", "Selection is not a knot") + "\n")
return
- else: #point is a knot
- if style == 'Sharp':
- if obj.Closed and point == len(pts)-1:
+ else: # point is a knot
+ if style == "Sharp":
+ if obj.Closed and point == len(pts) - 1:
knot = 0
else:
knot = point
- elif style == 'Tangent' and point > 0 and point < len(pts)-1:
- prev, next = obj.Proxy.tangentpoles(pts[point], pts[point-1], pts[point+1])
- pts[point-1] = prev
- pts[point+1] = next
+ elif style == "Tangent" and point > 0 and point < len(pts) - 1:
+ prev, next = obj.Proxy.tangentpoles(pts[point], pts[point - 1], pts[point + 1])
+ pts[point - 1] = prev
+ pts[point + 1] = next
knot = point # index for continuity
- elif style == 'Symmetric' and point > 0 and point < len(pts)-1:
- prev, next = obj.Proxy.symmetricpoles(pts[point], pts[point-1], pts[point+1])
- pts[point-1] = prev
- pts[point+1] = next
+ elif style == "Symmetric" and point > 0 and point < len(pts) - 1:
+ prev, next = obj.Proxy.symmetricpoles(pts[point], pts[point - 1], pts[point + 1])
+ pts[point - 1] = prev
+ pts[point + 1] = next
knot = point # index for continuity
- elif obj.Closed and (style == 'Symmetric' or style == 'Tangent'):
- if style == 'Tangent':
+ elif obj.Closed and (style == "Symmetric" or style == "Tangent"):
+ if style == "Tangent":
pts[1], pts[-1] = obj.Proxy.tangentpoles(pts[0], pts[1], pts[-1])
- elif style == 'Symmetric':
+ elif style == "Symmetric":
pts[1], pts[-1] = obj.Proxy.symmetricpoles(pts[0], pts[1], pts[-1])
knot = 0
else:
- App.Console.PrintWarning(translate("draft",
- "Endpoint of Bézier curve cannot be smoothed")
- + "\n")
+ App.Console.PrintWarning(
+ translate("draft", "Endpoint of Bézier curve cannot be smoothed") + "\n"
+ )
return
segment = knot // deg # segment index
newcont = obj.Continuity[:] # don't edit a property inplace !!!
- if not obj.Closed and (len(obj.Continuity) == segment -1 or
- segment == 0) :
- pass # open curve
- elif (len(obj.Continuity) >= segment or obj.Closed and segment == 0 and
- len(obj.Continuity) >1):
- newcont[segment-1] = style2cont.get(style)
- else: #should not happen
- App.Console.PrintWarning('Continuity indexing error:'
- + 'point:%d deg:%d len(cont):%d' % (knot,deg,
- len(obj.Continuity)))
+ if not obj.Closed and (len(obj.Continuity) == segment - 1 or segment == 0):
+ pass # open curve
+ elif (
+ len(obj.Continuity) >= segment
+ or obj.Closed
+ and segment == 0
+ and len(obj.Continuity) > 1
+ ):
+ newcont[segment - 1] = style2cont.get(style)
+ else: # should not happen
+ App.Console.PrintWarning(
+ "Continuity indexing error:"
+ + "point:%d deg:%d len(cont):%d" % (knot, deg, len(obj.Continuity))
+ )
obj.Points = pts
obj.Continuity = newcont
def add_point(self, edit_command, obj, pos):
- """Add point to obj and reset trackers.
- """
- info, pt = edit_command.get_specific_object_info(obj,pos)
+ """Add point to obj and reset trackers."""
+ info, pt = edit_command.get_specific_object_info(obj, pos)
if not info or (pt is None):
return
import Part
pts = obj.Points
- if not info['Component'].startswith('Edge'):
+ if not info["Component"].startswith("Edge"):
return # clicked control point
- edgeindex = int(info['Component'].lstrip('Edge')) - 1
+ edgeindex = int(info["Component"].lstrip("Edge")) - 1
wire = obj.Shape.Wires[0]
bz = wire.Edges[edgeindex].Curve
param = bz.parameter(pt)
@@ -861,11 +880,14 @@ class DraftBezCurveGuiTools(GuiTools):
seg2.segment(param, seg2.LastParameter)
if edgeindex == len(wire.Edges):
# we hit the last segment, we need to fix the degree
- degree=wire.Edges[0].Curve.Degree
+ degree = wire.Edges[0].Curve.Degree
seg1.increase(degree)
seg2.increase(degree)
- edges = wire.Edges[0:edgeindex] + [Part.Edge(seg1),Part.Edge(seg2)] \
- + wire.Edges[edgeindex + 1:]
+ edges = (
+ wire.Edges[0:edgeindex]
+ + [Part.Edge(seg1), Part.Edge(seg2)]
+ + wire.Edges[edgeindex + 1 :]
+ )
pts = edges[0].Curve.getPoles()[0:1]
for edge in edges:
pts.extend(edge.Curve.getPoles()[1:])
@@ -900,4 +922,5 @@ class DraftBezCurveGuiTools(GuiTools):
obj.Points = reversed(obj.Points)
obj.recompute()
+
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_edit_part_objects.py b/src/Mod/Draft/draftguitools/gui_edit_part_objects.py
index 7433cf3869..5d0eed7bbc 100644
--- a/src/Mod/Draft/draftguitools/gui_edit_part_objects.py
+++ b/src/Mod/Draft/draftguitools/gui_edit_part_objects.py
@@ -24,8 +24,9 @@
# \brief Provides support functions to edit Part objects.
__title__ = "FreeCAD Draft Edit Tool"
-__author__ = ("Yorik van Havre, Werner Mayer, Martin Burbaum, Ken Cline, "
- "Dmitry Chigrin, Carlo Pavan")
+__author__ = (
+ "Yorik van Havre, Werner Mayer, Martin Burbaum, Ken Cline, " "Dmitry Chigrin, Carlo Pavan"
+)
__url__ = "https://www.freecad.org"
## \addtogroup draftguitools
@@ -43,8 +44,8 @@ class PartLineGuiTools(GuiTools):
def get_edit_points(self, obj):
editpoints = []
- editpoints.append(App.Vector(obj.X1,obj.Y1,obj.Z1))
- editpoints.append(App.Vector(obj.X2,obj.Y2,obj.Z2))
+ editpoints.append(App.Vector(obj.X1, obj.Y1, obj.Z1))
+ editpoints.append(App.Vector(obj.X2, obj.Y2, obj.Z2))
return editpoints
def update_object_from_edit_points(self, obj, node_idx, v, alt_edit_mode=0):
@@ -125,11 +126,11 @@ class PartConeGuiTools(GuiTools):
if node_idx == 0:
obj.Placement.Base = obj.Placement.Base + v
elif node_idx == 1:
- obj.Radius1 = v.Length # TODO: Perhaps better to project on the face?
+ obj.Radius1 = v.Length # TODO: Perhaps better to project on the face?
elif node_idx == 2:
v.z = 0
- obj.Radius2 = v.Length # TODO: Perhaps better to project on the face?
- elif node_idx == 3: # Height is last to have the priority on the radius
+ obj.Radius2 = v.Length # TODO: Perhaps better to project on the face?
+ elif node_idx == 3: # Height is last to have the priority on the radius
_vector = DraftVecUtils.project(v, App.Vector(0, 0, 1))
obj.Height = _vector.Length
@@ -150,6 +151,7 @@ class PartSphereGuiTools(GuiTools):
obj.Placement.Base = obj.Placement.Base + v
elif node_idx == 1:
if v.Length > 0.0:
- obj.Radius = v.Length # TODO: Perhaps better to project on the face?
+ obj.Radius = v.Length # TODO: Perhaps better to project on the face?
+
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_edit_sketcher_objects.py b/src/Mod/Draft/draftguitools/gui_edit_sketcher_objects.py
index 620432e0f3..7b1ecea7da 100644
--- a/src/Mod/Draft/draftguitools/gui_edit_sketcher_objects.py
+++ b/src/Mod/Draft/draftguitools/gui_edit_sketcher_objects.py
@@ -26,8 +26,9 @@
# \brief Provides support functions to edit Sketch objects.
__title__ = "FreeCAD Draft Edit Tool"
-__author__ = ("Yorik van Havre, Werner Mayer, Martin Burbaum, Ken Cline, "
- "Dmitry Chigrin, Carlo Pavan")
+__author__ = (
+ "Yorik van Havre, Werner Mayer, Martin Burbaum, Ken Cline, " "Dmitry Chigrin, Carlo Pavan"
+)
__url__ = "https://www.freecad.org"
## \addtogroup draftguitools
@@ -50,16 +51,22 @@ class SketcherSketchObjectGuiTools(GuiTools):
1 : endpoint
"""
import Part
+
editpoints = []
- if (obj.ConstraintCount == 0
- and obj.GeometryCount == 1
- and type(obj.Geometry[0]) == Part.LineSegment):
- editpoints.append(obj.getPoint(0,1))
- editpoints.append(obj.getPoint(0,2))
+ if (
+ obj.ConstraintCount == 0
+ and obj.GeometryCount == 1
+ and type(obj.Geometry[0]) == Part.LineSegment
+ ):
+ editpoints.append(obj.getPoint(0, 1))
+ editpoints.append(obj.getPoint(0, 2))
return editpoints
else:
- _wrn = translate("draft", "Sketch is too complex to edit: "
- "it is suggested to use the default Sketcher editor")
+ _wrn = translate(
+ "draft",
+ "Sketch is too complex to edit: "
+ "it is suggested to use the default Sketcher editor",
+ )
App.Console.PrintWarning(_wrn + "\n")
return None
@@ -79,4 +86,5 @@ class SketcherSketchObjectGuiTools(GuiTools):
obj.Geometry = [line]
obj.recompute()
+
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_ellipses.py b/src/Mod/Draft/draftguitools/gui_ellipses.py
index ded39d51ea..8a198eba6b 100644
--- a/src/Mod/Draft/draftguitools/gui_ellipses.py
+++ b/src/Mod/Draft/draftguitools/gui_ellipses.py
@@ -54,10 +54,12 @@ class Ellipse(gui_base_original.Creator):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_Ellipse',
- 'Accel': "E, L",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Ellipse", "Ellipse"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Ellipse", "Creates an ellipse")}
+ return {
+ "Pixmap": "Draft_Ellipse",
+ "Accel": "E, L",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Ellipse", "Ellipse"),
+ "ToolTip": QT_TRANSLATE_NOOP("Draft_Ellipse", "Creates an ellipse"),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -96,8 +98,8 @@ class Ellipse(gui_base_original.Creator):
center = p1.add(halfdiag)
p2 = p1.add(DraftVecUtils.project(diagonal, self.wp.v))
p4 = p1.add(DraftVecUtils.project(diagonal, self.wp.u))
- r1 = (p4.sub(p1).Length)/2
- r2 = (p2.sub(p1).Length)/2
+ r1 = (p4.sub(p1).Length) / 2
+ r2 = (p2.sub(p1).Length) / 2
try:
# The command to run is built as a series of text strings
# to be committed through the `draftutils.todo.ToDo` class.
@@ -105,7 +107,7 @@ class Ellipse(gui_base_original.Creator):
if r2 > r1:
r1, r2 = r2, r1
m = App.Matrix()
- m.rotateZ(math.pi/2)
+ m.rotateZ(math.pi / 2)
rot1 = App.Rotation()
rot1.Q = eval(rot)
rot2 = App.Placement(m)
@@ -114,37 +116,39 @@ class Ellipse(gui_base_original.Creator):
Gui.addModule("Draft")
if params.get_param("UsePartPrimitives"):
# Insert a Part::Primitive object
- _cmd = 'FreeCAD.ActiveDocument.'
+ _cmd = "FreeCAD.ActiveDocument."
_cmd += 'addObject("Part::Ellipse", "Ellipse")'
- _cmd_list = ['ellipse = ' + _cmd,
- 'ellipse.MajorRadius = ' + str(r1),
- 'ellipse.MinorRadius = ' + str(r2),
- 'pl = FreeCAD.Placement()',
- 'pl.Rotation.Q= ' + rot,
- 'pl.Base = ' + DraftVecUtils.toString(center),
- 'ellipse.Placement = pl',
- 'Draft.autogroup(ellipse)',
- 'Draft.select(ellipse)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Ellipse"),
- _cmd_list)
+ _cmd_list = [
+ "ellipse = " + _cmd,
+ "ellipse.MajorRadius = " + str(r1),
+ "ellipse.MinorRadius = " + str(r2),
+ "pl = FreeCAD.Placement()",
+ "pl.Rotation.Q= " + rot,
+ "pl.Base = " + DraftVecUtils.toString(center),
+ "ellipse.Placement = pl",
+ "Draft.autogroup(ellipse)",
+ "Draft.select(ellipse)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Ellipse"), _cmd_list)
else:
# Insert a Draft ellipse
- _cmd = 'Draft.make_ellipse'
- _cmd += '('
- _cmd += str(r1) + ', ' + str(r2) + ', '
- _cmd += 'placement=pl, '
- _cmd += 'face=' + fil + ', '
- _cmd += 'support=' + sup
- _cmd += ')'
- _cmd_list = ['pl = FreeCAD.Placement()',
- 'pl.Rotation.Q = ' + rot,
- 'pl.Base = ' + DraftVecUtils.toString(center),
- 'ellipse = ' + _cmd,
- 'Draft.autogroup(ellipse)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Ellipse"),
- _cmd_list)
+ _cmd = "Draft.make_ellipse"
+ _cmd += "("
+ _cmd += str(r1) + ", " + str(r2) + ", "
+ _cmd += "placement=pl, "
+ _cmd += "face=" + fil + ", "
+ _cmd += "support=" + sup
+ _cmd += ")"
+ _cmd_list = [
+ "pl = FreeCAD.Placement()",
+ "pl.Rotation.Q = " + rot,
+ "pl.Base = " + DraftVecUtils.toString(center),
+ "ellipse = " + _cmd,
+ "Draft.autogroup(ellipse)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Ellipse"), _cmd_list)
except Exception:
_err("Draft: Error: Unable to create object.")
self.finish(cont=None)
@@ -217,12 +221,14 @@ class Ellipse(gui_base_original.Creator):
hints = [
Gui.InputHint(translate("draft", "%1 pick opposite point"), Gui.UserInput.MouseLeft)
]
- return hints \
- + gui_tool_utils._get_hint_xyz_constrain() \
- + gui_tool_utils._get_hint_mod_constrain() \
+ return (
+ hints
+ + gui_tool_utils._get_hint_xyz_constrain()
+ + gui_tool_utils._get_hint_mod_constrain()
+ gui_tool_utils._get_hint_mod_snap()
+ )
-Gui.addCommand('Draft_Ellipse', Ellipse())
+Gui.addCommand("Draft_Ellipse", Ellipse())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_facebinders.py b/src/Mod/Draft/draftguitools/gui_facebinders.py
index 0b2f1f0e20..94a55b4fc4 100644
--- a/src/Mod/Draft/draftguitools/gui_facebinders.py
+++ b/src/Mod/Draft/draftguitools/gui_facebinders.py
@@ -55,10 +55,14 @@ class Facebinder(gui_base_original.Creator):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_Facebinder",
- "Accel": "F,F",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Facebinder", "Facebinder"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Facebinder", "Creates a facebinder from the selected faces")}
+ return {
+ "Pixmap": "Draft_Facebinder",
+ "Accel": "F,F",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Facebinder", "Facebinder"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Facebinder", "Creates a facebinder from the selected faces"
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
diff --git a/src/Mod/Draft/draftguitools/gui_fillets.py b/src/Mod/Draft/draftguitools/gui_fillets.py
index 3624acbfcf..ed788ef3da 100644
--- a/src/Mod/Draft/draftguitools/gui_fillets.py
+++ b/src/Mod/Draft/draftguitools/gui_fillets.py
@@ -64,10 +64,14 @@ class Fillet(gui_base_original.Creator):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_Fillet",
- "Accel": "F,I",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Fillet", "Fillet"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Fillet", "Creates a fillet between 2 selected edges")}
+ return {
+ "Pixmap": "Draft_Fillet",
+ "Accel": "F,I",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Fillet", "Fillet"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Fillet", "Creates a fillet between 2 selected edges"
+ ),
+ }
def Activated(self, name="Fillet"):
"""Execute when the command is called."""
@@ -87,23 +91,21 @@ class Fillet(gui_base_original.Creator):
self.ui.radiusValue.setToolTip(tooltip)
self.ui.radius = params.get_param("FilletRadius")
self.ui.setRadiusValue(self.ui.radius, "Length")
- self.ui.check_delete = self.ui._checkbox("isdelete",
- self.ui.layout,
- checked=self.delete)
- self.ui.check_delete.setText(translate("Draft",
- "Delete original objects"))
+ self.ui.check_delete = self.ui._checkbox(
+ "isdelete", self.ui.layout, checked=self.delete
+ )
+ self.ui.check_delete.setText(translate("Draft", "Delete original objects"))
self.ui.check_delete.show()
- self.ui.check_chamfer = self.ui._checkbox("ischamfer",
- self.ui.layout,
- checked=self.chamfer)
- self.ui.check_chamfer.setText(translate("Draft",
- "Create chamfer"))
+ self.ui.check_chamfer = self.ui._checkbox(
+ "ischamfer", self.ui.layout, checked=self.chamfer
+ )
+ self.ui.check_chamfer.setText(translate("Draft", "Create chamfer"))
self.ui.check_chamfer.show()
- if hasattr(self.ui.check_delete, "checkStateChanged"): # Qt version >= 6.7.0
+ if hasattr(self.ui.check_delete, "checkStateChanged"): # Qt version >= 6.7.0
self.ui.check_delete.checkStateChanged.connect(self.set_delete)
self.ui.check_chamfer.checkStateChanged.connect(self.set_chamfer)
- else: # Qt version < 6.7.0
+ else: # Qt version < 6.7.0
self.ui.check_delete.stateChanged.connect(self.set_delete)
self.ui.check_chamfer.stateChanged.connect(self.set_chamfer)
@@ -163,15 +165,17 @@ class Fillet(gui_base_original.Creator):
if delete:
cmd += ", delete=True"
cmd += ")"
- cmd_list = ["sels = FreeCADGui.Selection.getSelectionEx('', 0)",
- "fillet = " + cmd,
- "Draft.autogroup(fillet)",
- "FreeCAD.ActiveDocument.recompute()"]
+ cmd_list = [
+ "sels = FreeCADGui.Selection.getSelectionEx('', 0)",
+ "fillet = " + cmd,
+ "Draft.autogroup(fillet)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
self.commit(translate("draft", "Create Fillet"), cmd_list)
self.finish()
-Gui.addCommand('Draft_Fillet', Fillet())
+Gui.addCommand("Draft_Fillet", Fillet())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_grid.py b/src/Mod/Draft/draftguitools/gui_grid.py
index f3459fcb83..9d6db4daf6 100644
--- a/src/Mod/Draft/draftguitools/gui_grid.py
+++ b/src/Mod/Draft/draftguitools/gui_grid.py
@@ -55,12 +55,15 @@ class ToggleGrid(gui_base.GuiCommandSimplest):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_Grid",
- "Accel": "G, R",
- "MenuText": QT_TRANSLATE_NOOP("Draft_ToggleGrid", "Toggle Grid"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_ToggleGrid",
- "Toggles the visibility of the Draft grid"),
- "CmdType": "ForEdit"}
+ return {
+ "Pixmap": "Draft_Grid",
+ "Accel": "G, R",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_ToggleGrid", "Toggle Grid"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_ToggleGrid", "Toggles the visibility of the Draft grid"
+ ),
+ "CmdType": "ForEdit",
+ }
def IsActive(self):
"""Return True when this command should be available."""
@@ -90,6 +93,7 @@ class ToggleGrid(gui_base.GuiCommandSimplest):
WorkingPlane.get_working_plane()
grid.show_always = True
+
Gui.addCommand("Draft_ToggleGrid", ToggleGrid())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_groups.py b/src/Mod/Draft/draftguitools/gui_groups.py
index 920f922de6..41f0035cd7 100644
--- a/src/Mod/Draft/draftguitools/gui_groups.py
+++ b/src/Mod/Draft/draftguitools/gui_groups.py
@@ -69,9 +69,14 @@ class AddToGroup(gui_base.GuiCommandNeedsSelection):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_AddToGroup",
- "MenuText": QT_TRANSLATE_NOOP("Draft_AddToGroup", "Add to Group"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_AddToGroup", "Adds selected objects to a group, or removes them from any group")}
+ return {
+ "Pixmap": "Draft_AddToGroup",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_AddToGroup", "Add to Group"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_AddToGroup",
+ "Adds selected objects to a group, or removes them from any group",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -83,19 +88,21 @@ class AddToGroup(gui_base.GuiCommandNeedsSelection):
self.ui = Gui.draftToolBar
objs = [obj for obj in self.doc.Objects if groups.is_group(obj)]
objs.sort(key=lambda obj: obj.Label)
- self.objects = [None] \
- + [None] \
- + objs
- self.labels = [translate("draft", "Ungroup")] \
- + ["---"] \
- + [obj.Label for obj in objs] \
- + ["---"] \
- + [translate("draft", "Add to New Group")]
- self.icons = [self.ui.getIcon(":/icons/list-remove.svg")] \
- + [None] \
- + [obj.ViewObject.Icon for obj in objs] \
- + [None] \
- + [self.ui.getIcon(":/icons/list-add.svg")]
+ self.objects = [None] + [None] + objs
+ self.labels = (
+ [translate("draft", "Ungroup")]
+ + ["---"]
+ + [obj.Label for obj in objs]
+ + ["---"]
+ + [translate("draft", "Add to New Group")]
+ )
+ self.icons = (
+ [self.ui.getIcon(":/icons/list-remove.svg")]
+ + [None]
+ + [obj.ViewObject.Icon for obj in objs]
+ + [None]
+ + [self.ui.getIcon(":/icons/list-add.svg")]
+ )
# It uses the `DraftToolBar` class defined in the `DraftGui` module and
# globally initialized in the `Gui` namespace to pop up a menu.
@@ -149,7 +156,7 @@ def moveToGroup(group):
for obj in Gui.Selection.getSelection():
try:
- #retrieve group's visibility
+ # retrieve group's visibility
obj.ViewObject.Visibility = group.ViewObject.Visibility
group.addObject(obj)
@@ -165,9 +172,14 @@ class SelectGroup(gui_base.GuiCommandNeedsSelection):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_SelectGroup",
- "MenuText": QT_TRANSLATE_NOOP("Draft_SelectGroup", "Select Group"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_SelectGroup", "Selects the contents of selected groups. For selected non-group objects, the contents of the group they are in are selected.")}
+ return {
+ "Pixmap": "Draft_SelectGroup",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_SelectGroup", "Select Group"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_SelectGroup",
+ "Selects the contents of selected groups. For selected non-group objects, the contents of the group they are in are selected.",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -194,7 +206,9 @@ class SelectGroup(gui_base.GuiCommandNeedsSelection):
# Inform the user if there is no new selection:
if not Gui.Selection.hasSelection():
- msg = translate("draft", "No new selection. Select non-empty groups or objects inside groups.")
+ msg = translate(
+ "draft", "No new selection. Select non-empty groups or objects inside groups."
+ )
App.Console.PrintMessage(msg + "\n")
@@ -209,9 +223,13 @@ class SetAutoGroup(gui_base.GuiCommandSimplest):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_AutoGroup",
- "MenuText": QT_TRANSLATE_NOOP("Draft_AutoGroup", "Auto-Group"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_AutoGroup", "Adds new Draft and BIM objects to the selected layer or group")}
+ return {
+ "Pixmap": "Draft_AutoGroup",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_AutoGroup", "Auto-Group"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_AutoGroup", "Adds new Draft and BIM objects to the selected layer or group"
+ ),
+ }
def Activated(self):
"""Execute when the command is called.
@@ -230,9 +248,9 @@ class SetAutoGroup(gui_base.GuiCommandSimplest):
self.ui = Gui.draftToolBar
sel = Gui.Selection.getSelection()
if len(sel) == 1:
- if (utils.get_type(sel[0]) == "Layer"
- or (params.get_param("AutogroupAddGroups")
- and groups.is_group(sel[0]))):
+ if utils.get_type(sel[0]) == "Layer" or (
+ params.get_param("AutogroupAddGroups") and groups.is_group(sel[0])
+ ):
self.ui.setAutoGroup(sel[0].Name)
return
@@ -245,30 +263,34 @@ class SetAutoGroup(gui_base.GuiCommandSimplest):
grps = []
lyrs = [obj for obj in self.doc.Objects if utils.get_type(obj) == "Layer"]
lyrs.sort(key=lambda obj: obj.Label)
- self.names = [None] \
- + [None] \
- + [obj.Name for obj in grps] \
- + [None] \
- + [obj.Name for obj in lyrs]
- self.labels = [translate("draft", "None")] \
- + ["---"] \
- + [obj.Label for obj in grps] \
- + ["---"] \
- + [obj.Label for obj in lyrs] \
- + ["---"] \
- + [translate("draft", "New Layer")]
- self.icons = [self.ui.getIcon(":/icons/button_invalid.svg")] \
- + [None] \
- + [obj.ViewObject.Icon for obj in grps] \
- + [None] \
- + [obj.ViewObject.Icon for obj in lyrs] \
- + [None] \
- + [self.ui.getIcon(":/icons/Draft_NewLayer.svg")]
+ self.names = (
+ [None] + [None] + [obj.Name for obj in grps] + [None] + [obj.Name for obj in lyrs]
+ )
+ self.labels = (
+ [translate("draft", "None")]
+ + ["---"]
+ + [obj.Label for obj in grps]
+ + ["---"]
+ + [obj.Label for obj in lyrs]
+ + ["---"]
+ + [translate("draft", "New Layer")]
+ )
+ self.icons = (
+ [self.ui.getIcon(":/icons/button_invalid.svg")]
+ + [None]
+ + [obj.ViewObject.Icon for obj in grps]
+ + [None]
+ + [obj.ViewObject.Icon for obj in lyrs]
+ + [None]
+ + [self.ui.getIcon(":/icons/Draft_NewLayer.svg")]
+ )
# With the created lists it uses the interface to pop up a menu with options.
# Once the desired option is chosen it launches the `proceed` method.
self.ui.sourceCmd = self
- pos = self.ui.autoGroupButton.mapToGlobal(QtCore.QPoint(0, self.ui.autoGroupButton.geometry().height()))
+ pos = self.ui.autoGroupButton.mapToGlobal(
+ QtCore.QPoint(0, self.ui.autoGroupButton.geometry().height())
+ )
self.ui.popupMenu(self.labels, self.icons, pos)
def proceed(self, option):
@@ -292,18 +314,24 @@ class SetAutoGroup(gui_base.GuiCommandSimplest):
None,
translate("draft", "New Layer"),
translate("draft", "Layer name"),
- text=translate("draft", "Layer", "Object label")
+ text=translate("draft", "Layer", "Object label"),
)
if not ok:
return
if not txt:
return
self.doc.openTransaction(translate("draft", "New layer"))
- lyr = make_layer.make_layer(name=txt, line_color=None, shape_color=None,
- line_width=None, draw_style=None, transparency=None)
+ lyr = make_layer.make_layer(
+ name=txt,
+ line_color=None,
+ shape_color=None,
+ line_width=None,
+ draw_style=None,
+ transparency=None,
+ )
self.doc.commitTransaction()
self.doc.recompute()
- self.ui.setAutoGroup(lyr.Name) # this...
+ self.ui.setAutoGroup(lyr.Name) # this...
# self.ui.autoGroupButton.setDown(False) # or this?
return
@@ -333,9 +361,14 @@ class AddToConstruction(gui_base.GuiCommandNeedsSelection):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_AddConstruction",
- "MenuText": QT_TRANSLATE_NOOP("Draft_AddConstruction", "Add to Construction Group"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_AddConstruction", "Adds the selected objects to the construction group,\nand changes their appearance to the construction style.\nThe construction group is created if it does not exist.")}
+ return {
+ "Pixmap": "Draft_AddConstruction",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_AddConstruction", "Add to Construction Group"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_AddConstruction",
+ "Adds the selected objects to the construction group,\nand changes their appearance to the construction style.\nThe construction group is created if it does not exist.",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -387,9 +420,11 @@ class AddNamedGroup(gui_base.GuiCommandSimplest):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_AddNamedGroup",
- "MenuText": QT_TRANSLATE_NOOP("Draft_AddNamedGroup", "New Named Group"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_AddNamedGroup", "Adds a group with a given name")}
+ return {
+ "Pixmap": "Draft_AddNamedGroup",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_AddNamedGroup", "New Named Group"),
+ "ToolTip": QT_TRANSLATE_NOOP("Draft_AddNamedGroup", "Adds a group with a given name"),
+ }
def Activated(self):
super().Activated()
@@ -398,7 +433,7 @@ class AddNamedGroup(gui_base.GuiCommandSimplest):
None,
translate("draft", "New Group"),
translate("draft", "Group name"),
- text=translate("draft", "Group", "Object label")
+ text=translate("draft", "Group", "Object label"),
)
if not ok:
return
diff --git a/src/Mod/Draft/draftguitools/gui_hatch.py b/src/Mod/Draft/draftguitools/gui_hatch.py
index 4c476ad939..ee2daccaea 100644
--- a/src/Mod/Draft/draftguitools/gui_hatch.py
+++ b/src/Mod/Draft/draftguitools/gui_hatch.py
@@ -1,24 +1,24 @@
-#***************************************************************************
-#* *
-#* Copyright (c) 2021 Yorik van Havre *
-#* *
-#* This program is free software; you can redistribute it and/or modify *
-#* it under the terms of the GNU Lesser General Public License (LGPL) *
-#* as published by the Free Software Foundation; either version 2 of *
-#* the License, or (at your option) any later version. *
-#* for detail see the LICENCE text file. *
-#* *
-#* This program is distributed in the hope that it will be useful, *
-#* but WITHOUT ANY WARRANTY; without even the implied warranty of *
-#* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
-#* GNU Library General Public License for more details. *
-#* *
-#* You should have received a copy of the GNU Library General Public *
-#* License along with this program; if not, write to the Free Software *
-#* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 *
-#* USA *
-#* *
-#***************************************************************************
+# ***************************************************************************
+# * *
+# * Copyright (c) 2021 Yorik van Havre *
+# * *
+# * This program is free software; you can redistribute it and/or modify *
+# * it under the terms of the GNU Lesser General Public License (LGPL) *
+# * as published by the Free Software Foundation; either version 2 of *
+# * the License, or (at your option) any later version. *
+# * for detail see the LICENCE text file. *
+# * *
+# * This program is distributed in the hope that it will be useful, *
+# * but WITHOUT ANY WARRANTY; without even the implied warranty of *
+# * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
+# * GNU Library General Public License for more details. *
+# * *
+# * You should have received a copy of the GNU Library General Public *
+# * License along with this program; if not, write to the Free Software *
+# * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 *
+# * USA *
+# * *
+# ***************************************************************************
"""This module contains FreeCAD commands for the Draft workbench"""
@@ -33,33 +33,39 @@ from draftutils.translate import QT_TRANSLATE_NOOP, translate
class Draft_Hatch(gui_base.GuiCommandNeedsSelection):
-
def GetResources(self):
- return {"Pixmap": "Draft_Hatch",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Hatch", "Hatch"),
- "Accel": "H, A",
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Hatch", "Creates hatches on the faces of a selected object")}
+ return {
+ "Pixmap": "Draft_Hatch",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Hatch", "Hatch"),
+ "Accel": "H, A",
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Hatch", "Creates hatches on the faces of a selected object"
+ ),
+ }
def Activated(self):
import FreeCADGui
if FreeCADGui.Selection.getSelection():
- task = FreeCADGui.Control.showDialog(Draft_Hatch_TaskPanel(FreeCADGui.Selection.getSelection()[0]))
+ task = FreeCADGui.Control.showDialog(
+ Draft_Hatch_TaskPanel(FreeCADGui.Selection.getSelection()[0])
+ )
task.setDocumentName(FreeCADGui.ActiveDocument.Document.Name)
task.setAutoCloseOnDeletedDocument(True)
else:
- FreeCAD.Console.PrintError(translate("Draft", "Choose a base object before using this command") + "\n")
+ FreeCAD.Console.PrintError(
+ translate("Draft", "Choose a base object before using this command") + "\n"
+ )
class Draft_Hatch_TaskPanel:
-
- def __init__(self,baseobj):
+ def __init__(self, baseobj):
import FreeCADGui
- from PySide import QtCore,QtGui
+ from PySide import QtCore, QtGui
import Draft_rc
self.baseobj = baseobj
@@ -84,25 +90,25 @@ class Draft_Hatch_TaskPanel:
params.set_param("HatchPatternScale", self.form.Scale.value())
params.set_param("HatchPatternRotation", self.form.Rotation.value())
params.set_param("HatchPatternTranslate", self.form.Translate.isChecked())
- if hasattr(self.baseobj,"File") and hasattr(self.baseobj,"Pattern"):
+ if hasattr(self.baseobj, "File") and hasattr(self.baseobj, "Pattern"):
# modify existing hatch object
- o = "FreeCAD.ActiveDocument.getObject(\""+self.baseobj.Name+"\")"
- FreeCADGui.doCommand(o+".File=\""+self.form.File.property("fileName")+"\"")
- FreeCADGui.doCommand(o+".Pattern=\""+self.form.Pattern.currentText()+"\"")
- FreeCADGui.doCommand(o+".Scale="+str(self.form.Scale.value()))
- FreeCADGui.doCommand(o+".Rotation="+str(self.form.Rotation.value()))
- FreeCADGui.doCommand(o+".Translate="+str(self.form.Translate.isChecked()))
+ o = 'FreeCAD.ActiveDocument.getObject("' + self.baseobj.Name + '")'
+ FreeCADGui.doCommand(o + '.File="' + self.form.File.property("fileName") + '"')
+ FreeCADGui.doCommand(o + '.Pattern="' + self.form.Pattern.currentText() + '"')
+ FreeCADGui.doCommand(o + ".Scale=" + str(self.form.Scale.value()))
+ FreeCADGui.doCommand(o + ".Rotation=" + str(self.form.Rotation.value()))
+ FreeCADGui.doCommand(o + ".Translate=" + str(self.form.Translate.isChecked()))
else:
# create new hatch object
FreeCAD.ActiveDocument.openTransaction("Create Hatch")
FreeCADGui.addModule("Draft")
cmd = "Draft.make_hatch("
- cmd += "baseobject=FreeCAD.ActiveDocument.getObject(\""+self.baseobj.Name
- cmd += "\"),filename=\""+self.form.File.property("fileName")
- cmd += "\",pattern=\""+self.form.Pattern.currentText()
- cmd += "\",scale="+str(self.form.Scale.value())
- cmd += ",rotation="+str(self.form.Rotation.value())
- cmd += ",translate="+str(self.form.Translate.isChecked())+")"
+ cmd += 'baseobject=FreeCAD.ActiveDocument.getObject("' + self.baseobj.Name
+ cmd += '"),filename="' + self.form.File.property("fileName")
+ cmd += '",pattern="' + self.form.Pattern.currentText()
+ cmd += '",scale=' + str(self.form.Scale.value())
+ cmd += ",rotation=" + str(self.form.Rotation.value())
+ cmd += ",translate=" + str(self.form.Translate.isChecked()) + ")"
FreeCADGui.doCommand(cmd)
FreeCAD.ActiveDocument.commitTransaction()
FreeCADGui.doCommand("FreeCAD.ActiveDocument.recompute()")
@@ -116,7 +122,7 @@ class Draft_Hatch_TaskPanel:
FreeCADGui.ActiveDocument.resetEdit()
FreeCAD.ActiveDocument.recompute()
- def onFileChanged(self,filename):
+ def onFileChanged(self, filename):
pat = self.form.Pattern.currentText()
self.form.Pattern.clear()
@@ -125,8 +131,7 @@ class Draft_Hatch_TaskPanel:
if pat in patterns:
self.form.Pattern.setCurrentText(pat)
- def getPatterns(self,filename):
-
+ def getPatterns(self, filename):
"""returns a list of pattern names found in a PAT file"""
patterns = []
if os.path.exists(filename):
@@ -136,6 +141,8 @@ class Draft_Hatch_TaskPanel:
patterns.append(line.split(",")[0][1:])
return patterns
+
if FreeCAD.GuiUp:
import FreeCADGui
- FreeCADGui.addCommand("Draft_Hatch",Draft_Hatch())
+
+ FreeCADGui.addCommand("Draft_Hatch", Draft_Hatch())
diff --git a/src/Mod/Draft/draftguitools/gui_heal.py b/src/Mod/Draft/draftguitools/gui_heal.py
index c4bc68a565..dedb112936 100644
--- a/src/Mod/Draft/draftguitools/gui_heal.py
+++ b/src/Mod/Draft/draftguitools/gui_heal.py
@@ -48,15 +48,20 @@ class Heal(gui_base.GuiCommandSimplest):
"""
def __init__(self):
- super(Heal, self).__init__(name=translate("draft","Heal"))
+ super(Heal, self).__init__(name=translate("draft", "Heal"))
def GetResources(self):
"""Set icon, menu and tooltip."""
_tip = ()
- return {'Pixmap': 'Draft_Heal',
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Heal", "Heal"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Heal", "Heals faulty Draft objects saved with an earlier version of FreeCAD.\nIf an object is selected it tries to heal only that object,\notherwise it tries to heal all objects in the active document.")}
+ return {
+ "Pixmap": "Draft_Heal",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Heal", "Heal"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Heal",
+ "Heals faulty Draft objects saved with an earlier version of FreeCAD.\nIf an object is selected it tries to heal only that object,\notherwise it tries to heal all objects in the active document.",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -71,6 +76,6 @@ class Heal(gui_base.GuiCommandSimplest):
self.doc.commitTransaction()
-Gui.addCommand('Draft_Heal', Heal())
+Gui.addCommand("Draft_Heal", Heal())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_hyperlink.py b/src/Mod/Draft/draftguitools/gui_hyperlink.py
index 7080449aa4..6f6ea46b25 100644
--- a/src/Mod/Draft/draftguitools/gui_hyperlink.py
+++ b/src/Mod/Draft/draftguitools/gui_hyperlink.py
@@ -38,14 +38,18 @@ if FreeCAD.GuiUp:
import Draft_rc
from PySide.QtCore import QUrl
from PySide.QtGui import QDesktopServices
-def QT_TRANSLATE_NOOP(ctx,txt):
+
+
+def QT_TRANSLATE_NOOP(ctx, txt):
return txt
+
+
translate = FreeCAD.Qt.translate
from PySide import QtWidgets
__title__ = "FreeCAD Draft Workbench GUI Tools - Hyperlinks tools"
-__author__ = ("")
+__author__ = ""
__url__ = "https://www.freecad.org"
@@ -53,10 +57,12 @@ class Draft_Hyperlink:
"""The Draft_Hyperlink FreeCAD command definition."""
def GetResources(self):
- d = {'Pixmap': '',
- 'Accel': "",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Hyperlink", "Open Links"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Hyperlink", "Opens linked documents")}
+ d = {
+ "Pixmap": "",
+ "Accel": "",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Hyperlink", "Open Links"),
+ "ToolTip": QT_TRANSLATE_NOOP("Draft_Hyperlink", "Opens linked documents"),
+ }
return d
def Activated(self):
@@ -66,17 +72,9 @@ class Draft_Hyperlink:
if len(self.hyperlinks_list) > 1:
m = QtWidgets.QMessageBox()
m.setWindowTitle(translate("draft", "Opening Multiple Links"))
- m.setText(
- translate(
- "draft",
- "Multiple links found"
- )
- )
+ m.setText(translate("draft", "Multiple links found"))
m.setInformativeText(
- translate(
- "draft",
- "This may lead to the opening of various windows"
- )
+ translate("draft", "This may lead to the opening of various windows")
)
m.setStandardButtons(m.Ok | m.Cancel)
ret = m.exec_()
@@ -92,7 +90,9 @@ class Draft_Hyperlink:
if hasattr(o.Object, "Text"):
for text in o.Object.Text:
- hyperlinks = re.findall(r"((\w:[\\/]|%\w+%|\\\\\w+|/\w+|\w{3,5}://)[\w\\/: ]+\.[\S]+)", text)
+ hyperlinks = re.findall(
+ r"((\w:[\\/]|%\w+%|\\\\\w+|/\w+|\w{3,5}://)[\w\\/: ]+\.[\S]+)", text
+ )
for hyperlink in hyperlinks:
self.hyperlinks_list.append(hyperlink[0])
@@ -116,8 +116,11 @@ class Draft_Hyperlink:
_toolmsg(translate("draft", "Opening hyperlink") + " " + hyperlink)
- QDesktopServices.openUrl(url) #ToDo: add management to open FCStd files in the current instance and to open web pages with the Web Workbench
+ QDesktopServices.openUrl(
+ url
+ ) # ToDo: add management to open FCStd files in the current instance and to open web pages with the Web Workbench
-FreeCADGui.addCommand('Draft_Hyperlink', Draft_Hyperlink())
+
+FreeCADGui.addCommand("Draft_Hyperlink", Draft_Hyperlink())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_join.py b/src/Mod/Draft/draftguitools/gui_join.py
index dcb2886abe..d680668ed3 100644
--- a/src/Mod/Draft/draftguitools/gui_join.py
+++ b/src/Mod/Draft/draftguitools/gui_join.py
@@ -49,10 +49,15 @@ class Join(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_Join",
- "Accel": "J, O",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Join", "Join"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Join", "Joins the selected lines or polylines into a single object.\nThe lines must share a common point at the start or at the end.")}
+ return {
+ "Pixmap": "Draft_Join",
+ "Accel": "J, O",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Join", "Join"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Join",
+ "Joins the selected lines or polylines into a single object.\nThe lines must share a common point at the start or at the end.",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -83,10 +88,8 @@ class Join(gui_base_original.Modifier):
_cmd += "("
_cmd += "FreeCADGui.Selection.getSelection()"
_cmd += ")"
- _cmd_list = ['j = ' + _cmd,
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Join Lines"),
- _cmd_list)
+ _cmd_list = ["j = " + _cmd, "FreeCAD.ActiveDocument.recompute()"]
+ self.commit(translate("draft", "Join Lines"), _cmd_list)
else:
_err(translate("draft", "Only Draft lines and wires can be joined"))
self.finish()
@@ -98,9 +101,9 @@ class Join(gui_base_original.Modifier):
labels.append(obj.Label)
labels = ", ".join(labels)
- _toolmsg(translate("draft","Selection:") + " {}".format(labels))
+ _toolmsg(translate("draft", "Selection:") + " {}".format(labels))
-Gui.addCommand('Draft_Join', Join())
+Gui.addCommand("Draft_Join", Join())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_labels.py b/src/Mod/Draft/draftguitools/gui_labels.py
index da088f815b..36c23356f7 100644
--- a/src/Mod/Draft/draftguitools/gui_labels.py
+++ b/src/Mod/Draft/draftguitools/gui_labels.py
@@ -58,10 +58,15 @@ class Label(gui_base_original.Creator):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_Label',
- 'Accel': "D, L",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Label", "Label"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Label", "Creates a label, optionally attached to a selected object or subelement")}
+ return {
+ "Pixmap": "Draft_Label",
+ "Accel": "D, L",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Label", "Label"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Label",
+ "Creates a label, optionally attached to a selected object or subelement",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -71,7 +76,7 @@ class Label(gui_base_original.Creator):
self.sel = Gui.Selection.getSelectionEx()
if self.sel:
self.sel = self.sel[0]
- self.ui.labelUi(title=translate("draft",self.featureName), callback=self.setmode)
+ self.ui.labelUi(title=translate("draft", self.featureName), callback=self.setmode)
self.ui.xValue.setFocus()
self.ui.xValue.selectAll()
self.ghost = trackers.lineTracker()
@@ -82,6 +87,7 @@ class Label(gui_base_original.Creator):
def setmode(self, i):
"""Set the type of label, if it is associated to an object."""
from draftobjects.label import get_label_types
+
self.labeltype = get_label_types()[i]
params.set_param("labeltype", self.labeltype)
@@ -103,10 +109,10 @@ class Label(gui_base_original.Creator):
n = self.wp.axis
r = self.wp.get_placement().Rotation
- if abs(DraftVecUtils.angle(v, h, n)) <= math.pi/4:
+ if abs(DraftVecUtils.angle(v, h, n)) <= math.pi / 4:
direction = "Horizontal"
dist = -dist
- elif abs(DraftVecUtils.angle(v, h, n)) >= math.pi*3/4:
+ elif abs(DraftVecUtils.angle(v, h, n)) >= math.pi * 3 / 4:
direction = "Horizontal"
elif DraftVecUtils.angle(v, h, n) > 0:
direction = "Vertical"
@@ -146,11 +152,12 @@ class Label(gui_base_original.Creator):
# Commit the creation instructions through the parent class,
# the Creator class
- _cmd_list = ['_label_ = ' + _cmd,
- 'Draft.autogroup(_label_)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Label"),
- _cmd_list)
+ _cmd_list = [
+ "_label_ = " + _cmd,
+ "Draft.autogroup(_label_)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Label"), _cmd_list)
self.finish()
def action(self, arg):
@@ -182,8 +189,7 @@ class Label(gui_base_original.Creator):
# first click
self.node.append(self.point)
self.ui.isRelative.show()
- _toolmsg(translate("draft",
- "Pick endpoint of leader line"))
+ _toolmsg(translate("draft", "Pick endpoint of leader line"))
if self.planetrack:
self.planetrack.set(self.point)
elif len(self.node) == 1:
@@ -228,6 +234,6 @@ class Label(gui_base_original.Creator):
Draft_Label = Label
-Gui.addCommand('Draft_Label', Label())
+Gui.addCommand("Draft_Label", Label())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_layers.py b/src/Mod/Draft/draftguitools/gui_layers.py
index 67f9bc6010..bb6c7dcd7c 100644
--- a/src/Mod/Draft/draftguitools/gui_layers.py
+++ b/src/Mod/Draft/draftguitools/gui_layers.py
@@ -47,12 +47,12 @@ bool(Draft_rc.__name__)
def getColorIcon(color):
-
"returns a QtGui.QIcon from a color 3-float tuple"
- from PySide import QtCore,QtGui
- c = QtGui.QColor(int(color[0]*255),int(color[1]*255),int(color[2]*255))
- im = QtGui.QImage(48,48,QtGui.QImage.Format_ARGB32)
+ from PySide import QtCore, QtGui
+
+ c = QtGui.QColor(int(color[0] * 255), int(color[1] * 255), int(color[2] * 255))
+ im = QtGui.QImage(48, 48, QtGui.QImage.Format_ARGB32)
im.fill(c)
px = QtGui.QPixmap.fromImage(im)
return QtGui.QIcon(px)
@@ -66,9 +66,14 @@ class Layer(gui_base.GuiCommandSimplest):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_Layer",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Layer", "New Layer"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Layer", "Adds a layer to the document.\nObjects added to this layer can share the same visual properties.")}
+ return {
+ "Pixmap": "Draft_Layer",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Layer", "New Layer"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Layer",
+ "Adds a layer to the document.\nObjects added to this layer can share the same visual properties.",
+ ),
+ }
def Activated(self):
"""Execute when the command is called.
@@ -79,7 +84,9 @@ class Layer(gui_base.GuiCommandSimplest):
self.doc.openTransaction(translate("draft", "Create layer"))
Gui.addModule("Draft")
- Gui.doCommand("layer = Draft.make_layer(name=None, line_color=None, shape_color=None, line_width=None, draw_style=None, transparency=None)")
+ Gui.doCommand(
+ "layer = Draft.make_layer(name=None, line_color=None, shape_color=None, line_width=None, draw_style=None, transparency=None)"
+ )
Gui.doCommand("FreeCAD.ActiveDocument.recompute()")
self.doc.commitTransaction()
@@ -92,9 +99,14 @@ class AddToLayer(gui_base.GuiCommandNeedsSelection):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_AddToLayer",
- "MenuText": QT_TRANSLATE_NOOP("Draft_AddToLayer", "Add to Layer"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_AddToLayer", "Adds selected objects to a layer, or removes them from any layer")}
+ return {
+ "Pixmap": "Draft_AddToLayer",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_AddToLayer", "Add to Layer"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_AddToLayer",
+ "Adds selected objects to a layer, or removes them from any layer",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -106,19 +118,21 @@ class AddToLayer(gui_base.GuiCommandNeedsSelection):
self.ui = Gui.draftToolBar
objs = [obj for obj in App.ActiveDocument.Objects if utils.get_type(obj) == "Layer"]
objs.sort(key=lambda obj: obj.Label)
- self.objects = [None] \
- + [None] \
- + objs
- self.labels = [translate("draft", "Remove From Layer")] \
- + ["---"] \
- + [obj.Label for obj in objs] \
- + ["---"] \
- + [translate("draft", "Add to New Layer")]
- self.icons = [self.ui.getIcon(":/icons/list-remove.svg")] \
- + [None] \
- + [obj.ViewObject.Icon for obj in objs] \
- + [None] \
- + [self.ui.getIcon(":/icons/list-add.svg")]
+ self.objects = [None] + [None] + objs
+ self.labels = (
+ [translate("draft", "Remove From Layer")]
+ + ["---"]
+ + [obj.Label for obj in objs]
+ + ["---"]
+ + [translate("draft", "Add to New Layer")]
+ )
+ self.icons = (
+ [self.ui.getIcon(":/icons/list-remove.svg")]
+ + [None]
+ + [obj.ViewObject.Icon for obj in objs]
+ + [None]
+ + [self.ui.getIcon(":/icons/list-add.svg")]
+ )
self.ui.sourceCmd = self
self.ui.popupMenu(self.labels, self.icons)
@@ -143,19 +157,26 @@ class AddToLayer(gui_base.GuiCommandNeedsSelection):
if option == self.labels[-1]:
# "Add to new layer..."
from PySide import QtWidgets
+
txt, ok = QtWidgets.QInputDialog.getText(
None,
translate("draft", "New Layer"),
translate("draft", "Layer name"),
- text=translate("draft", "Layer", "Object label")
+ text=translate("draft", "Layer", "Object label"),
)
if not ok:
return
if not txt:
return
self.doc.openTransaction(translate("draft", "Add to new layer"))
- lyr = make_layer.make_layer(name=txt, line_color=None, shape_color=None,
- line_width=None, draw_style=None, transparency=None)
+ lyr = make_layer.make_layer(
+ name=txt,
+ line_color=None,
+ shape_color=None,
+ line_width=None,
+ draw_style=None,
+ transparency=None,
+ )
for obj in Gui.Selection.getSelection():
lyr.Proxy.addObject(lyr, obj)
self.doc.commitTransaction()
@@ -173,14 +194,15 @@ class AddToLayer(gui_base.GuiCommandNeedsSelection):
class LayerManager:
-
"""GuiCommand that displays a Layers manager dialog"""
def GetResources(self):
- return {"Pixmap" : "Draft_LayerManager",
- "MenuText": QT_TRANSLATE_NOOP("Draft_LayerManager", "Manage Layers"),
- "ToolTip" : QT_TRANSLATE_NOOP("Draft_LayerManager", "Allows to modify the layers")}
+ return {
+ "Pixmap": "Draft_LayerManager",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_LayerManager", "Manage Layers"),
+ "ToolTip": QT_TRANSLATE_NOOP("Draft_LayerManager", "Allows to modify the layers"),
+ }
def IsActive(self):
"""Return True when this command should be available."""
@@ -209,11 +231,13 @@ class LayerManager:
# restore window geometry from stored state
w = params.get_param("LayersManagerWidth")
h = params.get_param("LayersManagerHeight")
- self.dialog.resize(w,h)
+ self.dialog.resize(w, h)
# center the dialog over FreeCAD window
mw = Gui.getMainWindow()
- self.dialog.move(mw.frameGeometry().topLeft() + mw.rect().center() - self.dialog.rect().center())
+ self.dialog.move(
+ mw.frameGeometry().topLeft() + mw.rect().center() - self.dialog.rect().center()
+ )
# connect signals/slots
self.dialog.buttonNew.clicked.connect(self.addItem)
@@ -231,8 +255,10 @@ class LayerManager:
self.dialog.tree.setUniformRowHeights(True)
self.dialog.tree.setItemDelegate(Layers_Delegate())
self.dialog.tree.setItemsExpandable(False)
- self.dialog.tree.setRootIsDecorated(False) # removes spacing in first column
- self.dialog.tree.setSelectionMode(QtWidgets.QTreeView.ExtendedSelection) # allow one to select many
+ self.dialog.tree.setRootIsDecorated(False) # removes spacing in first column
+ self.dialog.tree.setSelectionMode(
+ QtWidgets.QTreeView.ExtendedSelection
+ ) # allow one to select many
# fill the tree view
self.update()
@@ -241,7 +267,6 @@ class LayerManager:
self.dialog.exec_()
def accept(self):
-
"when OK button is pressed"
doc = App.ActiveDocument
@@ -267,8 +292,14 @@ class LayerManager:
if not changed:
doc.openTransaction(trans_name)
changed = True
- obj = make_layer.make_layer(name=None, line_color=None, shape_color=None,
- line_width=None, draw_style=None, transparency=None)
+ obj = make_layer.make_layer(
+ name=None,
+ line_color=None,
+ shape_color=None,
+ line_width=None,
+ draw_style=None,
+ transparency=None,
+ )
vobj = obj.ViewObject
# visibility
@@ -346,7 +377,6 @@ class LayerManager:
self.dialog.reject()
def reject(self):
-
"when Cancel button is pressed or dialog is closed"
# save dialog size
@@ -356,32 +386,34 @@ class LayerManager:
return True
def update(self):
-
"rebuild the model from document contents"
self.model.clear()
# set header
- self.model.setHorizontalHeaderLabels([translate("Draft","On"),
- translate("Draft","Name"),
- translate("Draft","Line Width"),
- translate("Draft","Draw Style"),
- translate("Draft","Line Color"),
- translate("Draft","Face Color"),
- translate("Draft","Transparency"),
- translate("Draft","Line Print Color")])
+ self.model.setHorizontalHeaderLabels(
+ [
+ translate("Draft", "On"),
+ translate("Draft", "Name"),
+ translate("Draft", "Line Width"),
+ translate("Draft", "Draw Style"),
+ translate("Draft", "Line Color"),
+ translate("Draft", "Face Color"),
+ translate("Draft", "Transparency"),
+ translate("Draft", "Line Print Color"),
+ ]
+ )
self.dialog.tree.header().setDefaultSectionSize(72)
- self.dialog.tree.setColumnWidth(0,32) # on/off column
- self.dialog.tree.setColumnWidth(1,128) # name column
+ self.dialog.tree.setColumnWidth(0, 32) # on/off column
+ self.dialog.tree.setColumnWidth(1, 128) # name column
# populate
objs = [obj for obj in App.ActiveDocument.Objects if utils.get_type(obj) == "Layer"]
- objs.sort(key=lambda o:o.Label)
+ objs.sort(key=lambda o: o.Label)
for obj in objs:
self.addItem(obj)
- def addItem(self,obj=None):
-
+ def addItem(self, obj=None):
"adds a row to the model"
from PySide import QtCore, QtGui
@@ -397,22 +429,19 @@ class LayerManager:
lineColorItem = QtGui.QStandardItem()
lineColorItem.setData(
utils.get_rgba_tuple(params.get_param_view("DefaultShapeLineColor"))[:3],
- QtCore.Qt.UserRole
+ QtCore.Qt.UserRole,
)
shapeColorItem = QtGui.QStandardItem()
shapeColorItem.setData(
- utils.get_rgba_tuple(params.get_param_view("DefaultShapeColor"))[:3],
- QtCore.Qt.UserRole
+ utils.get_rgba_tuple(params.get_param_view("DefaultShapeColor"))[:3], QtCore.Qt.UserRole
)
transparencyItem = QtGui.QStandardItem()
transparencyItem.setData(
- params.get_param_view("DefaultShapeTransparency"),
- QtCore.Qt.DisplayRole
+ params.get_param_view("DefaultShapeTransparency"), QtCore.Qt.DisplayRole
)
linePrintColorItem = QtGui.QStandardItem()
linePrintColorItem.setData(
- utils.get_rgba_tuple(params.get_param("DefaultPrintColor"))[:3],
- QtCore.Qt.UserRole
+ utils.get_rgba_tuple(params.get_param("DefaultPrintColor"))[:3], QtCore.Qt.UserRole
)
# populate with object data
@@ -421,29 +450,32 @@ class LayerManager:
onItem.setCheckState(QtCore.Qt.Checked if vobj.Visibility else QtCore.Qt.Unchecked)
nameItem.setText(obj.Label)
nameItem.setToolTip(obj.Name)
- widthItem.setData(vobj.LineWidth,QtCore.Qt.DisplayRole)
+ widthItem.setData(vobj.LineWidth, QtCore.Qt.DisplayRole)
styleItem.setText(vobj.DrawStyle)
- lineColorItem.setData(vobj.LineColor[:3],QtCore.Qt.UserRole)
- shapeColorItem.setData(vobj.ShapeColor[:3],QtCore.Qt.UserRole)
- transparencyItem.setData(vobj.Transparency,QtCore.Qt.DisplayRole)
- if hasattr(vobj,"LinePrintColor"):
- linePrintColorItem.setData(vobj.LinePrintColor[:3],QtCore.Qt.UserRole)
+ lineColorItem.setData(vobj.LineColor[:3], QtCore.Qt.UserRole)
+ shapeColorItem.setData(vobj.ShapeColor[:3], QtCore.Qt.UserRole)
+ transparencyItem.setData(vobj.Transparency, QtCore.Qt.DisplayRole)
+ if hasattr(vobj, "LinePrintColor"):
+ linePrintColorItem.setData(vobj.LinePrintColor[:3], QtCore.Qt.UserRole)
lineColorItem.setIcon(getColorIcon(lineColorItem.data(QtCore.Qt.UserRole)))
shapeColorItem.setIcon(getColorIcon(shapeColorItem.data(QtCore.Qt.UserRole)))
linePrintColorItem.setIcon(getColorIcon(linePrintColorItem.data(QtCore.Qt.UserRole)))
# append row
- self.model.appendRow([onItem,
- nameItem,
- widthItem,
- styleItem,
- lineColorItem,
- shapeColorItem,
- transparencyItem,
- linePrintColorItem])
+ self.model.appendRow(
+ [
+ onItem,
+ nameItem,
+ widthItem,
+ styleItem,
+ lineColorItem,
+ shapeColorItem,
+ transparencyItem,
+ linePrintColorItem,
+ ]
+ )
def onDelete(self):
-
"delete selected rows"
rows = []
@@ -465,7 +497,6 @@ class LayerManager:
self.model.takeRow(row)
def onToggle(self):
-
"toggle selected layers on/off"
from PySide import QtCore
@@ -482,7 +513,6 @@ class LayerManager:
self.model.itemFromIndex(index).setCheckState(state)
def onIsolate(self):
-
"isolates the selected layers (turns all the others off"
from PySide import QtCore
@@ -501,7 +531,6 @@ if App.GuiUp:
from PySide import QtCore, QtGui, QtWidgets
class Layers_Delegate(QtWidgets.QStyledItemDelegate):
-
"model delegate"
def __init__(self, parent=None, *args):
@@ -511,91 +540,97 @@ if App.GuiUp:
# But we want to show the color dialog only the first time
self.first = True
- def createEditor(self,parent,option,index):
+ def createEditor(self, parent, option, index):
- if index.column() == 0: # Layer on/off
+ if index.column() == 0: # Layer on/off
editor = QtWidgets.QCheckBox(parent)
- if index.column() == 1: # Layer name
+ if index.column() == 1: # Layer name
editor = QtWidgets.QLineEdit(parent)
- elif index.column() == 2: # Line width
+ elif index.column() == 2: # Line width
editor = QtWidgets.QSpinBox(parent)
editor.setMaximum(99)
- elif index.column() == 3: # Line style
+ elif index.column() == 3: # Line style
editor = QtWidgets.QComboBox(parent)
editor.addItems(utils.DRAW_STYLES)
- elif index.column() == 4: # Line color
+ elif index.column() == 4: # Line color
editor = QtWidgets.QLineEdit(parent)
self.first = True
- elif index.column() == 5: # Shape color
+ elif index.column() == 5: # Shape color
editor = QtWidgets.QLineEdit(parent)
self.first = True
- elif index.column() == 6: # Transparency
+ elif index.column() == 6: # Transparency
editor = QtWidgets.QSpinBox(parent)
editor.setMaximum(100)
- elif index.column() == 7: # Line print color
+ elif index.column() == 7: # Line print color
editor = QtWidgets.QLineEdit(parent)
self.first = True
return editor
def setEditorData(self, editor, index):
- if index.column() == 0: # Layer on/off
+ if index.column() == 0: # Layer on/off
editor.setChecked(index.data())
- elif index.column() == 1: # Layer name
+ elif index.column() == 1: # Layer name
editor.setText(index.data())
- elif index.column() == 2: # Line width
+ elif index.column() == 2: # Line width
editor.setValue(index.data())
- elif index.column() == 3: # Line style
+ elif index.column() == 3: # Line style
editor.setCurrentIndex(utils.DRAW_STYLES.index(index.data()))
- elif index.column() == 4: # Line color
+ elif index.column() == 4: # Line color
editor.setText(str(index.data(QtCore.Qt.UserRole)))
if self.first:
c = index.data(QtCore.Qt.UserRole)
- color = QtWidgets.QColorDialog.getColor(QtGui.QColor(int(c[0]*255),int(c[1]*255),int(c[2]*255)))
+ color = QtWidgets.QColorDialog.getColor(
+ QtGui.QColor(int(c[0] * 255), int(c[1] * 255), int(c[2] * 255))
+ )
editor.setText(str(color.getRgbF()))
self.first = False
- elif index.column() == 5: # Shape color
+ elif index.column() == 5: # Shape color
editor.setText(str(index.data(QtCore.Qt.UserRole)))
if self.first:
c = index.data(QtCore.Qt.UserRole)
- color = QtWidgets.QColorDialog.getColor(QtGui.QColor(int(c[0]*255),int(c[1]*255),int(c[2]*255)))
+ color = QtWidgets.QColorDialog.getColor(
+ QtGui.QColor(int(c[0] * 255), int(c[1] * 255), int(c[2] * 255))
+ )
editor.setText(str(color.getRgbF()))
self.first = False
- elif index.column() == 6: # Transparency
+ elif index.column() == 6: # Transparency
editor.setValue(index.data())
elif index.column() == 7: # Line print color
editor.setText(str(index.data(QtCore.Qt.UserRole)))
if self.first:
c = index.data(QtCore.Qt.UserRole)
- color = QtWidgets.QColorDialog.getColor(QtGui.QColor(int(c[0]*255),int(c[1]*255),int(c[2]*255)))
+ color = QtWidgets.QColorDialog.getColor(
+ QtGui.QColor(int(c[0] * 255), int(c[1] * 255), int(c[2] * 255))
+ )
editor.setText(str(color.getRgbF()))
self.first = False
def setModelData(self, editor, model, index):
- if index.column() == 0: # Layer on/off
- model.setData(index,editor.isChecked())
- elif index.column() == 1: # Layer name
- model.setData(index,editor.text())
- elif index.column() == 2: # Line width
- model.setData(index,editor.value())
- elif index.column() == 3: # Line style
- model.setData(index,utils.DRAW_STYLES[editor.currentIndex()])
- elif index.column() == 4: # Line color
- model.setData(index,eval(editor.text()),QtCore.Qt.UserRole)
+ if index.column() == 0: # Layer on/off
+ model.setData(index, editor.isChecked())
+ elif index.column() == 1: # Layer name
+ model.setData(index, editor.text())
+ elif index.column() == 2: # Line width
+ model.setData(index, editor.value())
+ elif index.column() == 3: # Line style
+ model.setData(index, utils.DRAW_STYLES[editor.currentIndex()])
+ elif index.column() == 4: # Line color
+ model.setData(index, eval(editor.text()), QtCore.Qt.UserRole)
model.itemFromIndex(index).setIcon(getColorIcon(eval(editor.text())))
- elif index.column() == 5: # Shape color
- model.setData(index,eval(editor.text()),QtCore.Qt.UserRole)
+ elif index.column() == 5: # Shape color
+ model.setData(index, eval(editor.text()), QtCore.Qt.UserRole)
model.itemFromIndex(index).setIcon(getColorIcon(eval(editor.text())))
- elif index.column() == 6: # Transparency
- model.setData(index,editor.value())
- elif index.column() == 7: # Line prin color
- model.setData(index,eval(editor.text()),QtCore.Qt.UserRole)
+ elif index.column() == 6: # Transparency
+ model.setData(index, editor.value())
+ elif index.column() == 7: # Line prin color
+ model.setData(index, eval(editor.text()), QtCore.Qt.UserRole)
model.itemFromIndex(index).setIcon(getColorIcon(eval(editor.text())))
-Gui.addCommand('Draft_Layer', Layer())
-Gui.addCommand('Draft_AddToLayer', AddToLayer())
-Gui.addCommand('Draft_LayerManager', LayerManager())
+Gui.addCommand("Draft_Layer", Layer())
+Gui.addCommand("Draft_AddToLayer", AddToLayer())
+Gui.addCommand("Draft_LayerManager", LayerManager())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_lines.py b/src/Mod/Draft/draftguitools/gui_lines.py
index 199211154a..1c41e219a8 100644
--- a/src/Mod/Draft/draftguitools/gui_lines.py
+++ b/src/Mod/Draft/draftguitools/gui_lines.py
@@ -58,12 +58,16 @@ class Line(gui_base_original.Creator):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_Line',
- 'Accel': "L,I",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Line", "Line"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Line", "Creates a 2-point line")}
+ return {
+ "Pixmap": "Draft_Line",
+ "Accel": "L,I",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Line", "Line"),
+ "ToolTip": QT_TRANSLATE_NOOP("Draft_Line", "Creates a 2-point line"),
+ }
- def Activated(self, name=QT_TRANSLATE_NOOP("draft", "Line"), icon="Draft_Line", task_title=None):
+ def Activated(
+ self, name=QT_TRANSLATE_NOOP("draft", "Line"), icon="Draft_Line", task_title=None
+ ):
"""Execute when the command is called."""
super().Activated(name)
if task_title is None:
@@ -153,48 +157,49 @@ class Line(gui_base_original.Creator):
Gui.addModule("Draft")
# The command to run is built as a series of text strings
# to be committed through the `draftutils.todo.ToDo` class.
- if (len(self.node) == 2
- and params.get_param("UsePartPrimitives")):
+ if len(self.node) == 2 and params.get_param("UsePartPrimitives"):
# Insert a Part::Primitive object
p1 = self.node[0]
p2 = self.node[-1]
- _cmd = 'FreeCAD.ActiveDocument.'
+ _cmd = "FreeCAD.ActiveDocument."
_cmd += 'addObject("Part::Line", "Line")'
- _cmd_list = ['line = ' + _cmd,
- 'line.X1 = ' + str(p1.x),
- 'line.Y1 = ' + str(p1.y),
- 'line.Z1 = ' + str(p1.z),
- 'line.X2 = ' + str(p2.x),
- 'line.Y2 = ' + str(p2.y),
- 'line.Z2 = ' + str(p2.z),
- 'Draft.autogroup(line)',
- 'Draft.select(line)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Line"),
- _cmd_list)
+ _cmd_list = [
+ "line = " + _cmd,
+ "line.X1 = " + str(p1.x),
+ "line.Y1 = " + str(p1.y),
+ "line.Z1 = " + str(p1.z),
+ "line.X2 = " + str(p2.x),
+ "line.Y2 = " + str(p2.y),
+ "line.Z2 = " + str(p2.z),
+ "Draft.autogroup(line)",
+ "Draft.select(line)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Line"), _cmd_list)
else:
# Insert a Draft line
rot, sup, pts, fil = self.getStrings()
_base = DraftVecUtils.toString(self.node[0])
- _cmd = 'Draft.make_wire'
- _cmd += '('
- _cmd += 'points, '
- _cmd += 'placement=pl, '
- _cmd += 'closed=' + str(closed) + ', '
- _cmd += 'face=' + fil + ', '
- _cmd += 'support=' + sup
- _cmd += ')'
- _cmd_list = ['pl = FreeCAD.Placement()',
- 'pl.Rotation.Q = ' + rot,
- 'pl.Base = ' + _base,
- 'points = ' + pts,
- 'line = ' + _cmd,
- 'Draft.autogroup(line)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Wire"),
- _cmd_list)
+ _cmd = "Draft.make_wire"
+ _cmd += "("
+ _cmd += "points, "
+ _cmd += "placement=pl, "
+ _cmd += "closed=" + str(closed) + ", "
+ _cmd += "face=" + fil + ", "
+ _cmd += "support=" + sup
+ _cmd += ")"
+ _cmd_list = [
+ "pl = FreeCAD.Placement()",
+ "pl.Rotation.Q = " + rot,
+ "pl.Base = " + _base,
+ "points = " + pts,
+ "line = " + _cmd,
+ "Draft.autogroup(line)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Wire"), _cmd_list)
super().finish()
if cont or (cont is None and self.ui and self.ui.continueMode):
self.Activated()
@@ -214,6 +219,7 @@ class Line(gui_base_original.Creator):
def undolast(self):
"""Undoes last line segment."""
import Part
+
if len(self.node) > 1:
self.node.pop()
# last = self.node[-1]
@@ -232,6 +238,7 @@ class Line(gui_base_original.Creator):
def drawUpdate(self, point):
"""Draws new line segment."""
import Part
+
if self.planetrack and self.node:
self.planetrack.set(self.node[-1])
if len(self.node) == 1:
@@ -268,6 +275,7 @@ class Line(gui_base_original.Creator):
"""Orient the working plane."""
if len(self.node) > 1 and self.obj:
import DraftGeomUtils
+
n = DraftGeomUtils.getNormal(self.obj.Shape)
if not n:
n = self.wp.axis
@@ -303,20 +311,22 @@ class Line(gui_base_original.Creator):
hints = [
Gui.InputHint(
translate("draft", "%1 pick next point, snap to first point to close"),
- Gui.UserInput.MouseLeft
+ Gui.UserInput.MouseLeft,
)
]
else:
hints = [
Gui.InputHint(translate("draft", "%1 pick next point"), Gui.UserInput.MouseLeft)
]
- return hints \
- + gui_tool_utils._get_hint_xyz_constrain() \
- + gui_tool_utils._get_hint_mod_constrain() \
+ return (
+ hints
+ + gui_tool_utils._get_hint_xyz_constrain()
+ + gui_tool_utils._get_hint_mod_constrain()
+ gui_tool_utils._get_hint_mod_snap()
+ )
-Gui.addCommand('Draft_Line', Line())
+Gui.addCommand("Draft_Line", Line())
class Wire(Line):
@@ -333,10 +343,12 @@ class Wire(Line):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_Wire',
- 'Accel': "P, L",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Wire", "Polyline"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Wire", "Creates a polyline")}
+ return {
+ "Pixmap": "Draft_Wire",
+ "Accel": "P, L",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Wire", "Polyline"),
+ "ToolTip": QT_TRANSLATE_NOOP("Draft_Wire", "Creates a polyline"),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -357,9 +369,7 @@ class Wire(Line):
try:
w = Part.Wire(Part.__sortEdges__(edges))
except Exception:
- _err(translate("draft",
- "Unable to create a wire "
- "from the selected objects"))
+ _err(translate("draft", "Unable to create a wire " "from the selected objects"))
else:
# Points of the new fused Wire in string form
# 'FreeCAD.Vector(x,y,z), FreeCAD.Vector(x1,y1,z1), ...'
@@ -369,19 +379,18 @@ class Wire(Line):
# List of commands to remove the old objects
rems = list()
for o in Gui.Selection.getSelection():
- rems.append('FreeCAD.ActiveDocument.'
- 'removeObject("' + o.Name + '")')
+ rems.append("FreeCAD.ActiveDocument." 'removeObject("' + o.Name + '")')
Gui.addModule("Draft")
# The command to run is built as a series of text strings
# to be committed through the `draftutils.todo.ToDo` class
- _cmd = 'wire = Draft.make_wire('
- _cmd += '[' + pts + '], closed=' + str(w.isClosed())
- _cmd += ')'
+ _cmd = "wire = Draft.make_wire("
+ _cmd += "[" + pts + "], closed=" + str(w.isClosed())
+ _cmd += ")"
_cmd_list = [_cmd]
_cmd_list.extend(rems)
- _cmd_list.append('Draft.autogroup(wire)')
- _cmd_list.append('FreeCAD.ActiveDocument.recompute()')
+ _cmd_list.append("Draft.autogroup(wire)")
+ _cmd_list.append("FreeCAD.ActiveDocument.recompute()")
_op_name = translate("draft", "Convert to Wire")
todo.ToDo.delayCommit([(_op_name, _cmd_list)])
@@ -390,11 +399,11 @@ class Wire(Line):
# If there was no selection or the selection was just one object
# then we proceed with the normal line creation functions,
# only this time we will be able to input more than two points
- super().Activated(name="Polyline",
- icon="Draft_Wire",
- task_title=translate("draft", "Polyline"))
+ super().Activated(
+ name="Polyline", icon="Draft_Wire", task_title=translate("draft", "Polyline")
+ )
-Gui.addCommand('Draft_Wire', Wire())
+Gui.addCommand("Draft_Wire", Wire())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_lineslope.py b/src/Mod/Draft/draftguitools/gui_lineslope.py
index 928a64500e..d440296def 100644
--- a/src/Mod/Draft/draftguitools/gui_lineslope.py
+++ b/src/Mod/Draft/draftguitools/gui_lineslope.py
@@ -62,9 +62,14 @@ class LineSlope(gui_base.GuiCommandNeedsSelection):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_Slope",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Slope", "Set Slope"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Slope", "Sets the slope of the selected line by changing the value of the Z value of one of its points.\nIf a polyline is selected, it will apply the slope transformation to each of its segments.\n\nThe slope will always change the Z value, therefore this command only works well for\nstraight Draft lines that are drawn on the XY-plane.")}
+ return {
+ "Pixmap": "Draft_Slope",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Slope", "Set Slope"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Slope",
+ "Sets the slope of the selected line by changing the value of the Z value of one of its points.\nIf a polyline is selected, it will apply the slope transformation to each of its segments.\n\nThe slope will always change the Z value, therefore this command only works well for\nstraight Draft lines that are drawn on the XY-plane.",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -92,11 +97,13 @@ class LineSlope(gui_base.GuiCommandNeedsSelection):
self.spinbox.setMaximum(9999.99)
self.spinbox.setSingleStep(0.01)
- _tip = ("New slope of the selected lines.\n"
- "This is the tangent of the horizontal angle:\n"
- "0 = horizontal\n"
- "1 = 45 deg up\n"
- "-1 = 45deg down\n")
+ _tip = (
+ "New slope of the selected lines.\n"
+ "This is the tangent of the horizontal angle:\n"
+ "0 = horizontal\n"
+ "1 = 45 deg up\n"
+ "-1 = 45deg down\n"
+ )
label.setToolTip(translate("Draft", _tip))
self.spinbox.setToolTip(translate("Draft", _tip))
layout.addWidget(self.spinbox)
@@ -145,6 +152,6 @@ class LineSlope(gui_base.GuiCommandNeedsSelection):
Draft_Slope = LineSlope
-Gui.addCommand('Draft_Slope', LineSlope())
+Gui.addCommand("Draft_Slope", LineSlope())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_mirror.py b/src/Mod/Draft/draftguitools/gui_mirror.py
index d2837fd254..600483dfc4 100644
--- a/src/Mod/Draft/draftguitools/gui_mirror.py
+++ b/src/Mod/Draft/draftguitools/gui_mirror.py
@@ -59,10 +59,14 @@ class Mirror(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_Mirror',
- 'Accel': "M, I",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Mirror", "Mirror"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Mirror", "Mirrors the selected objects along a line defined by 2 points")}
+ return {
+ "Pixmap": "Draft_Mirror",
+ "Accel": "M, I",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Mirror", "Mirror"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Mirror", "Mirrors the selected objects along a line defined by 2 points"
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -72,9 +76,7 @@ class Mirror(gui_base_original.Modifier):
if not Gui.Selection.getSelection():
self.ui.selectUi(on_close_call=self.finish)
_msg(translate("draft", "Select an object to mirror"))
- self.call = \
- self.view.addEventCallback("SoEvent",
- gui_tool_utils.selectObject)
+ self.call = self.view.addEventCallback("SoEvent", gui_tool_utils.selectObject)
else:
self.proceed()
@@ -101,23 +103,21 @@ class Mirror(gui_base_original.Modifier):
def mirror(self, p1, p2, copy=False):
"""Mirror the real shapes."""
- sel = '['
+ sel = "["
for o in self.sel:
if len(sel) > 1:
- sel += ', '
- sel += 'FreeCAD.ActiveDocument.' + o.Name
- sel += ']'
+ sel += ", "
+ sel += "FreeCAD.ActiveDocument." + o.Name
+ sel += "]"
Gui.addModule("Draft")
- _cmd = 'Draft.mirror'
- _cmd += '('
- _cmd += sel + ', '
- _cmd += DraftVecUtils.toString(p1) + ', '
+ _cmd = "Draft.mirror"
+ _cmd += "("
+ _cmd += sel + ", "
+ _cmd += DraftVecUtils.toString(p1) + ", "
_cmd += DraftVecUtils.toString(p2)
- _cmd += ')'
- _cmd_list = ['m = ' + _cmd,
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Mirror"),
- _cmd_list)
+ _cmd += ")"
+ _cmd_list = ["m = " + _cmd, "FreeCAD.ActiveDocument.recompute()"]
+ self.commit(translate("draft", "Mirror"), _cmd_list)
def action(self, arg):
"""Handle the 3D scene events.
@@ -147,7 +147,7 @@ class Mirror(gui_base_original.Modifier):
if nor.Length > tol:
nor.normalize()
mtx = DraftGeomUtils.mirror_matrix(App.Matrix(), last, nor)
- self.ghost.setMatrix(mtx) # Ignores the position of the matrix.
+ self.ghost.setMatrix(mtx) # Ignores the position of the matrix.
self.ghost.move(App.Vector(mtx.col(3)[:3]))
if self.extendedCopy:
if not gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key()):
@@ -157,19 +157,19 @@ class Mirror(gui_base_original.Modifier):
if (arg["State"] == "DOWN") and (arg["Button"] == "BUTTON1"):
if self.point:
self.ui.redraw()
- if (self.node == []):
+ if self.node == []:
self.node.append(self.point)
self.ui.isRelative.show()
if self.ghost:
self.ghost.on()
- _toolmsg(translate("draft",
- "Pick end point of mirror line"))
+ _toolmsg(translate("draft", "Pick end point of mirror line"))
if self.planetrack:
self.planetrack.set(self.point)
else:
last = self.node[0]
- if (self.ui.isCopy.isChecked()
- or gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key())):
+ if self.ui.isCopy.isChecked() or gui_tool_utils.hasMod(
+ arg, gui_tool_utils.get_mod_alt_key()
+ ):
self.mirror(last, self.point, True)
else:
self.mirror(last, self.point)
@@ -199,6 +199,6 @@ class Mirror(gui_base_original.Modifier):
self.finish()
-Gui.addCommand('Draft_Mirror', Mirror())
+Gui.addCommand("Draft_Mirror", Mirror())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_move.py b/src/Mod/Draft/draftguitools/gui_move.py
index 8b0569a7d4..ce440b81e1 100644
--- a/src/Mod/Draft/draftguitools/gui_move.py
+++ b/src/Mod/Draft/draftguitools/gui_move.py
@@ -50,16 +50,21 @@ class Move(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_Move",
- "Accel": "M, V",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Move", "Move"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Move", "Moves the selected objects.\nIf the \"Copy\" option is active, it creates displaced copies.")}
+ return {
+ "Pixmap": "Draft_Move",
+ "Accel": "M, V",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Move", "Move"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Move",
+ 'Moves the selected objects.\nIf the "Copy" option is active, it creates displaced copies.',
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
- super().Activated(name="Move",
- is_subtool=isinstance(App.activeDraftCommand,
- SubelementHighlight))
+ super().Activated(
+ name="Move", is_subtool=isinstance(App.activeDraftCommand, SubelementHighlight)
+ )
if not self.ui:
return
self.ghosts = []
@@ -78,7 +83,7 @@ class Move(gui_base_original.Modifier):
if self.call:
self.view.removeEventCallback("SoEvent", self.call)
self.selection = Gui.Selection.getSelectionEx("", 0)
- Gui.doCommand("selection = FreeCADGui.Selection.getSelectionEx(\"\", 0)")
+ Gui.doCommand('selection = FreeCADGui.Selection.getSelectionEx("", 0)')
self.ui.lineUi(title=translate("draft", self.featureName), icon="Draft_Move")
self.ui.modUi()
if self.copymode:
@@ -119,9 +124,11 @@ class Move(gui_base_original.Modifier):
self.finish()
elif arg["Type"] == "SoLocation2Event":
self.handle_mouse_move_event(arg)
- elif (arg["Type"] == "SoMouseButtonEvent"
- and arg["State"] == "DOWN"
- and arg["Button"] == "BUTTON1"):
+ elif (
+ arg["Type"] == "SoMouseButtonEvent"
+ and arg["State"] == "DOWN"
+ and arg["Button"] == "BUTTON1"
+ ):
self.handle_mouse_click_event(arg)
def handle_mouse_move_event(self, arg):
@@ -162,8 +169,10 @@ class Move(gui_base_original.Modifier):
else:
last = self.node[0]
self.vector = self.point.sub(last)
- self.move(self.ui.isCopy.isChecked()
- or gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key()))
+ self.move(
+ self.ui.isCopy.isChecked()
+ or gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key())
+ )
if gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key()):
self.extendedCopy = True
else:
@@ -179,12 +188,15 @@ class Move(gui_base_original.Modifier):
if not self.ghosts:
_err(translate("draft", "No valid subelements selected"))
else:
- objs, places, _ = utils._modifiers_process_selection(self.selection, copy, add_movable_children=(not copy))
+ objs, places, _ = utils._modifiers_process_selection(
+ self.selection, copy, add_movable_children=(not copy)
+ )
self.ghosts = [trackers.ghostTracker(objs, parent_places=places)]
def get_subelement_ghosts(self, selection, copy):
"""Get ghost for the subelements (vertices, edges)."""
import Part
+
ghosts = []
for sel in selection:
for sub in sel.SubElementNames if sel.SubElementNames else [""]:
@@ -228,6 +240,6 @@ class Move(gui_base_original.Modifier):
self.finish(cont=None)
-Gui.addCommand('Draft_Move', Move())
+Gui.addCommand("Draft_Move", Move())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_offset.py b/src/Mod/Draft/draftguitools/gui_offset.py
index 50d9eae88d..614c06f018 100644
--- a/src/Mod/Draft/draftguitools/gui_offset.py
+++ b/src/Mod/Draft/draftguitools/gui_offset.py
@@ -58,10 +58,15 @@ class Offset(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_Offset',
- 'Accel': "O, S",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Offset", "Offset"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Offset", "Offsets the selected object.\nIt can also create an offset copy of the original object.")}
+ return {
+ "Pixmap": "Draft_Offset",
+ "Accel": "O, S",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Offset", "Offset"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Offset",
+ "Offsets the selected object.\nIt can also create an offset copy of the original object.",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -74,12 +79,9 @@ class Offset(gui_base_original.Modifier):
if not Gui.Selection.getSelection():
self.ui.selectUi(on_close_call=self.finish)
_msg(translate("draft", "Select an object to offset"))
- self.call = self.view.addEventCallback(
- "SoEvent",
- gui_tool_utils.selectObject)
+ self.call = self.view.addEventCallback("SoEvent", gui_tool_utils.selectObject)
elif len(Gui.Selection.getSelection()) > 1:
- _wrn(translate("draft", "Offset only works "
- "on one object at a time"))
+ _wrn(translate("draft", "Offset only works " "on one object at a time"))
else:
self.proceed()
@@ -119,8 +121,7 @@ class Offset(gui_base_original.Modifier):
self.ghost = trackers.bsplineTracker(points=self.sel.Points)
self.mode = "BSpline"
elif utils.getType(self.sel) == "BezCurve":
- _wrn(translate("draft", "Offset of Bézier curves "
- "is currently not supported"))
+ _wrn(translate("draft", "Offset of Bézier curves " "is currently not supported"))
self.finish()
return
else:
@@ -165,29 +166,26 @@ class Offset(gui_base_original.Modifier):
pass
elif arg["Type"] == "SoLocation2Event":
self.point, ctrlPoint, info = gui_tool_utils.getPoint(self, arg)
- if (gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_constrain_key())
- and self.constrainSeg):
- dist = DraftGeomUtils.findPerpendicular(self.point,
- self.shape,
- self.constrainSeg[1])
+ if (
+ gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_constrain_key())
+ and self.constrainSeg
+ ):
+ dist = DraftGeomUtils.findPerpendicular(
+ self.point, self.shape, self.constrainSeg[1]
+ )
else:
- dist = DraftGeomUtils.findPerpendicular(self.point,
- self.shape.Edges)
+ dist = DraftGeomUtils.findPerpendicular(self.point, self.shape.Edges)
if dist:
self.ghost.on()
if self.mode == "Wire":
d = dist[0].negative()
- v1 = DraftGeomUtils.getTangent(self.shape.Edges[0],
- self.point)
- v2 = DraftGeomUtils.getTangent(self.shape.Edges[dist[1]],
- self.point)
+ v1 = DraftGeomUtils.getTangent(self.shape.Edges[0], self.point)
+ v2 = DraftGeomUtils.getTangent(self.shape.Edges[dist[1]], self.point)
a = -DraftVecUtils.angle(v1, v2, self.wp.axis)
self.dvec = DraftVecUtils.rotate(d, a, self.wp.axis)
occmode = self.ui.occOffset.isChecked()
params.set_param("Offset_OCC", occmode)
- _wire = DraftGeomUtils.offsetWire(self.shape,
- self.dvec,
- occ=occmode)
+ _wire = DraftGeomUtils.offsetWire(self.shape, self.dvec, occ=occmode)
self.ghost.update(_wire, forceclosed=occmode)
elif self.mode == "BSpline":
d = dist[0].negative()
@@ -225,39 +223,37 @@ class Offset(gui_base_original.Modifier):
copymode = False
occmode = self.ui.occOffset.isChecked()
params.set_param("Offset_OCC", occmode)
- if (gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key())
- or self.ui.isCopy.isChecked()):
+ if (
+ gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key())
+ or self.ui.isCopy.isChecked()
+ ):
copymode = True
Gui.addModule("Draft")
if self.npts:
- _cmd = 'Draft.offset'
- _cmd += '('
- _cmd += 'FreeCAD.ActiveDocument.'
- _cmd += self.sel.Name + ', '
- _cmd += DraftVecUtils.toString(self.npts) + ', '
- _cmd += 'copy=' + str(copymode)
- _cmd += ')'
- _cmd_list = ['offst = ' + _cmd,
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Offset"),
- _cmd_list)
+ _cmd = "Draft.offset"
+ _cmd += "("
+ _cmd += "FreeCAD.ActiveDocument."
+ _cmd += self.sel.Name + ", "
+ _cmd += DraftVecUtils.toString(self.npts) + ", "
+ _cmd += "copy=" + str(copymode)
+ _cmd += ")"
+ _cmd_list = ["offst = " + _cmd, "FreeCAD.ActiveDocument.recompute()"]
+ self.commit(translate("draft", "Offset"), _cmd_list)
elif self.dvec:
if isinstance(self.dvec, float):
delta = str(self.dvec)
else:
delta = DraftVecUtils.toString(self.dvec)
- _cmd = 'Draft.offset'
- _cmd += '('
- _cmd += 'FreeCAD.ActiveDocument.'
- _cmd += self.sel.Name + ', '
- _cmd += delta + ', '
- _cmd += 'copy=' + str(copymode) + ', '
- _cmd += 'occ=' + str(occmode)
- _cmd += ')'
- _cmd_list = ['offst = ' + _cmd,
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Offset"),
- _cmd_list)
+ _cmd = "Draft.offset"
+ _cmd += "("
+ _cmd += "FreeCAD.ActiveDocument."
+ _cmd += self.sel.Name + ", "
+ _cmd += delta + ", "
+ _cmd += "copy=" + str(copymode) + ", "
+ _cmd += "occ=" + str(occmode)
+ _cmd += ")"
+ _cmd_list = ["offst = " + _cmd, "FreeCAD.ActiveDocument.recompute()"]
+ self.commit(translate("draft", "Offset"), _cmd_list)
if gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key()):
self.extendedCopy = True
else:
@@ -298,7 +294,7 @@ class Offset(gui_base_original.Modifier):
new_points = []
for old_point, new_point in zip(self.sel.Points, self.npts):
diff_direction = new_point.sub(old_point).normalize()
- new_points.append(old_point.add(diff_direction*rad))
+ new_points.append(old_point.add(diff_direction * rad))
delta = DraftVecUtils.toString(new_points)
else:
self.dvec.normalize()
@@ -311,24 +307,26 @@ class Offset(gui_base_original.Modifier):
if self.ui.isCopy.isChecked():
copymode = True
Gui.addModule("Draft")
- _cmd = 'Draft.offset'
- _cmd += '('
- _cmd += 'FreeCAD.ActiveDocument.'
- _cmd += self.sel.Name + ', '
- _cmd += delta + ', '
- _cmd += 'copy=' + str(copymode) + ', '
- _cmd += 'occ=' + str(occmode)
- _cmd += ')'
- _cmd_list = ['offst = ' + _cmd,
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Offset"),
- _cmd_list)
+ _cmd = "Draft.offset"
+ _cmd += "("
+ _cmd += "FreeCAD.ActiveDocument."
+ _cmd += self.sel.Name + ", "
+ _cmd += delta + ", "
+ _cmd += "copy=" + str(copymode) + ", "
+ _cmd += "occ=" + str(occmode)
+ _cmd += ")"
+ _cmd_list = ["offst = " + _cmd, "FreeCAD.ActiveDocument.recompute()"]
+ self.commit(translate("draft", "Offset"), _cmd_list)
self.finish()
else:
- _err(translate("Draft",
- "Offset direction is not defined. Move the mouse on either side of the object first to indicate a direction."))
+ _err(
+ translate(
+ "Draft",
+ "Offset direction is not defined. Move the mouse on either side of the object first to indicate a direction.",
+ )
+ )
-Gui.addCommand('Draft_Offset', Offset())
+Gui.addCommand("Draft_Offset", Offset())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_orthoarray.py b/src/Mod/Draft/draftguitools/gui_orthoarray.py
index b03c2c7209..b55e0c4487 100644
--- a/src/Mod/Draft/draftguitools/gui_orthoarray.py
+++ b/src/Mod/Draft/draftguitools/gui_orthoarray.py
@@ -51,9 +51,13 @@ class OrthoArray(gui_base.GuiCommandBase):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_Array",
- "MenuText": QT_TRANSLATE_NOOP("Draft_OrthoArray", "Array"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_OrthoArray", "Creates copies of the selected object in an orthogonal pattern")}
+ return {
+ "Pixmap": "Draft_Array",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_OrthoArray", "Array"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_OrthoArray", "Creates copies of the selected object in an orthogonal pattern"
+ ),
+ }
def Activated(self):
"""Execute when the command is called.
@@ -67,8 +71,7 @@ class OrthoArray(gui_base.GuiCommandBase):
self.mouse_event = coin.SoMouseButtonEvent.getClassTypeId()
# self.callback_move = \
# self.view.addEventCallbackPivy(self.location, self.move)
- self.callback_click = \
- self.view.addEventCallbackPivy(self.mouse_event, self.click)
+ self.callback_click = self.view.addEventCallbackPivy(self.mouse_event, self.click)
self.ui = task_orthoarray.TaskPanelOrthoArray()
# The calling class (this one) is saved in the object
@@ -86,8 +89,10 @@ class OrthoArray(gui_base.GuiCommandBase):
"""
if event_cb:
event = event_cb.getEvent()
- if (event.getState() != coin.SoMouseButtonEvent.DOWN
- or event.getButton() != coin.SoMouseButtonEvent.BUTTON1):
+ if (
+ event.getState() != coin.SoMouseButtonEvent.DOWN
+ or event.getButton() != coin.SoMouseButtonEvent.BUTTON1
+ ):
return
if self.ui and self.point:
# The accept function of the interface
@@ -113,6 +118,6 @@ class OrthoArray(gui_base.GuiCommandBase):
self.finish()
-Gui.addCommand('Draft_OrthoArray', OrthoArray())
+Gui.addCommand("Draft_OrthoArray", OrthoArray())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_patharray.py b/src/Mod/Draft/draftguitools/gui_patharray.py
index 9cd6fece38..3f9189f125 100644
--- a/src/Mod/Draft/draftguitools/gui_patharray.py
+++ b/src/Mod/Draft/draftguitools/gui_patharray.py
@@ -69,9 +69,13 @@ class PathArray(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_PathArray',
- 'MenuText': QT_TRANSLATE_NOOP("Draft_PathArray", "Path Array"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_PathArray", "Creates copies of the selected object along a selected path")}
+ return {
+ "Pixmap": "Draft_PathArray",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_PathArray", "Path Array"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_PathArray", "Creates copies of the selected object along a selected path"
+ ),
+ }
def Activated(self, name="Path array"):
"""Execute when the command is called."""
@@ -99,7 +103,12 @@ class PathArray(gui_base_original.Modifier):
"""Proceed with the command if one object was selected."""
sel = Gui.Selection.getSelectionEx()
if len(sel) != 2:
- _err(translate("draft","Select exactly 2 objects, the base object and the path object, before calling this command"))
+ _err(
+ translate(
+ "draft",
+ "Select exactly 2 objects, the base object and the path object, before calling this command",
+ )
+ )
else:
base_object = sel[0].Object
path_object = sel[1].Object
@@ -141,17 +150,19 @@ class PathArray(gui_base_original.Modifier):
_cmd += "use_link=" + str(use_link)
_cmd += ")"
- _cmd_list = ["_obj_ = " + _cmd,
- "Draft.autogroup(_obj_)",
- "App.ActiveDocument.recompute()"]
- self.commit(translate("draft","Create Path Array"), _cmd_list)
+ _cmd_list = [
+ "_obj_ = " + _cmd,
+ "Draft.autogroup(_obj_)",
+ "App.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Path Array"), _cmd_list)
# Commit the transaction and execute the commands
# through the parent class
self.finish()
-Gui.addCommand('Draft_PathArray', PathArray())
+Gui.addCommand("Draft_PathArray", PathArray())
class PathLinkArray(PathArray):
@@ -163,15 +174,20 @@ class PathLinkArray(PathArray):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_PathLinkArray',
- 'MenuText': QT_TRANSLATE_NOOP("Draft_PathLinkArray", "Path Link Array"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_PathLinkArray", "Creates linked copies of the selected object along a selected path")}
+ return {
+ "Pixmap": "Draft_PathLinkArray",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_PathLinkArray", "Path Link Array"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_PathLinkArray",
+ "Creates linked copies of the selected object along a selected path",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
super(PathLinkArray, self).Activated(name="Path link array")
-Gui.addCommand('Draft_PathLinkArray', PathLinkArray())
+Gui.addCommand("Draft_PathLinkArray", PathLinkArray())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_pathtwistedarray.py b/src/Mod/Draft/draftguitools/gui_pathtwistedarray.py
index e11dfd1b43..852f326c67 100644
--- a/src/Mod/Draft/draftguitools/gui_pathtwistedarray.py
+++ b/src/Mod/Draft/draftguitools/gui_pathtwistedarray.py
@@ -62,9 +62,14 @@ class PathTwistedArray(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_PathTwistedArray',
- 'MenuText': QT_TRANSLATE_NOOP("Draft_PathTwistedArray", "Twisted Path Array"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_PathTwistedArray", "Creates twisted copies of the selected object along a selected path")}
+ return {
+ "Pixmap": "Draft_PathTwistedArray",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_PathTwistedArray", "Twisted Path Array"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_PathTwistedArray",
+ "Creates twisted copies of the selected object along a selected path",
+ ),
+ }
def Activated(self, name="Path twisted array"):
"""Execute when the command is called."""
@@ -76,7 +81,12 @@ class PathTwistedArray(gui_base_original.Modifier):
"""Proceed with the command if one object was selected."""
sel = Gui.Selection.getSelectionEx()
if len(sel) != 2:
- _err(translate("draft","Select exactly 2 objects, the base object and the path object, before calling this command"))
+ _err(
+ translate(
+ "draft",
+ "Select exactly 2 objects, the base object and the path object, before calling this command",
+ )
+ )
else:
base_object = sel[0].Object
path_object = sel[1].Object
@@ -95,17 +105,19 @@ class PathTwistedArray(gui_base_original.Modifier):
_cmd += "use_link=" + str(use_link)
_cmd += ")"
- _cmd_list = ["_obj_ = " + _cmd,
- "Draft.autogroup(_obj_)",
- "App.ActiveDocument.recompute()"]
- self.commit(translate("draft","Create Path Twisted Array"), _cmd_list)
+ _cmd_list = [
+ "_obj_ = " + _cmd,
+ "Draft.autogroup(_obj_)",
+ "App.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Path Twisted Array"), _cmd_list)
# Commit the transaction and execute the commands
# through the parent class
self.finish()
-Gui.addCommand('Draft_PathTwistedArray', PathTwistedArray())
+Gui.addCommand("Draft_PathTwistedArray", PathTwistedArray())
class PathTwistedLinkArray(PathTwistedArray):
@@ -117,16 +129,20 @@ class PathTwistedLinkArray(PathTwistedArray):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_PathTwistedLinkArray',
- 'MenuText': QT_TRANSLATE_NOOP("Draft_PathTwistedLinkArray","Twisted Path Link Array"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_PathTwistedLinkArray","Creates twisted linked copies of the selected object along a selected path")}
+ return {
+ "Pixmap": "Draft_PathTwistedLinkArray",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_PathTwistedLinkArray", "Twisted Path Link Array"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_PathTwistedLinkArray",
+ "Creates twisted linked copies of the selected object along a selected path",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
- super(PathTwistedLinkArray,
- self).Activated(name="Path twisted link array")
+ super(PathTwistedLinkArray, self).Activated(name="Path twisted link array")
-Gui.addCommand('Draft_PathTwistedLinkArray', PathTwistedLinkArray())
+Gui.addCommand("Draft_PathTwistedLinkArray", PathTwistedLinkArray())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_planeproxy.py b/src/Mod/Draft/draftguitools/gui_planeproxy.py
index 2d2253ae72..56369a06c0 100644
--- a/src/Mod/Draft/draftguitools/gui_planeproxy.py
+++ b/src/Mod/Draft/draftguitools/gui_planeproxy.py
@@ -32,8 +32,7 @@ import FreeCADGui as Gui
from draftutils import gui_utils
__title__ = "FreeCAD Draft Workbench GUI Tools - Working plane-related tools"
-__author__ = ("Yorik van Havre, Werner Mayer, Martin Burbaum, Ken Cline, "
- "Dmitry Chigrin")
+__author__ = "Yorik van Havre, Werner Mayer, Martin Burbaum, Ken Cline, " "Dmitry Chigrin"
__url__ = "https://www.freecad.org"
@@ -42,9 +41,14 @@ class Draft_WorkingPlaneProxy:
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_PlaneProxy",
- "MenuText": QT_TRANSLATE_NOOP("Draft_WorkingPlaneProxy", "Working Plane Proxy"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_WorkingPlaneProxy", "Creates a proxy object from the current working plane that allows to restore the camera position and visibility of objects")}
+ return {
+ "Pixmap": "Draft_PlaneProxy",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_WorkingPlaneProxy", "Working Plane Proxy"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_WorkingPlaneProxy",
+ "Creates a proxy object from the current working plane that allows to restore the camera position and visibility of objects",
+ ),
+ }
def IsActive(self):
"""Return True when this command should be available."""
@@ -61,6 +65,6 @@ class Draft_WorkingPlaneProxy:
App.ActiveDocument.recompute()
-Gui.addCommand('Draft_WorkingPlaneProxy', Draft_WorkingPlaneProxy())
+Gui.addCommand("Draft_WorkingPlaneProxy", Draft_WorkingPlaneProxy())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_pointarray.py b/src/Mod/Draft/draftguitools/gui_pointarray.py
index f00bda7d3e..fcbaa041ab 100644
--- a/src/Mod/Draft/draftguitools/gui_pointarray.py
+++ b/src/Mod/Draft/draftguitools/gui_pointarray.py
@@ -63,9 +63,14 @@ class PointArray(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_PointArray',
- 'MenuText': QT_TRANSLATE_NOOP("Draft_PointArray", "Point Array"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_PointArray", "Creates copies of the selected object at the points of a point object")}
+ return {
+ "Pixmap": "Draft_PointArray",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_PointArray", "Point Array"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_PointArray",
+ "Creates copies of the selected object at the points of a point object",
+ ),
+ }
def Activated(self, name="Point array"):
"""Execute when the command is called."""
@@ -92,32 +97,40 @@ class PointArray(gui_base_original.Modifier):
"""Proceed with the command if one object was selected."""
sel = Gui.Selection.getSelectionEx()
if len(sel) != 2:
- _err(translate("draft","Select exactly 2 objects, the base object and the point object, before calling this command"))
+ _err(
+ translate(
+ "draft",
+ "Select exactly 2 objects, the base object and the point object, before calling this command",
+ )
+ )
else:
base_object = sel[0].Object
point_object = sel[1].Object
extra = None
- Gui.addModule('Draft')
+ Gui.addModule("Draft")
_cmd = "Draft.make_point_array"
_cmd += "("
_cmd += "App.ActiveDocument." + base_object.Name + ", "
_cmd += "App.ActiveDocument." + point_object.Name + ", "
_cmd += "extra=" + str(extra) + ", "
- _cmd += 'use_link=' + str(self.use_link)
+ _cmd += "use_link=" + str(self.use_link)
_cmd += ")"
- _cmd_list = ["_obj_ = " + _cmd,
- "Draft.autogroup(_obj_)",
- "App.ActiveDocument.recompute()"]
- self.commit(translate("draft","Create Point Array"), _cmd_list)
+ _cmd_list = [
+ "_obj_ = " + _cmd,
+ "Draft.autogroup(_obj_)",
+ "App.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Point Array"), _cmd_list)
# Commit the transaction and execute the commands
# through the parent class
self.finish()
-Gui.addCommand('Draft_PointArray', PointArray())
+Gui.addCommand("Draft_PointArray", PointArray())
+
class PointLinkArray(PointArray):
"""Gui Command for the PointLinkArray tool based on the PointArray tool."""
@@ -128,15 +141,20 @@ class PointLinkArray(PointArray):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_PointLinkArray',
- 'MenuText': QT_TRANSLATE_NOOP("Draft_PointLinkArray", "Point Link Array"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_PointLinkArray", "Creates linked copies of the selected object at the points of a point object")}
+ return {
+ "Pixmap": "Draft_PointLinkArray",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_PointLinkArray", "Point Link Array"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_PointLinkArray",
+ "Creates linked copies of the selected object at the points of a point object",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
super(PointLinkArray, self).Activated(name="Point link array")
-Gui.addCommand('Draft_PointLinkArray', PointLinkArray())
+Gui.addCommand("Draft_PointLinkArray", PointLinkArray())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_points.py b/src/Mod/Draft/draftguitools/gui_points.py
index 1d6addcbd9..f5607213fd 100644
--- a/src/Mod/Draft/draftguitools/gui_points.py
+++ b/src/Mod/Draft/draftguitools/gui_points.py
@@ -59,9 +59,11 @@ class Point(gui_base_original.Creator):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_Point',
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Point", "Point"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Point", "Creates a point")}
+ return {
+ "Pixmap": "Draft_Point",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Point", "Point"),
+ "ToolTip": QT_TRANSLATE_NOOP("Draft_Point", "Creates a point"),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -71,8 +73,12 @@ class Point(gui_base_original.Creator):
self.ui.isRelative.hide()
self.ui.continueCmd.show()
# adding 2 callback functions
- self.callbackClick = self.view.addEventCallbackPivy(coin.SoMouseButtonEvent.getClassTypeId(), self.click)
- self.callbackMove = self.view.addEventCallbackPivy(coin.SoLocation2Event.getClassTypeId(), self.move)
+ self.callbackClick = self.view.addEventCallbackPivy(
+ coin.SoMouseButtonEvent.getClassTypeId(), self.click
+ )
+ self.callbackMove = self.view.addEventCallbackPivy(
+ coin.SoLocation2Event.getClassTypeId(), self.move
+ )
def move(self, event_cb):
"""Execute as a callback when the pointer moves in the 3D view.
@@ -108,34 +114,40 @@ class Point(gui_base_original.Creator):
if not self.ui.mouse:
return
event = event_cb.getEvent()
- if (event.getState() != coin.SoMouseButtonEvent.DOWN or
- event.getButton() != event.BUTTON1):
+ if (
+ event.getState() != coin.SoMouseButtonEvent.DOWN
+ or event.getButton() != event.BUTTON1
+ ):
return
if self.point:
Gui.addModule("Draft")
if params.get_param("UsePartPrimitives"):
# Insert a Part::Primitive object
- _cmd = 'FreeCAD.ActiveDocument.'
+ _cmd = "FreeCAD.ActiveDocument."
_cmd += 'addObject("Part::Vertex", "Point")'
- _cmd_list = ['point = ' + _cmd,
- 'point.X = ' + str(self.point[0]),
- 'point.Y = ' + str(self.point[1]),
- 'point.Z = ' + str(self.point[2]),
- 'Draft.autogroup(point)',
- 'Draft.select(point)',
- 'FreeCAD.ActiveDocument.recompute()']
+ _cmd_list = [
+ "point = " + _cmd,
+ "point.X = " + str(self.point[0]),
+ "point.Y = " + str(self.point[1]),
+ "point.Z = " + str(self.point[2]),
+ "Draft.autogroup(point)",
+ "Draft.select(point)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
self.commit(translate("draft", "Create Point"), _cmd_list)
else:
# Insert a Draft point
- _cmd = 'Draft.make_point'
- _cmd += '('
- _cmd += str(self.point[0]) + ', '
- _cmd += str(self.point[1]) + ', '
+ _cmd = "Draft.make_point"
+ _cmd += "("
+ _cmd += str(self.point[0]) + ", "
+ _cmd += str(self.point[1]) + ", "
_cmd += str(self.point[2])
- _cmd += ')'
- _cmd_list = ['point = ' + _cmd,
- 'Draft.autogroup(point)',
- 'FreeCAD.ActiveDocument.recompute()']
+ _cmd += ")"
+ _cmd_list = [
+ "point = " + _cmd,
+ "Draft.autogroup(point)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
self.commit(translate("draft", "Create Point"), _cmd_list)
self.finish(cont=None)
@@ -150,9 +162,13 @@ class Point(gui_base_original.Creator):
"""
try:
if self.callbackClick:
- self.view.removeEventCallbackPivy(coin.SoMouseButtonEvent.getClassTypeId(), self.callbackClick)
+ self.view.removeEventCallbackPivy(
+ coin.SoMouseButtonEvent.getClassTypeId(), self.callbackClick
+ )
if self.callbackMove:
- self.view.removeEventCallbackPivy(coin.SoLocation2Event.getClassTypeId(), self.callbackMove)
+ self.view.removeEventCallbackPivy(
+ coin.SoLocation2Event.getClassTypeId(), self.callbackMove
+ )
if self.callbackClick or self.callbackMove:
# Next line fixes https://github.com/FreeCAD/FreeCAD/issues/10469:
gui_utils.end_all_events()
@@ -166,12 +182,14 @@ class Point(gui_base_original.Creator):
self.Activated()
def get_hints(self):
- return [Gui.InputHint(translate("draft", "%1 pick point"), Gui.UserInput.MouseLeft)] \
- + gui_tool_utils._get_hint_xyz_constrain() \
- + gui_tool_utils._get_hint_mod_constrain() \
+ return (
+ [Gui.InputHint(translate("draft", "%1 pick point"), Gui.UserInput.MouseLeft)]
+ + gui_tool_utils._get_hint_xyz_constrain()
+ + gui_tool_utils._get_hint_mod_constrain()
+ gui_tool_utils._get_hint_mod_snap()
+ )
-Gui.addCommand('Draft_Point', Point())
+Gui.addCommand("Draft_Point", Point())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_polararray.py b/src/Mod/Draft/draftguitools/gui_polararray.py
index 9a0248998b..4faf576636 100644
--- a/src/Mod/Draft/draftguitools/gui_polararray.py
+++ b/src/Mod/Draft/draftguitools/gui_polararray.py
@@ -51,9 +51,13 @@ class PolarArray(gui_base.GuiCommandBase):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_PolarArray",
- "MenuText": QT_TRANSLATE_NOOP("Draft_PolarArray", "Polar Array"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_PolarArray", "Creates copies of the selected object in a polar pattern")}
+ return {
+ "Pixmap": "Draft_PolarArray",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_PolarArray", "Polar Array"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_PolarArray", "Creates copies of the selected object in a polar pattern"
+ ),
+ }
def Activated(self):
"""Execute when the command is called.
@@ -65,10 +69,8 @@ class PolarArray(gui_base.GuiCommandBase):
self.location = coin.SoLocation2Event.getClassTypeId()
self.mouse_event = coin.SoMouseButtonEvent.getClassTypeId()
- self.callback_move = \
- self.view.addEventCallbackPivy(self.location, self.move)
- self.callback_click = \
- self.view.addEventCallbackPivy(self.mouse_event, self.click)
+ self.callback_move = self.view.addEventCallbackPivy(self.location, self.move)
+ self.callback_click = self.view.addEventCallbackPivy(self.mouse_event, self.click)
self.ui = task_polararray.TaskPanelPolarArray()
# The calling class (this one) is saved in the object
@@ -99,8 +101,10 @@ class PolarArray(gui_base.GuiCommandBase):
"""
if event_cb:
event = event_cb.getEvent()
- if (event.getState() != coin.SoMouseButtonEvent.DOWN
- or event.getButton() != coin.SoMouseButtonEvent.BUTTON1):
+ if (
+ event.getState() != coin.SoMouseButtonEvent.DOWN
+ or event.getButton() != coin.SoMouseButtonEvent.BUTTON1
+ ):
return
if self.ui and self.point:
# The accept function of the interface
@@ -128,6 +132,6 @@ class PolarArray(gui_base.GuiCommandBase):
self.finish()
-Gui.addCommand('Draft_PolarArray', PolarArray())
+Gui.addCommand("Draft_PolarArray", PolarArray())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_polygons.py b/src/Mod/Draft/draftguitools/gui_polygons.py
index e437458712..ad19dd2955 100644
--- a/src/Mod/Draft/draftguitools/gui_polygons.py
+++ b/src/Mod/Draft/draftguitools/gui_polygons.py
@@ -52,10 +52,14 @@ class Polygon(gui_base_original.Creator):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_Polygon',
- 'Accel': "P, G",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Polygon", "Polygon"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Polygon", "Creates a regular polygon (triangle, square, pentagon…)")}
+ return {
+ "Pixmap": "Draft_Polygon",
+ "Accel": "P, G",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Polygon", "Polygon"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Polygon", "Creates a regular polygon (triangle, square, pentagon…)"
+ ),
+ }
def Activated(self, numVertices=None):
"""Execute when the command is called."""
@@ -107,6 +111,7 @@ class Polygon(gui_base_original.Creator):
from the 3D view.
"""
import DraftGeomUtils
+
if self.ui.numFaces.value() != self.numVertices:
self.polygonTrack.setNumVertices(self.ui.numFaces.value())
self.numVertices = self.ui.numFaces.value()
@@ -121,8 +126,7 @@ class Polygon(gui_base_original.Creator):
# this is to make sure radius is what you see on screen
if self.center and DraftVecUtils.dist(self.point, self.center) > 0:
- viewdelta = DraftVecUtils.project(self.point.sub(self.center),
- self.wp.axis)
+ viewdelta = DraftVecUtils.project(self.point.sub(self.center), self.wp.axis)
if not DraftVecUtils.isNull(viewdelta):
self.point = self.point.add(viewdelta.negative())
if self.step == 0: # choose center
@@ -136,60 +140,61 @@ class Polygon(gui_base_original.Creator):
self.ui.switchUi(False)
else: # choose radius
if len(self.tangents) == 2:
- cir = DraftGeomUtils.circleFrom2tan1pt(self.tangents[0],
- self.tangents[1],
- self.point)
+ cir = DraftGeomUtils.circleFrom2tan1pt(
+ self.tangents[0], self.tangents[1], self.point
+ )
_c = DraftGeomUtils.findClosestCircle(self.point, cir)
self.center = _c.Center
elif self.tangents and self.tanpoints:
- cir = DraftGeomUtils.circleFrom1tan2pt(self.tangents[0],
- self.tanpoints[0],
- self.point)
+ cir = DraftGeomUtils.circleFrom1tan2pt(
+ self.tangents[0], self.tanpoints[0], self.point
+ )
_c = DraftGeomUtils.findClosestCircle(self.point, cir)
self.center = _c.Center
if gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key()):
if not self.altdown:
self.altdown = True
- snapped = self.view.getObjectInfo((arg["Position"][0],
- arg["Position"][1]))
+ snapped = self.view.getObjectInfo((arg["Position"][0], arg["Position"][1]))
if snapped:
- ob = self.doc.getObject(snapped['Object'])
- num = int(snapped['Component'].lstrip('Edge')) - 1
+ ob = self.doc.getObject(snapped["Object"])
+ num = int(snapped["Component"].lstrip("Edge")) - 1
ed = ob.Shape.Edges[num]
if len(self.tangents) == 2:
- cir = DraftGeomUtils.circleFrom3tan(self.tangents[0],
- self.tangents[1],
- ed)
+ cir = DraftGeomUtils.circleFrom3tan(
+ self.tangents[0], self.tangents[1], ed
+ )
cl = DraftGeomUtils.findClosestCircle(self.point, cir)
self.center = cl.Center
self.rad = cl.Radius
else:
- self.rad = self.center.add(DraftGeomUtils.findDistance(self.center,ed).sub(self.center)).Length
+ self.rad = self.center.add(
+ DraftGeomUtils.findDistance(self.center, ed).sub(self.center)
+ ).Length
else:
self.rad = DraftVecUtils.dist(self.point, self.center)
else:
if self.altdown:
self.altdown = False
self.rad = DraftVecUtils.dist(self.point, self.center)
- self.ui.setRadiusValue(self.rad, 'Length')
+ self.ui.setRadiusValue(self.rad, "Length")
gui_tool_utils.redraw3DView()
- elif (arg["Type"] == "SoMouseButtonEvent"
- and arg["State"] == "DOWN"
- and arg["Button"] == "BUTTON1"): # mouse click
+ elif (
+ arg["Type"] == "SoMouseButtonEvent"
+ and arg["State"] == "DOWN"
+ and arg["Button"] == "BUTTON1"
+ ): # mouse click
if self.point:
if self.step == 0: # choose center
if (not self.node) and (not self.support):
gui_tool_utils.getSupport(arg)
- (self.point,
- ctrlPoint, info) = gui_tool_utils.getPoint(self, arg)
+ (self.point, ctrlPoint, info) = gui_tool_utils.getPoint(self, arg)
if gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key()):
- snapped = self.view.getObjectInfo((arg["Position"][0],
- arg["Position"][1]))
+ snapped = self.view.getObjectInfo((arg["Position"][0], arg["Position"][1]))
if snapped:
- ob = self.doc.getObject(snapped['Object'])
- num = int(snapped['Component'].lstrip('Edge')) - 1
+ ob = self.doc.getObject(snapped["Object"])
+ num = int(snapped["Component"].lstrip("Edge")) - 1
ed = ob.Shape.Edges[num]
self.tangents.append(ed)
if len(self.tangents) == 2:
@@ -221,39 +226,41 @@ class Polygon(gui_base_original.Creator):
if params.get_param("UsePartPrimitives"):
# Insert a Part::Primitive object
Gui.addModule("Part")
- _cmd = 'FreeCAD.ActiveDocument.'
+ _cmd = "FreeCAD.ActiveDocument."
_cmd += 'addObject("Part::RegularPolygon","RegularPolygon")'
- _cmd_list = ['pl = FreeCAD.Placement()',
- 'pl.Rotation.Q = ' + rot,
- 'pl.Base = ' + DraftVecUtils.toString(self.center),
- 'pol = ' + _cmd,
- 'pol.Polygon = ' + str(self.ui.numFaces.value()),
- 'pol.Circumradius = ' + str(self.rad),
- 'pol.Placement = pl',
- 'Draft.autogroup(pol)',
- 'Draft.select(pol)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Polygon (Part)"),
- _cmd_list)
+ _cmd_list = [
+ "pl = FreeCAD.Placement()",
+ "pl.Rotation.Q = " + rot,
+ "pl.Base = " + DraftVecUtils.toString(self.center),
+ "pol = " + _cmd,
+ "pol.Polygon = " + str(self.ui.numFaces.value()),
+ "pol.Circumradius = " + str(self.rad),
+ "pol.Placement = pl",
+ "Draft.autogroup(pol)",
+ "Draft.select(pol)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Polygon (Part)"), _cmd_list)
else:
# Insert a Draft polygon
- _cmd = 'Draft.make_polygon'
- _cmd += '('
- _cmd += str(self.ui.numFaces.value()) + ', '
- _cmd += 'radius=' + str(self.rad) + ', '
- _cmd += 'inscribed=True, '
- _cmd += 'placement=pl, '
- _cmd += 'face=' + fil + ', '
- _cmd += 'support=' + sup
- _cmd += ')'
- _cmd_list = ['pl = FreeCAD.Placement()',
- 'pl.Rotation.Q = ' + rot,
- 'pl.Base = ' + DraftVecUtils.toString(self.center),
- 'pol = ' + _cmd,
- 'Draft.autogroup(pol)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Polygon"),
- _cmd_list)
+ _cmd = "Draft.make_polygon"
+ _cmd += "("
+ _cmd += str(self.ui.numFaces.value()) + ", "
+ _cmd += "radius=" + str(self.rad) + ", "
+ _cmd += "inscribed=True, "
+ _cmd += "placement=pl, "
+ _cmd += "face=" + fil + ", "
+ _cmd += "support=" + sup
+ _cmd += ")"
+ _cmd_list = [
+ "pl = FreeCAD.Placement()",
+ "pl.Rotation.Q = " + rot,
+ "pl.Base = " + DraftVecUtils.toString(self.center),
+ "pol = " + _cmd,
+ "Draft.autogroup(pol)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Polygon"), _cmd_list)
self.finish(cont=None)
def numericInput(self, numx, numy, numz):
@@ -281,18 +288,14 @@ class Polygon(gui_base_original.Creator):
self.rad = rad
if len(self.tangents) == 2:
- cir = DraftGeomUtils.circleFrom2tan1rad(self.tangents[0],
- self.tangents[1],
- rad)
+ cir = DraftGeomUtils.circleFrom2tan1rad(self.tangents[0], self.tangents[1], rad)
if self.center:
_c = DraftGeomUtils.findClosestCircle(self.center, cir)
self.center = _c.Center
else:
self.center = cir[-1].Center
elif self.tangents and self.tanpoints:
- cir = DraftGeomUtils.circleFrom1tan1pt1rad(self.tangents[0],
- self.tanpoints[0],
- rad)
+ cir = DraftGeomUtils.circleFrom1tan1pt1rad(self.tangents[0], self.tanpoints[0], rad)
if self.center:
_c = DraftGeomUtils.findClosestCircle(self.center, cir)
self.center = _c.Center
@@ -302,19 +305,17 @@ class Polygon(gui_base_original.Creator):
def get_hints(self):
if self.step == 0:
- hints = [
- Gui.InputHint(translate("draft", "%1 pick center"), Gui.UserInput.MouseLeft)
- ]
+ hints = [Gui.InputHint(translate("draft", "%1 pick center"), Gui.UserInput.MouseLeft)]
else:
- hints = [
- Gui.InputHint(translate("draft", "%1 pick radius"), Gui.UserInput.MouseLeft)
- ]
- return hints \
- + gui_tool_utils._get_hint_xyz_constrain() \
- + gui_tool_utils._get_hint_mod_constrain() \
+ hints = [Gui.InputHint(translate("draft", "%1 pick radius"), Gui.UserInput.MouseLeft)]
+ return (
+ hints
+ + gui_tool_utils._get_hint_xyz_constrain()
+ + gui_tool_utils._get_hint_mod_constrain()
+ gui_tool_utils._get_hint_mod_snap()
+ )
-Gui.addCommand('Draft_Polygon', Polygon())
+Gui.addCommand("Draft_Polygon", Polygon())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_rectangles.py b/src/Mod/Draft/draftguitools/gui_rectangles.py
index ecdaf15019..49d4058b14 100644
--- a/src/Mod/Draft/draftguitools/gui_rectangles.py
+++ b/src/Mod/Draft/draftguitools/gui_rectangles.py
@@ -49,10 +49,12 @@ class Rectangle(gui_base_original.Creator):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_Rectangle',
- 'Accel': "R, E",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Rectangle", "Rectangle"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Rectangle", "Creates a 2-point rectangle")}
+ return {
+ "Pixmap": "Draft_Rectangle",
+ "Accel": "R, E",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Rectangle", "Rectangle"),
+ "ToolTip": QT_TRANSLATE_NOOP("Draft_Rectangle", "Creates a 2-point rectangle"),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -109,37 +111,39 @@ class Rectangle(gui_base_original.Creator):
Gui.addModule("Draft")
if params.get_param("UsePartPrimitives"):
# Insert a Part::Primitive object
- _cmd = 'FreeCAD.ActiveDocument.'
+ _cmd = "FreeCAD.ActiveDocument."
_cmd += 'addObject("Part::Plane", "Plane")'
- _cmd_list = ['plane = ' + _cmd,
- 'plane.Length = ' + str(length),
- 'plane.Width = ' + str(height),
- 'pl = FreeCAD.Placement()',
- 'pl.Rotation.Q=' + rot,
- 'pl.Base = ' + DraftVecUtils.toString(base),
- 'plane.Placement = pl',
- 'Draft.autogroup(plane)',
- 'Draft.select(plane)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Plane"),
- _cmd_list)
+ _cmd_list = [
+ "plane = " + _cmd,
+ "plane.Length = " + str(length),
+ "plane.Width = " + str(height),
+ "pl = FreeCAD.Placement()",
+ "pl.Rotation.Q=" + rot,
+ "pl.Base = " + DraftVecUtils.toString(base),
+ "plane.Placement = pl",
+ "Draft.autogroup(plane)",
+ "Draft.select(plane)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Plane"), _cmd_list)
else:
- _cmd = 'Draft.make_rectangle'
- _cmd += '('
- _cmd += 'length=' + str(length) + ', '
- _cmd += 'height=' + str(height) + ', '
- _cmd += 'placement=pl, '
- _cmd += 'face=' + fil + ', '
- _cmd += 'support=' + sup
- _cmd += ')'
- _cmd_list = ['pl = FreeCAD.Placement()',
- 'pl.Rotation.Q = ' + rot,
- 'pl.Base = ' + DraftVecUtils.toString(base),
- 'rec = ' + _cmd,
- 'Draft.autogroup(rec)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Rectangle"),
- _cmd_list)
+ _cmd = "Draft.make_rectangle"
+ _cmd += "("
+ _cmd += "length=" + str(length) + ", "
+ _cmd += "height=" + str(height) + ", "
+ _cmd += "placement=pl, "
+ _cmd += "face=" + fil + ", "
+ _cmd += "support=" + sup
+ _cmd += ")"
+ _cmd_list = [
+ "pl = FreeCAD.Placement()",
+ "pl.Rotation.Q = " + rot,
+ "pl.Base = " + DraftVecUtils.toString(base),
+ "rec = " + _cmd,
+ "Draft.autogroup(rec)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Rectangle"), _cmd_list)
except Exception:
_err("Draft: error delaying commit")
self.finish(cont=None)
@@ -164,9 +168,11 @@ class Rectangle(gui_base_original.Creator):
self.point, ctrlPoint, info = gui_tool_utils.getPoint(self, arg, noTracker=True)
self.rect.update(self.point)
gui_tool_utils.redraw3DView()
- elif (arg["Type"] == "SoMouseButtonEvent"
- and arg["State"] == "DOWN"
- and arg["Button"] == "BUTTON1"):
+ elif (
+ arg["Type"] == "SoMouseButtonEvent"
+ and arg["State"] == "DOWN"
+ and arg["Button"] == "BUTTON1"
+ ):
if arg["Position"] == self.pos:
self.finish(cont=None)
@@ -213,12 +219,14 @@ class Rectangle(gui_base_original.Creator):
hints = [
Gui.InputHint(translate("draft", "%1 pick opposite point"), Gui.UserInput.MouseLeft)
]
- return hints \
- + gui_tool_utils._get_hint_xyz_constrain() \
- + gui_tool_utils._get_hint_mod_constrain() \
+ return (
+ hints
+ + gui_tool_utils._get_hint_xyz_constrain()
+ + gui_tool_utils._get_hint_mod_constrain()
+ gui_tool_utils._get_hint_mod_snap()
+ )
-Gui.addCommand('Draft_Rectangle', Rectangle())
+Gui.addCommand("Draft_Rectangle", Rectangle())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_rotate.py b/src/Mod/Draft/draftguitools/gui_rotate.py
index 7651e8c08b..197f87ab84 100644
--- a/src/Mod/Draft/draftguitools/gui_rotate.py
+++ b/src/Mod/Draft/draftguitools/gui_rotate.py
@@ -52,10 +52,15 @@ class Rotate(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_Rotate",
- "Accel": "R, O",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Rotate", "Rotate"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Rotate", "Rotates the selected objects.\nIf the \"Copy\" option is active, it will create rotated copies.")}
+ return {
+ "Pixmap": "Draft_Rotate",
+ "Accel": "R, O",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Rotate", "Rotate"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Rotate",
+ 'Rotates the selected objects.\nIf the "Copy" option is active, it will create rotated copies.',
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -79,7 +84,7 @@ class Rotate(gui_base_original.Modifier):
if self.call:
self.view.removeEventCallback("SoEvent", self.call)
self.selection = Gui.Selection.getSelectionEx("", 0)
- Gui.doCommand("selection = FreeCADGui.Selection.getSelectionEx(\"\", 0)")
+ Gui.doCommand('selection = FreeCADGui.Selection.getSelectionEx("", 0)')
self.step = 0
self.center = None
self.point = None
@@ -106,9 +111,11 @@ class Rotate(gui_base_original.Modifier):
pass
elif arg["Type"] == "SoLocation2Event":
self.handle_mouse_move_event(arg)
- elif (arg["Type"] == "SoMouseButtonEvent"
- and arg["State"] == "DOWN"
- and arg["Button"] == "BUTTON1"):
+ elif (
+ arg["Type"] == "SoMouseButtonEvent"
+ and arg["State"] == "DOWN"
+ and arg["Button"] == "BUTTON1"
+ ):
self.handle_mouse_click_event(arg)
def _get_angle(self):
@@ -134,11 +141,7 @@ class Rotate(gui_base_original.Modifier):
# Project self.point on a plane that is parallel to the wp and that
# passes through self.center.
self.point = geometry.project_point_on_plane(
- self.point,
- self.center,
- self.wp.axis,
- direction=None,
- force_projection=True
+ self.point, self.center, self.wp.axis, direction=None, force_projection=True
)
if self.extendedCopy:
if not gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key()):
@@ -183,7 +186,9 @@ class Rotate(gui_base_original.Modifier):
self.ui.radiusValue.setText(U.Quantity(0, U.Angle).UserString)
self.ui.makeFace.hide()
self.ui.labelRadius.setText(translate("draft", "Base angle"))
- self.ui.radiusValue.setToolTip(translate("draft", "The base angle to start the rotation from"))
+ self.ui.radiusValue.setToolTip(
+ translate("draft", "The base angle to start the rotation from")
+ )
self.arctrack.setCenter(self.center)
for ghost in self.ghosts:
ghost.center(self.center)
@@ -196,7 +201,12 @@ class Rotate(gui_base_original.Modifier):
"""Set the starting point of the rotation."""
self.firstangle = self._get_angle()
self.ui.labelRadius.setText(translate("draft", "Rotation"))
- self.ui.radiusValue.setToolTip(translate("draft", "The amount of rotation to perform.\nThe final angle will be the base angle plus this amount."))
+ self.ui.radiusValue.setToolTip(
+ translate(
+ "draft",
+ "The amount of rotation to perform.\nThe final angle will be the base angle plus this amount.",
+ )
+ )
self.arctrack.on()
self.arctrack.setStartPoint(self.point)
for ghost in self.ghosts:
@@ -208,8 +218,10 @@ class Rotate(gui_base_original.Modifier):
"""Set the rotation angle."""
self.angle = self._get_angle()
if self.angle != 0:
- self.rotate(self.ui.isCopy.isChecked()
- or gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key()))
+ self.rotate(
+ self.ui.isCopy.isChecked()
+ or gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key())
+ )
if gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_alt_key()):
self.extendedCopy = True
else:
@@ -225,7 +237,9 @@ class Rotate(gui_base_original.Modifier):
if not self.ghosts:
_err(translate("draft", "No valid subelements selected"))
else:
- objs, places, _ = utils._modifiers_process_selection(self.selection, copy, add_movable_children=(not copy))
+ objs, places, _ = utils._modifiers_process_selection(
+ self.selection, copy, add_movable_children=(not copy)
+ )
self.ghosts = [trackers.ghostTracker(objs, parent_places=places)]
if self.center:
for ghost in self.ghosts:
@@ -234,6 +248,7 @@ class Rotate(gui_base_original.Modifier):
def get_subelement_ghosts(self, selection, copy):
"""Get ghost for the subelements (vertices, edges)."""
import Part
+
ghosts = []
for sel in selection:
for sub in sel.SubElementNames if sel.SubElementNames else [""]:
@@ -290,7 +305,9 @@ class Rotate(gui_base_original.Modifier):
self.ui.radiusUi()
self.ui.makeFace.hide()
self.ui.labelRadius.setText(translate("draft", "Base angle"))
- self.ui.radiusValue.setToolTip(translate("draft", "The base angle to start the rotation from"))
+ self.ui.radiusValue.setToolTip(
+ translate("draft", "The base angle to start the rotation from")
+ )
self.ui.radiusValue.setText(U.Quantity(0, U.Angle).UserString)
self.step = 1
_toolmsg(translate("draft", "Pick base angle"))
@@ -303,7 +320,12 @@ class Rotate(gui_base_original.Modifier):
"""
if self.step == 1:
self.ui.labelRadius.setText(translate("draft", "Rotation"))
- self.ui.radiusValue.setToolTip(translate("draft", "The amount of rotation to perform.\nThe final angle will be the base angle plus this amount."))
+ self.ui.radiusValue.setToolTip(
+ translate(
+ "draft",
+ "The amount of rotation to perform.\nThe final angle will be the base angle plus this amount.",
+ )
+ )
self.ui.radiusValue.setText(U.Quantity(0, U.Angle).UserString)
self.firstangle = math.radians(rad)
self.arctrack.setStartAngle(self.firstangle)
@@ -318,6 +340,6 @@ class Rotate(gui_base_original.Modifier):
self.finish(cont=None)
-Gui.addCommand('Draft_Rotate', Rotate())
+Gui.addCommand("Draft_Rotate", Rotate())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_scale.py b/src/Mod/Draft/draftguitools/gui_scale.py
index 0118343615..62fb932161 100644
--- a/src/Mod/Draft/draftguitools/gui_scale.py
+++ b/src/Mod/Draft/draftguitools/gui_scale.py
@@ -62,10 +62,14 @@ class Scale(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_Scale",
- "Accel": "S, C",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Scale", "Scale"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Scale", "Scales the selected objects from a base point")}
+ return {
+ "Pixmap": "Draft_Scale",
+ "Accel": "S, C",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Scale", "Scale"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Scale", "Scales the selected objects from a base point"
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -88,9 +92,9 @@ class Scale(gui_base_original.Modifier):
if self.call:
self.view.removeEventCallback("SoEvent", self.call)
self.selection = Gui.Selection.getSelectionEx("", 0)
- Gui.doCommand("selection = FreeCADGui.Selection.getSelectionEx(\"\", 0)")
+ Gui.doCommand('selection = FreeCADGui.Selection.getSelectionEx("", 0)')
self.refs = []
- self.ui.pointUi(title=translate("draft",self.featureName), icon="Draft_Scale")
+ self.ui.pointUi(title=translate("draft", self.featureName), icon="Draft_Scale")
self.ui.isRelative.hide()
self.ui.xValue.setFocus()
self.ui.xValue.selectAll()
@@ -116,12 +120,15 @@ class Scale(gui_base_original.Modifier):
if not self.ghosts:
_err(translate("draft", "No valid subelements selected"))
else:
- objs, places, _ = utils._modifiers_process_selection(self.selection, (copy or clone), scale=True)
+ objs, places, _ = utils._modifiers_process_selection(
+ self.selection, (copy or clone), scale=True
+ )
self.ghosts = [trackers.ghostTracker(objs, parent_places=places)]
def get_subelement_ghosts(self, selection, copy):
"""Get ghost for the subelements (vertices, edges)."""
import Part
+
ghosts = []
for sel in selection:
for sub in sel.SubElementNames if sel.SubElementNames else [""]:
@@ -135,7 +142,7 @@ class Scale(gui_base_original.Modifier):
delta = App.Vector(x, y, z)
# ScaleRelative option removed in v1.1 as it does not work properly:
# if rel:
- # delta = self.wp.get_local_coords(delta)
+ # delta = self.wp.get_local_coords(delta)
for ghost in self.ghosts:
ghost.scale(delta)
# calculate a correction factor depending on the scaling center
@@ -170,10 +177,12 @@ class Scale(gui_base_original.Modifier):
self.finish()
elif arg["Type"] == "SoLocation2Event":
self.handle_mouse_move_event(arg)
- elif (arg["Type"] == "SoMouseButtonEvent"
- and arg["State"] == "DOWN"
- and arg["Button"] == "BUTTON1"
- and self.point):
+ elif (
+ arg["Type"] == "SoMouseButtonEvent"
+ and arg["State"] == "DOWN"
+ and arg["Button"] == "BUTTON1"
+ and self.point
+ ):
self.handle_mouse_click_event()
def handle_mouse_move_event(self, arg):
@@ -204,7 +213,7 @@ class Scale(gui_base_original.Modifier):
self.delta = App.Vector(sx, sy, sz)
# ScaleRelative option removed in v1.1 as it does not work properly:
# if self.task.relative.isChecked():
- # self.delta = self.wp.get_local_coords(self.delta)
+ # self.delta = self.wp.get_local_coords(self.delta)
self.center = self.node[0]
if self.task.isCopy.isChecked():
cmd_name = translate("draft", "Copy")
@@ -255,7 +264,7 @@ class Scale(gui_base_original.Modifier):
if hasattr(self, "task"):
if self.task:
self.task.lock.setChecked(True)
- self.task.setValue(d2/d1)
+ self.task.setValue(d2 / d1)
def finish(self, cont=False):
"""Terminate the operation."""
@@ -265,6 +274,6 @@ class Scale(gui_base_original.Modifier):
super().finish()
-Gui.addCommand('Draft_Scale', Scale())
+Gui.addCommand("Draft_Scale", Scale())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_selectplane.py b/src/Mod/Draft/draftguitools/gui_selectplane.py
index 6b0288c127..75152caafb 100644
--- a/src/Mod/Draft/draftguitools/gui_selectplane.py
+++ b/src/Mod/Draft/draftguitools/gui_selectplane.py
@@ -44,8 +44,7 @@ from draftutils.todo import todo
from draftutils.translate import translate
__title__ = "FreeCAD Draft Workbench GUI Tools - Working plane-related tools"
-__author__ = ("Yorik van Havre, Werner Mayer, Martin Burbaum, Ken Cline, "
- "Dmitry Chigrin")
+__author__ = "Yorik van Havre, Werner Mayer, Martin Burbaum, Ken Cline, " "Dmitry Chigrin"
__url__ = "https://www.freecad.org"
@@ -54,10 +53,15 @@ class Draft_SelectPlane:
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_SelectPlane",
- "Accel": "W, P",
- "MenuText": QT_TRANSLATE_NOOP("Draft_SelectPlane", "Working Plane"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_SelectPlane", "Defines the working plane from 3 vertices, 1 or more shapes, or an object")}
+ return {
+ "Pixmap": "Draft_SelectPlane",
+ "Accel": "W, P",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_SelectPlane", "Working Plane"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_SelectPlane",
+ "Defines the working plane from 3 vertices, 1 or more shapes, or an object",
+ ),
+ }
def IsActive(self):
"""Return True when this command should be available."""
@@ -126,9 +130,9 @@ class Draft_SelectPlane:
form.buttonPrevious.clicked.connect(self.on_click_previous)
form.buttonNext.clicked.connect(self.on_click_next)
form.fieldOffset.textEdited.connect(self.on_set_offset)
- if hasattr(form.checkCenter, "checkStateChanged"): # Qt version >= 6.7.0
+ if hasattr(form.checkCenter, "checkStateChanged"): # Qt version >= 6.7.0
form.checkCenter.checkStateChanged.connect(self.on_set_center)
- else: # Qt version < 6.7.0
+ else: # Qt version < 6.7.0
form.checkCenter.stateChanged.connect(self.on_set_center)
form.fieldGridSpacing.textEdited.connect(self.on_set_grid_size)
form.fieldGridMainLine.valueChanged.connect(self.on_set_main_line)
@@ -150,9 +154,12 @@ class Draft_SelectPlane:
# Execute the actual task panel delayed to catch possible active Draft command
todo.delay(Gui.Control.showDialog, self.taskd)
todo.delay(form.setFocus, None)
- _toolmsg(translate(
+ _toolmsg(
+ translate(
"draft",
- "Select 3 vertices, one or more shapes or an object to define a working plane"))
+ "Select 3 vertices, one or more shapes or an object to define a working plane",
+ )
+ )
self.call = self.view.addEventCallback("SoEvent", self.action)
def finish(self):
@@ -178,9 +185,11 @@ class Draft_SelectPlane:
"""Set the callbacks for the view."""
if arg["Type"] == "SoKeyboardEvent" and arg["Key"] == "ESCAPE":
self.reject()
- if arg["Type"] == "SoMouseButtonEvent" \
- and (arg["State"] == "UP") \
- and (arg["Button"] == "BUTTON1"):
+ if (
+ arg["Type"] == "SoMouseButtonEvent"
+ and (arg["State"] == "UP")
+ and (arg["Button"] == "BUTTON1")
+ ):
self.check_selection()
def check_selection(self):
@@ -211,13 +220,14 @@ class Draft_SelectPlane:
def on_click_move(self):
sels = Gui.Selection.getSelectionEx("", 0)
- if len(sels) == 1 \
- and len(sels[0].SubObjects) == 1 \
- and sels[0].SubObjects[0].ShapeType == "Vertex":
- vert = Part.getShape(sels[0].Object,
- sels[0].SubElementNames[0],
- needSubElement=True,
- retType=0)
+ if (
+ len(sels) == 1
+ and len(sels[0].SubObjects) == 1
+ and sels[0].SubObjects[0].ShapeType == "Vertex"
+ ):
+ vert = Part.getShape(
+ sels[0].Object, sels[0].SubElementNames[0], needSubElement=True, retType=0
+ )
self.wp.set_to_position(vert.Point)
Gui.Selection.clearSelection()
self.finish()
@@ -287,6 +297,7 @@ class Draft_SelectPlane:
color = utils.argb_to_rgba(self.taskd.form.buttonColor.property("color").rgba())
params.set_param("gridColor", color)
-Gui.addCommand('Draft_SelectPlane', Draft_SelectPlane())
+
+Gui.addCommand("Draft_SelectPlane", Draft_SelectPlane())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_setstyle.py b/src/Mod/Draft/draftguitools/gui_setstyle.py
index 5699571350..5d6982966b 100644
--- a/src/Mod/Draft/draftguitools/gui_setstyle.py
+++ b/src/Mod/Draft/draftguitools/gui_setstyle.py
@@ -40,19 +40,21 @@ from FreeCAD import Units as U
from draftutils import params
from draftutils import utils
-def QT_TRANSLATE_NOOP(ctx,txt):
+
+def QT_TRANSLATE_NOOP(ctx, txt):
return txt
+
+
translate = App.Qt.translate
__title__ = "FreeCAD Draft Workbench GUI Tools - Styling tools"
-__author__ = ("Yorik van Havre")
+__author__ = "Yorik van Havre"
__url__ = "https://www.freecad.org"
PRESETPATH = os.path.join(App.getUserAppDataDir(), "Draft", "StylePresets.json")
class Draft_SetStyle:
-
"""The Draft_SetStyle FreeCAD command definition."""
def GetResources(self):
@@ -61,7 +63,9 @@ class Draft_SetStyle:
"Pixmap": "Draft_Apply",
"Accel": "S, S",
"MenuText": QT_TRANSLATE_NOOP("Draft_SetStyle", "Set Style"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_SetStyle", "Sets the default style and can apply the style to objects")
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_SetStyle", "Sets the default style and can apply the style to objects"
+ ),
}
def Activated(self):
@@ -70,50 +74,81 @@ class Draft_SetStyle:
class Draft_SetStyle_TaskPanel:
-
"""The task panel for the Draft_SetStyle command"""
def __init__(self):
self.form = Gui.PySideUic.loadUi(":/ui/TaskPanel_SetStyle.ui")
- self.form.setWindowIcon(QtGui.QIcon.fromTheme("gtk-apply", QtGui.QIcon(":/icons/Draft_Apply.svg")))
+ self.form.setWindowIcon(
+ QtGui.QIcon.fromTheme("gtk-apply", QtGui.QIcon(":/icons/Draft_Apply.svg"))
+ )
- self.form.saveButton.setIcon(QtGui.QIcon.fromTheme("gtk-save", QtGui.QIcon(":/icons/document-save.svg")))
- self.form.applyButton.setIcon(QtGui.QIcon.fromTheme("gtk-apply", QtGui.QIcon(":/icons/Draft_Apply.svg")))
+ self.form.saveButton.setIcon(
+ QtGui.QIcon.fromTheme("gtk-save", QtGui.QIcon(":/icons/document-save.svg"))
+ )
+ self.form.applyButton.setIcon(
+ QtGui.QIcon.fromTheme("gtk-apply", QtGui.QIcon(":/icons/Draft_Apply.svg"))
+ )
self.form.annotButton.setIcon(QtGui.QIcon(":/icons/Draft_Text.svg"))
- self.form.ShapeColor.setProperty("color", self.getColor(params.get_param_view("DefaultShapeColor")))
- self.form.AmbientColor.setProperty("color", self.getColor(params.get_param_view("DefaultAmbientColor")))
- self.form.EmissiveColor.setProperty("color", self.getColor(params.get_param_view("DefaultEmissiveColor")))
- self.form.SpecularColor.setProperty("color", self.getColor(params.get_param_view("DefaultSpecularColor")))
+ self.form.ShapeColor.setProperty(
+ "color", self.getColor(params.get_param_view("DefaultShapeColor"))
+ )
+ self.form.AmbientColor.setProperty(
+ "color", self.getColor(params.get_param_view("DefaultAmbientColor"))
+ )
+ self.form.EmissiveColor.setProperty(
+ "color", self.getColor(params.get_param_view("DefaultEmissiveColor"))
+ )
+ self.form.SpecularColor.setProperty(
+ "color", self.getColor(params.get_param_view("DefaultSpecularColor"))
+ )
self.form.Transparency.setValue(params.get_param_view("DefaultShapeTransparency"))
self.form.Shininess.setValue(params.get_param_view("DefaultShapeShininess"))
- self.form.LineColor.setProperty("color", self.getColor(params.get_param_view("DefaultShapeLineColor")))
+ self.form.LineColor.setProperty(
+ "color", self.getColor(params.get_param_view("DefaultShapeLineColor"))
+ )
self.form.LineWidth.setValue(params.get_param_view("DefaultShapeLineWidth"))
- self.form.PointColor.setProperty("color", self.getColor(params.get_param_view("DefaultShapeVertexColor")))
+ self.form.PointColor.setProperty(
+ "color", self.getColor(params.get_param_view("DefaultShapeVertexColor"))
+ )
self.form.PointSize.setValue(params.get_param_view("DefaultShapePointSize"))
self.form.DrawStyle.setCurrentIndex(params.get_param("DefaultDrawStyle"))
self.form.DisplayMode.setCurrentIndex(params.get_param("DefaultDisplayMode"))
- self.form.TextColor.setProperty("color", self.getColor(params.get_param("DefaultTextColor")))
+ self.form.TextColor.setProperty(
+ "color", self.getColor(params.get_param("DefaultTextColor"))
+ )
self.form.TextFont.setCurrentFont(QtGui.QFont(params.get_param("textfont")))
self.form.TextSize.setText(U.Quantity(params.get_param("textheight"), U.Length).UserString)
self.form.LineSpacing.setValue(params.get_param("LineSpacing"))
self.form.ScaleMultiplier.setValue(params.get_param("DefaultAnnoScaleMultiplier"))
- self.form.AnnoLineColor.setProperty("color", self.getColor(params.get_param("DefaultAnnoLineColor")))
+ self.form.AnnoLineColor.setProperty(
+ "color", self.getColor(params.get_param("DefaultAnnoLineColor"))
+ )
self.form.AnnoLineWidth.setValue(params.get_param("DefaultAnnoLineWidth"))
self.form.ArrowStyleStart.setCurrentIndex(params.get_param("dimsymbolstart"))
- self.form.ArrowSizeStart.setText(U.Quantity(params.get_param("arrowsizestart"), U.Length).UserString)
+ self.form.ArrowSizeStart.setText(
+ U.Quantity(params.get_param("arrowsizestart"), U.Length).UserString
+ )
self.form.ArrowStyleEnd.setCurrentIndex(params.get_param("dimsymbolend"))
- self.form.ArrowSizeEnd.setText(U.Quantity(params.get_param("arrowsizeend"), U.Length).UserString)
+ self.form.ArrowSizeEnd.setText(
+ U.Quantity(params.get_param("arrowsizeend"), U.Length).UserString
+ )
self.form.ShowUnit.setChecked(params.get_param("showUnit"))
self.form.UnitOverride.setText(params.get_param("overrideUnit"))
- self.form.DimOvershoot.setText(U.Quantity(params.get_param("dimovershoot"), U.Length).UserString)
+ self.form.DimOvershoot.setText(
+ U.Quantity(params.get_param("dimovershoot"), U.Length).UserString
+ )
self.form.ExtLines.setText(U.Quantity(params.get_param("extlines"), U.Length).UserString)
- self.form.ExtOvershoot.setText(U.Quantity(params.get_param("extovershoot"), U.Length).UserString)
- self.form.TextSpacing.setText(U.Quantity(params.get_param("dimspacing"), U.Length).UserString)
+ self.form.ExtOvershoot.setText(
+ U.Quantity(params.get_param("extovershoot"), U.Length).UserString
+ )
+ self.form.TextSpacing.setText(
+ U.Quantity(params.get_param("dimspacing"), U.Length).UserString
+ )
self.form.saveButton.clicked.connect(self.onSaveStyle)
self.form.applyButton.clicked.connect(self.onApplyStyle)
@@ -143,38 +178,35 @@ class Draft_SetStyle_TaskPanel:
def getValues(self):
return {
- "ShapeColor": utils.argb_to_rgba(self.form.ShapeColor.property("color").rgba()),
- "AmbientColor": utils.argb_to_rgba(self.form.AmbientColor.property("color").rgba()),
- "EmissiveColor": utils.argb_to_rgba(self.form.EmissiveColor.property("color").rgba()),
- "SpecularColor": utils.argb_to_rgba(self.form.SpecularColor.property("color").rgba()),
- "Transparency": self.form.Transparency.value(),
- "Shininess": self.form.Shininess.value(),
-
- "LineColor": utils.argb_to_rgba(self.form.LineColor.property("color").rgba()),
- "LineWidth": self.form.LineWidth.value(),
- "PointColor": utils.argb_to_rgba(self.form.PointColor.property("color").rgba()),
- "PointSize": self.form.PointSize.value(),
- "DrawStyle": self.form.DrawStyle.currentIndex(),
- "DisplayMode": self.form.DisplayMode.currentIndex(),
-
- "TextColor": utils.argb_to_rgba(self.form.TextColor.property("color").rgba()),
- "TextFont": self.form.TextFont.currentFont().family(),
- "TextSize": U.Quantity(self.form.TextSize.text()).Value,
- "LineSpacing": self.form.LineSpacing.value(),
+ "ShapeColor": utils.argb_to_rgba(self.form.ShapeColor.property("color").rgba()),
+ "AmbientColor": utils.argb_to_rgba(self.form.AmbientColor.property("color").rgba()),
+ "EmissiveColor": utils.argb_to_rgba(self.form.EmissiveColor.property("color").rgba()),
+ "SpecularColor": utils.argb_to_rgba(self.form.SpecularColor.property("color").rgba()),
+ "Transparency": self.form.Transparency.value(),
+ "Shininess": self.form.Shininess.value(),
+ "LineColor": utils.argb_to_rgba(self.form.LineColor.property("color").rgba()),
+ "LineWidth": self.form.LineWidth.value(),
+ "PointColor": utils.argb_to_rgba(self.form.PointColor.property("color").rgba()),
+ "PointSize": self.form.PointSize.value(),
+ "DrawStyle": self.form.DrawStyle.currentIndex(),
+ "DisplayMode": self.form.DisplayMode.currentIndex(),
+ "TextColor": utils.argb_to_rgba(self.form.TextColor.property("color").rgba()),
+ "TextFont": self.form.TextFont.currentFont().family(),
+ "TextSize": U.Quantity(self.form.TextSize.text()).Value,
+ "LineSpacing": self.form.LineSpacing.value(),
"ScaleMultiplier": self.form.ScaleMultiplier.value(),
-
- "AnnoLineColor": utils.argb_to_rgba(self.form.AnnoLineColor.property("color").rgba()),
- "AnnoLineWidth": self.form.AnnoLineWidth.value(),
+ "AnnoLineColor": utils.argb_to_rgba(self.form.AnnoLineColor.property("color").rgba()),
+ "AnnoLineWidth": self.form.AnnoLineWidth.value(),
"ArrowStyleStart": self.form.ArrowStyleStart.currentIndex(),
- "ArrowSizeStart": U.Quantity(self.form.ArrowSizeStart.text()).Value,
- "ArrowStyleEnd": self.form.ArrowStyleEnd.currentIndex(),
- "ArrowSizeEnd": U.Quantity(self.form.ArrowSizeEnd.text()).Value,
- "ShowUnit": self.form.ShowUnit.isChecked(),
- "UnitOverride": self.form.UnitOverride.text(),
- "DimOvershoot": U.Quantity(self.form.DimOvershoot.text()).Value,
- "ExtLines": U.Quantity(self.form.ExtLines.text()).Value,
- "ExtOvershoot": U.Quantity(self.form.ExtOvershoot.text()).Value,
- "TextSpacing": U.Quantity(self.form.TextSpacing.text()).Value
+ "ArrowSizeStart": U.Quantity(self.form.ArrowSizeStart.text()).Value,
+ "ArrowStyleEnd": self.form.ArrowStyleEnd.currentIndex(),
+ "ArrowSizeEnd": U.Quantity(self.form.ArrowSizeEnd.text()).Value,
+ "ShowUnit": self.form.ShowUnit.isChecked(),
+ "UnitOverride": self.form.UnitOverride.text(),
+ "DimOvershoot": U.Quantity(self.form.DimOvershoot.text()).Value,
+ "ExtLines": U.Quantity(self.form.ExtLines.text()).Value,
+ "ExtOvershoot": U.Quantity(self.form.ExtOvershoot.text()).Value,
+ "TextSpacing": U.Quantity(self.form.TextSpacing.text()).Value,
}
def setValues(self, preset):
@@ -196,40 +228,35 @@ class Draft_SetStyle_TaskPanel:
# ---------------------------------------------------------------------
self.form.ShapeColor.setProperty(
- "color",
- self.getColor(preset.get("ShapeColor", getDefView("DefaultShapeColor")))
+ "color", self.getColor(preset.get("ShapeColor", getDefView("DefaultShapeColor")))
)
self.form.AmbientColor.setProperty(
- "color",
- self.getColor(preset.get("AmbientColor", getDefView("DefaultAmbientColor")))
+ "color", self.getColor(preset.get("AmbientColor", getDefView("DefaultAmbientColor")))
)
self.form.EmissiveColor.setProperty(
- "color",
- self.getColor(preset.get("EmissiveColor", getDefView("DefaultEmissiveColor")))
+ "color", self.getColor(preset.get("EmissiveColor", getDefView("DefaultEmissiveColor")))
)
self.form.SpecularColor.setProperty(
- "color",
- self.getColor(preset.get("SpecularColor", getDefView("DefaultSpecularColor")))
+ "color", self.getColor(preset.get("SpecularColor", getDefView("DefaultSpecularColor")))
)
self.form.Transparency.setValue(
preset.get("Transparency", getDefView("DefaultShapeTransparency"))
)
- self.form.Shininess.setValue(
- preset.get("Shininess", getDefView("DefaultShapeShininess"))
- )
+ self.form.Shininess.setValue(preset.get("Shininess", getDefView("DefaultShapeShininess")))
# ---------------------------------------------------------------------
self.form.LineColor.setProperty(
- "color",
- self.getColor(preset.get("LineColor", getDefView("DefaultShapeLineColor")))
- )
- self.form.LineWidth.setValue(
- preset.get("LineWidth", getDefView("DefaultShapeLineWidth"))
+ "color", self.getColor(preset.get("LineColor", getDefView("DefaultShapeLineColor")))
)
+ self.form.LineWidth.setValue(preset.get("LineWidth", getDefView("DefaultShapeLineWidth")))
self.form.PointColor.setProperty(
"color",
- self.getColor(preset.get("PointColor", preset.get("LineColor", getDefView("DefaultShapeVertexColor"))))
+ self.getColor(
+ preset.get(
+ "PointColor", preset.get("LineColor", getDefView("DefaultShapeVertexColor"))
+ )
+ ),
)
self.form.PointSize.setValue(
preset.get("PointSize", preset.get("LineWidth", getDefView("DefaultShapePointSize")))
@@ -244,18 +271,15 @@ class Draft_SetStyle_TaskPanel:
# ---------------------------------------------------------------------
self.form.TextColor.setProperty(
- "color",
- self.getColor(preset.get("TextColor", getDefDraft("DefaultTextColor")))
+ "color", self.getColor(preset.get("TextColor", getDefDraft("DefaultTextColor")))
)
self.form.TextFont.setCurrentFont(
QtGui.QFont(preset.get("TextFont", getDefDraft("textfont")))
)
self.form.TextSize.setText(
- U.Quantity(preset.get("TextSize", getDefDraft("textheight")),U.Length).UserString
- )
- self.form.LineSpacing.setValue(
- preset.get("LineSpacing", getDefDraft("LineSpacing"))
+ U.Quantity(preset.get("TextSize", getDefDraft("textheight")), U.Length).UserString
)
+ self.form.LineSpacing.setValue(preset.get("LineSpacing", getDefDraft("LineSpacing")))
self.form.ScaleMultiplier.setValue(
preset.get("ScaleMultiplier", getDefDraft("DefaultAnnoScaleMultiplier"))
)
@@ -264,16 +288,24 @@ class Draft_SetStyle_TaskPanel:
self.form.AnnoLineColor.setProperty(
"color",
- self.getColor(preset.get("AnnoLineColor", preset.get("LineColor", getDefDraft("DefaultAnnoLineColor"))))
+ self.getColor(
+ preset.get(
+ "AnnoLineColor", preset.get("LineColor", getDefDraft("DefaultAnnoLineColor"))
+ )
+ ),
)
self.form.AnnoLineWidth.setValue(
- preset.get("AnnoLineWidth", preset.get("LineWidth", getDefDraft("DefaultAnnoLineWidth")))
+ preset.get(
+ "AnnoLineWidth", preset.get("LineWidth", getDefDraft("DefaultAnnoLineWidth"))
+ )
)
self.form.ArrowStyleStart.setCurrentIndex(
preset.get("ArrowStyleStart", getDefDraft("dimsymbolstart"))
)
self.form.ArrowSizeStart.setText(
- U.Quantity(preset.get("ArrowSizeStart", getDefDraft("arrowsizestart")), U.Length).UserString
+ U.Quantity(
+ preset.get("ArrowSizeStart", getDefDraft("arrowsizestart")), U.Length
+ ).UserString
)
self.form.ArrowStyleEnd.setCurrentIndex(
preset.get("ArrowStyleEnd", getDefDraft("dimsymbolend"))
@@ -281,12 +313,8 @@ class Draft_SetStyle_TaskPanel:
self.form.ArrowSizeEnd.setText(
U.Quantity(preset.get("ArrowSizeEnd", getDefDraft("arrowsizeend")), U.Length).UserString
)
- self.form.ShowUnit.setChecked(
- preset.get("ShowUnit", getDefDraft("showUnit"))
- )
- self.form.UnitOverride.setText(
- preset.get("UnitOverride", getDefDraft("overrideUnit"))
- )
+ self.form.ShowUnit.setChecked(preset.get("ShowUnit", getDefDraft("showUnit")))
+ self.form.UnitOverride.setText(preset.get("UnitOverride", getDefDraft("overrideUnit")))
self.form.DimOvershoot.setText(
U.Quantity(preset.get("DimOvershoot", getDefDraft("dimovershoot")), U.Length).UserString
)
@@ -306,27 +334,49 @@ class Draft_SetStyle_TaskPanel:
def accept(self):
- params.set_param_view("DefaultShapeColor", utils.argb_to_rgba(self.form.ShapeColor.property("color").rgba()))
- params.set_param_view("DefaultAmbientColor", utils.argb_to_rgba(self.form.AmbientColor.property("color").rgba()))
- params.set_param_view("DefaultEmissiveColor", utils.argb_to_rgba(self.form.EmissiveColor.property("color").rgba()))
- params.set_param_view("DefaultSpecularColor", utils.argb_to_rgba(self.form.SpecularColor.property("color").rgba()))
+ params.set_param_view(
+ "DefaultShapeColor", utils.argb_to_rgba(self.form.ShapeColor.property("color").rgba())
+ )
+ params.set_param_view(
+ "DefaultAmbientColor",
+ utils.argb_to_rgba(self.form.AmbientColor.property("color").rgba()),
+ )
+ params.set_param_view(
+ "DefaultEmissiveColor",
+ utils.argb_to_rgba(self.form.EmissiveColor.property("color").rgba()),
+ )
+ params.set_param_view(
+ "DefaultSpecularColor",
+ utils.argb_to_rgba(self.form.SpecularColor.property("color").rgba()),
+ )
params.set_param_view("DefaultShapeTransparency", self.form.Transparency.value())
params.set_param_view("DefaultShapeShininess", self.form.Shininess.value())
- params.set_param_view("DefaultShapeLineColor", utils.argb_to_rgba(self.form.LineColor.property("color").rgba()))
+ params.set_param_view(
+ "DefaultShapeLineColor",
+ utils.argb_to_rgba(self.form.LineColor.property("color").rgba()),
+ )
params.set_param_view("DefaultShapeLineWidth", self.form.LineWidth.value())
- params.set_param_view("DefaultShapeVertexColor", utils.argb_to_rgba(self.form.PointColor.property("color").rgba()))
+ params.set_param_view(
+ "DefaultShapeVertexColor",
+ utils.argb_to_rgba(self.form.PointColor.property("color").rgba()),
+ )
params.set_param_view("DefaultShapePointSize", self.form.PointSize.value())
params.set_param("DefaultDrawStyle", self.form.DrawStyle.currentIndex())
params.set_param("DefaultDisplayMode", self.form.DisplayMode.currentIndex())
- params.set_param("DefaultTextColor", utils.argb_to_rgba(self.form.TextColor.property("color").rgba()))
+ params.set_param(
+ "DefaultTextColor", utils.argb_to_rgba(self.form.TextColor.property("color").rgba())
+ )
params.set_param("textfont", self.form.TextFont.currentFont().family())
params.set_param("textheight", U.Quantity(self.form.TextSize.text()).Value)
params.set_param("LineSpacing", self.form.LineSpacing.value())
params.set_param("DefaultAnnoScaleMultiplier", self.form.ScaleMultiplier.value())
- params.set_param("DefaultAnnoLineColor", utils.argb_to_rgba(self.form.AnnoLineColor.property("color").rgba()))
+ params.set_param(
+ "DefaultAnnoLineColor",
+ utils.argb_to_rgba(self.form.AnnoLineColor.property("color").rgba()),
+ )
params.set_param("DefaultAnnoLineWidth", self.form.AnnoLineWidth.value())
params.set_param("dimsymbolstart", self.form.ArrowStyleStart.currentIndex())
params.set_param("arrowsizestart", U.Quantity(self.form.ArrowSizeStart.text()).Value)
@@ -350,8 +400,14 @@ class Draft_SetStyle_TaskPanel:
if App.ActiveDocument is not None: # Command can be called without a document.
objs = App.ActiveDocument.Objects
- typs = ["Dimension", "LinearDimension", "AngularDimension",
- "Text", "DraftText", "Label"]
+ typs = [
+ "Dimension",
+ "LinearDimension",
+ "AngularDimension",
+ "Text",
+ "DraftText",
+ "Label",
+ ]
for obj in objs:
if utils.get_type(obj) in typs:
self.apply_style_to_obj(obj)
@@ -366,13 +422,15 @@ class Draft_SetStyle_TaskPanel:
if "FontName" not in properties: # Shapes
if "ShapeAppearance" in properties:
material = App.Material()
- material.DiffuseColor = self.form.ShapeColor.property("color").getRgbF()[:3] # Remove Alpha (which is 1 instead of 0).
+ material.DiffuseColor = self.form.ShapeColor.property("color").getRgbF()[
+ :3
+ ] # Remove Alpha (which is 1 instead of 0).
material.AmbientColor = self.form.AmbientColor.property("color").getRgbF()[:3]
material.EmissiveColor = self.form.EmissiveColor.property("color").getRgbF()[:3]
material.SpecularColor = self.form.SpecularColor.property("color").getRgbF()[:3]
material.Transparency = self.form.Transparency.value() / 100
material.Shininess = self.form.Shininess.value() / 100
- vobj.ShapeAppearance = (material, )
+ vobj.ShapeAppearance = (material,)
if "LineColor" in properties:
vobj.LineColor = self.form.LineColor.property("color").getRgbF()[:3]
if "LineWidth" in properties:
@@ -423,7 +481,7 @@ class Draft_SetStyle_TaskPanel:
if "TextSpacing" in properties:
vobj.TextSpacing = U.Quantity(self.form.TextSpacing.text()).Value
- def onLoadStyle(self,index):
+ def onLoadStyle(self, index):
if index > 0:
pdict = self.load()
@@ -433,19 +491,21 @@ class Draft_SetStyle_TaskPanel:
def onSaveStyle(self):
- reply = QtWidgets.QInputDialog.getText(None,
- translate("Draft", "Save style"),
- translate("Draft", "Name of this new style"))
+ reply = QtWidgets.QInputDialog.getText(
+ None, translate("Draft", "Save style"), translate("Draft", "Name of this new style")
+ )
if reply[1]:
name = reply[0]
pdict = self.load()
if pdict:
if name in pdict:
- reply = QtWidgets.QMessageBox.question(None,
- translate("Draft", "Warning"),
- translate("Draft", "Name exists. Overwrite?"),
- QtWidgets.QMessageBox.Yes | QtWidgets.QMessageBox.No,
- QtWidgets.QMessageBox.No)
+ reply = QtWidgets.QMessageBox.question(
+ None,
+ translate("Draft", "Warning"),
+ translate("Draft", "Name exists. Overwrite?"),
+ QtWidgets.QMessageBox.Yes | QtWidgets.QMessageBox.No,
+ QtWidgets.QMessageBox.No,
+ )
if reply == QtWidgets.QMessageBox.No:
return
preset = self.getValues()
@@ -454,7 +514,6 @@ class Draft_SetStyle_TaskPanel:
self.loadDefaults()
def load(self):
-
"""loads the presets json file, returns a dict"""
pdict = {}
@@ -474,8 +533,7 @@ class Draft_SetStyle_TaskPanel:
return {}
return pdict
- def save(self,d):
-
+ def save(self, d):
"""saves the given dict to the presets json file"""
try:
diff --git a/src/Mod/Draft/draftguitools/gui_shape2dview.py b/src/Mod/Draft/draftguitools/gui_shape2dview.py
index d9269cb9a4..898a9f2bc3 100644
--- a/src/Mod/Draft/draftguitools/gui_shape2dview.py
+++ b/src/Mod/Draft/draftguitools/gui_shape2dview.py
@@ -55,9 +55,14 @@ class Shape2DView(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_2DShapeView',
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Shape2DView", "Shape 2D View"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Shape2DView", "Creates a 2D projection of the selected objects on the XY-plane.\nThe initial projection direction is the opposite of the current active view direction.")}
+ return {
+ "Pixmap": "Draft_2DShapeView",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Shape2DView", "Shape 2D View"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Shape2DView",
+ "Creates a 2D projection of the selected objects on the XY-plane.\nThe initial projection direction is the opposite of the current active view direction.",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -112,11 +117,10 @@ class Shape2DView(gui_base_original.Modifier):
n += 1
if commitlist:
commitlist.append("FreeCAD.ActiveDocument.recompute()")
- self.commit(translate("draft", "Create 2D View"),
- commitlist)
+ self.commit(translate("draft", "Create 2D View"), commitlist)
self.finish()
-Gui.addCommand('Draft_Shape2DView', Shape2DView())
+Gui.addCommand("Draft_Shape2DView", Shape2DView())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_shapestrings.py b/src/Mod/Draft/draftguitools/gui_shapestrings.py
index 2ea8b19c5b..7acd4df13d 100644
--- a/src/Mod/Draft/draftguitools/gui_shapestrings.py
+++ b/src/Mod/Draft/draftguitools/gui_shapestrings.py
@@ -56,9 +56,13 @@ class ShapeString(gui_base.GuiCommandBase):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_ShapeString",
- "MenuText": QT_TRANSLATE_NOOP("Draft_ShapeString", "Shape From Text"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_ShapeString", "Creates a shape from a text string and a specified font")}
+ return {
+ "Pixmap": "Draft_ShapeString",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_ShapeString", "Shape From Text"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_ShapeString", "Creates a shape from a text string and a specified font"
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -84,6 +88,6 @@ class ShapeString(gui_base.GuiCommandBase):
super().finish()
-Gui.addCommand('Draft_ShapeString', ShapeString())
+Gui.addCommand("Draft_ShapeString", ShapeString())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_snapper.py b/src/Mod/Draft/draftguitools/gui_snapper.py
index 061db54d2c..c1ffd4d8ee 100644
--- a/src/Mod/Draft/draftguitools/gui_snapper.py
+++ b/src/Mod/Draft/draftguitools/gui_snapper.py
@@ -61,7 +61,8 @@ __title__ = "FreeCAD Draft Snap tools"
__author__ = "Yorik van Havre"
__url__ = "https://www.freecad.org"
-UNSNAPPABLES = ('Image::ImagePlane',)
+UNSNAPPABLES = ("Image::ImagePlane",)
+
class Snapper:
"""Classes to manage snapping in Draft and Arch.
@@ -148,20 +149,22 @@ class Snapper:
self.init_active_snaps()
self.set_snap_style()
- self.cursors = \
- coll.OrderedDict([('passive', ':/icons/Draft_Snap_Near.svg'),
- ('extension', ':/icons/Draft_Snap_Extension.svg'),
- ('parallel', ':/icons/Draft_Snap_Parallel.svg'),
- ('grid', ':/icons/Draft_Snap_Grid.svg'),
- ('endpoint', ':/icons/Draft_Snap_Endpoint.svg'),
- ('midpoint', ':/icons/Draft_Snap_Midpoint.svg'),
- ('perpendicular', ':/icons/Draft_Snap_Perpendicular.svg'),
- ('angle', ':/icons/Draft_Snap_Angle.svg'),
- ('center', ':/icons/Draft_Snap_Center.svg'),
- ('ortho', ':/icons/Draft_Snap_Ortho.svg'),
- ('intersection', ':/icons/Draft_Snap_Intersection.svg'),
- ('special', ':/icons/Draft_Snap_Special.svg')])
-
+ self.cursors = coll.OrderedDict(
+ [
+ ("passive", ":/icons/Draft_Snap_Near.svg"),
+ ("extension", ":/icons/Draft_Snap_Extension.svg"),
+ ("parallel", ":/icons/Draft_Snap_Parallel.svg"),
+ ("grid", ":/icons/Draft_Snap_Grid.svg"),
+ ("endpoint", ":/icons/Draft_Snap_Endpoint.svg"),
+ ("midpoint", ":/icons/Draft_Snap_Midpoint.svg"),
+ ("perpendicular", ":/icons/Draft_Snap_Perpendicular.svg"),
+ ("angle", ":/icons/Draft_Snap_Angle.svg"),
+ ("center", ":/icons/Draft_Snap_Center.svg"),
+ ("ortho", ":/icons/Draft_Snap_Ortho.svg"),
+ ("intersection", ":/icons/Draft_Snap_Intersection.svg"),
+ ("special", ":/icons/Draft_Snap_Special.svg"),
+ ]
+ )
def _get_wp(self):
# update=False is required, without it WorkingPlane.get_working_plane()
@@ -170,7 +173,6 @@ class Snapper:
# See: https://github.com/FreeCAD/FreeCAD/issues/24013
return WorkingPlane.get_working_plane(update=False)
-
def init_active_snaps(self):
"""
set self.active_snaps according to user prefs
@@ -183,36 +185,42 @@ class Snapper:
self.active_snaps.append(self.snaps[i])
i += 1
-
def set_snap_style(self):
self.snapStyle = params.get_param("snapStyle")
if self.snapStyle:
- self.mk = coll.OrderedDict([("passive", "SQUARE_LINE"),
- ("extension", "SQUARE_LINE"),
- ("parallel", "SQUARE_LINE"),
- ("grid", "SQUARE_FILLED"),
- ("endpoint", "SQUARE_FILLED"),
- ("midpoint", "SQUARE_FILLED"),
- ("perpendicular", "SQUARE_FILLED"),
- ("angle", "SQUARE_FILLED"),
- ("center", "SQUARE_FILLED"),
- ("ortho", "SQUARE_FILLED"),
- ("intersection", "SQUARE_FILLED"),
- ("special", "SQUARE_FILLED")])
+ self.mk = coll.OrderedDict(
+ [
+ ("passive", "SQUARE_LINE"),
+ ("extension", "SQUARE_LINE"),
+ ("parallel", "SQUARE_LINE"),
+ ("grid", "SQUARE_FILLED"),
+ ("endpoint", "SQUARE_FILLED"),
+ ("midpoint", "SQUARE_FILLED"),
+ ("perpendicular", "SQUARE_FILLED"),
+ ("angle", "SQUARE_FILLED"),
+ ("center", "SQUARE_FILLED"),
+ ("ortho", "SQUARE_FILLED"),
+ ("intersection", "SQUARE_FILLED"),
+ ("special", "SQUARE_FILLED"),
+ ]
+ )
else:
- self.mk = coll.OrderedDict([("passive", "CIRCLE_LINE"),
- ("extension", "CIRCLE_LINE"),
- ("parallel", "CIRCLE_LINE"),
- ("grid", "CIRCLE_LINE"),
- ("endpoint", "CIRCLE_FILLED"),
- ("midpoint", "DIAMOND_FILLED"),
- ("perpendicular", "CIRCLE_FILLED"),
- ("angle", "DIAMOND_FILLED"),
- ("center", "CIRCLE_FILLED"),
- ("ortho", "CIRCLE_FILLED"),
- ("intersection", "CIRCLE_FILLED"),
- ("special", "CIRCLE_FILLED")])
-
+ self.mk = coll.OrderedDict(
+ [
+ ("passive", "CIRCLE_LINE"),
+ ("extension", "CIRCLE_LINE"),
+ ("parallel", "CIRCLE_LINE"),
+ ("grid", "CIRCLE_LINE"),
+ ("endpoint", "CIRCLE_FILLED"),
+ ("midpoint", "DIAMOND_FILLED"),
+ ("perpendicular", "CIRCLE_FILLED"),
+ ("angle", "DIAMOND_FILLED"),
+ ("center", "CIRCLE_FILLED"),
+ ("ortho", "CIRCLE_FILLED"),
+ ("intersection", "CIRCLE_FILLED"),
+ ("special", "CIRCLE_FILLED"),
+ ]
+ )
def cstr(self, lastpoint, constrain, point):
"""Return constraints if needed."""
@@ -225,10 +233,7 @@ class Snapper:
self.radiusTracker.update(fpt)
return fpt
-
- def snap(self, screenpos,
- lastpoint=None, active=True,
- constrain=False, noTracker=False):
+ def snap(self, screenpos, lastpoint=None, active=True, constrain=False, noTracker=False):
"""Return a snapped point from the given (x, y) screen position.
snap(screenpos,lastpoint=None,active=True,constrain=False,
@@ -270,8 +275,7 @@ class Snapper:
self.setTrackers()
# Get current snap radius
- self.radius = self.getScreenDist(params.get_param("snapRange"),
- screenpos)
+ self.radius = self.getScreenDist(params.get_param("snapRange"), screenpos)
if self.radiusTracker:
self.radiusTracker.update(self.radius)
self.radiusTracker.off()
@@ -280,7 +284,7 @@ class Snapper:
if params.get_param("alwaysSnap"):
active = True
- self.setCursor('passive')
+ self.setCursor("passive")
if self.tracker:
self.tracker.off()
if self.extLine2:
@@ -305,8 +309,7 @@ class Snapper:
eline = None
if active:
point, eline = self.snapToPolar(point, lastpoint)
- point, eline = self.snapToExtensions(point, lastpoint,
- constrain, eline)
+ point, eline = self.snapToExtensions(point, lastpoint, constrain, eline)
# Check if we have an object under the cursor and try to
# snap to it
@@ -344,12 +347,10 @@ class Snapper:
self.running = False
return fp
-
def cycleSnapObject(self):
"""Increase the index of the snap object by one."""
self.snapObjectIndex = self.snapObjectIndex + 1
-
def snapToObject(self, lastpoint, active, constrain, eline, point):
"""Snap to an object."""
@@ -365,9 +366,11 @@ class Snapper:
parent = obj
subname = self.snapInfo["Component"]
- if not obj \
- or Draft.getType(obj) in UNSNAPPABLES \
- or not getattr(obj.ViewObject, "Selectable", True):
+ if (
+ not obj
+ or Draft.getType(obj) in UNSNAPPABLES
+ or not getattr(obj.ViewObject, "Selectable", True)
+ ):
return None
snaps = []
@@ -382,11 +385,9 @@ class Snapper:
# Special snapping for polygons: add the center
snaps.extend(self.snapToPolygon(obj))
- elif (Draft.getType(obj) == "BuildingPart"
- and self.isEnabled("Center")):
+ elif Draft.getType(obj) == "BuildingPart" and self.isEnabled("Center"):
# snap to the base placement of empty BuildingParts
- snaps.append([obj.Placement.Base, 'center',
- self.toWP(obj.Placement.Base)])
+ snaps.append([obj.Placement.Base, "center", self.toWP(obj.Placement.Base)])
if (not self.maxEdges) or (len(shape.Edges) <= self.maxEdges):
if "Edge" in comp:
@@ -442,12 +443,12 @@ class Snapper:
elif Draft.getType(obj).startswith("Points::"):
snaps.extend(self.snapToEndpoints(obj.Points, point))
- elif (Draft.getType(obj) in ("WorkingPlaneProxy", "BuildingPart")
- and self.isEnabled("Center")):
+ elif Draft.getType(obj) in ("WorkingPlaneProxy", "BuildingPart") and self.isEnabled(
+ "Center"
+ ):
# snap to the center of WPProxies or to the base
# placement of no empty BuildingParts
- snaps.append([obj.Placement.Base, 'center',
- self.toWP(obj.Placement.Base)])
+ snaps.append([obj.Placement.Base, "center", self.toWP(obj.Placement.Base)])
elif Draft.getType(obj) == "SectionPlane":
# snap to corners of section planes
@@ -521,14 +522,12 @@ class Snapper:
self.spoint = fp
return self.spoint
-
def toWP(self, point):
"""Project the given point on the working plane, if needed."""
if self.isEnabled("WorkingPlane"):
return self._get_wp().project_point(point)
return point
-
def getApparentPoint(self, x, y):
"""Return a 3D point, projected on the current working plane."""
view = Draft.get3DView()
@@ -543,18 +542,18 @@ class Snapper:
return self._get_wp().project_point(pt, dv)
return pt
-
def snapToDim(self, obj):
snaps = []
- if self.isEnabled("Endpoint") \
- and obj.ViewObject \
- and hasattr(obj.ViewObject.Proxy, "p2") \
- and hasattr(obj.ViewObject.Proxy, "p3"):
- snaps.append([obj.ViewObject.Proxy.p2, 'endpoint', self.toWP(obj.ViewObject.Proxy.p2)])
- snaps.append([obj.ViewObject.Proxy.p3, 'endpoint', self.toWP(obj.ViewObject.Proxy.p3)])
+ if (
+ self.isEnabled("Endpoint")
+ and obj.ViewObject
+ and hasattr(obj.ViewObject.Proxy, "p2")
+ and hasattr(obj.ViewObject.Proxy, "p3")
+ ):
+ snaps.append([obj.ViewObject.Proxy.p2, "endpoint", self.toWP(obj.ViewObject.Proxy.p2)])
+ snaps.append([obj.ViewObject.Proxy.p3, "endpoint", self.toWP(obj.ViewObject.Proxy.p3)])
return snaps
-
def snapToExtensions(self, point, last, constrain, eline):
"""Return a point snapped to extension or parallel line.
@@ -603,8 +602,7 @@ class Snapper:
return tsnap[2], eline
for o in self.lastObj:
- if (self.isEnabled('Extension')
- or self.isEnabled('Parallel')):
+ if self.isEnabled("Extension") or self.isEnabled("Parallel"):
ob = App.ActiveDocument.getObject(o)
if not ob:
continue
@@ -612,7 +610,7 @@ class Snapper:
continue
edges = ob.Shape.Edges
if Draft.getType(ob) == "Wall":
- for so in [ob]+ob.Additions:
+ for so in [ob] + ob.Additions:
if Draft.getType(so) == "Wall":
if so.Base:
edges.extend(so.Base.Shape.Edges)
@@ -621,69 +619,81 @@ class Snapper:
for e in edges:
if DraftGeomUtils.geomType(e) != "Line":
continue
- np = self.getPerpendicular(e,point)
+ np = self.getPerpendicular(e, point)
if (np.sub(point)).Length < self.radius:
- if self.isEnabled('Extension'):
- if DraftGeomUtils.isPtOnEdge(np,e):
+ if self.isEnabled("Extension"):
+ if DraftGeomUtils.isPtOnEdge(np, e):
continue
if np != e.Vertexes[0].Point:
p0 = e.Vertexes[0].Point
if self.tracker and not self.selectMode:
self.tracker.setCoords(np)
- self.tracker.setMarker(self.mk['extension'])
+ self.tracker.setMarker(self.mk["extension"])
self.tracker.on()
if self.extLine:
self.extLine.p1(p0)
self.extLine.p2(np)
self.extLine.setColor()
self.extLine.on()
- self.setCursor('extension')
- ne = Part.LineSegment(p0,np).toShape()
+ self.setCursor("extension")
+ ne = Part.LineSegment(p0, np).toShape()
# storing extension line for intersection calculations later
if len(self.lastExtensions) == 0:
self.lastExtensions.append(ne)
elif len(self.lastExtensions) == 1:
- if not DraftGeomUtils.areColinear(ne,self.lastExtensions[0]):
+ if not DraftGeomUtils.areColinear(
+ ne, self.lastExtensions[0]
+ ):
self.lastExtensions.append(self.lastExtensions[0])
self.lastExtensions[0] = ne
else:
- if (not DraftGeomUtils.areColinear(ne,self.lastExtensions[0])) and \
- (not DraftGeomUtils.areColinear(ne,self.lastExtensions[1])):
+ if (
+ not DraftGeomUtils.areColinear(
+ ne, self.lastExtensions[0]
+ )
+ ) and (
+ not DraftGeomUtils.areColinear(
+ ne, self.lastExtensions[1]
+ )
+ ):
self.lastExtensions[1] = self.lastExtensions[0]
self.lastExtensions[0] = ne
- return np,ne
- elif self.isEnabled('Parallel'):
+ return np, ne
+ elif self.isEnabled("Parallel"):
if last:
ve = DraftGeomUtils.vec(e)
if not DraftVecUtils.isNull(ve):
- de = Part.LineSegment(last,last.add(ve)).toShape()
- np = self.getPerpendicular(de,point)
+ de = Part.LineSegment(last, last.add(ve)).toShape()
+ np = self.getPerpendicular(de, point)
if (np.sub(point)).Length < self.radius:
if self.tracker and not self.selectMode:
self.tracker.setCoords(np)
- self.tracker.setMarker(self.mk['parallel'])
+ self.tracker.setMarker(self.mk["parallel"])
self.tracker.on()
- self.setCursor('parallel')
- return np,de
- return point,eline
-
+ self.setCursor("parallel")
+ return np, de
+ return point, eline
def snapToCrossExtensions(self, point):
"""Snap to the intersection of the last 2 extension lines."""
- if self.isEnabled('Extension'):
+ if self.isEnabled("Extension"):
if len(self.lastExtensions) == 2:
- np = DraftGeomUtils.findIntersection(self.lastExtensions[0], self.lastExtensions[1], True, True)
+ np = DraftGeomUtils.findIntersection(
+ self.lastExtensions[0], self.lastExtensions[1], True, True
+ )
if np:
for p in np:
dv = point.sub(p)
if (self.radius == 0) or (dv.Length <= self.radius):
if self.tracker and not self.selectMode:
self.tracker.setCoords(p)
- self.tracker.setMarker(self.mk['intersection'])
+ self.tracker.setMarker(self.mk["intersection"])
self.tracker.on()
- self.setCursor('intersection')
+ self.setCursor("intersection")
if self.extLine and self.extLine2:
- if DraftVecUtils.equals(self.extLine.p1(), self.lastExtensions[0].Vertexes[0].Point):
+ if DraftVecUtils.equals(
+ self.extLine.p1(), self.lastExtensions[0].Vertexes[0].Point
+ ):
p0 = self.lastExtensions[1].Vertexes[0].Point
else:
p0 = self.lastExtensions[0].Vertexes[0].Point
@@ -695,10 +705,9 @@ class Snapper:
return p
return None
-
- def snapToPolar(self,point,last):
+ def snapToPolar(self, point, last):
"""Snap to polar lines from the given point."""
- if self.isEnabled('Ortho') and (not self.mask):
+ if self.isEnabled("Ortho") and (not self.mask):
if last:
vecs = []
wp = self._get_wp()
@@ -719,17 +728,17 @@ class Snapper:
except Part.OCCError:
return point, None
np = self.getPerpendicular(de, point)
- if ((self.radius == 0) and (point.sub(last).getAngle(v) < 0.087)) \
- or ((np.sub(point)).Length < self.radius):
+ if ((self.radius == 0) and (point.sub(last).getAngle(v) < 0.087)) or (
+ (np.sub(point)).Length < self.radius
+ ):
if self.tracker and not self.selectMode:
self.tracker.setCoords(np)
- self.tracker.setMarker(self.mk['parallel'])
+ self.tracker.setMarker(self.mk["parallel"])
self.tracker.on()
- self.setCursor('ortho')
- return np,de
+ self.setCursor("ortho")
+ return np, de
return point, None
-
def snapToGrid(self, point):
"""Return a grid snap point if available."""
if self.grid:
@@ -741,13 +750,12 @@ class Snapper:
if (self.radius == 0) or (dv.Length <= self.radius):
if self.tracker and not self.selectMode:
self.tracker.setCoords(np)
- self.tracker.setMarker(self.mk['grid'])
+ self.tracker.setMarker(self.mk["grid"])
self.tracker.on()
- self.setCursor('grid')
+ self.setCursor("grid")
return np
return point
-
def snapToEndpoints(self, shape, point=None):
"""Return a list of endpoints snap locations."""
if self.isEnabled("Endpoint"):
@@ -775,7 +783,6 @@ class Snapper:
return snaps
return []
-
def snapToMidpoint(self, shape):
"""Return a list of midpoints snap locations."""
snaps = []
@@ -783,10 +790,9 @@ class Snapper:
if isinstance(shape, Part.Edge):
mp = DraftGeomUtils.findMidpoint(shape)
if mp:
- snaps.append([mp, 'midpoint', self.toWP(mp)])
+ snaps.append([mp, "midpoint", self.toWP(mp)])
return snaps
-
def snapToNear(self, shape, point):
"""Return a list with a near snap location for an edge."""
if self.isEnabled("Near") and point:
@@ -798,7 +804,6 @@ class Snapper:
else:
return []
-
def snapToNearFace(self, shape, point):
"""Return a list with a near snap location for a face."""
if self.isEnabled("Near") and point:
@@ -810,7 +815,6 @@ class Snapper:
else:
return []
-
def snapToNearUnprojected(self, point):
"""Return a list with a near snap location that is not projected on the object."""
if self.isEnabled("Near") and point:
@@ -818,7 +822,6 @@ class Snapper:
else:
return []
-
def snapToPerpendicular(self, shape, last):
"""Return a list of perpendicular snap locations for an edge."""
if self.isEnabled("Perpendicular") and last:
@@ -835,7 +838,6 @@ class Snapper:
else:
return []
-
def snapToPerpendicularFace(self, shape, last):
"""Return a list of perpendicular snap locations for a face."""
if self.isEnabled("Perpendicular") and last:
@@ -852,7 +854,6 @@ class Snapper:
else:
return []
-
def snapToOrtho(self, shape, last, constrain):
"""Return a list of ortho snap locations."""
snaps = []
@@ -862,15 +863,16 @@ class Snapper:
if last:
if DraftGeomUtils.geomType(shape) == "Line":
if self.constraintAxis:
- tmpEdge = Part.LineSegment(last, last.add(self.constraintAxis)).toShape()
+ tmpEdge = Part.LineSegment(
+ last, last.add(self.constraintAxis)
+ ).toShape()
# get the intersection points
pt = DraftGeomUtils.findIntersection(tmpEdge, shape, True, True)
if pt:
for p in pt:
- snaps.append([p, 'ortho', self.toWP(p)])
+ snaps.append([p, "ortho", self.toWP(p)])
return snaps
-
def snapToExtOrtho(self, last, constrain, eline):
"""Return an ortho X extension snap location."""
if self.isEnabled("Extension") and self.isEnabled("Ortho"):
@@ -880,19 +882,18 @@ class Snapper:
# get the intersection points
pt = DraftGeomUtils.findIntersection(tmpEdge1, tmpEdge2, True, True)
if pt:
- return [pt[0], 'ortho', pt[0]]
+ return [pt[0], "ortho", pt[0]]
if eline:
try:
tmpEdge2 = Part.LineSegment(self.extLine.p1(), self.extLine.p2()).toShape()
# get the intersection points
pt = DraftGeomUtils.findIntersection(eline, tmpEdge2, True, True)
if pt:
- return [pt[0], 'ortho', pt[0]]
+ return [pt[0], "ortho", pt[0]]
except Exception:
return None
return None
-
def snapToHold(self, point):
"""Return a snap location that is orthogonal to hold points.
@@ -910,7 +911,7 @@ class Snapper:
for p1, p2 in itertools.combinations(l, 2):
p3 = p1.add((p2.sub(p1)).multiply(0.5))
if (p3.sub(point)).Length < self.radius:
- return [p1, 'midpoint', p3]
+ return [p1, "midpoint", p3]
# then try int points
ipoints = []
l = list(self.holdPoints)
@@ -925,22 +926,21 @@ class Snapper:
ipoints.append([p1, i2[0]])
for p in ipoints:
if (p[1].sub(point)).Length < self.radius:
- return [p[0], 'ortho', p[1]]
+ return [p[0], "ortho", p[1]]
# then try to stick to a line
for p in self.holdPoints:
d = DraftGeomUtils.findDistance(point, [p, p.add(u)])
if d:
if d.Length < self.radius:
fp = point.add(d)
- return [p, 'extension', fp]
+ return [p, "extension", fp]
d = DraftGeomUtils.findDistance(point, [p, p.add(v)])
if d:
if d.Length < self.radius:
fp = point.add(d)
- return [p, 'extension', fp]
+ return [p, "extension", fp]
return None
-
def snapToExtPerpendicular(self, last):
"""Return a perpendicular X extension snap location."""
if self.isEnabled("Extension") and self.isEnabled("Perpendicular"):
@@ -948,10 +948,9 @@ class Snapper:
if self.extLine.p1() != self.extLine.p2():
tmpEdge = Part.LineSegment(self.extLine.p1(), self.extLine.p2()).toShape()
np = self.getPerpendicular(tmpEdge, last)
- return [np, 'perpendicular', np]
+ return [np, "perpendicular", np]
return None
-
def snapToElines(self, e1, e2):
"""Return a snap at the infinite intersection of the given edges."""
snaps = []
@@ -961,32 +960,26 @@ class Snapper:
pts = DraftGeomUtils.findIntersection(e1, e2, True, True)
if pts:
for p in pts:
- snaps.append([p, 'intersection', self.toWP(p)])
+ snaps.append([p, "intersection", self.toWP(p)])
return snaps
-
def snapToAngles(self, shape):
"""Return a list of angle snap locations."""
snaps = []
if self.isEnabled("Angle"):
place = App.Placement()
place.Base = shape.Curve.Center
- place.Rotation = App.Rotation(App.Vector(1, 0, 0),
- App.Vector(0, 1, 0),
- shape.Curve.Axis,
- 'ZXY')
+ place.Rotation = App.Rotation(
+ App.Vector(1, 0, 0), App.Vector(0, 1, 0), shape.Curve.Axis, "ZXY"
+ )
rad = shape.Curve.Radius
- for deg in (0, 30, 45, 60,
- 90, 120, 135, 150,
- 180, 210, 225, 240,
- 270, 300, 315, 330):
+ for deg in (0, 30, 45, 60, 90, 120, 135, 150, 180, 210, 225, 240, 270, 300, 315, 330):
ang = math.radians(deg)
cur = App.Vector(math.sin(ang) * rad, math.cos(ang) * rad, 0)
cur = place.multVec(cur)
- snaps.append([cur, 'angle', self.toWP(cur)])
+ snaps.append([cur, "angle", self.toWP(cur)])
return snaps
-
def snapToCenter(self, shape):
"""Return a list of center snap locations."""
snaps = []
@@ -996,34 +989,45 @@ class Snapper:
if hasattr(shape.Curve, "Radius"):
place = App.Placement()
place.Base = cen
- place.Rotation = App.Rotation(App.Vector(1, 0, 0),
- App.Vector(0, 1, 0),
- shape.Curve.Axis,
- 'ZXY')
+ place.Rotation = App.Rotation(
+ App.Vector(1, 0, 0), App.Vector(0, 1, 0), shape.Curve.Axis, "ZXY"
+ )
rad = shape.Curve.Radius
- for deg in (15, 37.5, 52.5, 75,
- 105, 127.5, 142.5, 165,
- 195, 217.5, 232.5, 255,
- 285, 307.5, 322.5, 345):
+ for deg in (
+ 15,
+ 37.5,
+ 52.5,
+ 75,
+ 105,
+ 127.5,
+ 142.5,
+ 165,
+ 195,
+ 217.5,
+ 232.5,
+ 255,
+ 285,
+ 307.5,
+ 322.5,
+ 345,
+ ):
ang = math.radians(deg)
cur = App.Vector(math.sin(ang) * rad, math.cos(ang) * rad, 0)
cur = place.multVec(cur)
- snaps.append([cur, 'center', cen_wp])
+ snaps.append([cur, "center", cen_wp])
else:
- snaps.append([cen, 'center', cen_wp])
+ snaps.append([cen, "center", cen_wp])
return snaps
-
def snapToCenterFace(self, shape):
"""Return a face center snap location."""
snaps = []
if self.isEnabled("Center"):
pos = shape.CenterOfMass
c = self.toWP(pos)
- snaps.append([pos, 'center', c])
+ snaps.append([pos, "center", c])
return snaps
-
def snapToIntersection(self, shape):
"""Return a list of intersection snap locations."""
snaps = []
@@ -1043,17 +1047,21 @@ class Snapper:
if (not self.maxEdges) or (len(obj.Shape.Edges) <= self.maxEdges):
for edge in obj.Shape.Edges:
try:
- if self.isEnabled("WorkingPlane") \
- and hasattr(edge, "Curve") \
- and isinstance(edge.Curve,(Part.Line,Part.LineSegment)) \
- and hasattr(shape, "Curve") \
- and isinstance(shape.Curve,(Part.Line,Part.LineSegment)):
+ if (
+ self.isEnabled("WorkingPlane")
+ and hasattr(edge, "Curve")
+ and isinstance(edge.Curve, (Part.Line, Part.LineSegment))
+ and hasattr(shape, "Curve")
+ and isinstance(shape.Curve, (Part.Line, Part.LineSegment))
+ ):
# get apparent intersection (lines projected on WP)
p1 = self.toWP(edge.Vertexes[0].Point)
p2 = self.toWP(edge.Vertexes[-1].Point)
p3 = self.toWP(shape.Vertexes[0].Point)
p4 = self.toWP(shape.Vertexes[-1].Point)
- pts = DraftGeomUtils.findIntersection(p1, p2, p3, p4, True, True)
+ pts = DraftGeomUtils.findIntersection(
+ p1, p2, p3, p4, True, True
+ )
else:
pts = DraftGeomUtils.findIntersection(edge, shape)
for pt in pts:
@@ -1064,7 +1072,6 @@ class Snapper:
# when trying to read their types
return snaps
-
def snapToPolygon(self, obj):
"""Return a list of polygon center snap locations."""
snaps = []
@@ -1075,32 +1082,31 @@ class Snapper:
p2 = edge.Vertexes[-1].Point
v1 = p1.add((p2 - p1).scale(0.25, 0.25, 0.25))
v2 = p1.add((p2 - p1).scale(0.75, 0.75, 0.75))
- snaps.append([v1, 'center', self.toWP(c)])
- snaps.append([v2, 'center', self.toWP(c)])
+ snaps.append([v1, "center", self.toWP(c)])
+ snaps.append([v2, "center", self.toWP(c)])
return snaps
-
def snapToSpecials(self, obj, lastpoint=None, eline=None):
"""Return special snap locations, if any."""
snaps = []
if self.isEnabled("Special"):
- if (Draft.getType(obj) == "Wall"):
+ if Draft.getType(obj) == "Wall":
# special snapping for wall: snap to its base shape if it is linear
if obj.Base:
if not obj.Base.Shape.Solids:
for v in obj.Base.Shape.Vertexes:
- snaps.append([v.Point, 'special', self.toWP(v.Point)])
+ snaps.append([v.Point, "special", self.toWP(v.Point)])
- elif (Draft.getType(obj) == "Structure"):
+ elif Draft.getType(obj) == "Structure":
# special snapping for struct: only to its base point
if obj.Base:
if not obj.Base.Shape.Solids:
for v in obj.Base.Shape.Vertexes:
- snaps.append([v.Point, 'special', self.toWP(v.Point)])
+ snaps.append([v.Point, "special", self.toWP(v.Point)])
else:
b = obj.Placement.Base
- snaps.append([b, 'special', self.toWP(b)])
+ snaps.append([b, "special", self.toWP(b)])
if obj.ViewObject.ShowNodes:
for edge in obj.Proxy.getNodeEdges(obj):
snaps.extend(self.snapToEndpoints(edge))
@@ -1112,11 +1118,10 @@ class Snapper:
elif hasattr(obj, "SnapPoints"):
for p in obj.SnapPoints:
p2 = obj.Placement.multVec(p)
- snaps.append([p2, 'special', p2])
+ snaps.append([p2, "special", p2])
return snaps
-
def getScreenDist(self, dist, cursor):
"""Return a distance in 3D space from a screen pixels distance."""
view = Draft.get3DView()
@@ -1124,7 +1129,6 @@ class Snapper:
p2 = view.getPoint((cursor[0] + dist, cursor[1]))
return (p2.sub(p1)).Length
-
def getPerpendicular(self, edge, pt):
"""Return a point on an edge, perpendicular to the given point."""
dv = pt.sub(edge.Vertexes[0].Point)
@@ -1132,7 +1136,6 @@ class Snapper:
np = (edge.Vertexes[0].Point).add(nv)
return np
-
def setArchDims(self, p1, p2):
"""Show arc dimensions between 2 points."""
if self.isEnabled("Dimensions"):
@@ -1205,8 +1208,7 @@ class Snapper:
else:
self.cursorMode = mode
self.cursorQt = self.get_cursor_with_tail(
- ":/icons/Draft_Cursor.svg",
- None if mode == "passive" else self.cursors[mode]
+ ":/icons/Draft_Cursor.svg", None if mode == "passive" else self.cursors[mode]
)
for view in views:
view.setCursor(self.cursorQt)
@@ -1216,7 +1218,6 @@ class Snapper:
if self.grid:
self.grid.lowerTracker()
-
def off(self):
"""Finish snapping."""
if self.tracker:
@@ -1255,7 +1256,6 @@ class Snapper:
if toolbar:
toolbar.hide()
-
def setSelectMode(self, mode):
"""Set the snapper into select mode (hides snapping temporarily)."""
self.selectMode = mode
@@ -1265,7 +1265,6 @@ class Snapper:
if self.trackLine:
self.trackLine.off()
-
def setAngle(self, delta=None):
"""Keep the current angle."""
if delta:
@@ -1276,7 +1275,6 @@ class Snapper:
if self.trackLine.Visible:
self.mask = self.trackLine.p2().sub(self.trackLine.p1())
-
def constrain(self, point, basepoint=None, axis=None):
"""Return a constrained point.
@@ -1303,6 +1301,7 @@ class Snapper:
if Gui.draftToolBar.globalMode:
import WorkingPlane
+
wp = WorkingPlane.PlaneBase() # matches the global coordinate system
else:
wp = self._get_wp()
@@ -1350,7 +1349,6 @@ class Snapper:
return npoint
-
def unconstrain(self):
"""Unset the basepoint and the constrain line."""
self.basepoint = None
@@ -1358,9 +1356,9 @@ class Snapper:
if self.constrainLine:
self.constrainLine.off()
-
- def getPoint(self, last=None, callback=None, movecallback=None,
- extradlg=None, title=None, mode="point"):
+ def getPoint(
+ self, last=None, callback=None, movecallback=None, extradlg=None, title=None, mode="point"
+ ):
"""Get a 3D point from the screen.
getPoint([last],[callback],[movecallback],[extradlg],[title]):
@@ -1399,9 +1397,13 @@ class Snapper:
# remove any previous leftover callbacks
try:
if self.callbackClick:
- self.view.removeEventCallbackPivy(coin.SoMouseButtonEvent.getClassTypeId(), self.callbackClick)
+ self.view.removeEventCallbackPivy(
+ coin.SoMouseButtonEvent.getClassTypeId(), self.callbackClick
+ )
if self.callbackMove:
- self.view.removeEventCallbackPivy(coin.SoLocation2Event.getClassTypeId(), self.callbackMove)
+ self.view.removeEventCallbackPivy(
+ coin.SoLocation2Event.getClassTypeId(), self.callbackMove
+ )
if self.callbackClick or self.callbackMove:
# Next line fixes https://github.com/FreeCAD/FreeCAD/issues/10469:
gui_utils.end_all_events()
@@ -1418,11 +1420,8 @@ class Snapper:
mousepos = event.getPosition()
ctrl = event.wasCtrlDown()
shift = event.wasShiftDown()
- self.pt = Gui.Snapper.snap(mousepos, lastpoint=last,
- active=ctrl, constrain=shift)
- self.ui.displayPoint(self.pt, last,
- plane=self._get_wp(),
- mask=Gui.Snapper.affinity)
+ self.pt = Gui.Snapper.snap(mousepos, lastpoint=last, active=ctrl, constrain=shift)
+ self.ui.displayPoint(self.pt, last, plane=self._get_wp(), mask=Gui.Snapper.affinity)
if movecallback:
movecallback(self.pt, self.snapInfo)
@@ -1450,9 +1449,13 @@ class Snapper:
def accept():
try:
if self.callbackClick:
- self.view.removeEventCallbackPivy(coin.SoMouseButtonEvent.getClassTypeId(), self.callbackClick)
+ self.view.removeEventCallbackPivy(
+ coin.SoMouseButtonEvent.getClassTypeId(), self.callbackClick
+ )
if self.callbackMove:
- self.view.removeEventCallbackPivy(coin.SoLocation2Event.getClassTypeId(), self.callbackMove)
+ self.view.removeEventCallbackPivy(
+ coin.SoLocation2Event.getClassTypeId(), self.callbackMove
+ )
if self.callbackClick or self.callbackMove:
# Next line fixes https://github.com/FreeCAD/FreeCAD/issues/10469:
gui_utils.end_all_events()
@@ -1476,9 +1479,13 @@ class Snapper:
def cancel():
try:
if self.callbackClick:
- self.view.removeEventCallbackPivy(coin.SoMouseButtonEvent.getClassTypeId(), self.callbackClick)
+ self.view.removeEventCallbackPivy(
+ coin.SoMouseButtonEvent.getClassTypeId(), self.callbackClick
+ )
if self.callbackMove:
- self.view.removeEventCallbackPivy(coin.SoLocation2Event.getClassTypeId(), self.callbackMove)
+ self.view.removeEventCallbackPivy(
+ coin.SoLocation2Event.getClassTypeId(), self.callbackMove
+ )
if self.callbackClick or self.callbackMove:
# Next line fixes https://github.com/FreeCAD/FreeCAD/issues/10469:
gui_utils.end_all_events()
@@ -1504,13 +1511,17 @@ class Snapper:
interface = self.ui.pointUi
if callback:
if title:
- interface(title=title, cancel=cancel, getcoords=getcoords,
- extra=extradlg, rel=bool(last))
+ interface(
+ title=title, cancel=cancel, getcoords=getcoords, extra=extradlg, rel=bool(last)
+ )
else:
- interface(cancel=cancel,getcoords=getcoords,extra=extradlg,rel=bool(last))
- self.callbackClick = self.view.addEventCallbackPivy(coin.SoMouseButtonEvent.getClassTypeId(),click)
- self.callbackMove = self.view.addEventCallbackPivy(coin.SoLocation2Event.getClassTypeId(),move)
-
+ interface(cancel=cancel, getcoords=getcoords, extra=extradlg, rel=bool(last))
+ self.callbackClick = self.view.addEventCallbackPivy(
+ coin.SoMouseButtonEvent.getClassTypeId(), click
+ )
+ self.callbackMove = self.view.addEventCallbackPivy(
+ coin.SoLocation2Event.getClassTypeId(), move
+ )
def get_snap_toolbar(self):
"""Get the snap toolbar."""
@@ -1520,21 +1531,17 @@ class Snapper:
if self.toolbar:
return self.toolbar
-
def toggleGrid(self):
"""Toggle FreeCAD Draft Grid."""
Gui.runCommand("Draft_ToggleGrid")
-
def showradius(self):
"""Show the snap radius indicator."""
- self.radius = self.getScreenDist(params.get_param("snapRange"),
- (400, 300))
+ self.radius = self.getScreenDist(params.get_param("snapRange"), (400, 300))
if self.radiusTracker:
self.radiusTracker.update(self.radius)
self.radiusTracker.on()
-
def isEnabled(self, snap):
"""Returns true if the given snap is on"""
if "Lock" in self.active_snaps and snap in self.active_snaps:
@@ -1542,10 +1549,9 @@ class Snapper:
else:
return False
-
- def toggle_snap(self, snap, set_to = None):
+ def toggle_snap(self, snap, set_to=None):
"""Sets the given snap on/off according to the given parameter"""
- if set_to: # set mode
+ if set_to: # set mode
if set_to is True:
if not snap in self.active_snaps:
self.active_snaps.append(snap)
@@ -1554,7 +1560,7 @@ class Snapper:
if snap in self.active_snaps:
self.active_snaps.remove(snap)
status = False
- else: # toggle mode, default
+ else: # toggle mode, default
if not snap in self.active_snaps:
self.active_snaps.append(snap)
status = True
@@ -1564,7 +1570,6 @@ class Snapper:
self.save_snap_state()
return status
-
def save_snap_state(self):
"""
Save snap state to user preferences to be restored in next session.
@@ -1577,7 +1582,6 @@ class Snapper:
snap_modes += "0"
params.set_param("snapModes", snap_modes)
-
def show_hide_grids(self, show=True):
"""Show the grid in all 3D views where it was previously visible, or
hide the grid in all 3D view. Used when switching to different workbenches.
@@ -1588,7 +1592,9 @@ class Snapper:
if (not show) and (not params.get_param("GridHideInOtherWorkbenches")):
return
mw = Gui.getMainWindow()
- views = mw.getWindowsOfType(App.Base.TypeId.fromName("Gui::View3DInventor")) # All 3D views.
+ views = mw.getWindowsOfType(
+ App.Base.TypeId.fromName("Gui::View3DInventor")
+ ) # All 3D views.
for view in views:
if view in self.trackers[0]:
i = self.trackers[0].index(view)
@@ -1598,22 +1604,18 @@ class Snapper:
else:
grid.off()
-
def show(self):
"""Show the grid in all 3D views where it was previously visible."""
self.show_hide_grids(show=True)
-
def hide(self):
"""Hide the grid in all 3D views."""
self.show_hide_grids(show=False)
-
def setGrid(self):
"""Set the grid, if visible."""
self.setTrackers()
-
def setTrackers(self, update_grid=True):
"""Set the trackers."""
v = Draft.get3DView()
@@ -1663,13 +1665,13 @@ class Snapper:
if not update_grid:
return
- if self.grid.show_always \
- or (self.grid.show_during_command \
- and hasattr(App, "activeDraftCommand") \
- and App.activeDraftCommand):
+ if self.grid.show_always or (
+ self.grid.show_during_command
+ and hasattr(App, "activeDraftCommand")
+ and App.activeDraftCommand
+ ):
self.grid.set()
-
def addHoldPoint(self):
"""Add hold snap point to list of hold points."""
if self.spoint and self.spoint not in self.holdPoints:
diff --git a/src/Mod/Draft/draftguitools/gui_snaps.py b/src/Mod/Draft/draftguitools/gui_snaps.py
index 95999ac237..18c0c39bb6 100644
--- a/src/Mod/Draft/draftguitools/gui_snaps.py
+++ b/src/Mod/Draft/draftguitools/gui_snaps.py
@@ -40,7 +40,7 @@ from draftutils.messages import _log
from draftutils.translate import translate
-class Draft_Snap_Base():
+class Draft_Snap_Base:
"""Base Class inherited by all Draft Snap commands."""
def Activated(self, status=0):
@@ -61,14 +61,19 @@ class Draft_Snap_Lock(Draft_Snap_Base):
"""GuiCommand for the Draft_Snap_Lock tool."""
def GetResources(self):
- return {"Pixmap": "Draft_Snap_Lock",
- "Accel": "Shift+S",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Lock", "Snap Lock"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Snap_Lock", "Enables or disables snapping globally"),
- "CmdType": "NoTransaction",
- "Checkable": self.isChecked()}
+ return {
+ "Pixmap": "Draft_Snap_Lock",
+ "Accel": "Shift+S",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Lock", "Snap Lock"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Snap_Lock", "Enables or disables snapping globally"
+ ),
+ "CmdType": "NoTransaction",
+ "Checkable": self.isChecked(),
+ }
- def IsActive(self): return True
+ def IsActive(self):
+ return True
Gui.addCommand("Draft_Snap_Lock", Draft_Snap_Lock())
@@ -78,11 +83,13 @@ class Draft_Snap_Midpoint(Draft_Snap_Base):
"""GuiCommand for the Draft_Snap_Midpoint tool."""
def GetResources(self):
- return {"Pixmap": "Draft_Snap_Midpoint",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Midpoint", "Snap Midpoint"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Snap_Midpoint", "Snaps to the midpoint of edges"),
- "CmdType": "NoTransaction",
- "Checkable": self.isChecked()}
+ return {
+ "Pixmap": "Draft_Snap_Midpoint",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Midpoint", "Snap Midpoint"),
+ "ToolTip": QT_TRANSLATE_NOOP("Draft_Snap_Midpoint", "Snaps to the midpoint of edges"),
+ "CmdType": "NoTransaction",
+ "Checkable": self.isChecked(),
+ }
Gui.addCommand("Draft_Snap_Midpoint", Draft_Snap_Midpoint())
@@ -92,11 +99,15 @@ class Draft_Snap_Perpendicular(Draft_Snap_Base):
"""GuiCommand for the Draft_Snap_Perpendicular tool."""
def GetResources(self):
- return {"Pixmap": "Draft_Snap_Perpendicular",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Perpendicular", "Snap Perpendicular"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Snap_Perpendicular", "Snaps to the perpendicular points on faces and edges"),
- "CmdType": "NoTransaction",
- "Checkable": self.isChecked()}
+ return {
+ "Pixmap": "Draft_Snap_Perpendicular",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Perpendicular", "Snap Perpendicular"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Snap_Perpendicular", "Snaps to the perpendicular points on faces and edges"
+ ),
+ "CmdType": "NoTransaction",
+ "Checkable": self.isChecked(),
+ }
Gui.addCommand("Draft_Snap_Perpendicular", Draft_Snap_Perpendicular())
@@ -106,11 +117,15 @@ class Draft_Snap_Grid(Draft_Snap_Base):
"""GuiCommand for the Draft_Snap_Grid tool."""
def GetResources(self):
- return {"Pixmap": "Draft_Snap_Grid",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Grid", "Snap Grid"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Snap_Grid", "Snaps to the intersections of grid lines"),
- "CmdType": "NoTransaction",
- "Checkable": self.isChecked()}
+ return {
+ "Pixmap": "Draft_Snap_Grid",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Grid", "Snap Grid"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Snap_Grid", "Snaps to the intersections of grid lines"
+ ),
+ "CmdType": "NoTransaction",
+ "Checkable": self.isChecked(),
+ }
Gui.addCommand("Draft_Snap_Grid", Draft_Snap_Grid())
@@ -120,11 +135,16 @@ class Draft_Snap_Intersection(Draft_Snap_Base):
"""GuiCommand for the Draft_Snap_Intersection tool."""
def GetResources(self):
- return {"Pixmap": "Draft_Snap_Intersection",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Intersection", "Snap Intersection"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Snap_Intersection", "Snaps to the intersection of 2 edges, and the intersection of a face and an edge"),
- "CmdType": "NoTransaction",
- "Checkable": self.isChecked()}
+ return {
+ "Pixmap": "Draft_Snap_Intersection",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Intersection", "Snap Intersection"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Snap_Intersection",
+ "Snaps to the intersection of 2 edges, and the intersection of a face and an edge",
+ ),
+ "CmdType": "NoTransaction",
+ "Checkable": self.isChecked(),
+ }
Gui.addCommand("Draft_Snap_Intersection", Draft_Snap_Intersection())
@@ -134,11 +154,15 @@ class Draft_Snap_Parallel(Draft_Snap_Base):
"""GuiCommand for the Draft_Snap_Parallel tool."""
def GetResources(self):
- return {"Pixmap": "Draft_Snap_Parallel",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Parallel", "Snap Parallel"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Snap_Parallel", "Snaps to an imaginary line parallel to straight edges"),
- "CmdType": "NoTransaction",
- "Checkable": self.isChecked()}
+ return {
+ "Pixmap": "Draft_Snap_Parallel",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Parallel", "Snap Parallel"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Snap_Parallel", "Snaps to an imaginary line parallel to straight edges"
+ ),
+ "CmdType": "NoTransaction",
+ "Checkable": self.isChecked(),
+ }
Gui.addCommand("Draft_Snap_Parallel", Draft_Snap_Parallel())
@@ -148,11 +172,13 @@ class Draft_Snap_Endpoint(Draft_Snap_Base):
"""GuiCommand for the Draft_Snap_Endpoint tool."""
def GetResources(self):
- return {"Pixmap": "Draft_Snap_Endpoint",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Endpoint", "Snap Endpoint"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Snap_Endpoint", "Snaps to the endpoints of edges"),
- "CmdType": "NoTransaction",
- "Checkable": self.isChecked()}
+ return {
+ "Pixmap": "Draft_Snap_Endpoint",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Endpoint", "Snap Endpoint"),
+ "ToolTip": QT_TRANSLATE_NOOP("Draft_Snap_Endpoint", "Snaps to the endpoints of edges"),
+ "CmdType": "NoTransaction",
+ "Checkable": self.isChecked(),
+ }
Gui.addCommand("Draft_Snap_Endpoint", Draft_Snap_Endpoint())
@@ -162,11 +188,16 @@ class Draft_Snap_Angle(Draft_Snap_Base):
"""GuiCommand for the Draft_Snap_Angle tool."""
def GetResources(self):
- return {"Pixmap": "Draft_Snap_Angle",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Angle", "Snap Angle"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Snap_Angle", "Snaps to the special cardinal points on circular edges, at multiples of 30° and 45°"),
- "CmdType": "NoTransaction",
- "Checkable": self.isChecked()}
+ return {
+ "Pixmap": "Draft_Snap_Angle",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Angle", "Snap Angle"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Snap_Angle",
+ "Snaps to the special cardinal points on circular edges, at multiples of 30° and 45°",
+ ),
+ "CmdType": "NoTransaction",
+ "Checkable": self.isChecked(),
+ }
Gui.addCommand("Draft_Snap_Angle", Draft_Snap_Angle())
@@ -176,11 +207,16 @@ class Draft_Snap_Center(Draft_Snap_Base):
"""GuiCommand for the Draft_Snap_Center tool."""
def GetResources(self):
- return {"Pixmap": "Draft_Snap_Center",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Center", "Snap Center"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Snap_Center", "Snaps to the center point of faces and circular edges, and to the placement point of working plane proxies and building parts"),
- "CmdType": "NoTransaction",
- "Checkable": self.isChecked()}
+ return {
+ "Pixmap": "Draft_Snap_Center",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Center", "Snap Center"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Snap_Center",
+ "Snaps to the center point of faces and circular edges, and to the placement point of working plane proxies and building parts",
+ ),
+ "CmdType": "NoTransaction",
+ "Checkable": self.isChecked(),
+ }
Gui.addCommand("Draft_Snap_Center", Draft_Snap_Center())
@@ -190,11 +226,16 @@ class Draft_Snap_Extension(Draft_Snap_Base):
"""GuiCommand for the Draft_Snap_Extension tool."""
def GetResources(self):
- return {"Pixmap": "Draft_Snap_Extension",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Extension", "Snap Extension"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Snap_Extension", "Snaps to an imaginary line that extends beyond the endpoints of straight edges"),
- "CmdType": "NoTransaction",
- "Checkable": self.isChecked()}
+ return {
+ "Pixmap": "Draft_Snap_Extension",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Extension", "Snap Extension"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Snap_Extension",
+ "Snaps to an imaginary line that extends beyond the endpoints of straight edges",
+ ),
+ "CmdType": "NoTransaction",
+ "Checkable": self.isChecked(),
+ }
Gui.addCommand("Draft_Snap_Extension", Draft_Snap_Extension())
@@ -204,11 +245,15 @@ class Draft_Snap_Near(Draft_Snap_Base):
"""GuiCommand for the Draft_Snap_Near tool."""
def GetResources(self):
- return {"Pixmap": "Draft_Snap_Near",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Near", "Snap Near"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Snap_Near", "Snaps to the nearest point on faces and edges"),
- "CmdType": "NoTransaction",
- "Checkable": self.isChecked()}
+ return {
+ "Pixmap": "Draft_Snap_Near",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Near", "Snap Near"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Snap_Near", "Snaps to the nearest point on faces and edges"
+ ),
+ "CmdType": "NoTransaction",
+ "Checkable": self.isChecked(),
+ }
Gui.addCommand("Draft_Snap_Near", Draft_Snap_Near())
@@ -218,11 +263,16 @@ class Draft_Snap_Ortho(Draft_Snap_Base):
"""GuiCommand for the Draft_Snap_Ortho tool."""
def GetResources(self):
- return {"Pixmap": "Draft_Snap_Ortho",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Ortho", "Snap Ortho"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Snap_Ortho", "Snaps to imaginary lines that cross the previous point at multiples of 45°"),
- "CmdType": "NoTransaction",
- "Checkable": self.isChecked()}
+ return {
+ "Pixmap": "Draft_Snap_Ortho",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Ortho", "Snap Ortho"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Snap_Ortho",
+ "Snaps to imaginary lines that cross the previous point at multiples of 45°",
+ ),
+ "CmdType": "NoTransaction",
+ "Checkable": self.isChecked(),
+ }
Gui.addCommand("Draft_Snap_Ortho", Draft_Snap_Ortho())
@@ -232,11 +282,15 @@ class Draft_Snap_Special(Draft_Snap_Base):
"""GuiCommand for the Draft_Snap_Special tool."""
def GetResources(self):
- return {"Pixmap": "Draft_Snap_Special",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Special", "Snap Special"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Snap_Special", "Snaps to special points defined by the object"),
- "CmdType": "NoTransaction",
- "Checkable": self.isChecked()}
+ return {
+ "Pixmap": "Draft_Snap_Special",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Special", "Snap Special"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Snap_Special", "Snaps to special points defined by the object"
+ ),
+ "CmdType": "NoTransaction",
+ "Checkable": self.isChecked(),
+ }
Gui.addCommand("Draft_Snap_Special", Draft_Snap_Special())
@@ -246,11 +300,15 @@ class Draft_Snap_Dimensions(Draft_Snap_Base):
"""GuiCommand for the Draft_Snap_Dimensions tool."""
def GetResources(self):
- return {"Pixmap": "Draft_Snap_Dimensions",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Dimensions", "Snap Dimensions"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Snap_Dimensions", "Shows temporary X and Y dimensions"),
- "CmdType": "NoTransaction",
- "Checkable": self.isChecked()}
+ return {
+ "Pixmap": "Draft_Snap_Dimensions",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_Dimensions", "Snap Dimensions"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Snap_Dimensions", "Shows temporary X and Y dimensions"
+ ),
+ "CmdType": "NoTransaction",
+ "Checkable": self.isChecked(),
+ }
Gui.addCommand("Draft_Snap_Dimensions", Draft_Snap_Dimensions())
@@ -260,11 +318,15 @@ class Draft_Snap_WorkingPlane(Draft_Snap_Base):
"""GuiCommand for the Draft_Snap_WorkingPlane tool."""
def GetResources(self):
- return {"Pixmap": "Draft_Snap_WorkingPlane",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_WorkingPlane", "Snap Working Plane"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Snap_WorkingPlane", "Projects snap points onto the current working plane"),
- "CmdType": "NoTransaction",
- "Checkable": self.isChecked()}
+ return {
+ "Pixmap": "Draft_Snap_WorkingPlane",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Snap_WorkingPlane", "Snap Working Plane"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Snap_WorkingPlane", "Projects snap points onto the current working plane"
+ ),
+ "CmdType": "NoTransaction",
+ "Checkable": self.isChecked(),
+ }
Gui.addCommand("Draft_Snap_WorkingPlane", Draft_Snap_WorkingPlane())
@@ -274,10 +336,14 @@ class ShowSnapBar(Draft_Snap_Base):
"""GuiCommand for the Draft_ShowSnapBar tool."""
def GetResources(self):
- return {"Pixmap": "Draft_Snap",
- "MenuText": QT_TRANSLATE_NOOP("Draft_ShowSnapBar", "Show Snap Toolbar"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_ShowSnapBar", "Shows the snap toolbar if it is hidden"),
- "CmdType": "NoTransaction"}
+ return {
+ "Pixmap": "Draft_Snap",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_ShowSnapBar", "Show Snap Toolbar"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_ShowSnapBar", "Shows the snap toolbar if it is hidden"
+ ),
+ "CmdType": "NoTransaction",
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -287,6 +353,6 @@ class ShowSnapBar(Draft_Snap_Base):
toolbar.show()
-Gui.addCommand('Draft_ShowSnapBar', ShowSnapBar())
+Gui.addCommand("Draft_ShowSnapBar", ShowSnapBar())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_splines.py b/src/Mod/Draft/draftguitools/gui_splines.py
index 212e2dc37e..b4cf2ef3da 100644
--- a/src/Mod/Draft/draftguitools/gui_splines.py
+++ b/src/Mod/Draft/draftguitools/gui_splines.py
@@ -55,17 +55,21 @@ class BSpline(gui_lines.Line):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_BSpline',
- 'Accel': "B, S",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_BSpline", "B-Spline"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_BSpline", "Creates a multiple-point B-spline")}
+ return {
+ "Pixmap": "Draft_BSpline",
+ "Accel": "B, S",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_BSpline", "B-Spline"),
+ "ToolTip": QT_TRANSLATE_NOOP("Draft_BSpline", "Creates a multiple-point B-spline"),
+ }
def Activated(self):
"""Execute when the command is called.
Activate the specific BSpline tracker.
"""
- super(BSpline, self).Activated(name="Bspline", icon="Draft_BSpline", task_title=translate("draft","B-Spline"))
+ super(BSpline, self).Activated(
+ name="Bspline", icon="Draft_BSpline", task_title=translate("draft", "B-Spline")
+ )
if self.doc:
self.bsplinetrack = trackers.bsplineTracker()
@@ -125,6 +129,7 @@ class BSpline(gui_lines.Line):
def undolast(self):
"""Undo last line segment."""
import Part
+
if len(self.node) > 1:
self.node.pop()
self.bsplinetrack.update(self.node)
@@ -136,6 +141,7 @@ class BSpline(gui_lines.Line):
def drawUpdate(self, point):
"""Draw and update to the spline."""
import Part
+
if len(self.node) == 1:
self.bsplinetrack.on()
if self.planetrack:
@@ -173,19 +179,20 @@ class BSpline(gui_lines.Line):
rot, sup, pts, fil = self.getStrings()
Gui.addModule("Draft")
- _cmd = 'Draft.make_bspline'
- _cmd += '('
- _cmd += 'points, '
- _cmd += 'closed=' + str(closed) + ', '
- _cmd += 'face=' + fil + ', '
- _cmd += 'support=' + sup
- _cmd += ')'
- _cmd_list = ['points = ' + pts,
- 'spline = ' + _cmd,
- 'Draft.autogroup(spline)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create B-Spline"),
- _cmd_list)
+ _cmd = "Draft.make_bspline"
+ _cmd += "("
+ _cmd += "points, "
+ _cmd += "closed=" + str(closed) + ", "
+ _cmd += "face=" + fil + ", "
+ _cmd += "support=" + sup
+ _cmd += ")"
+ _cmd_list = [
+ "points = " + pts,
+ "spline = " + _cmd,
+ "Draft.autogroup(spline)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create B-Spline"), _cmd_list)
except Exception:
_err("Draft: error delaying commit")
@@ -200,6 +207,6 @@ class BSpline(gui_lines.Line):
self.Activated()
-Gui.addCommand('Draft_BSpline', BSpline())
+Gui.addCommand("Draft_BSpline", BSpline())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_split.py b/src/Mod/Draft/draftguitools/gui_split.py
index 6be1b5fc0a..e90c628d3d 100644
--- a/src/Mod/Draft/draftguitools/gui_split.py
+++ b/src/Mod/Draft/draftguitools/gui_split.py
@@ -46,10 +46,14 @@ class Split(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {"Pixmap": "Draft_Split",
- "Accel": "S, P",
- "MenuText": QT_TRANSLATE_NOOP("Draft_Split", "Split"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_Split", "Splits the selected line or polyline at a specified point")}
+ return {
+ "Pixmap": "Draft_Split",
+ "Accel": "S, P",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Split", "Split"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Split", "Splits the selected line or polyline at a specified point"
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -77,9 +81,11 @@ class Split(gui_base_original.Modifier):
elif arg["Type"] == "SoLocation2Event":
gui_tool_utils.getPoint(self, arg)
gui_tool_utils.redraw3DView()
- elif (arg["Type"] == "SoMouseButtonEvent"
- and arg["Button"] == "BUTTON1"
- and arg["State"] == "DOWN"):
+ elif (
+ arg["Type"] == "SoMouseButtonEvent"
+ and arg["Button"] == "BUTTON1"
+ and arg["State"] == "DOWN"
+ ):
self.point, ctrlPoint, info = gui_tool_utils.getPoint(self, arg)
if info is not None and "Edge" in info["Component"]:
return self.proceed(info)
@@ -95,7 +101,7 @@ class Split(gui_base_original.Modifier):
cmd_list = [
"obj = FreeCAD.ActiveDocument." + wire,
"new = Draft.split(obj, " + point + ", " + index + ")",
- "FreeCAD.ActiveDocument.recompute()"
+ "FreeCAD.ActiveDocument.recompute()",
]
self.commit(translate("draft", "Split Line"), cmd_list)
@@ -107,6 +113,6 @@ class Split(gui_base_original.Modifier):
super().finish()
-Gui.addCommand('Draft_Split', Split())
+Gui.addCommand("Draft_Split", Split())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_stretch.py b/src/Mod/Draft/draftguitools/gui_stretch.py
index 2c4e9b60d8..e566ff8d24 100644
--- a/src/Mod/Draft/draftguitools/gui_stretch.py
+++ b/src/Mod/Draft/draftguitools/gui_stretch.py
@@ -59,10 +59,12 @@ class Stretch(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_Stretch',
- 'Accel': "S, H",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Stretch", "Stretch"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Stretch", "Stretches the selected objects")}
+ return {
+ "Pixmap": "Draft_Stretch",
+ "Accel": "S, H",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Stretch", "Stretch"),
+ "ToolTip": QT_TRANSLATE_NOOP("Draft_Stretch", "Stretches the selected objects"),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -73,9 +75,7 @@ class Stretch(gui_base_original.Modifier):
if not Gui.Selection.getSelection():
self.ui.selectUi(on_close_call=self.finish)
_msg(translate("draft", "Select an object to stretch"))
- self.call = \
- self.view.addEventCallback("SoEvent",
- gui_tool_utils.selectObject)
+ self.call = self.view.addEventCallback("SoEvent", gui_tool_utils.selectObject)
else:
self.proceed()
@@ -104,7 +104,9 @@ class Stretch(gui_base_original.Modifier):
elif hasattr(obj.Base, "Base"):
if obj.Base.Base:
if utils.getType(obj.Base.Base) in supported:
- self.sel.append([obj.Base.Base, obj.Placement.multiply(obj.Base.Placement)])
+ self.sel.append(
+ [obj.Base.Base, obj.Placement.multiply(obj.Base.Placement)]
+ )
elif utils.getType(obj) in ["Offset2D", "Array"]:
base = None
if hasattr(obj, "Source") and obj.Source:
@@ -119,9 +121,9 @@ class Stretch(gui_base_original.Modifier):
self.refpoint = None
self.ui.pointUi(title=translate("draft", self.featureName), icon="Draft_Stretch")
self.call = self.view.addEventCallback("SoEvent", self.action)
- self.rectracker = trackers.rectangleTracker(dotted=True,
- scolor=(0.0, 0.0, 1.0),
- swidth=2)
+ self.rectracker = trackers.rectangleTracker(
+ dotted=True, scolor=(0.0, 0.0, 1.0), swidth=2
+ )
self.nodetracker = []
self.displacement = None
_toolmsg(translate("draft", "Pick first point of selection rectangle"))
@@ -158,8 +160,7 @@ class Stretch(gui_base_original.Modifier):
"""Add point to defined selection rectangle."""
if self.step == 1:
# first rctangle point
- _toolmsg(translate("draft", "Pick the opposite point "
- "of the selection rectangle"))
+ _toolmsg(translate("draft", "Pick the opposite point " "of the selection rectangle"))
self.ui.setRelative(-1)
self.rectracker.setorigin(point)
self.rectracker.on()
@@ -294,7 +295,9 @@ class Stretch(gui_base_original.Modifier):
_cmd = _doc + ops[0].Name + ".Points=" + pts
commitops.append(_cmd)
elif tp in ["Sketch"]:
- baseverts = [ops[0].Shape.Vertexes[i].Point for i in range(len(ops[1])) if ops[1][i]]
+ baseverts = [
+ ops[0].Shape.Vertexes[i].Point for i in range(len(ops[1])) if ops[1][i]
+ ]
for i in range(ops[0].GeometryCount):
j = 0
while True:
@@ -325,9 +328,7 @@ class Stretch(gui_base_original.Modifier):
elif tp in ["Rectangle"]:
p1 = App.Vector(0, 0, 0)
p2 = App.Vector(ops[0].Length.Value, 0, 0)
- p3 = App.Vector(ops[0].Length.Value,
- ops[0].Height.Value,
- 0)
+ p3 = App.Vector(ops[0].Length.Value, ops[0].Height.Value, 0)
p4 = App.Vector(0, ops[0].Height.Value, 0)
if ops[1] == [False, True, True, False]:
optype = 1
@@ -486,6 +487,6 @@ class Stretch(gui_base_original.Modifier):
self.finish()
-Gui.addCommand('Draft_Stretch', Stretch())
+Gui.addCommand("Draft_Stretch", Stretch())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_styles.py b/src/Mod/Draft/draftguitools/gui_styles.py
index 5661f80382..111a8e2030 100644
--- a/src/Mod/Draft/draftguitools/gui_styles.py
+++ b/src/Mod/Draft/draftguitools/gui_styles.py
@@ -37,6 +37,7 @@ from draftguitools import gui_base_original
from draftutils.translate import translate
from draftutils import groups
+
class ApplyStyle(gui_base_original.Modifier):
"""Gui Command for the ApplyStyle tool."""
@@ -45,7 +46,9 @@ class ApplyStyle(gui_base_original.Modifier):
return {
"Pixmap": "Draft_Apply",
"MenuText": QT_TRANSLATE_NOOP("Draft_ApplyStyle", "Apply Current Style"),
- "ToolTip": QT_TRANSLATE_NOOP("Draft_ApplyStyle", "Applies the current style to the selected objects and groups")
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_ApplyStyle", "Applies the current style to the selected objects and groups"
+ ),
}
def IsActive(self):
@@ -60,8 +63,10 @@ class ApplyStyle(gui_base_original.Modifier):
Gui.addModule("Draft")
cmd_list = [
"doc = FreeCAD.ActiveDocument",
- "Draft.apply_current_style([" + ", ".join(["doc." + obj.Name for obj in objs]) + "])",
- "doc.recompute()"
+ "Draft.apply_current_style(["
+ + ", ".join(["doc." + obj.Name for obj in objs])
+ + "])",
+ "doc.recompute()",
]
self.commit(translate("draft", "Change Style"), cmd_list)
self.finish()
diff --git a/src/Mod/Draft/draftguitools/gui_subelements.py b/src/Mod/Draft/draftguitools/gui_subelements.py
index 94aa97d5ca..559ed1a77b 100644
--- a/src/Mod/Draft/draftguitools/gui_subelements.py
+++ b/src/Mod/Draft/draftguitools/gui_subelements.py
@@ -57,10 +57,15 @@ class SubelementHighlight(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_SubelementHighlight',
- 'Accel': "H, S",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_SubelementHighlight","Highlight Subelements"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_SubelementHighlight","Highlights the subelements of the selected objects, to be able to move, rotate, and scale them")}
+ return {
+ "Pixmap": "Draft_SubelementHighlight",
+ "Accel": "H, S",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_SubelementHighlight", "Highlight Subelements"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_SubelementHighlight",
+ "Highlights the subelements of the selected objects, to be able to move, rotate, and scale them",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -108,20 +113,23 @@ class SubelementHighlight(gui_base_original.Modifier):
"""Get the selection."""
if not Gui.Selection.getSelection() and self.ui:
_msg(translate("draft", "Select an object to edit"))
- self.call = self.view.addEventCallback("SoEvent",
- gui_tool_utils.selectObject)
+ self.call = self.view.addEventCallback("SoEvent", gui_tool_utils.selectObject)
else:
self.proceed()
def get_editable_objects_from_selection(self):
"""Get editable Draft objects for the selection."""
for obj in Gui.Selection.getSelection():
- if (obj.isDerivedFrom("Part::Part2DObject")
- or utils.get_type(obj) in ["BezCurve", "BSpline", "Wire"]):
+ if obj.isDerivedFrom("Part::Part2DObject") or utils.get_type(obj) in [
+ "BezCurve",
+ "BSpline",
+ "Wire",
+ ]:
self.editable_objects.append(obj)
- elif (hasattr(obj, "Base")
- and (obj.Base.isDerivedFrom("Part::Part2DObject")
- or utils.get_type(obj.Base) in ["BezCurve", "BSpline", "Wire"])):
+ elif hasattr(obj, "Base") and (
+ obj.Base.isDerivedFrom("Part::Part2DObject")
+ or utils.get_type(obj.Base) in ["BezCurve", "BSpline", "Wire"]
+ ):
self.editable_objects.append(obj.Base)
def highlight_editable_objects(self):
@@ -129,10 +137,11 @@ class SubelementHighlight(gui_base_original.Modifier):
for obj in self.editable_objects:
vobj = obj.ViewObject
self.original_view_settings[obj.Name] = {
- 'Visibility': vobj.Visibility,
- 'PointSize': vobj.PointSize,
- 'PointColor': vobj.PointColor,
- 'LineColor': vobj.LineColor}
+ "Visibility": vobj.Visibility,
+ "PointSize": vobj.PointSize,
+ "PointColor": vobj.PointColor,
+ "LineColor": vobj.LineColor,
+ }
vobj.Visibility = True
vobj.PointSize = 10
vobj.PointColor = (1.0, 0.0, 0.0)
@@ -157,6 +166,6 @@ class SubelementHighlight(gui_base_original.Modifier):
pass
-Gui.addCommand('Draft_SubelementHighlight', SubelementHighlight())
+Gui.addCommand("Draft_SubelementHighlight", SubelementHighlight())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_texts.py b/src/Mod/Draft/draftguitools/gui_texts.py
index 104bea8bef..7696cbe8cf 100644
--- a/src/Mod/Draft/draftguitools/gui_texts.py
+++ b/src/Mod/Draft/draftguitools/gui_texts.py
@@ -55,16 +55,18 @@ class Text(gui_base_original.Creator):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_Text',
- 'Accel': "T, E",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Text", "Text"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Text", "Creates a multi-line annotation")}
+ return {
+ "Pixmap": "Draft_Text",
+ "Accel": "T, E",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Text", "Text"),
+ "ToolTip": QT_TRANSLATE_NOOP("Draft_Text", "Creates a multi-line annotation"),
+ }
def Activated(self):
"""Execute when the command is called."""
super().Activated(name="Text")
if self.ui:
- self.text = ''
+ self.text = ""
self.ui.sourceCmd = self
self.ui.pointUi(title=translate("draft", self.featureName), icon="Draft_Text")
self.ui.isRelative.hide()
@@ -108,23 +110,24 @@ class Text(gui_base_original.Creator):
list_as_text = ", ".join(t_list)
- string = '[' + list_as_text + ']'
+ string = "[" + list_as_text + "]"
Gui.addModule("Draft")
- _cmd = 'Draft.make_text'
- _cmd += '('
- _cmd += string + ', '
- _cmd += 'placement=pl, '
- _cmd += 'screen=None, height=None, line_spacing=None'
- _cmd += ')'
- _cmd_list = ['pl = FreeCAD.Placement()',
- 'pl.Rotation.Q = ' + rot,
- 'pl.Base = ' + base,
- '_text_ = ' + _cmd,
- 'Draft.autogroup(_text_)',
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Create Text"),
- _cmd_list)
+ _cmd = "Draft.make_text"
+ _cmd += "("
+ _cmd += string + ", "
+ _cmd += "placement=pl, "
+ _cmd += "screen=None, height=None, line_spacing=None"
+ _cmd += ")"
+ _cmd_list = [
+ "pl = FreeCAD.Placement()",
+ "pl.Rotation.Q = " + rot,
+ "pl.Base = " + base,
+ "_text_ = " + _cmd,
+ "Draft.autogroup(_text_)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ]
+ self.commit(translate("draft", "Create Text"), _cmd_list)
self.finish(cont=None)
def action(self, arg):
@@ -143,8 +146,7 @@ class Text(gui_base_original.Creator):
self.finish()
elif arg["Type"] == "SoLocation2Event": # mouse movement detection
if self.active:
- (self.point,
- ctrlPoint, info) = gui_tool_utils.getPoint(self, arg)
+ (self.point, ctrlPoint, info) = gui_tool_utils.getPoint(self, arg)
gui_tool_utils.redraw3DView()
elif arg["Type"] == "SoMouseButtonEvent":
if arg["State"] == "DOWN" and arg["Button"] == "BUTTON1":
@@ -167,6 +169,6 @@ class Text(gui_base_original.Creator):
self.ui.textValue.setFocus()
-Gui.addCommand('Draft_Text', Text())
+Gui.addCommand("Draft_Text", Text())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_togglemodes.py b/src/Mod/Draft/draftguitools/gui_togglemodes.py
index edc0c283ae..957648f69f 100644
--- a/src/Mod/Draft/draftguitools/gui_togglemodes.py
+++ b/src/Mod/Draft/draftguitools/gui_togglemodes.py
@@ -70,7 +70,7 @@ class BaseMode(gui_base.GuiCommandSimplest):
if hasattr(Gui, "draftToolBar"):
_ui = Gui.draftToolBar
else:
- _msg(translate("draft","No active Draft toolbar"))
+ _msg(translate("draft", "No active Draft toolbar"))
return
if _ui is not None:
@@ -89,16 +89,21 @@ class ToggleConstructionMode(BaseMode):
"""
def __init__(self):
- super(ToggleConstructionMode,
- self).__init__(name=translate("draft","Construction Mode"))
+ super(ToggleConstructionMode, self).__init__(name=translate("draft", "Construction Mode"))
def GetResources(self):
"""Set icon, menu and tooltip."""
- d = {'Pixmap': 'Draft_Construction',
- 'MenuText': QT_TRANSLATE_NOOP("Draft_ToggleConstructionMode","Toggle Construction Mode"),
- 'Accel': "C, M",
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_ToggleConstructionMode","Toggles the construction mode")}
+ d = {
+ "Pixmap": "Draft_Construction",
+ "MenuText": QT_TRANSLATE_NOOP(
+ "Draft_ToggleConstructionMode", "Toggle Construction Mode"
+ ),
+ "Accel": "C, M",
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_ToggleConstructionMode", "Toggles the construction mode"
+ ),
+ }
return d
def Activated(self):
@@ -110,7 +115,7 @@ class ToggleConstructionMode(BaseMode):
super(ToggleConstructionMode, self).Activated(mode="construction")
-Gui.addCommand('Draft_ToggleConstructionMode', ToggleConstructionMode())
+Gui.addCommand("Draft_ToggleConstructionMode", ToggleConstructionMode())
class ToggleDisplayMode(gui_base.GuiCommandNeedsSelection):
@@ -125,16 +130,20 @@ class ToggleDisplayMode(gui_base.GuiCommandNeedsSelection):
"""
def __init__(self):
- super(ToggleDisplayMode,
- self).__init__(name=translate("draft","Toggle Display Mode"))
+ super(ToggleDisplayMode, self).__init__(name=translate("draft", "Toggle Display Mode"))
def GetResources(self):
"""Set icon, menu and tooltip."""
- d = {'Pixmap': 'Draft_SwitchMode',
- 'Accel': "Shift+Space",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_ToggleDisplayMode","Toggle Wireframe"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_ToggleDisplayMode","Switches the view style of the selected objects from Flat Lines to Wireframe and back")}
+ d = {
+ "Pixmap": "Draft_SwitchMode",
+ "Accel": "Shift+Space",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_ToggleDisplayMode", "Toggle Wireframe"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_ToggleDisplayMode",
+ "Switches the view style of the selected objects from Flat Lines to Wireframe and back",
+ ),
+ }
return d
def Activated(self):
@@ -155,6 +164,6 @@ class ToggleDisplayMode(gui_base.GuiCommandNeedsSelection):
obj.ViewObject.DisplayMode = "Flat Lines"
-Gui.addCommand('Draft_ToggleDisplayMode', ToggleDisplayMode())
+Gui.addCommand("Draft_ToggleDisplayMode", ToggleDisplayMode())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_tool_utils.py b/src/Mod/Draft/draftguitools/gui_tool_utils.py
index 4190bb4d37..b4e638fff0 100644
--- a/src/Mod/Draft/draftguitools/gui_tool_utils.py
+++ b/src/Mod/Draft/draftguitools/gui_tool_utils.py
@@ -68,6 +68,7 @@ _HINT_MOD_KEYS = [Gui.UserInput.KeyShift, Gui.UserInput.KeyControl, Gui.UserInpu
# To allows for easy concatenation the _get_hint_* functions
# always return a list (with a single item or an empty list).
+
def _get_hint_mod_constrain():
key = _HINT_MOD_KEYS[params.get_param("modconstrain")]
return [Gui.InputHint(translate("draft", "%1 constrain"), key)]
@@ -85,13 +86,17 @@ def _get_hint_xyz_constrain():
shortcut_x = params.get_param("inCommandShortcutRestrictX").upper()
shortcut_y = params.get_param("inCommandShortcutRestrictY").upper()
shortcut_z = params.get_param("inCommandShortcutRestrictZ").upper()
- if pattern.fullmatch(shortcut_x) \
- and pattern.fullmatch(shortcut_y) \
- and pattern.fullmatch(shortcut_z):
+ if (
+ pattern.fullmatch(shortcut_x)
+ and pattern.fullmatch(shortcut_y)
+ and pattern.fullmatch(shortcut_z)
+ ):
key_x = getattr(Gui.UserInput, "Key" + shortcut_x)
key_y = getattr(Gui.UserInput, "Key" + shortcut_y)
key_z = getattr(Gui.UserInput, "Key" + shortcut_z)
- return [Gui.InputHint(translate("draft", "%1/%2/%3 switch constraint"), key_x, key_y, key_z)]
+ return [
+ Gui.InputHint(translate("draft", "%1/%2/%3 switch constraint"), key_x, key_y, key_z)
+ ]
return []
@@ -267,11 +272,9 @@ def get_point(target, args, noTracker=False):
point = None
if hasattr(Gui, "Snapper"):
- point = Gui.Snapper.snap(args["Position"],
- lastpoint=last,
- active=smod,
- constrain=cmod,
- noTracker=noTracker)
+ point = Gui.Snapper.snap(
+ args["Position"], lastpoint=last, active=smod, constrain=cmod, noTracker=noTracker
+ )
info = Gui.Snapper.snapInfo
mask = Gui.Snapper.affinity
if not point:
@@ -310,9 +313,9 @@ def set_working_plane_to_object_under_cursor(mouseEvent):
App::DocumentObject or None
The parent object the face belongs to, if alignment occurred, or None.
"""
- objectUnderCursor = gui_utils.get_3d_view().getObjectInfo((
- mouseEvent["Position"][0],
- mouseEvent["Position"][1]))
+ objectUnderCursor = gui_utils.get_3d_view().getObjectInfo(
+ (mouseEvent["Position"][0], mouseEvent["Position"][1])
+ )
if not objectUnderCursor:
return None
@@ -323,6 +326,7 @@ def set_working_plane_to_object_under_cursor(mouseEvent):
return None
import Part
+
if "ParentObject" in objectUnderCursor:
obj = objectUnderCursor["ParentObject"]
sub = objectUnderCursor["SubName"]
@@ -357,14 +361,16 @@ def set_working_plane_to_selected_object():
sels = Gui.Selection.getSelectionEx("", 0)
- if len(sels) == 1 \
- and len(sels[0].SubObjects) == 1 \
- and sels[0].SubObjects[0].ShapeType == "Face":
+ if (
+ len(sels) == 1
+ and len(sels[0].SubObjects) == 1
+ and sels[0].SubObjects[0].ShapeType == "Face"
+ ):
import Part
- shape = Part.getShape(sels[0].Object,
- sels[0].SubElementNames[0],
- needSubElement=True,
- retType=0)
+
+ shape = Part.getShape(
+ sels[0].Object, sels[0].SubElementNames[0], needSubElement=True, retType=0
+ )
if wp.align_to_face(shape, _hist_add=False):
wp.auto = True
@@ -377,7 +383,7 @@ setWorkingPlaneToSelectedObject = set_working_plane_to_selected_object
def get_support(mouseEvent=None):
- """"Align the working plane to a preselected face or the face under the cursor.
+ """ "Align the working plane to a preselected face or the face under the cursor.
The working plane is only aligned if it is `'auto'`.
diff --git a/src/Mod/Draft/draftguitools/gui_trackers.py b/src/Mod/Draft/draftguitools/gui_trackers.py
index 67e93748ce..be440e4229 100644
--- a/src/Mod/Draft/draftguitools/gui_trackers.py
+++ b/src/Mod/Draft/draftguitools/gui_trackers.py
@@ -58,11 +58,11 @@ __url__ = "https://www.freecad.org"
class Tracker:
"""A generic Draft Tracker, to be used by other specific trackers."""
- def __init__(self, dotted=False, scolor=None, swidth=None,
- children=[], ontop=False, name=None):
+ def __init__(self, dotted=False, scolor=None, swidth=None, children=[], ontop=False, name=None):
global Part, DraftGeomUtils
import Part
import DraftGeomUtils
+
self.ontop = ontop
self.color = coin.SoBaseColor()
drawstyle = coin.SoDrawStyle()
@@ -71,7 +71,7 @@ class Tracker:
if dotted:
drawstyle.style = coin.SoDrawStyle.LINES
drawstyle.lineWeight = 3
- drawstyle.linePattern = 0x0f0f # 0xaa
+ drawstyle.linePattern = 0x0F0F # 0xaa
node = coin.SoSeparator()
for c in [drawstyle, self.color] + children:
node.addChild(c)
@@ -92,8 +92,7 @@ class Tracker:
self.switch = None
def get_scene_graph(self):
- """Returns the current scenegraph or None if this is not a 3D view
- """
+ """Returns the current scenegraph or None if this is not a 3D view"""
v = Draft.get3DView()
if v:
return v.getSceneGraph()
@@ -164,13 +163,17 @@ class Tracker:
"""Set the color."""
if color is not None:
self.color.rgb = color
- elif hasattr(FreeCAD, "activeDraftCommand") \
- and FreeCAD.activeDraftCommand is not None \
- and hasattr(FreeCAD.activeDraftCommand, "featureName") \
- and FreeCAD.activeDraftCommand.featureName in ("Dimension", "Label", "Text"):
+ elif (
+ hasattr(FreeCAD, "activeDraftCommand")
+ and FreeCAD.activeDraftCommand is not None
+ and hasattr(FreeCAD.activeDraftCommand, "featureName")
+ and FreeCAD.activeDraftCommand.featureName in ("Dimension", "Label", "Text")
+ ):
self.color.rgb = utils.get_rgba_tuple(params.get_param("DefaultAnnoLineColor"))[:3]
else:
- self.color.rgb = utils.get_rgba_tuple(params.get_param_view("DefaultShapeLineColor"))[:3]
+ self.color.rgb = utils.get_rgba_tuple(params.get_param_view("DefaultShapeLineColor"))[
+ :3
+ ]
def _get_wp(self):
return FreeCAD.DraftWorkingPlane
@@ -181,7 +184,9 @@ class snapTracker(Tracker):
def __init__(self):
self.marker = coin.SoMarkerSet() # this is the marker symbol
- self.marker.markerIndex = FreeCADGui.getMarkerIndex("CIRCLE_FILLED", params.get_param_view("MarkerSize"))
+ self.marker.markerIndex = FreeCADGui.getMarkerIndex(
+ "CIRCLE_FILLED", params.get_param_view("MarkerSize")
+ )
self.coords = coin.SoCoordinate3() # this is the coordinate
self.coords.point.setValue((0, 0, 0))
node = coin.SoAnnotation()
@@ -192,7 +197,9 @@ class snapTracker(Tracker):
def setMarker(self, style):
"""Set the marker index."""
- self.marker.markerIndex = FreeCADGui.getMarkerIndex(style, params.get_param_view("MarkerSize"))
+ self.marker.markerIndex = FreeCADGui.getMarkerIndex(
+ style, params.get_param_view("MarkerSize")
+ )
def setColor(self, color=None):
"""Set the color."""
@@ -224,9 +231,7 @@ class lineTracker(Tracker):
line.numVertices.setValue(2)
self.coords = coin.SoCoordinate3() # this is the coordinate
self.coords.point.setValues(0, 2, [[0, 0, 0], [1, 0, 0]])
- super().__init__(dotted, scolor, swidth,
- [self.coords, line],
- ontop, name="lineTracker")
+ super().__init__(dotted, scolor, swidth, [self.coords, line], ontop, name="lineTracker")
def p1(self, point=None):
"""Set or get the first point of the line."""
@@ -273,13 +278,13 @@ class polygonTracker(Tracker):
m1.diffuseColor.setValue([0.5, 0.5, 1.0])
f = coin.SoIndexedFaceSet()
f.coordIndex.setValues([0, 1, 2, 3])
- super().__init__(dotted, scolor, swidth,
- [self.coords, self.line, m1, f],
- name="polygonTracker")
+ super().__init__(
+ dotted, scolor, swidth, [self.coords, self.line, m1, f], name="polygonTracker"
+ )
else:
- super().__init__(dotted, scolor, swidth,
- [self.coords, self.line],
- name="polygonTracker")
+ super().__init__(
+ dotted, scolor, swidth, [self.coords, self.line], name="polygonTracker"
+ )
def setNumVertices(self, num):
self.line.numVertices.setValue(num + 1)
@@ -312,6 +317,7 @@ class polygonTracker(Tracker):
radius = math.hypot(local_vec.x, local_vec.y)
self._drawPolygon(self.origin, radius)
+
class rectangleTracker(Tracker):
"""A Rectangle tracker, used by the rectangle tool."""
@@ -333,13 +339,11 @@ class rectangleTracker(Tracker):
m1.diffuseColor.setValue([0.5, 0.5, 1.0])
f = coin.SoIndexedFaceSet()
f.coordIndex.setValues([0, 1, 2, 3])
- super().__init__(dotted, scolor, swidth,
- [self.coords, line, m1, f],
- name="rectangleTracker")
+ super().__init__(
+ dotted, scolor, swidth, [self.coords, line, m1, f], name="rectangleTracker"
+ )
else:
- super().__init__(dotted, scolor, swidth,
- [self.coords, line],
- name="rectangleTracker")
+ super().__init__(dotted, scolor, swidth, [self.coords, line], name="rectangleTracker")
wp = self._get_wp()
self.u = wp.u
self.v = wp.v
@@ -399,8 +403,10 @@ class rectangleTracker(Tracker):
p1 = Vector(self.coords.point.getValues()[0].getValue())
p2 = Vector(self.coords.point.getValues()[2].getValue())
diag = p2.sub(p1)
- return ((DraftVecUtils.project(diag, self.u)).Length,
- (DraftVecUtils.project(diag, self.v)).Length)
+ return (
+ (DraftVecUtils.project(diag, self.u)).Length,
+ (DraftVecUtils.project(diag, self.v)).Length,
+ )
def getNormal(self):
"""Return the normal of the rectangle."""
@@ -435,8 +441,7 @@ class dimTracker(Tracker):
[0, 0, 0],
[0, 0, 0]])
# fmt: on
- super().__init__(dotted, scolor, swidth,
- [self.coords, line], name="dimTracker")
+ super().__init__(dotted, scolor, swidth, [self.coords, line], name="dimTracker")
self.p1 = self.p2 = self.p3 = None
def update(self, pts):
@@ -455,6 +460,7 @@ class dimTracker(Tracker):
def calc(self):
"""Calculate the new points from p1 and p2."""
import Part
+
if (self.p1 is not None) and (self.p2 is not None):
# fmt: off
points = [DraftVecUtils.tup(self.p1, True),
@@ -494,8 +500,7 @@ class bsplineTracker(Tracker):
self.trans = coin.SoTransform()
self.sep = coin.SoSeparator()
self.recompute()
- super().__init__(dotted, scolor, swidth,
- [self.trans, self.sep], name="bsplineTracker")
+ super().__init__(dotted, scolor, swidth, [self.trans, self.sep], name="bsplineTracker")
def update(self, points):
"""Update the points and recompute."""
@@ -508,9 +513,11 @@ class bsplineTracker(Tracker):
if self.bspline:
self.sep.removeChild(self.bspline)
self.bspline = None
- c = Part.BSplineCurve()
+ c = Part.BSplineCurve()
# DNC: allows one to close the curve by placing ends close to each other
- if len(self.points) >= 3 and ( (self.points[0] - self.points[-1]).Length < Draft.tolerance() ):
+ if len(self.points) >= 3 and (
+ (self.points[0] - self.points[-1]).Length < Draft.tolerance()
+ ):
# YVH: Added a try to bypass some hazardous situations
try:
c.interpolate(self.points[:-1], True)
@@ -554,7 +561,9 @@ class bsplineTracker(Tracker):
self.bspline.removeChild(self.bspline.getChild(0))
self.sep.addChild(self.bspline)
else:
- FreeCAD.Console.PrintWarning("bsplineTracker.recompute() failed to read-in Inventor string\n")
+ FreeCAD.Console.PrintWarning(
+ "bsplineTracker.recompute() failed to read-in Inventor string\n"
+ )
class bezcurveTracker(Tracker):
@@ -567,8 +576,7 @@ class bezcurveTracker(Tracker):
self.trans = coin.SoTransform()
self.sep = coin.SoSeparator()
self.recompute()
- super().__init__(dotted, scolor, swidth,
- [self.trans, self.sep], name="bezcurveTracker")
+ super().__init__(dotted, scolor, swidth, [self.trans, self.sep], name="bezcurveTracker")
def update(self, points, degree=None):
"""Update the points and recompute."""
@@ -586,10 +594,12 @@ class bezcurveTracker(Tracker):
self.bezcurve = []
- if (len(self.points) >= 2):
+ if len(self.points) >= 2:
if self.degree:
poles = self.points[1:]
- segpoleslst = [poles[x:x+self.degree] for x in range(0, len(poles), (self.degree or 1))]
+ segpoleslst = [
+ poles[x : x + self.degree] for x in range(0, len(poles), (self.degree or 1))
+ ]
else:
segpoleslst = [self.points]
startpoint = self.points[0]
@@ -601,16 +611,16 @@ class bezcurveTracker(Tracker):
c = c.toShape()
startpoint = segpoles[-1]
buf = c.writeInventor(2, 0.01)
- # fp=open("spline.iv", "w")
- # fp.write(buf)
- # fp.close()
+ # fp=open("spline.iv", "w")
+ # fp.write(buf)
+ # fp.close()
try:
ivin = coin.SoInput()
ivin.setBuffer(buf)
ivob = coin.SoDB.readAll(ivin)
except Exception:
# workaround for pivy SoInput.setBuffer() bug
- buf = buf.replace("\n","")
+ buf = buf.replace("\n", "")
pts = re.findall(r"point \\[(.*?)\\]", buf)[0]
pts = pts.split(",")
pc = []
@@ -632,15 +642,17 @@ class bezcurveTracker(Tracker):
bezcurveseg.removeChild(bezcurveseg.getChild(0))
self.sep.addChild(bezcurveseg)
else:
- FreeCAD.Console.PrintWarning("bezcurveTracker.recompute() failed to read-in Inventor string\n")
+ FreeCAD.Console.PrintWarning(
+ "bezcurveTracker.recompute() failed to read-in Inventor string\n"
+ )
self.bezcurve.append(bezcurveseg)
class arcTracker(Tracker):
"""An arc tracker."""
+
# Note: used by the Arc command but also for angular dimensions.
- def __init__(self, dotted=False, scolor=None, swidth=None,
- start=0, end=math.pi*2):
+ def __init__(self, dotted=False, scolor=None, swidth=None, start=0, end=math.pi * 2):
self.circle = None
self.startangle = math.degrees(start)
self.endangle = math.degrees(end)
@@ -650,12 +662,12 @@ class arcTracker(Tracker):
self.autoinvert = True
self.normal = self._get_wp().axis
self.recompute()
- super().__init__(dotted, scolor, swidth,
- [self.trans, self.sep], name="arcTracker")
+ super().__init__(dotted, scolor, swidth, [self.trans, self.sep], name="arcTracker")
def getDeviation(self):
"""Return a deviation vector that represents the base of the circle."""
import Part
+
c = Part.makeCircle(1, Vector(0, 0, 0), self.normal)
return c.Vertexes[0].Point
@@ -689,7 +701,7 @@ class arcTracker(Tracker):
def getAngles(self):
"""Return the start and end angles in degrees."""
- return(self.startangle, self.endangle)
+ return (self.startangle, self.endangle)
def setStartPoint(self, pt):
"""Set the start angle from a point."""
@@ -708,6 +720,7 @@ class arcTracker(Tracker):
def setBy3Points(self, p1, p2, p3):
"""Set the arc by three points."""
import Part
+
try:
arc = Part.ArcOfCircle(p1, p2, p3)
except Exception:
@@ -723,15 +736,14 @@ class arcTracker(Tracker):
def recompute(self):
"""Recompute the tracker."""
import Part
+
if self.circle:
self.sep.removeChild(self.circle)
self.circle = None
if (self.endangle < self.startangle) or not self.autoinvert:
- c = Part.makeCircle(1, Vector(0, 0, 0),
- self.normal, self.endangle, self.startangle)
+ c = Part.makeCircle(1, Vector(0, 0, 0), self.normal, self.endangle, self.startangle)
else:
- c = Part.makeCircle(1, Vector(0, 0, 0),
- self.normal, self.startangle, self.endangle)
+ c = Part.makeCircle(1, Vector(0, 0, 0), self.normal, self.startangle, self.endangle)
buf = c.writeInventor(2, 0.01)
try:
ivin = coin.SoInput()
@@ -761,7 +773,9 @@ class arcTracker(Tracker):
self.circle.removeChild(self.circle.getChild(0))
self.sep.addChild(self.circle)
else:
- FreeCAD.Console.PrintWarning("arcTracker.recompute() failed to read-in Inventor string\n")
+ FreeCAD.Console.PrintWarning(
+ "arcTracker.recompute() failed to read-in Inventor string\n"
+ )
class ghostTracker(Tracker):
@@ -770,7 +784,9 @@ class ghostTracker(Tracker):
You can pass it an object or a list of objects, or a shape.
"""
- def __init__(self, sel, dotted=False, scolor=None, swidth=None, mirror=False, parent_places=None):
+ def __init__(
+ self, sel, dotted=False, scolor=None, swidth=None, mirror=False, parent_places=None
+ ):
self.trans = coin.SoTransform()
self.trans.translation.setValue([0, 0, 0])
self.children = [self.trans]
@@ -783,13 +799,16 @@ class ghostTracker(Tracker):
else:
parent_place = None
import Part
+
if not isinstance(obj, Part.Vertex):
self.rootsep.addChild(self.getNode(obj, parent_place))
else:
self.coords = coin.SoCoordinate3()
self.coords.point.setValue((obj.X, obj.Y, obj.Z))
self.marker = coin.SoMarkerSet() # this is the marker symbol
- self.marker.markerIndex = FreeCADGui.getMarkerIndex("SQUARE_FILLED", params.get_param_view("MarkerSize"))
+ self.marker.markerIndex = FreeCADGui.getMarkerIndex(
+ "SQUARE_FILLED", params.get_param_view("MarkerSize")
+ )
node = coin.SoAnnotation()
selnode = coin.SoSeparator()
selnode.addChild(self.coords)
@@ -802,8 +821,7 @@ class ghostTracker(Tracker):
else:
self.flipped = False
self.children.append(self.rootsep)
- super().__init__(dotted, scolor, swidth,
- children=self.children, name="ghostTracker")
+ super().__init__(dotted, scolor, swidth, children=self.children, name="ghostTracker")
self.setColor(scolor)
def setColor(self, color=None):
@@ -840,6 +858,7 @@ class ghostTracker(Tracker):
def getNode(self, obj, parent_place=None):
"""Return a coin node representing the given object."""
import Part
+
if isinstance(obj, Part.Shape):
return self.getNodeLight(obj)
else:
@@ -886,7 +905,11 @@ class ghostTracker(Tracker):
def getMatrix(self):
"""Get matrix of the active view."""
- r = FreeCADGui.ActiveDocument.ActiveView.getViewer().getSoRenderManager().getViewportRegion()
+ r = (
+ FreeCADGui.ActiveDocument.ActiveView.getViewer()
+ .getSoRenderManager()
+ .getViewportRegion()
+ )
v = coin.SoGetMatrixAction(r)
m = self.trans.getMatrix(v)
if m:
@@ -937,8 +960,8 @@ class ghostTracker(Tracker):
if len(index) % 4 == 0:
for i in range(0, len(index), 4):
tmp = index[i]
- index[i] = index[i+1]
- index[i+1] = tmp
+ index[i] = index[i + 1]
+ index[i + 1] = tmp
node.coordIndex.setValues(index)
@@ -946,11 +969,14 @@ class ghostTracker(Tracker):
class editTracker(Tracker):
"""A node edit tracker."""
- def __init__(self, pos=Vector(0, 0, 0), name=None, idx=0, objcol=None,
- marker=None, inactive=False):
+ def __init__(
+ self, pos=Vector(0, 0, 0), name=None, idx=0, objcol=None, marker=None, inactive=False
+ ):
self.marker = coin.SoMarkerSet() # this is the marker symbol
if marker is None:
- self.marker.markerIndex = FreeCADGui.getMarkerIndex("SQUARE_FILLED", params.get_param_view("MarkerSize"))
+ self.marker.markerIndex = FreeCADGui.getMarkerIndex(
+ "SQUARE_FILLED", params.get_param_view("MarkerSize")
+ )
else:
self.marker.markerIndex = marker
self.coords = coin.SoCoordinate3() # this is the coordinate
@@ -970,8 +996,7 @@ class editTracker(Tracker):
self.selnode.addChild(self.marker)
node.addChild(self.selnode)
ontop = not inactive
- super().__init__(children=[node],
- ontop=ontop, name="editTracker")
+ super().__init__(children=[node], ontop=ontop, name="editTracker")
if objcol is None:
self.setColor()
else:
@@ -1024,7 +1049,7 @@ class PlaneTracker(Tracker):
# getting screen distance
p1 = Draft.get3DView().getPoint((100, 100))
p2 = Draft.get3DView().getPoint((110, 100))
- bl = (p2.sub(p1)).Length * (params.get_param("snapRange")/2.0)
+ bl = (p2.sub(p1)).Length * (params.get_param("snapRange") / 2.0)
pick = coin.SoPickStyle()
pick.style.setValue(coin.SoPickStyle.UNPICKABLE)
self.trans = coin.SoTransform()
@@ -1083,13 +1108,12 @@ class wireTracker(Tracker):
self.line = coin.SoLineSet()
self.closed = DraftGeomUtils.isReallyClosed(wire)
if self.closed:
- self.line.numVertices.setValue(len(wire.Vertexes)+1)
+ self.line.numVertices.setValue(len(wire.Vertexes) + 1)
else:
self.line.numVertices.setValue(len(wire.Vertexes))
self.coords = coin.SoCoordinate3()
self.update(wire)
- super().__init__(children=[self.coords, self.line],
- name="wireTracker")
+ super().__init__(children=[self.coords, self.line], name="wireTracker")
def update(self, wire, forceclosed=False):
"""Update the tracker."""
@@ -1127,11 +1151,11 @@ class gridTracker(Tracker):
# small squares
self.mat1 = coin.SoMaterial()
- self.mat1.transparency.setValue(0.8*(1-gtrans))
+ self.mat1.transparency.setValue(0.8 * (1 - gtrans))
self.mat1.diffuseColor.setValue(col)
self.font = coin.SoFont()
self.coords1 = coin.SoCoordinate3()
- self.lines1 = coin.SoLineSet() # small squares
+ self.lines1 = coin.SoLineSet() # small squares
# texts
texts = coin.SoSeparator()
@@ -1154,14 +1178,14 @@ class gridTracker(Tracker):
# big squares
self.mat2 = coin.SoMaterial()
- self.mat2.transparency.setValue(0.2*(1-gtrans))
+ self.mat2.transparency.setValue(0.2 * (1 - gtrans))
self.mat2.diffuseColor.setValue(col)
self.coords2 = coin.SoCoordinate3()
- self.lines2 = coin.SoLineSet() # big squares
+ self.lines2 = coin.SoLineSet() # big squares
# human figure
mat_human = coin.SoMaterial()
- mat_human.transparency.setValue(0.3*(1-gtrans))
+ mat_human.transparency.setValue(0.3 * (1 - gtrans))
mat_human.diffuseColor.setValue(col)
self.coords_human = coin.SoCoordinate3()
self.human = coin.SoLineSet()
@@ -1169,11 +1193,11 @@ class gridTracker(Tracker):
# axes
self.mat3 = coin.SoMaterial()
self.mat3.transparency.setValue(gtrans)
- self.mat3.diffuseColor.setValues([col,red,green,blue])
+ self.mat3.diffuseColor.setValues([col, red, green, blue])
self.coords3 = coin.SoCoordinate3()
- self.lines3 = coin.SoIndexedLineSet() # axes
- self.lines3.coordIndex.setValues(0,5,[0,1,-1,2,3])
- self.lines3.materialIndex.setValues(0,2,[0,0])
+ self.lines3 = coin.SoIndexedLineSet() # axes
+ self.lines3.coordIndex.setValues(0, 5, [0, 1, -1, 2, 3])
+ self.lines3.materialIndex.setValues(0, 2, [0, 0])
mbind3 = coin.SoMaterialBinding()
mbind3.value = coin.SoMaterialBinding.PER_PART_INDEXED
@@ -1223,8 +1247,8 @@ class gridTracker(Tracker):
return
numlines = self.numlines // self.mainlines // 2 * 2 * self.mainlines
bound = (numlines // 2) * self.space
- border = (numlines//2 + self.mainlines/2) * self.space
- cursor = self.mainlines//4 * self.space
+ border = (numlines // 2 + self.mainlines / 2) * self.space
+ cursor = self.mainlines // 4 * self.space
pts = []
mpts = []
apts = []
@@ -1239,73 +1263,83 @@ class gridTracker(Tracker):
else:
mpts.extend([[-bound, curr, z], [bound, curr, z]])
mpts.extend([[curr, -bound, z], [curr, bound, z]])
- cpts.extend([[-border,curr,z], [-border+cursor,curr,z]])
- cpts.extend([[border-cursor,curr,z], [border,curr,z]])
- cpts.extend([[curr,-border,z], [curr,-border+cursor,z]])
- cpts.extend([[curr,border-cursor,z], [curr,border,z]])
+ cpts.extend([[-border, curr, z], [-border + cursor, curr, z]])
+ cpts.extend([[border - cursor, curr, z], [border, curr, z]])
+ cpts.extend([[curr, -border, z], [curr, -border + cursor, z]])
+ cpts.extend([[curr, border - cursor, z], [curr, border, z]])
else:
pts.extend([[-bound, curr, z], [bound, curr, z]])
pts.extend([[curr, -bound, z], [curr, bound, z]])
if pts != self.pts:
idx = []
midx = []
- #aidx = []
+ # aidx = []
cidx = []
for p in range(0, len(pts), 2):
idx.append(2)
for mp in range(0, len(mpts), 2):
midx.append(2)
- #for ap in range(0, len(apts), 2):
+ # for ap in range(0, len(apts), 2):
# aidx.append(2)
- for cp in range(0, len(cpts),2):
+ for cp in range(0, len(cpts), 2):
cidx.append(2)
if params.get_param("gridBorder"):
# extra border
- border = (numlines//2 + self.mainlines/2) * self.space
- mpts.extend([[-border, -border, z], [border, -border, z], [border, border, z], [-border, border, z], [-border, -border, z]])
+ border = (numlines // 2 + self.mainlines / 2) * self.space
+ mpts.extend(
+ [
+ [-border, -border, z],
+ [border, -border, z],
+ [border, border, z],
+ [-border, border, z],
+ [-border, -border, z],
+ ]
+ )
midx.append(5)
# cursors
mpts.extend(cpts)
midx.extend(cidx)
# texts
- self.font.size = self.space*(self.mainlines//4) or 1
+ self.font.size = self.space * (self.mainlines // 4) or 1
self.font.name = params.get_param("textfont")
- txt = FreeCAD.Units.Quantity(self.space*self.mainlines,FreeCAD.Units.Length).UserString
+ txt = FreeCAD.Units.Quantity(
+ self.space * self.mainlines, FreeCAD.Units.Length
+ ).UserString
self.text1.string = txt
self.text2.string = txt
- self.textpos1.translation.setValue((-bound+self.space,-border+self.space,z))
- self.textpos2.translation.setValue((-bound-self.space,-bound+self.space,z))
+ self.textpos1.translation.setValue((-bound + self.space, -border + self.space, z))
+ self.textpos2.translation.setValue((-bound - self.space, -bound + self.space, z))
else:
self.text1.string = " "
self.text2.string = " "
self.lines1.numVertices.deleteValues(0)
self.lines2.numVertices.deleteValues(0)
- #self.lines3.numVertices.deleteValues(0)
+ # self.lines3.numVertices.deleteValues(0)
self.coords1.point.setValues(pts)
self.lines1.numVertices.setValues(idx)
self.coords2.point.setValues(mpts)
self.lines2.numVertices.setValues(midx)
self.coords3.point.setValues(apts)
- #self.lines3.numVertices.setValues(aidx)
+ # self.lines3.numVertices.setValues(aidx)
self.pts = pts
# update the grid colors
col, red, green, blue, gtrans = self.getGridColors()
self.mat1.diffuseColor.setValue(col)
self.mat2.diffuseColor.setValue(col)
- self.mat3.diffuseColor.setValues([col,red,green,blue])
+ self.mat3.diffuseColor.setValues([col, red, green, blue])
def getGridColors(self):
"""Returns grid colors stored in the preferences"""
- gtrans = params.get_param("gridTransparency")/100.0
+ gtrans = params.get_param("gridTransparency") / 100.0
col = utils.get_rgba_tuple(params.get_param("gridColor"))[:3]
if params.get_param("coloredGridAxes"):
vp = FreeCAD.ParamGet("User parameter:BaseApp/Preferences/View")
- red = vp.GetUnsigned("AxisXColor",0xCC333300)
- green = vp.GetUnsigned("AxisYColor",0x33CC3300)
- blue = vp.GetUnsigned("AxisZColor",0x3333CC00)
+ red = vp.GetUnsigned("AxisXColor", 0xCC333300)
+ green = vp.GetUnsigned("AxisYColor", 0x33CC3300)
+ blue = vp.GetUnsigned("AxisZColor", 0x3333CC00)
red = utils.get_rgba_tuple(red)[:3]
green = utils.get_rgba_tuple(green)[:3]
blue = utils.get_rgba_tuple(blue)[:3]
@@ -1321,38 +1355,88 @@ class gridTracker(Tracker):
Based on "HumanFigure.brep" from the BIM Workbench.
"""
pts = [
- Vector (131.2, 0.0, 175.8), Vector (135.7, 0.0, 211.7), Vector (142.1, 0.0, 229.3),
- Vector (154.0, 0.0, 276.3), Vector (163.6, 0.0, 333.4), Vector (173.8, 0.0, 411.5),
- Vector (186.0, 0.0, 491.7), Vector (200.2, 0.0, 591.8), Vector (215.4, 0.0, 714.8),
- Vector (224.1, 0.0, 650.0), Vector (234.1, 0.0, 575.8), Vector (251.9, 0.0, 425.5),
- Vector (240.8, 0.0, 273.3), Vector (235.9, 0.0, 243.2), Vector (197.3, 0.0, 81.7),
- Vector (188.8, 0.0, 37.6), Vector (195.1, 0.0, 0.0), Vector (278.8, 0.0, 0.0),
- Vector (294.5, 0.0, 121.0), Vector (308.4, 0.0, 184.3), Vector (318.1, 0.0, 225.4),
- Vector (322.0, 0.0, 235.2), Vector (340.1, 0.0, 283.5), Vector (349.0, 0.0, 341.4),
- Vector (354.2, 0.0, 523.7), Vector (383.1, 0.0, 719.7), Vector (399.6, 0.0, 820.3),
- Vector (381.2, 0.0, 1029.6), Vector (385.6, 0.0, 1164.0), Vector (390.1, 0.0, 1184.6),
- Vector (398.3, 0.0, 1201.9), Vector (430.2, 0.0, 1273.1), Vector (438.2, 0.0, 1321.2),
- Vector (441.3, 0.0, 1368.2), Vector (428.1, 0.0, 1405.3), Vector (395.0, 0.0, 1424.3),
- Vector (365.5, 0.0, 1446.6), Vector (349.8, 0.0, 1460.2), Vector (345.6, 0.0, 1476.7),
- Vector (337.9, 0.0, 1570.3), Vector (332.8, 0.0, 1624.7), Vector (322.2, 0.0, 1666.9),
- Vector (216.2, 0.0, 1680.2), Vector (163.5, 0.0, 1559.1), Vector (179.8, 0.0, 1475.5),
- Vector (195.6, 0.0, 1459.9), Vector (193.1, 0.0, 1447.8), Vector (171.0, 0.0, 1429.4),
- Vector (132.3, 0.0, 1399.8), Vector (96.8, 0.0, 1374.7), Vector (74.0, 0.0, 1275.1),
- Vector (46.2, 0.0, 1095.6), Vector (38.0, 0.0, 1041.5), Vector (25.2, 0.0, 958.5),
- Vector (15.9, 0.0, 889.7), Vector (2.5, 0.0, 842.1), Vector (-5.8, 0.0, 785.4),
- Vector (15.8, 0.0, 755.1), Vector (38.0, 0.0, 750.4), Vector (45.0, 0.0, 755.4),
- Vector (53.1, 0.0, 736.1), Vector (76.4, 0.0, 572.2), Vector (83.6, 0.0, 512.0),
- Vector (81.3, 0.0, 499.0), Vector (74.0, 0.0, 460.9), Vector (61.9, 0.0, 363.4),
- Vector (53.4, 0.0, 269.3), Vector (44.5, 0.0, 179.7), Vector (25.6, 0.0, 121.6),
- Vector (0.6, 0.0, 76.5), Vector (-23.7, 0.0, 54.5), Vector (-43.8, 0.0, 33.5),
- Vector (-25.6, 0.0, 0.0), Vector (117.9, 0.0, 0.0), Vector (131.2, 0.0, 175.8)
+ Vector(131.2, 0.0, 175.8),
+ Vector(135.7, 0.0, 211.7),
+ Vector(142.1, 0.0, 229.3),
+ Vector(154.0, 0.0, 276.3),
+ Vector(163.6, 0.0, 333.4),
+ Vector(173.8, 0.0, 411.5),
+ Vector(186.0, 0.0, 491.7),
+ Vector(200.2, 0.0, 591.8),
+ Vector(215.4, 0.0, 714.8),
+ Vector(224.1, 0.0, 650.0),
+ Vector(234.1, 0.0, 575.8),
+ Vector(251.9, 0.0, 425.5),
+ Vector(240.8, 0.0, 273.3),
+ Vector(235.9, 0.0, 243.2),
+ Vector(197.3, 0.0, 81.7),
+ Vector(188.8, 0.0, 37.6),
+ Vector(195.1, 0.0, 0.0),
+ Vector(278.8, 0.0, 0.0),
+ Vector(294.5, 0.0, 121.0),
+ Vector(308.4, 0.0, 184.3),
+ Vector(318.1, 0.0, 225.4),
+ Vector(322.0, 0.0, 235.2),
+ Vector(340.1, 0.0, 283.5),
+ Vector(349.0, 0.0, 341.4),
+ Vector(354.2, 0.0, 523.7),
+ Vector(383.1, 0.0, 719.7),
+ Vector(399.6, 0.0, 820.3),
+ Vector(381.2, 0.0, 1029.6),
+ Vector(385.6, 0.0, 1164.0),
+ Vector(390.1, 0.0, 1184.6),
+ Vector(398.3, 0.0, 1201.9),
+ Vector(430.2, 0.0, 1273.1),
+ Vector(438.2, 0.0, 1321.2),
+ Vector(441.3, 0.0, 1368.2),
+ Vector(428.1, 0.0, 1405.3),
+ Vector(395.0, 0.0, 1424.3),
+ Vector(365.5, 0.0, 1446.6),
+ Vector(349.8, 0.0, 1460.2),
+ Vector(345.6, 0.0, 1476.7),
+ Vector(337.9, 0.0, 1570.3),
+ Vector(332.8, 0.0, 1624.7),
+ Vector(322.2, 0.0, 1666.9),
+ Vector(216.2, 0.0, 1680.2),
+ Vector(163.5, 0.0, 1559.1),
+ Vector(179.8, 0.0, 1475.5),
+ Vector(195.6, 0.0, 1459.9),
+ Vector(193.1, 0.0, 1447.8),
+ Vector(171.0, 0.0, 1429.4),
+ Vector(132.3, 0.0, 1399.8),
+ Vector(96.8, 0.0, 1374.7),
+ Vector(74.0, 0.0, 1275.1),
+ Vector(46.2, 0.0, 1095.6),
+ Vector(38.0, 0.0, 1041.5),
+ Vector(25.2, 0.0, 958.5),
+ Vector(15.9, 0.0, 889.7),
+ Vector(2.5, 0.0, 842.1),
+ Vector(-5.8, 0.0, 785.4),
+ Vector(15.8, 0.0, 755.1),
+ Vector(38.0, 0.0, 750.4),
+ Vector(45.0, 0.0, 755.4),
+ Vector(53.1, 0.0, 736.1),
+ Vector(76.4, 0.0, 572.2),
+ Vector(83.6, 0.0, 512.0),
+ Vector(81.3, 0.0, 499.0),
+ Vector(74.0, 0.0, 460.9),
+ Vector(61.9, 0.0, 363.4),
+ Vector(53.4, 0.0, 269.3),
+ Vector(44.5, 0.0, 179.7),
+ Vector(25.6, 0.0, 121.6),
+ Vector(0.6, 0.0, 76.5),
+ Vector(-23.7, 0.0, 54.5),
+ Vector(-43.8, 0.0, 33.5),
+ Vector(-25.6, 0.0, 0.0),
+ Vector(117.9, 0.0, 0.0),
+ Vector(131.2, 0.0, 175.8),
]
if loc:
pts = [p.add(loc) for p in pts]
return pts
def displayHumanFigure(self, wp):
- """ Display the human figure at the grid corner.
+ """Display the human figure at the grid corner.
The silhouette is displayed only if:
- preference BaseApp/Preferences/Mod/Draft/gridBorder is True;
- preference BaseApp/Preferences/Mod/Draft/gridShowHuman is True;
@@ -1362,10 +1446,12 @@ class gridTracker(Tracker):
bound = (numlines // 2) * self.space
pts = []
pidx = []
- if params.get_param("gridBorder") \
- and params.get_param("gridShowHuman") \
- and wp.axis.getAngle(FreeCAD.Vector(0,0,1)) < 0.001:
- loc = FreeCAD.Vector(-bound+self.space/2,-bound+self.space/2,0)
+ if (
+ params.get_param("gridBorder")
+ and params.get_param("gridShowHuman")
+ and wp.axis.getAngle(FreeCAD.Vector(0, 0, 1)) < 0.001
+ ):
+ loc = FreeCAD.Vector(-bound + self.space / 2, -bound + self.space / 2, 0)
hpts = self.get_human_figure(loc)
pts.extend([tuple(p) for p in hpts])
pidx.append(len(hpts))
@@ -1375,21 +1461,21 @@ class gridTracker(Tracker):
def setAxesColor(self, wp):
"""set axes color"""
- cols = [0,0]
+ cols = [0, 0]
if params.get_param("coloredGridAxes"):
- if round(wp.u.getAngle(FreeCAD.Vector(1,0,0)),2) in (0,3.14):
+ if round(wp.u.getAngle(FreeCAD.Vector(1, 0, 0)), 2) in (0, 3.14):
cols[0] = 1
- elif round(wp.u.getAngle(FreeCAD.Vector(0,1,0)),2) in (0,3.14):
+ elif round(wp.u.getAngle(FreeCAD.Vector(0, 1, 0)), 2) in (0, 3.14):
cols[0] = 2
- elif round(wp.u.getAngle(FreeCAD.Vector(0,0,1)),2) in (0,3.14):
+ elif round(wp.u.getAngle(FreeCAD.Vector(0, 0, 1)), 2) in (0, 3.14):
cols[0] = 3
- if round(wp.v.getAngle(FreeCAD.Vector(1,0,0)),2) in (0,3.14):
+ if round(wp.v.getAngle(FreeCAD.Vector(1, 0, 0)), 2) in (0, 3.14):
cols[1] = 1
- elif round(wp.v.getAngle(FreeCAD.Vector(0,1,0)),2) in (0,3.14):
+ elif round(wp.v.getAngle(FreeCAD.Vector(0, 1, 0)), 2) in (0, 3.14):
cols[1] = 2
- elif round(wp.v.getAngle(FreeCAD.Vector(0,0,1)),2) in (0,3.14):
+ elif round(wp.v.getAngle(FreeCAD.Vector(0, 0, 1)), 2) in (0, 3.14):
cols[1] = 3
- self.lines3.materialIndex.setValues(0,2,cols)
+ self.lines3.materialIndex.setValues(0, 2, cols)
def setSize(self, size):
"""Set size of the lines and update."""
@@ -1466,15 +1552,14 @@ class boxTracker(Tracker):
self.baseline = line
self.update()
if shaded:
- super().__init__(children=[self.trans, m, self.cube],
- name="boxTracker")
+ super().__init__(children=[self.trans, m, self.cube], name="boxTracker")
else:
- super().__init__(children=[self.trans, w, self.cube],
- name="boxTracker")
+ super().__init__(children=[self.trans, w, self.cube], name="boxTracker")
def update(self, line=None, normal=None):
"""Update the tracker."""
import DraftGeomUtils
+
if not normal:
normal = self._get_wp().axis
if line:
@@ -1491,14 +1576,13 @@ class boxTracker(Tracker):
return
self.cube.width.setValue(lvec.Length)
bp = bp.add(lvec.multiply(0.5))
- bp = bp.add(DraftVecUtils.scaleTo(normal, self.cube.depth.getValue()/2.0))
+ bp = bp.add(DraftVecUtils.scaleTo(normal, self.cube.depth.getValue() / 2.0))
self.pos(bp)
tol = 1e-6
if lvec.Length > tol and normal.Length > tol:
lvec.normalize()
normal.normalize()
- if not lvec.isEqual(normal, tol) \
- and not lvec.isEqual(normal.negative(), tol):
+ if not lvec.isEqual(normal, tol) and not lvec.isEqual(normal.negative(), tol):
rot = FreeCAD.Rotation(lvec, FreeCAD.Vector(), normal, "XZY")
self.trans.rotation.setValue(rot.Q)
@@ -1545,8 +1629,7 @@ class radiusTracker(Tracker):
self.sphere = coin.SoSphere()
self.sphere.radius.setValue(radius)
self.baseline = None
- super().__init__(children=[self.trans, m, self.sphere],
- name="radiusTracker")
+ super().__init__(children=[self.trans, m, self.sphere], name="radiusTracker")
def update(self, arg1, arg2=None):
"""Update the tracker."""
@@ -1566,6 +1649,7 @@ class archDimTracker(Tracker):
def __init__(self, p1=FreeCAD.Vector(0, 0, 0), p2=FreeCAD.Vector(1, 0, 0), mode=1):
import SketcherGui
+
self.transform = coin.SoMatrixTransform()
self.dimnode = coin.SoType.fromName("SoDatumLabel").createInstance()
p1node = coin.SbVec3f([p1.x, p1.y, p1.z])
@@ -1610,27 +1694,28 @@ class archDimTracker(Tracker):
# set the offset sign to prevent the dim line from intersecting the curve near the cursor
sign_dx = math.copysign(1, (p2.sub(p1)).x)
sign_dy = math.copysign(1, (p2.sub(p1)).y)
- sign = sign_dx*sign_dy
+ sign = sign_dx * sign_dy
if self.mode == 2:
self.Distance = abs((p2.sub(p1)).x)
- self.param1.setValue(sign*self.offset)
+ self.param1.setValue(sign * self.offset)
elif self.mode == 3:
self.Distance = abs((p2.sub(p1)).y)
- self.param1.setValue(-1*sign*self.offset)
+ self.param1.setValue(-1 * sign * self.offset)
else:
self.Distance = (p2.sub(p1)).Length
text = FreeCAD.Units.Quantity(self.Distance, FreeCAD.Units.Length).UserString
self.matrix.setValue(*plane.get_placement().Matrix.transposed().A)
- self.string.setValue(text.encode('utf8'))
+ self.string.setValue(text.encode("utf8"))
# change the text position to external depending on the distance and scale values
volume = self.camera.getViewVolume()
- scale = self.view.getSize()[1]/volume.getHeight()
- if scale*self.Distance > self.size_pixel*len(text):
+ scale = self.view.getSize()[1] / volume.getHeight()
+ if scale * self.Distance > self.size_pixel * len(text):
self.param2.setValue(0)
else:
- self.param2.setValue(1/2*self.Distance + 3/5*self.size_pixel*len(text)/scale)
-
+ self.param2.setValue(
+ 1 / 2 * self.Distance + 3 / 5 * self.size_pixel * len(text) / scale
+ )
def setMode(self, mode=1):
"""Set the mode.
@@ -1666,4 +1751,5 @@ class archDimTracker(Tracker):
else:
return Vector(self.pnts.getValues()[-1].getValue())
+
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_trimex.py b/src/Mod/Draft/draftguitools/gui_trimex.py
index bacea52ad4..2b67eb63e0 100644
--- a/src/Mod/Draft/draftguitools/gui_trimex.py
+++ b/src/Mod/Draft/draftguitools/gui_trimex.py
@@ -71,11 +71,14 @@ class Trimex(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_Trimex',
- 'Accel': "T, R",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Trimex", "Trimex"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Trimex",
- "Trims or extends the selected object, or extrudes single faces")}
+ return {
+ "Pixmap": "Draft_Trimex",
+ "Accel": "T, R",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Trimex", "Trimex"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Trimex", "Trims or extends the selected object, or extrudes single faces"
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -90,9 +93,7 @@ class Trimex(gui_base_original.Modifier):
if not Gui.Selection.getSelection():
self.ui.selectUi(on_close_call=self.finish)
_msg(translate("draft", "Select objects to trim or extend"))
- self.call = \
- self.view.addEventCallback("SoEvent",
- gui_tool_utils.selectObject)
+ self.call = self.view.addEventCallback("SoEvent", gui_tool_utils.selectObject)
else:
self.proceed()
@@ -106,7 +107,7 @@ class Trimex(gui_base_original.Modifier):
self.finish()
return
self.obj = sel[0]
- self.ui.trimUi(title=translate("draft",self.featureName))
+ self.ui.trimUi(title=translate("draft", self.featureName))
self.linetrack = trackers.lineTracker()
import DraftGeomUtils
@@ -148,7 +149,7 @@ class Trimex(gui_base_original.Modifier):
else:
self.edges = self.obj.Shape.Edges
for e in self.edges:
- if isinstance(e.Curve,(Part.BSplineCurve, Part.BezierCurve)):
+ if isinstance(e.Curve, (Part.BSplineCurve, Part.BezierCurve)):
self.obj = None
self.finish()
_err(translate("draft", "Trimex does not support this object type"))
@@ -162,11 +163,9 @@ class Trimex(gui_base_original.Modifier):
sw = self.width
for e in self.edges:
if DraftGeomUtils.geomType(e) == "Line":
- self.ghost.append(trackers.lineTracker(scolor=sc,
- swidth=sw))
+ self.ghost.append(trackers.lineTracker(scolor=sc, swidth=sw))
else:
- self.ghost.append(trackers.arcTracker(scolor=sc,
- swidth=sw))
+ self.ghost.append(trackers.arcTracker(scolor=sc, swidth=sw))
if not self.ghost:
self.obj = None
self.finish()
@@ -210,25 +209,21 @@ class Trimex(gui_base_original.Modifier):
if gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_snap_key()):
self.snapped = None
else:
- self.snapped = self.view.getObjectInfo((arg["Position"][0],
- arg["Position"][1]))
+ self.snapped = self.view.getObjectInfo((arg["Position"][0], arg["Position"][1]))
if self.extrudeMode:
dist, ang = (self.extrude(self.shift), None)
else:
# If the geomType of the edge is "Line" ang will be None,
# else dist will be None.
- dist, ang = self.redraw(self.point, self.snapped,
- self.shift, self.alt)
+ dist, ang = self.redraw(self.point, self.snapped, self.shift, self.alt)
if dist:
self.ui.labelRadius.setText(translate("draft", "Distance"))
- self.ui.radiusValue.setToolTip(translate("draft",
- "Offset distance"))
+ self.ui.radiusValue.setToolTip(translate("draft", "Offset distance"))
self.ui.setRadiusValue(dist, unit="Length")
elif ang:
self.ui.labelRadius.setText(translate("draft", "Angle"))
- self.ui.radiusValue.setToolTip(translate("draft",
- "Offset angle"))
+ self.ui.radiusValue.setToolTip(translate("draft", "Offset angle"))
self.ui.setRadiusValue(ang, unit="Angle")
else:
# both dist and ang are None, this indicates an impossible
@@ -246,8 +241,7 @@ class Trimex(gui_base_original.Modifier):
if gui_tool_utils.hasMod(arg, gui_tool_utils.get_mod_snap_key()):
self.snapped = None
else:
- self.snapped = self.view.getObjectInfo((cursor[0],
- cursor[1]))
+ self.snapped = self.view.getObjectInfo((cursor[0], cursor[1]))
self.trimObject()
self.finish()
@@ -263,7 +257,7 @@ class Trimex(gui_base_original.Modifier):
else:
delta = dvec
if self.force and delta.Length:
- ratio = self.force/delta.Length
+ ratio = self.force / delta.Length
delta.multiply(ratio)
if real:
return delta
@@ -273,7 +267,7 @@ class Trimex(gui_base_original.Modifier):
self.ghost[1].p2(self.newpoint + dvec)
# Update the vertex lineTrackers:
for i in range(2, len(self.ghost)):
- base = self.obj.Shape.Vertexes[i-2].Point
+ base = self.obj.Shape.Vertexes[i - 2].Point
self.ghost[i].p1(base)
self.ghost[i].p2(base + delta)
return delta.Length
@@ -299,7 +293,7 @@ class Trimex(gui_base_original.Modifier):
npoint = self.activePoint
else:
npoint = DraftGeomUtils.findClosest(point, vlist)
- if npoint > len(self.edges)/2:
+ if npoint > len(self.edges) / 2:
reverse = True
if alt:
reverse = not reverse
@@ -308,7 +302,7 @@ class Trimex(gui_base_original.Modifier):
# sorting out directions
if reverse and (npoint > 0):
npoint = npoint - 1
- if (npoint > len(self.edges) - 1):
+ if npoint > len(self.edges) - 1:
edge = self.edges[-1]
ghost = self.ghost[-1]
else:
@@ -382,8 +376,7 @@ class Trimex(gui_base_original.Modifier):
if real:
if self.force:
angle = math.radians(self.force)
- newray = DraftVecUtils.rotate(App.Vector(rad, 0, 0),
- -angle)
+ newray = DraftVecUtils.rotate(App.Vector(rad, 0, 0), -angle)
self.newpoint = App.Vector.add(center, newray)
chord = self.newpoint.sub(v2)
perp = chord.cross(App.Vector(0, 0, 1))
@@ -429,15 +422,14 @@ class Trimex(gui_base_original.Modifier):
if self.extrudeMode:
delta = self.extrude(self.shift, real=True)
- #print("delta", delta)
+ # print("delta", delta)
self.doc.openTransaction("Extrude")
Gui.addModule("Draft")
obj = Draft.extrude(self.obj, delta, solid=True)
self.doc.commitTransaction()
self.obj = obj
else:
- edges = self.redraw(self.point, self.snapped,
- self.shift, self.alt, real=True)
+ edges = self.redraw(self.point, self.snapped, self.shift, self.alt, real=True)
newshape = Part.Wire(edges)
self.doc.openTransaction("Trim/extend")
if utils.getType(self.obj) in ["Wire", "BSpline"]:
@@ -459,21 +451,21 @@ class Trimex(gui_base_original.Modifier):
if self.placement:
np = invpl.multVec(np)
p.append(np)
- if ((p[0].x == self.obj.X1)
- and (p[0].y == self.obj.Y1)
- and (p[0].z == self.obj.Z1)):
+ if (p[0].x == self.obj.X1) and (p[0].y == self.obj.Y1) and (p[0].z == self.obj.Z1):
self.obj.X2 = p[-1].x
self.obj.Y2 = p[-1].y
self.obj.Z2 = p[-1].z
- elif ((p[-1].x == self.obj.X1)
- and (p[-1].y == self.obj.Y1)
- and (p[-1].z == self.obj.Z1)):
+ elif (
+ (p[-1].x == self.obj.X1)
+ and (p[-1].y == self.obj.Y1)
+ and (p[-1].z == self.obj.Z1)
+ ):
self.obj.X2 = p[0].x
self.obj.Y2 = p[0].y
self.obj.Z2 = p[0].z
- elif ((p[0].x == self.obj.X2)
- and (p[0].y == self.obj.Y2)
- and (p[0].z == self.obj.Z2)):
+ elif (
+ (p[0].x == self.obj.X2) and (p[0].y == self.obj.Y2) and (p[0].z == self.obj.Z2)
+ ):
self.obj.X1 = p[-1].x
self.obj.Y1 = p[-1].y
self.obj.Z1 = p[-1].z
@@ -504,14 +496,15 @@ class Trimex(gui_base_original.Modifier):
wires = []
for obj in objectslist:
if not utils.getType(obj) in ["Wire", "Circle"]:
- _err(translate("draft",
- "Unable to trim these objects, "
- "only Draft wires and arcs are supported"))
+ _err(
+ translate(
+ "draft",
+ "Unable to trim these objects, " "only Draft wires and arcs are supported",
+ )
+ )
return
if len(obj.Shape.Wires) > 1:
- _err(translate("draft",
- "Unable to trim these objects, "
- "too many wires"))
+ _err(translate("draft", "Unable to trim these objects, " "too many wires"))
return
if len(obj.Shape.Wires) == 1:
wires.append(obj.Shape.Wires[0])
@@ -555,17 +548,17 @@ class Trimex(gui_base_original.Modifier):
la = last2
if utils.getType(obj) == "Wire":
if la:
- pts = obj.Points[:ed + 1] + ints
+ pts = obj.Points[: ed + 1] + ints
else:
- pts = ints + obj.Points[ed + 1:]
+ pts = ints + obj.Points[ed + 1 :]
obj.Points = pts
else:
vec = ints[0].sub(obj.Placement.Base)
vec = obj.Placement.inverse().Rotation.multVec(vec)
_x = App.Vector(1, 0, 0)
- _ang = -DraftVecUtils.angle(vec,
- obj.Placement.Rotation.multVec(_x),
- obj.Shape.Edges[0].Curve.Axis)
+ _ang = -DraftVecUtils.angle(
+ vec, obj.Placement.Rotation.multVec(_x), obj.Shape.Edges[0].Curve.Axis
+ )
ang = math.degrees(_ang)
if la:
obj.LastAngle = ang
@@ -602,6 +595,6 @@ class Trimex(gui_base_original.Modifier):
self.finish()
-Gui.addCommand('Draft_Trimex', Trimex())
+Gui.addCommand("Draft_Trimex", Trimex())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_upgrade.py b/src/Mod/Draft/draftguitools/gui_upgrade.py
index e57d9308d2..6cff995c47 100644
--- a/src/Mod/Draft/draftguitools/gui_upgrade.py
+++ b/src/Mod/Draft/draftguitools/gui_upgrade.py
@@ -53,10 +53,15 @@ class Upgrade(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_Upgrade',
- 'Accel': "U, P",
- 'MenuText': QT_TRANSLATE_NOOP("Draft_Upgrade", "Upgrade"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_Upgrade", "Upgrades the selected objects into more complex shapes.\nThe result of the operation depends on the types of objects, which may be able to be upgraded several times in a row.\nFor example, it can join the selected objects into one, convert simple edges into parametric polylines,\nconvert closed edges into filled faces and parametric polygons, and merge faces into a single face.")}
+ return {
+ "Pixmap": "Draft_Upgrade",
+ "Accel": "U, P",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_Upgrade", "Upgrade"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_Upgrade",
+ "Upgrades the selected objects into more complex shapes.\nThe result of the operation depends on the types of objects, which may be able to be upgraded several times in a row.\nFor example, it can join the selected objects into one, convert simple edges into parametric polylines,\nconvert closed edges into filled faces and parametric polygons, and merge faces into a single face.",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -76,18 +81,16 @@ class Upgrade(gui_base_original.Modifier):
self.end_callbacks(self.call)
if Gui.Selection.getSelection():
Gui.addModule("Draft")
- _cmd = 'Draft.upgrade'
- _cmd += '('
- _cmd += 'FreeCADGui.Selection.getSelection(), '
- _cmd += 'delete=True'
- _cmd += ')'
- _cmd_list = ['_objs_ = ' + _cmd,
- 'FreeCAD.ActiveDocument.recompute()']
- self.commit(translate("draft", "Upgrade"),
- _cmd_list)
+ _cmd = "Draft.upgrade"
+ _cmd += "("
+ _cmd += "FreeCADGui.Selection.getSelection(), "
+ _cmd += "delete=True"
+ _cmd += ")"
+ _cmd_list = ["_objs_ = " + _cmd, "FreeCAD.ActiveDocument.recompute()"]
+ self.commit(translate("draft", "Upgrade"), _cmd_list)
self.finish()
-Gui.addCommand('Draft_Upgrade', Upgrade())
+Gui.addCommand("Draft_Upgrade", Upgrade())
## @}
diff --git a/src/Mod/Draft/draftguitools/gui_wire2spline.py b/src/Mod/Draft/draftguitools/gui_wire2spline.py
index e6c1710711..340e58c3e3 100644
--- a/src/Mod/Draft/draftguitools/gui_wire2spline.py
+++ b/src/Mod/Draft/draftguitools/gui_wire2spline.py
@@ -60,9 +60,14 @@ class WireToBSpline(gui_base_original.Modifier):
def GetResources(self):
"""Set icon, menu and tooltip."""
- return {'Pixmap': 'Draft_WireToBSpline',
- 'MenuText': QT_TRANSLATE_NOOP("Draft_WireToBSpline", "Convert Wire/B-Spline"),
- 'ToolTip': QT_TRANSLATE_NOOP("Draft_WireToBSpline", "Converts the selected polyline to a B-spline, or the selected B-spline to a polyline")}
+ return {
+ "Pixmap": "Draft_WireToBSpline",
+ "MenuText": QT_TRANSLATE_NOOP("Draft_WireToBSpline", "Convert Wire/B-Spline"),
+ "ToolTip": QT_TRANSLATE_NOOP(
+ "Draft_WireToBSpline",
+ "Converts the selected polyline to a B-spline, or the selected B-spline to a polyline",
+ ),
+ }
def Activated(self):
"""Execute when the command is called."""
@@ -76,7 +81,7 @@ class WireToBSpline(gui_base_original.Modifier):
# in order to properly open a transaction and commit it.
selection = Gui.Selection.getSelection()
if selection:
- if utils.getType(selection[0]) in ['Wire', 'BSpline']:
+ if utils.getType(selection[0]) in ["Wire", "BSpline"]:
super(WireToBSpline, self).Activated(name="Convert polyline/B-spline")
if self.doc:
self.obj = Gui.Selection.getSelection()
@@ -88,18 +93,20 @@ class WireToBSpline(gui_base_original.Modifier):
self.Points = self.obj.Points
self.closed = self.obj.Closed
n = None
- if utils.getType(self.obj) == 'Wire':
- n = Draft.make_bspline(self.Points,
- closed=self.closed,
- placement=self.pl)
- elif utils.getType(self.obj) == 'BSpline':
+ if utils.getType(self.obj) == "Wire":
+ n = Draft.make_bspline(
+ self.Points, closed=self.closed, placement=self.pl
+ )
+ elif utils.getType(self.obj) == "BSpline":
self.bs2wire = True
- n = Draft.make_wire(self.Points,
- closed=self.closed,
- placement=self.pl,
- face=None,
- support=None,
- bs2wire=self.bs2wire)
+ n = Draft.make_wire(
+ self.Points,
+ closed=self.closed,
+ placement=self.pl,
+ face=None,
+ support=None,
+ bs2wire=self.bs2wire,
+ )
if n:
Draft.formatObject(n, self.obj)
self.doc.recompute()
@@ -107,6 +114,6 @@ class WireToBSpline(gui_base_original.Modifier):
self.finish()
-Gui.addCommand('Draft_WireToBSpline', WireToBSpline())
+Gui.addCommand("Draft_WireToBSpline", WireToBSpline())
## @}
diff --git a/src/Mod/Draft/draftmake/make_arc_3points.py b/src/Mod/Draft/draftmake/make_arc_3points.py
index 30947900fe..311ed4a186 100644
--- a/src/Mod/Draft/draftmake/make_arc_3points.py
+++ b/src/Mod/Draft/draftmake/make_arc_3points.py
@@ -84,37 +84,35 @@ def make_arc_3points(points, placement=None, face=False, support=None, primitive
try:
utils.type_check([(points, (list, tuple))], name=_name)
except TypeError:
- _err(translate("draft","Points:") + " {}".format(points))
- _err(translate("draft","Wrong input: must be a list or tuple of 3 points exactly."))
+ _err(translate("draft", "Points:") + " {}".format(points))
+ _err(translate("draft", "Wrong input: must be a list or tuple of 3 points exactly."))
return None
if len(points) != 3:
- _err(translate("draft","Points:") + " {}".format(points))
- _err(translate("draft","Wrong input: must be list or tuple of 3 points exactly."))
+ _err(translate("draft", "Points:") + " {}".format(points))
+ _err(translate("draft", "Wrong input: must be list or tuple of 3 points exactly."))
return None
p1, p2, p3 = points
try:
- utils.type_check([(p1, App.Vector),
- (p2, App.Vector),
- (p3, App.Vector)], name=_name)
+ utils.type_check([(p1, App.Vector), (p2, App.Vector), (p3, App.Vector)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: incorrect type of points."))
+ _err(translate("draft", "Wrong input: incorrect type of points."))
return None
if placement is not None:
try:
utils.type_check([(placement, App.Placement)], name=_name)
except TypeError:
- _err(translate("draft","Placement:") + " {}".format(placement))
- _err(translate("draft","Wrong input: incorrect type of placement."))
+ _err(translate("draft", "Placement:") + " {}".format(placement))
+ _err(translate("draft", "Wrong input: incorrect type of placement."))
return None
try:
edge = Part.Arc(p1, p2, p3).toShape()
except Part.OCCError as error:
- _err(translate("draft","Cannot generate shape:") + " " + "{}".format(error))
+ _err(translate("draft", "Cannot generate shape:") + " " + "{}".format(error))
return None
if primitive:
@@ -124,4 +122,5 @@ def make_arc_3points(points, placement=None, face=False, support=None, primitive
return make_circle.make_circle(edge, placement=placement, face=face, support=support)
+
## @}
diff --git a/src/Mod/Draft/draftmake/make_array.py b/src/Mod/Draft/draftmake/make_array.py
index 5183616923..41c7cd4e15 100644
--- a/src/Mod/Draft/draftmake/make_array.py
+++ b/src/Mod/Draft/draftmake/make_array.py
@@ -43,10 +43,7 @@ if App.GuiUp:
from draftviewproviders.view_draftlink import ViewProviderDraftLink
-def make_array(base_object,
- arg1, arg2, arg3,
- arg4=None, arg5=None, arg6=None,
- use_link=True):
+def make_array(base_object, arg1, arg2, arg3, arg4=None, arg5=None, arg6=None, use_link=True):
"""Create a Draft Array of the given object.
Rectangular array
@@ -82,14 +79,13 @@ def make_array(base_object,
"""
found, doc = utils.find_doc(App.activeDocument())
if not found:
- _err(translate("draft","No active document. Aborting."))
+ _err(translate("draft", "No active document. Aborting."))
return None
if use_link:
# The Array class must be called in this special way
# to make it a LinkArray
- new_obj = doc.addObject("Part::FeaturePython", "Array",
- Array(None), None, True)
+ new_obj = doc.addObject("Part::FeaturePython", "Array", Array(None), None, True)
else:
new_obj = doc.addObject("Part::FeaturePython", "Array")
Array(new_obj)
@@ -129,7 +125,9 @@ def make_array(base_object,
ViewProviderDraftLink(new_obj.ViewObject)
else:
if new_obj.ArrayType == "circular":
- new_obj.Proxy.execute(new_obj) # Updates Count which is required for correct DiffuseColor.
+ new_obj.Proxy.execute(
+ new_obj
+ ) # Updates Count which is required for correct DiffuseColor.
ViewProviderDraftArray(new_obj.ViewObject)
gui_utils.format_object(new_obj, new_obj.Base)
new_obj.ViewObject.Proxy.resetColors(new_obj.ViewObject)
@@ -139,17 +137,17 @@ def make_array(base_object,
return new_obj
-def makeArray(baseobject,
- arg1, arg2, arg3,
- arg4=None, arg5=None, arg6=None,
- name="Array", use_link=False):
+def makeArray(
+ baseobject, arg1, arg2, arg3, arg4=None, arg5=None, arg6=None, name="Array", use_link=False
+):
"""Create an Array. DEPRECATED. Use 'make_array'."""
- _wrn("Do not use this function directly; instead, use "
- "'make_ortho_array', 'make_polar_array', "
- "or 'make_circular_array'.")
+ _wrn(
+ "Do not use this function directly; instead, use "
+ "'make_ortho_array', 'make_polar_array', "
+ "or 'make_circular_array'."
+ )
+
+ return make_array(baseobject, arg1, arg2, arg3, arg4, arg5, arg6, use_link)
- return make_array(baseobject,
- arg1, arg2, arg3,
- arg4, arg5, arg6, use_link)
## @}
diff --git a/src/Mod/Draft/draftmake/make_bezcurve.py b/src/Mod/Draft/draftmake/make_bezcurve.py
index 9337104932..c4b5ee04f6 100644
--- a/src/Mod/Draft/draftmake/make_bezcurve.py
+++ b/src/Mod/Draft/draftmake/make_bezcurve.py
@@ -38,9 +38,7 @@ if App.GuiUp:
from draftviewproviders.view_bezcurve import ViewProviderBezCurve
-def make_bezcurve(pointslist,
- closed=False, placement=None, face=None, support=None,
- degree=None):
+def make_bezcurve(pointslist, closed=False, placement=None, face=None, support=None, degree=None):
"""make_bezcurve(pointslist, [closed], [placement])
Creates a Bezier Curve object from the given list of vectors.
@@ -72,15 +70,17 @@ def make_bezcurve(pointslist,
if not App.ActiveDocument:
App.Console.PrintError("No active document. Aborting\n")
return
- if not isinstance(pointslist,list):
+ if not isinstance(pointslist, list):
nlist = []
for v in pointslist.Vertexes:
nlist.append(v.Point)
pointslist = nlist
if placement:
- utils.type_check([(placement,App.Placement)], "make_bezcurve")
- if len(pointslist) == 2: fname = "Line"
- else: fname = "BezCurve"
+ utils.type_check([(placement, App.Placement)], "make_bezcurve")
+ if len(pointslist) == 2:
+ fname = "Line"
+ else:
+ fname = "BezCurve"
obj = App.ActiveDocument.addObject("Part::FeaturePython", fname)
obj.addExtension("Part::AttachExtensionPython")
BezCurve(obj)
@@ -89,18 +89,19 @@ def make_bezcurve(pointslist,
obj.Degree = degree
else:
import Part
- obj.Degree = min((len(pointslist)-(1 * (not closed))),
- Part.BezierCurve().MaxDegree)
+
+ obj.Degree = min((len(pointslist) - (1 * (not closed))), Part.BezierCurve().MaxDegree)
obj.Closed = closed
obj.AttachmentSupport = support
if face is not None:
obj.MakeFace = face
obj.Proxy.resetcontinuity(obj)
- if placement: obj.Placement = placement
+ if placement:
+ obj.Placement = placement
if App.GuiUp:
ViewProviderBezCurve(obj.ViewObject)
-# if not face: obj.ViewObject.DisplayMode = "Wireframe"
-# obj.ViewObject.DisplayMode = "Wireframe"
+ # if not face: obj.ViewObject.DisplayMode = "Wireframe"
+ # obj.ViewObject.DisplayMode = "Wireframe"
gui_utils.format_object(obj)
gui_utils.select(obj)
diff --git a/src/Mod/Draft/draftmake/make_bspline.py b/src/Mod/Draft/draftmake/make_bspline.py
index 265eb417f5..593866b49b 100644
--- a/src/Mod/Draft/draftmake/make_bspline.py
+++ b/src/Mod/Draft/draftmake/make_bspline.py
@@ -67,16 +67,16 @@ def make_bspline(pointslist, closed=False, placement=None, face=None, support=No
if not App.ActiveDocument:
App.Console.PrintError("No active document. Aborting\n")
return
- if not isinstance(pointslist,list):
+ if not isinstance(pointslist, list):
nlist = []
for v in pointslist.Vertexes:
nlist.append(v.Point)
pointslist = nlist
if len(pointslist) < 2:
_err = "Draft.make_bspline: not enough points"
- App.Console.PrintError(translate("draft", _err)+"\n")
+ App.Console.PrintError(translate("draft", _err) + "\n")
return
- if (pointslist[0] == pointslist[-1]):
+ if pointslist[0] == pointslist[-1]:
if len(pointslist) > 2:
closed = True
pointslist.pop()
@@ -85,13 +85,15 @@ def make_bspline(pointslist, closed=False, placement=None, face=None, support=No
else:
# len == 2 and first == last GIGO
_err = "Draft.make_bspline: Invalid pointslist"
- App.Console.PrintError(translate("Draft", _err)+"\n")
+ App.Console.PrintError(translate("Draft", _err) + "\n")
return
# should have sensible parms from here on
if placement:
- utils.type_check([(placement,App.Placement)], "make_bspline")
- if len(pointslist) == 2: fname = "Line"
- else: fname = "BSpline"
+ utils.type_check([(placement, App.Placement)], "make_bspline")
+ if len(pointslist) == 2:
+ fname = "Line"
+ else:
+ fname = "BSpline"
obj = App.ActiveDocument.addObject("Part::FeaturePython", fname)
obj.addExtension("Part::AttachExtensionPython")
BSpline(obj)
@@ -100,7 +102,8 @@ def make_bspline(pointslist, closed=False, placement=None, face=None, support=No
obj.AttachmentSupport = support
if face is not None:
obj.MakeFace = face
- if placement: obj.Placement = placement
+ if placement:
+ obj.Placement = placement
if App.GuiUp:
ViewProviderBSpline(obj.ViewObject)
gui_utils.format_object(obj)
diff --git a/src/Mod/Draft/draftmake/make_circle.py b/src/Mod/Draft/draftmake/make_circle.py
index 71f02e6e1c..817cc0868b 100644
--- a/src/Mod/Draft/draftmake/make_circle.py
+++ b/src/Mod/Draft/draftmake/make_circle.py
@@ -54,7 +54,7 @@ def _get_normal(axis, ref_rot):
local_comp_vec = App.Vector(1, 0, 0)
comp_vec = ref_rot.multVec(local_comp_vec)
axis = App.Vector(axis) # create independent copy
- if axis.getAngle(comp_vec) > math.pi/2:
+ if axis.getAngle(comp_vec) > math.pi / 2:
axis = axis.negative()
return axis
@@ -104,10 +104,9 @@ def make_circle(radius, placement=None, face=None, startangle=None, endangle=Non
return
if placement:
- utils.type_check([(placement,App.Placement)], "make_circle")
+ utils.type_check([(placement, App.Placement)], "make_circle")
- if (isinstance(radius, Part.Edge) and len(radius.Vertexes) > 1) \
- or startangle != endangle:
+ if (isinstance(radius, Part.Edge) and len(radius.Vertexes) > 1) or startangle != endangle:
name = "Arc"
else:
name = "Circle"
diff --git a/src/Mod/Draft/draftmake/make_circulararray.py b/src/Mod/Draft/draftmake/make_circulararray.py
index 0e105c6c2f..bba512b29b 100644
--- a/src/Mod/Draft/draftmake/make_circulararray.py
+++ b/src/Mod/Draft/draftmake/make_circulararray.py
@@ -35,11 +35,16 @@ from draftutils.messages import _err
from draftutils.translate import translate
-def make_circular_array(base_object,
- r_distance=100, tan_distance=50,
- number=3, symmetry=1,
- axis=App.Vector(0, 0, 1), center=App.Vector(0, 0, 0),
- use_link=True):
+def make_circular_array(
+ base_object,
+ r_distance=100,
+ tan_distance=50,
+ number=3,
+ symmetry=1,
+ axis=App.Vector(0, 0, 1),
+ center=App.Vector(0, 0, 0),
+ use_link=True,
+):
"""Create a circular array from the given object.
Parameters
@@ -122,38 +127,46 @@ def make_circular_array(base_object,
found, base_object = utils.find_object(base_object, doc=App.activeDocument())
if not found:
- _err(translate("draft","Wrong input: base_object not in document."))
+ _err(translate("draft", "Wrong input: base_object not in document."))
return None
try:
- utils.type_check([(r_distance, (int, float, App.Units.Quantity)),
- (tan_distance, (int, float, App.Units.Quantity))],
- name=_name)
+ utils.type_check(
+ [
+ (r_distance, (int, float, App.Units.Quantity)),
+ (tan_distance, (int, float, App.Units.Quantity)),
+ ],
+ name=_name,
+ )
except TypeError:
- _err(translate("draft","Wrong input: must be a number or quantity."))
+ _err(translate("draft", "Wrong input: must be a number or quantity."))
return None
try:
- utils.type_check([(number, int),
- (symmetry, int)], name=_name)
+ utils.type_check([(number, int), (symmetry, int)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be an integer number."))
+ _err(translate("draft", "Wrong input: must be an integer number."))
return None
try:
- utils.type_check([(axis, App.Vector),
- (center, App.Vector)], name=_name)
+ utils.type_check([(axis, App.Vector), (center, App.Vector)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a vector."))
+ _err(translate("draft", "Wrong input: must be a vector."))
return None
use_link = bool(use_link)
- new_obj = make_array.make_array(base_object,
- arg1=r_distance, arg2=tan_distance,
- arg3=axis, arg4=center,
- arg5=number, arg6=symmetry,
- use_link=use_link)
+ new_obj = make_array.make_array(
+ base_object,
+ arg1=r_distance,
+ arg2=tan_distance,
+ arg3=axis,
+ arg4=center,
+ arg5=number,
+ arg6=symmetry,
+ use_link=use_link,
+ )
return new_obj
+
## @}
diff --git a/src/Mod/Draft/draftmake/make_clone.py b/src/Mod/Draft/draftmake/make_clone.py
index 2c5bf5c9eb..dabb1fdadb 100644
--- a/src/Mod/Draft/draftmake/make_clone.py
+++ b/src/Mod/Draft/draftmake/make_clone.py
@@ -64,19 +64,23 @@ def make_clone(obj, delta=None, forcedraft=False):
if prefix:
prefix = prefix.strip() + " "
- if not isinstance(obj,list):
+ if not isinstance(obj, list):
obj = [obj]
- if len(obj) == 1 \
- and obj[0].isDerivedFrom("Part::Part2DObject") \
- and utils.get_type(obj[0]) not in ["BezCurve", "BSpline", "Wire"]:
+ if (
+ len(obj) == 1
+ and obj[0].isDerivedFrom("Part::Part2DObject")
+ and utils.get_type(obj[0]) not in ["BezCurve", "BSpline", "Wire"]
+ ):
# "BezCurve", "BSpline" and "Wire" objects created with < v1.1
# are "Part::Part2DObject" objects but they need not be 2D.
cl = App.ActiveDocument.addObject("Part::Part2DObjectPython", "Clone2D")
cl.Label = prefix + obj[0].Label + " (2D)"
- elif len(obj) == 1 \
- and (hasattr(obj[0], "CloneOf") or utils.get_type(obj[0]) == "BuildingPart") \
- and not forcedraft:
+ elif (
+ len(obj) == 1
+ and (hasattr(obj[0], "CloneOf") or utils.get_type(obj[0]) == "BuildingPart")
+ and not forcedraft
+ ):
# arch objects can be clones
try:
import Arch
@@ -87,13 +91,13 @@ def make_clone(obj, delta=None, forcedraft=False):
if utils.get_type(obj[0]) == "BuildingPart":
cl = Arch.makeComponent()
else:
- try: # new-style make function
+ try: # new-style make function
cl = getattr(Arch, "make_" + obj[0].Proxy.Type.lower())()
except Exception:
- try: # old-style make function
+ try: # old-style make function
cl = getattr(Arch, "make" + obj[0].Proxy.Type)()
except Exception:
- pass # not a standard Arch object... Fall back to Draft mode
+ pass # not a standard Arch object... Fall back to Draft mode
if cl:
base = utils.get_clone_base(obj[0])
cl.Label = prefix + base.Label
@@ -119,9 +123,9 @@ def make_clone(obj, delta=None, forcedraft=False):
cl.Objects = obj
if delta:
cl.Placement.move(delta)
- elif (len(obj) == 1) and hasattr(obj[0],"Placement"):
+ elif (len(obj) == 1) and hasattr(obj[0], "Placement"):
cl.Placement = obj[0].Placement
- if hasattr(cl,"LongName") and hasattr(obj[0],"LongName"):
+ if hasattr(cl, "LongName") and hasattr(obj[0], "LongName"):
cl.LongName = obj[0].LongName
if App.GuiUp:
ViewProviderClone(cl.ViewObject)
diff --git a/src/Mod/Draft/draftmake/make_copy.py b/src/Mod/Draft/draftmake/make_copy.py
index 5e45926bd7..20a3af2aea 100644
--- a/src/Mod/Draft/draftmake/make_copy.py
+++ b/src/Mod/Draft/draftmake/make_copy.py
@@ -58,7 +58,7 @@ def make_copy(obj, force=None, reparent=False, simple_copy=False):
newobj = None
- if simple_copy and hasattr(obj, 'Shape'):
+ if simple_copy and hasattr(obj, "Shape"):
# this was the old implementation that is actually not used by default
_name = utils.get_real_name(obj.Name)
newobj = App.ActiveDocument.addObject("Part::Feature", _name)
@@ -91,4 +91,5 @@ def make_copy(obj, force=None, reparent=False, simple_copy=False):
return newobj
+
## @}
diff --git a/src/Mod/Draft/draftmake/make_dimension.py b/src/Mod/Draft/draftmake/make_dimension.py
index 05f29d1d3d..005e768649 100644
--- a/src/Mod/Draft/draftmake/make_dimension.py
+++ b/src/Mod/Draft/draftmake/make_dimension.py
@@ -48,9 +48,10 @@ from draftutils.translate import translate
from draftobjects.dimension import LinearDimension, AngularDimension
if App.GuiUp:
- from draftviewproviders.view_dimension \
- import (ViewProviderLinearDimension,
- ViewProviderAngularDimension)
+ from draftviewproviders.view_dimension import (
+ ViewProviderLinearDimension,
+ ViewProviderAngularDimension,
+ )
def _get_flip_text_lin(p1, p2, wp, normal):
@@ -65,15 +66,15 @@ def _get_flip_text_lin(p1, p2, wp, normal):
return False
if math.isclose(abs(ang), math.pi, abs_tol=tol):
return True
- if math.isclose(ang, math.pi/2, abs_tol=tol):
+ if math.isclose(ang, math.pi / 2, abs_tol=tol):
return False
- if math.isclose(ang, -math.pi/2, abs_tol=tol):
+ if math.isclose(ang, -math.pi / 2, abs_tol=tol):
return True
# 90-180 (in that quadrant + 1st point closest to the origin):
- if math.pi/2 < ang < math.pi:
+ if math.pi / 2 < ang < math.pi:
return True
# 180-270:
- if -math.pi < ang < -math.pi/2:
+ if -math.pi < ang < -math.pi / 2:
return True
# 0-90 and 270-360:
return False
@@ -84,6 +85,7 @@ def _get_flip_text_ang(cen, sta, end, normal):
if not params.get_param("DimAutoFlipText"):
return False
import Part
+
circle = Part.makeCircle(1, cen, normal, sta, end)
mid = edges.findMidpoint(circle)
wp = WorkingPlane.get_working_plane(update=False)
@@ -135,7 +137,7 @@ def make_dimension(p1, p2, p3=None, p4=None):
if App.GuiUp:
# invert the normal if we are viewing it from the back
vnorm = gui_utils.get3DView().getViewDirection()
- if vnorm.getAngle(normal) < math.pi/2:
+ if vnorm.getAngle(normal) < math.pi / 2:
normal = normal.negative()
new_obj.Normal = normal
@@ -217,8 +219,8 @@ def make_dimension(p1, p2, p3=None, p4=None):
def makeDimension(p1, p2, p3=None, p4=None):
"""Create a dimension. DEPRECATED. Use 'make_dimension'."""
- _wrn(translate("draft","This function is deprecated. Do not use this function directly."))
- _wrn(translate("draft","Use one of 'make_linear_dimension', or 'make_linear_dimension_obj'."))
+ _wrn(translate("draft", "This function is deprecated. Do not use this function directly."))
+ _wrn(translate("draft", "Use one of 'make_linear_dimension', or 'make_linear_dimension_obj'."))
return make_dimension(p1, p2, p3, p4)
@@ -258,26 +260,26 @@ def make_linear_dimension(p1, p2, dim_line=None):
found, doc = utils.find_doc(App.activeDocument())
if not found:
- _err(translate("draft","No active document. Aborting."))
+ _err(translate("draft", "No active document. Aborting."))
return None
try:
utils.type_check([(p1, App.Vector)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a vector."))
+ _err(translate("draft", "Wrong input: must be a vector."))
return None
try:
utils.type_check([(p2, App.Vector)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a vector."))
+ _err(translate("draft", "Wrong input: must be a vector."))
return None
if dim_line:
try:
utils.type_check([(dim_line, App.Vector)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a vector."))
+ _err(translate("draft", "Wrong input: must be a vector."))
return None
else:
diff = p2.sub(p1)
@@ -347,61 +349,70 @@ def make_linear_dimension_obj(edge_object, i1=1, i2=2, dim_line=None):
found, doc = utils.find_doc(App.activeDocument())
if not found:
- _err(translate("draft","No active document. Aborting."))
+ _err(translate("draft", "No active document. Aborting."))
return None
if isinstance(edge_object, (list, tuple)):
- _err(translate("draft","Wrong input: edge_object must not be a list or tuple."))
+ _err(translate("draft", "Wrong input: edge_object must not be a list or tuple."))
return None
found, edge_object = utils.find_object(edge_object, doc)
if not found:
- _err(translate("draft","Wrong input: edge_object not in document."))
+ _err(translate("draft", "Wrong input: edge_object not in document."))
return None
if not hasattr(edge_object, "Shape"):
- _err(translate("draft","Wrong input: object doesn't have a 'Shape' to measure."))
+ _err(translate("draft", "Wrong input: object doesn't have a 'Shape' to measure."))
return None
- if (not hasattr(edge_object.Shape, "Vertexes")
- or len(edge_object.Shape.Vertexes) < 1):
- _err(translate("draft","Wrong input: object does not have at least 1 element in 'Vertexes' to use for measuring."))
+ if not hasattr(edge_object.Shape, "Vertexes") or len(edge_object.Shape.Vertexes) < 1:
+ _err(
+ translate(
+ "draft",
+ "Wrong input: object does not have at least 1 element in 'Vertexes' to use for measuring.",
+ )
+ )
return None
try:
utils.type_check([(i1, int)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be an integer."))
+ _err(translate("draft", "Wrong input: must be an integer."))
return None
if i1 < 1:
i1 = 1
- _wrn(translate("draft","i1: values below 1 are not allowed; will be set to 1."))
+ _wrn(translate("draft", "i1: values below 1 are not allowed; will be set to 1."))
vx1 = edge_object.getSubObject("Vertex" + str(i1))
if not vx1:
- _err(translate("draft","Wrong input: vertex not in object."))
+ _err(translate("draft", "Wrong input: vertex not in object."))
return None
try:
utils.type_check([(i2, int)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a vector."))
+ _err(translate("draft", "Wrong input: must be a vector."))
return None
if i2 < 1:
i2 = len(edge_object.Shape.Vertexes)
- _wrn(translate("draft","i2: values below 1 are not allowed; will be set to the last vertex in the object."))
+ _wrn(
+ translate(
+ "draft",
+ "i2: values below 1 are not allowed; will be set to the last vertex in the object.",
+ )
+ )
vx2 = edge_object.getSubObject("Vertex" + str(i2))
if not vx2:
- _err(translate("draft","Wrong input: vertex not in object."))
+ _err(translate("draft", "Wrong input: vertex not in object."))
return None
if dim_line:
try:
utils.type_check([(dim_line, App.Vector)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a vector."))
+ _err(translate("draft", "Wrong input: must be a vector."))
return None
else:
diff = vx2.Point.sub(vx1.Point)
@@ -419,8 +430,7 @@ def make_linear_dimension_obj(edge_object, i1=1, i2=2, dim_line=None):
return new_obj
-def make_radial_dimension_obj(edge_object, index=1, mode="radius",
- dim_line=None):
+def make_radial_dimension_obj(edge_object, index=1, mode="radius", dim_line=None):
"""Create a radial or diameter dimension from an arc object.
Parameters
@@ -467,56 +477,60 @@ def make_radial_dimension_obj(edge_object, index=1, mode="radius",
found, doc = utils.find_doc(App.activeDocument())
if not found:
- _err(translate("draft","No active document. Aborting."))
+ _err(translate("draft", "No active document. Aborting."))
return None
found, edge_object = utils.find_object(edge_object, doc)
if not found:
- _err(translate("draft","Wrong input: edge_object not in document."))
+ _err(translate("draft", "Wrong input: edge_object not in document."))
return None
if not hasattr(edge_object, "Shape"):
- _err(translate("draft","Wrong input: object doesn't have a 'Shape' to measure."))
+ _err(translate("draft", "Wrong input: object doesn't have a 'Shape' to measure."))
return None
- if (not hasattr(edge_object.Shape, "Edges")
- or len(edge_object.Shape.Edges) < 1):
- _err(translate("draft","Wrong input: object doesn't have at least one element in 'Edges' to use for measuring."))
+ if not hasattr(edge_object.Shape, "Edges") or len(edge_object.Shape.Edges) < 1:
+ _err(
+ translate(
+ "draft",
+ "Wrong input: object doesn't have at least one element in 'Edges' to use for measuring.",
+ )
+ )
return None
try:
utils.type_check([(index, int)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be an integer."))
+ _err(translate("draft", "Wrong input: must be an integer."))
return None
if index < 1:
index = 1
- _wrn(translate("draft","index: values below 1 are not allowed; will be set to 1."))
+ _wrn(translate("draft", "index: values below 1 are not allowed; will be set to 1."))
edge = edge_object.getSubObject("Edge" + str(index))
if not edge:
- _err(translate("draft","Wrong input: index doesn't correspond to an edge in the object."))
+ _err(translate("draft", "Wrong input: index doesn't correspond to an edge in the object."))
return None
- if not hasattr(edge, "Curve") or edge.Curve.TypeId != 'Part::GeomCircle':
- _err(translate("draft","Wrong input: index doesn't correspond to a circular edge."))
+ if not hasattr(edge, "Curve") or edge.Curve.TypeId != "Part::GeomCircle":
+ _err(translate("draft", "Wrong input: index doesn't correspond to a circular edge."))
return None
try:
utils.type_check([(mode, str)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a string, 'radius' or 'diameter'."))
+ _err(translate("draft", "Wrong input: must be a string, 'radius' or 'diameter'."))
return None
if mode not in ("radius", "diameter"):
- _err(translate("draft","Wrong input: must be a string, 'radius' or 'diameter'."))
+ _err(translate("draft", "Wrong input: must be a string, 'radius' or 'diameter'."))
return None
if dim_line:
try:
utils.type_check([(dim_line, App.Vector)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a vector."))
+ _err(translate("draft", "Wrong input: must be a vector."))
return None
else:
center = edge_object.Shape.Edges[index - 1].Curve.Center
@@ -532,9 +546,12 @@ def make_radial_dimension_obj(edge_object, index=1, mode="radius",
return new_obj
-def make_angular_dimension(center=App.Vector(0, 0, 0),
- angles=None, # If None, set to [0,90]
- dim_line=App.Vector(10, 10, 0), normal=None):
+def make_angular_dimension(
+ center=App.Vector(0, 0, 0),
+ angles=None, # If None, set to [0,90]
+ dim_line=App.Vector(10, 10, 0),
+ normal=None,
+):
"""Create an angular dimension from the given center and angles.
Parameters
@@ -581,27 +598,26 @@ def make_angular_dimension(center=App.Vector(0, 0, 0),
found, doc = utils.find_doc(App.activeDocument())
if not found:
- _err(translate("draft","No active document. Aborting."))
+ _err(translate("draft", "No active document. Aborting."))
return None
try:
utils.type_check([(center, App.Vector)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a vector."))
+ _err(translate("draft", "Wrong input: must be a vector."))
return None
try:
utils.type_check([(angles, (tuple, list))], name=_name)
if len(angles) != 2:
- _err(translate("draft","Wrong input: must be a list with two angles."))
+ _err(translate("draft", "Wrong input: must be a list with two angles."))
return None
ang1, ang2 = angles
- utils.type_check([(ang1, (int, float)),
- (ang2, (int, float))], name=_name)
+ utils.type_check([(ang1, (int, float)), (ang2, (int, float))], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a list with two angles."))
+ _err(translate("draft", "Wrong input: must be a list with two angles."))
return None
# If the angle is larger than 360 degrees, make sure
@@ -613,14 +629,14 @@ def make_angular_dimension(center=App.Vector(0, 0, 0),
try:
utils.type_check([(dim_line, App.Vector)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a vector."))
+ _err(translate("draft", "Wrong input: must be a vector."))
return None
if normal:
try:
utils.type_check([(dim_line, App.Vector)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a vector."))
+ _err(translate("draft", "Wrong input: must be a vector."))
return None
if not normal:
@@ -636,7 +652,7 @@ def make_angular_dimension(center=App.Vector(0, 0, 0),
# This is determined by the angle between the current
# 3D view and the provided normal being below 90 degrees
vnorm = gui_utils.get3DView().getViewDirection()
- if vnorm.getAngle(normal) < math.pi/2:
+ if vnorm.getAngle(normal) < math.pi / 2:
normal = normal.negative()
new_obj.Center = center
@@ -660,7 +676,7 @@ def makeAngularDimension(center, angles, p3, normal=None):
ang1, ang2 = angles
angles = [math.degrees(ang2), math.degrees(ang1)]
- return make_angular_dimension(center=center, angles=angles,
- dim_line=p3, normal=normal)
+ return make_angular_dimension(center=center, angles=angles, dim_line=p3, normal=normal)
+
## @}
diff --git a/src/Mod/Draft/draftmake/make_facebinder.py b/src/Mod/Draft/draftmake/make_facebinder.py
index da135e1d0c..7218135c2f 100644
--- a/src/Mod/Draft/draftmake/make_facebinder.py
+++ b/src/Mod/Draft/draftmake/make_facebinder.py
@@ -52,13 +52,13 @@ def make_facebinder(selectionset, name="Facebinder"):
if not App.ActiveDocument:
App.Console.PrintError("No active document. Aborting\n")
return
- if not isinstance(selectionset,list):
+ if not isinstance(selectionset, list):
selectionset = [selectionset]
- fb = App.ActiveDocument.addObject("Part::FeaturePython",name)
+ fb = App.ActiveDocument.addObject("Part::FeaturePython", name)
Facebinder(fb)
if App.GuiUp:
ViewProviderFacebinder(fb.ViewObject)
- faces = [] # unused variable?
+ faces = [] # unused variable?
fb.Proxy.addSubobjects(fb, selectionset)
gui_utils.select(fb)
return fb
diff --git a/src/Mod/Draft/draftmake/make_fillet.py b/src/Mod/Draft/draftmake/make_fillet.py
index a0eee54db8..2cf73160f9 100644
--- a/src/Mod/Draft/draftmake/make_fillet.py
+++ b/src/Mod/Draft/draftmake/make_fillet.py
@@ -48,6 +48,7 @@ DraftGeomUtils = lz.LazyLoader("DraftGeomUtils", globals(), "DraftGeomUtils")
## \addtogroup draftmake
# @{
+
def _preprocess(objs, radius, chamfer):
"""Check the inputs and return the edges for the fillet and the objects to be deleted."""
edges = []
@@ -139,4 +140,5 @@ def make_fillet(objs, radius=100, chamfer=False, delete=False):
return obj
+
## @}
diff --git a/src/Mod/Draft/draftmake/make_hatch.py b/src/Mod/Draft/draftmake/make_hatch.py
index 3a38333f0a..735d8974c3 100644
--- a/src/Mod/Draft/draftmake/make_hatch.py
+++ b/src/Mod/Draft/draftmake/make_hatch.py
@@ -1,35 +1,36 @@
-#***************************************************************************
-#* *
-#* Copyright (c) 2021 Yorik van Havre *
-#* *
-#* This program is free software; you can redistribute it and/or modify *
-#* it under the terms of the GNU Lesser General Public License (LGPL) *
-#* as published by the Free Software Foundation; either version 2 of *
-#* the License, or (at your option) any later version. *
-#* for detail see the LICENCE text file. *
-#* *
-#* This program is distributed in the hope that it will be useful, *
-#* but WITHOUT ANY WARRANTY; without even the implied warranty of *
-#* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
-#* GNU Library General Public License for more details. *
-#* *
-#* You should have received a copy of the GNU Library General Public *
-#* License along with this program; if not, write to the Free Software *
-#* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 *
-#* USA *
-#* *
-#***************************************************************************
+# ***************************************************************************
+# * *
+# * Copyright (c) 2021 Yorik van Havre *
+# * *
+# * This program is free software; you can redistribute it and/or modify *
+# * it under the terms of the GNU Lesser General Public License (LGPL) *
+# * as published by the Free Software Foundation; either version 2 of *
+# * the License, or (at your option) any later version. *
+# * for detail see the LICENCE text file. *
+# * *
+# * This program is distributed in the hope that it will be useful, *
+# * but WITHOUT ANY WARRANTY; without even the implied warranty of *
+# * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
+# * GNU Library General Public License for more details. *
+# * *
+# * You should have received a copy of the GNU Library General Public *
+# * License along with this program; if not, write to the Free Software *
+# * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 *
+# * USA *
+# * *
+# ***************************************************************************
"""This module contains FreeCAD commands for the Draft workbench"""
import FreeCAD
from draftobjects.hatch import Hatch
+
if FreeCAD.GuiUp:
from draftviewproviders.view_hatch import ViewProviderDraftHatch
import draftutils.gui_utils as gui_utils
-def make_hatch(baseobject, filename, pattern, scale, rotation, translate=True):
+def make_hatch(baseobject, filename, pattern, scale, rotation, translate=True):
"""make_hatch(baseobject, filename, pattern, scale, rotation, translate): Creates and returns a
hatch object made by applying the given pattern of the given PAT file to the faces of
the given base object. Given scale, rotation and translate factors are applied to the hatch object.
diff --git a/src/Mod/Draft/draftmake/make_label.py b/src/Mod/Draft/draftmake/make_label.py
index bdef51646f..c05cb9b4da 100644
--- a/src/Mod/Draft/draftmake/make_label.py
+++ b/src/Mod/Draft/draftmake/make_label.py
@@ -41,12 +41,17 @@ if App.GuiUp:
from draftviewproviders.view_label import ViewProviderLabel
-def make_label(target_point=App.Vector(0, 0, 0),
- placement=App.Vector(30, 30, 0),
- target_object=None, subelements=None,
- label_type="Custom", custom_text="Label",
- direction="Horizontal", distance=-10,
- points=None):
+def make_label(
+ target_point=App.Vector(0, 0, 0),
+ placement=App.Vector(30, 30, 0),
+ target_object=None,
+ subelements=None,
+ label_type="Custom",
+ custom_text="Label",
+ direction="Horizontal",
+ distance=-10,
+ points=None,
+):
"""Create a Label object containing different types of information.
The current color and text height and font specified in preferences
@@ -190,7 +195,7 @@ def make_label(target_point=App.Vector(0, 0, 0),
found, doc = utils.find_doc(App.activeDocument())
if not found:
- _err(translate("draft","No active document. Aborting."))
+ _err(translate("draft", "No active document. Aborting."))
return None
if not target_point:
@@ -198,17 +203,15 @@ def make_label(target_point=App.Vector(0, 0, 0),
try:
utils.type_check([(target_point, App.Vector)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a vector."))
+ _err(translate("draft", "Wrong input: must be a vector."))
return None
if not placement:
placement = App.Placement()
try:
- utils.type_check([(placement, (App.Placement,
- App.Vector,
- App.Rotation))], name=_name)
+ utils.type_check([(placement, (App.Placement, App.Vector, App.Rotation))], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a placement, a vector, or a rotation."))
+ _err(translate("draft", "Wrong input: must be a placement, a vector, or a rotation."))
return None
# Convert the vector or rotation to a full placement
@@ -219,12 +222,12 @@ def make_label(target_point=App.Vector(0, 0, 0),
if target_object:
if isinstance(target_object, (list, tuple)):
- _err(translate("draft","Wrong input: target_object must not be a list."))
+ _err(translate("draft", "Wrong input: target_object must not be a list."))
return None
found, target_object = utils.find_object(target_object, doc)
if not found:
- _err(translate("draft","Wrong input: target_object not in document."))
+ _err(translate("draft", "Wrong input: target_object not in document."))
return None
if target_object and subelements:
@@ -233,10 +236,14 @@ def make_label(target_point=App.Vector(0, 0, 0),
if isinstance(subelements, str):
subelements = [subelements]
- utils.type_check([(subelements, (list, tuple, str))],
- name=_name)
+ utils.type_check([(subelements, (list, tuple, str))], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: subelements must be a list or tuple of strings, or a single string."))
+ _err(
+ translate(
+ "draft",
+ "Wrong input: subelements must be a list or tuple of strings, or a single string.",
+ )
+ )
return None
# The subelements list is used to build a special list
@@ -247,7 +254,7 @@ def make_label(target_point=App.Vector(0, 0, 0),
for sub in subelements:
_sub = target_object.getSubObject(sub)
if not _sub:
- _err(translate("draft","Wrong input: subelement {} not in object.").format(sub))
+ _err(translate("draft", "Wrong input: subelement {} not in object.").format(sub))
return None
if not label_type:
@@ -255,12 +262,16 @@ def make_label(target_point=App.Vector(0, 0, 0),
try:
utils.type_check([(label_type, str)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: label_type must be a string."))
+ _err(translate("draft", "Wrong input: label_type must be a string."))
return None
types = label.get_label_types()
if label_type not in types:
- _err(translate("draft", "Wrong input: label_type must be one of the following:") + " " + str(types).strip("[]"))
+ _err(
+ translate("draft", "Wrong input: label_type must be one of the following:")
+ + " "
+ + str(types).strip("[]")
+ )
return None
if not custom_text:
@@ -268,12 +279,11 @@ def make_label(target_point=App.Vector(0, 0, 0),
try:
utils.type_check([(custom_text, (str, list))], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a list of strings or a single string."))
+ _err(translate("draft", "Wrong input: must be a list of strings or a single string."))
return None
- if (type(custom_text) is list
- and not all(isinstance(element, str) for element in custom_text)):
- _err(translate("draft","Wrong input: must be a list of strings or a single string."))
+ if type(custom_text) is list and not all(isinstance(element, str) for element in custom_text):
+ _err(translate("draft", "Wrong input: must be a list of strings or a single string."))
return None
if not direction:
@@ -281,11 +291,19 @@ def make_label(target_point=App.Vector(0, 0, 0),
try:
utils.type_check([(direction, str)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a string, 'Horizontal', 'Vertical', or 'Custom'."))
+ _err(
+ translate(
+ "draft", "Wrong input: must be a string, 'Horizontal', 'Vertical', or 'Custom'."
+ )
+ )
return None
if direction not in ("Horizontal", "Vertical", "Custom"):
- _err(translate("draft","Wrong input: must be a string, 'Horizontal', 'Vertical', or 'Custom'."))
+ _err(
+ translate(
+ "draft", "Wrong input: must be a string, 'Horizontal', 'Vertical', or 'Custom'."
+ )
+ )
return None
if not distance:
@@ -293,11 +311,13 @@ def make_label(target_point=App.Vector(0, 0, 0),
try:
utils.type_check([(distance, (int, float))], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a number."))
+ _err(translate("draft", "Wrong input: must be a number."))
return None
if points:
- _err_msg = translate("draft","Wrong input: points {} must be a list of at least two vectors.").format(points)
+ _err_msg = translate(
+ "draft", "Wrong input: points {} must be a list of at least two vectors."
+ ).format(points)
try:
utils.type_check([(points, (tuple, list))], name=_name)
except TypeError:
@@ -312,8 +332,7 @@ def make_label(target_point=App.Vector(0, 0, 0),
_err(_err_msg)
return None
- new_obj = doc.addObject("App::FeaturePython",
- "dLabel")
+ new_obj = doc.addObject("App::FeaturePython", "dLabel")
label.Label(new_obj)
new_obj.TargetPoint = target_point
@@ -331,7 +350,7 @@ def make_label(target_point=App.Vector(0, 0, 0),
new_obj.StraightDistance = distance
if points:
if direction != "Custom":
- _wrn(translate("draft","Direction is not 'Custom'; points won't be used."))
+ _wrn(translate("draft", "Direction is not 'Custom'; points won't be used."))
new_obj.Points = points
if App.GuiUp:
@@ -348,8 +367,9 @@ def make_label(target_point=App.Vector(0, 0, 0),
return new_obj
-def makeLabel(targetpoint=None, target=None, direction=None,
- distance=None, labeltype=None, placement=None):
+def makeLabel(
+ targetpoint=None, target=None, direction=None, distance=None, labeltype=None, placement=None
+):
"""Create a Label. DEPRECATED. Use 'make_label'."""
utils.use_instead("make_label")
@@ -358,10 +378,14 @@ def makeLabel(targetpoint=None, target=None, direction=None,
if target:
try:
- utils.type_check([(target, (tuple, list))],
- name=_name)
+ utils.type_check([(target, (tuple, list))], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a list of two elements. For example, [object, 'Edge1']."))
+ _err(
+ translate(
+ "draft",
+ "Wrong input: must be a list of two elements. For example, [object, 'Edge1'].",
+ )
+ )
return None
# In the old function `target` is the original parameter,
@@ -383,12 +407,15 @@ def makeLabel(targetpoint=None, target=None, direction=None,
target_object = target[0]
subelements = target[1]
- return make_label(target_point=targetpoint,
- placement=placement,
- target_object=target_object,
- subelements=subelements,
- label_type=labeltype,
- direction=direction,
- distance=distance)
+ return make_label(
+ target_point=targetpoint,
+ placement=placement,
+ target_object=target_object,
+ subelements=subelements,
+ label_type=labeltype,
+ direction=direction,
+ distance=distance,
+ )
+
## @}
diff --git a/src/Mod/Draft/draftmake/make_layer.py b/src/Mod/Draft/draftmake/make_layer.py
index 584c74ebf4..bd708b274a 100644
--- a/src/Mod/Draft/draftmake/make_layer.py
+++ b/src/Mod/Draft/draftmake/make_layer.py
@@ -35,8 +35,7 @@ from draftutils.messages import _err
from draftutils.translate import translate
if App.GuiUp:
- from draftviewproviders.view_layer import (ViewProviderLayer,
- ViewProviderLayerContainer)
+ from draftviewproviders.view_layer import ViewProviderLayer, ViewProviderLayerContainer
def get_layer_container():
@@ -51,15 +50,14 @@ def get_layer_container():
"""
found, doc = utils.find_doc(App.activeDocument())
if not found:
- _err(translate("draft","No active document. Aborting."))
+ _err(translate("draft", "No active document. Aborting."))
return None
for obj in doc.Objects:
if obj.Name == "LayerContainer":
return obj
- obj = doc.addObject("App::DocumentObjectGroupPython",
- "LayerContainer")
+ obj = doc.addObject("App::DocumentObjectGroupPython", "LayerContainer")
obj.Label = translate("draft", "Layers")
LayerContainer(obj)
@@ -77,12 +75,14 @@ def getLayerContainer():
return get_layer_container()
-def make_layer(name=None,
- line_color=(0.0, 0.0, 0.0), # does not match default DefaultShapeLineColor
- shape_color=(0.8, 0.8, 0.8), # does not match default DefaultShapeColor
- line_width=2.0,
- draw_style="Solid",
- transparency=0):
+def make_layer(
+ name=None,
+ line_color=(0.0, 0.0, 0.0), # does not match default DefaultShapeLineColor
+ shape_color=(0.8, 0.8, 0.8), # does not match default DefaultShapeColor
+ line_width=2.0,
+ draw_style="Solid",
+ transparency=0,
+):
"""Create a Layer object in the active document.
If a layer container named `'LayerContainer'` does not exist, it is created.
@@ -140,14 +140,14 @@ def make_layer(name=None,
found, doc = utils.find_doc(App.activeDocument())
if not found:
- _err(translate("draft","No active document. Aborting."))
+ _err(translate("draft", "No active document. Aborting."))
return None
if name is not None:
try:
utils.type_check([(name, str)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: it must be a string."))
+ _err(translate("draft", "Wrong input: it must be a string."))
return None
else:
name = translate("draft", "Layer")
@@ -156,22 +156,22 @@ def make_layer(name=None,
try:
utils.type_check([(line_color, tuple)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a tuple of three floats 0.0 to 1.0."))
+ _err(translate("draft", "Wrong input: must be a tuple of three floats 0.0 to 1.0."))
return None
if not all(isinstance(color, (int, float)) for color in line_color):
- _err(translate("draft","Wrong input: must be a tuple of three floats 0.0 to 1.0."))
+ _err(translate("draft", "Wrong input: must be a tuple of three floats 0.0 to 1.0."))
return None
if shape_color is not None:
try:
utils.type_check([(shape_color, tuple)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a tuple of three floats 0.0 to 1.0."))
+ _err(translate("draft", "Wrong input: must be a tuple of three floats 0.0 to 1.0."))
return None
if not all(isinstance(color, (int, float)) for color in shape_color):
- _err(translate("draft","Wrong input: must be a tuple of three floats 0.0 to 1.0."))
+ _err(translate("draft", "Wrong input: must be a tuple of three floats 0.0 to 1.0."))
return None
if line_width is not None:
@@ -179,18 +179,26 @@ def make_layer(name=None,
utils.type_check([(line_width, (int, float))], name=_name)
line_width = float(abs(line_width))
except TypeError:
- _err(translate("draft","Wrong input: must be a number."))
+ _err(translate("draft", "Wrong input: must be a number."))
return None
if draw_style is not None:
try:
utils.type_check([(draw_style, str)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be 'Solid', 'Dashed', 'Dotted', or 'Dashdot'."))
+ _err(
+ translate(
+ "draft", "Wrong input: must be 'Solid', 'Dashed', 'Dotted', or 'Dashdot'."
+ )
+ )
return None
- if draw_style not in ('Solid', 'Dashed', 'Dotted', 'Dashdot'):
- _err(translate("draft","Wrong input: must be 'Solid', 'Dashed', 'Dotted', or 'Dashdot'."))
+ if draw_style not in ("Solid", "Dashed", "Dotted", "Dashdot"):
+ _err(
+ translate(
+ "draft", "Wrong input: must be 'Solid', 'Dashed', 'Dotted', or 'Dashdot'."
+ )
+ )
return None
if transparency is not None:
@@ -198,7 +206,7 @@ def make_layer(name=None,
utils.type_check([(transparency, (int, float))], name=_name)
transparency = int(abs(transparency))
except TypeError:
- _err(translate("draft","Wrong input: must be a number between 0 and 100."))
+ _err(translate("draft", "Wrong input: must be a number between 0 and 100."))
return None
obj = doc.addObject("App::FeaturePython", "Layer")
@@ -225,4 +233,5 @@ def make_layer(name=None,
return obj
+
## @}
diff --git a/src/Mod/Draft/draftmake/make_line.py b/src/Mod/Draft/draftmake/make_line.py
index d1030a0be8..1b19e1d81b 100644
--- a/src/Mod/Draft/draftmake/make_line.py
+++ b/src/Mod/Draft/draftmake/make_line.py
@@ -54,7 +54,7 @@ def make_line(first_param, last_param=None):
if hasattr(first_param, "StartPoint") and hasattr(first_param, "EndPoint"):
p2 = first_param.EndPoint
p1 = first_param.StartPoint
- elif hasattr(p1,"Vertexes"):
+ elif hasattr(p1, "Vertexes"):
p2 = first_param.Vertexes[-1].Point
p1 = first_param.Vertexes[0].Point
else:
@@ -62,7 +62,7 @@ def make_line(first_param, last_param=None):
App.Console.PrintError(_err + "\n")
return
- obj = make_wire.make_wire([p1,p2])
+ obj = make_wire.make_wire([p1, p2])
return obj
diff --git a/src/Mod/Draft/draftmake/make_orthoarray.py b/src/Mod/Draft/draftmake/make_orthoarray.py
index f60085f8e7..c54d6d5453 100644
--- a/src/Mod/Draft/draftmake/make_orthoarray.py
+++ b/src/Mod/Draft/draftmake/make_orthoarray.py
@@ -35,14 +35,16 @@ from draftutils.messages import _wrn, _err
from draftutils.translate import translate
-def _make_ortho_array(base_object,
- v_x=App.Vector(10, 0, 0),
- v_y=App.Vector(0, 10, 0),
- v_z=App.Vector(0, 0, 10),
- n_x=2,
- n_y=2,
- n_z=1,
- use_link=True):
+def _make_ortho_array(
+ base_object,
+ v_x=App.Vector(10, 0, 0),
+ v_y=App.Vector(0, 10, 0),
+ v_z=App.Vector(0, 0, 10),
+ n_x=2,
+ n_y=2,
+ n_z=1,
+ use_link=True,
+):
"""Create an orthogonal array from the given object.
This is a simple wrapper of the `draftmake.make_array.make_array`
@@ -58,10 +60,9 @@ def _make_ortho_array(base_object,
"""
_name = "_make_ortho_array"
- new_obj = make_array.make_array(base_object,
- arg1=v_x, arg2=v_y, arg3=v_z,
- arg4=n_x, arg5=n_y, arg6=n_z,
- use_link=use_link)
+ new_obj = make_array.make_array(
+ base_object, arg1=v_x, arg2=v_y, arg3=v_z, arg4=n_x, arg5=n_y, arg6=n_z, use_link=use_link
+ )
return new_obj
@@ -69,27 +70,31 @@ def _are_vectors(v_x, v_y, v_z=None, name="Unknown"):
"""Check that the vectors are numbers."""
try:
if v_z:
- utils.type_check([(v_x, (int, float, App.Vector)),
- (v_y, (int, float, App.Vector)),
- (v_z, (int, float, App.Vector))],
- name=name)
+ utils.type_check(
+ [
+ (v_x, (int, float, App.Vector)),
+ (v_y, (int, float, App.Vector)),
+ (v_z, (int, float, App.Vector)),
+ ],
+ name=name,
+ )
else:
- utils.type_check([(v_x, (int, float, App.Vector)),
- (v_y, (int, float, App.Vector))],
- name=name)
+ utils.type_check(
+ [(v_x, (int, float, App.Vector)), (v_y, (int, float, App.Vector))], name=name
+ )
except TypeError:
- _err(translate("draft","Wrong input: must be a number or vector."))
+ _err(translate("draft", "Wrong input: must be a number or vector."))
return False, v_x, v_y, v_z
if not isinstance(v_x, App.Vector):
v_x = App.Vector(v_x, 0, 0)
- _wrn(translate("draft","Input: single value expanded to vector."))
+ _wrn(translate("draft", "Input: single value expanded to vector."))
if not isinstance(v_y, App.Vector):
v_y = App.Vector(0, v_y, 0)
- _wrn(translate("draft","Input: single value expanded to vector."))
+ _wrn(translate("draft", "Input: single value expanded to vector."))
if v_z and not isinstance(v_z, App.Vector):
v_z = App.Vector(0, 0, v_z)
- _wrn(translate("draft","Input: single value expanded to vector."))
+ _wrn(translate("draft", "Input: single value expanded to vector."))
return True, v_x, v_y, v_z
@@ -98,24 +103,21 @@ def _are_integers(n_x, n_y, n_z=None, name="Unknown"):
"""Check that the numbers are integers, with minimum value of 1."""
try:
if n_z:
- utils.type_check([(n_x, int),
- (n_y, int),
- (n_z, int)], name=name)
+ utils.type_check([(n_x, int), (n_y, int), (n_z, int)], name=name)
else:
- utils.type_check([(n_x, int),
- (n_y, int)], name=name)
+ utils.type_check([(n_x, int), (n_y, int)], name=name)
except TypeError:
- _err(translate("draft","Wrong input: must be an integer number."))
+ _err(translate("draft", "Wrong input: must be an integer number."))
return False, n_x, n_y, n_z
if n_x < 1:
- _wrn(translate("draft","Input: number of elements must be at least 1. It is set to 1."))
+ _wrn(translate("draft", "Input: number of elements must be at least 1. It is set to 1."))
n_x = 1
if n_y < 1:
- _wrn(translate("draft","Input: number of elements must be at least 1. It is set to 1."))
+ _wrn(translate("draft", "Input: number of elements must be at least 1. It is set to 1."))
n_y = 1
if n_z and n_z < 1:
- _wrn(translate("draft","Input: number of elements must be at least 1. It is set to 1."))
+ _wrn(translate("draft", "Input: number of elements must be at least 1. It is set to 1."))
n_z = 1
return True, n_x, n_y, n_z
@@ -125,14 +127,13 @@ def _are_numbers(d_x, d_y, d_z=None, name="Unknown"):
"""Check that the numbers are numbers."""
try:
if d_z:
- utils.type_check([(d_x, (int, float)),
- (d_y, (int, float)),
- (d_z, (int, float))], name=name)
+ utils.type_check(
+ [(d_x, (int, float)), (d_y, (int, float)), (d_z, (int, float))], name=name
+ )
else:
- utils.type_check([(d_x, (int, float)),
- (d_y, (int, float))], name=name)
+ utils.type_check([(d_x, (int, float)), (d_y, (int, float))], name=name)
except TypeError:
- _err(translate("draft","Wrong input: must be a number."))
+ _err(translate("draft", "Wrong input: must be a number."))
return False, d_x, d_y, d_z
return True, d_x, d_y, d_z
@@ -142,19 +143,21 @@ def _find_object_in_doc(base_object, doc=None):
"""Check that a document is available and the object exists."""
found, base_object = utils.find_object(base_object, doc=doc)
if not found:
- _err(translate("draft","Wrong input: base_object not in document."))
+ _err(translate("draft", "Wrong input: base_object not in document."))
return found, base_object
-def make_ortho_array(base_object,
- v_x=App.Vector(10, 0, 0),
- v_y=App.Vector(0, 10, 0),
- v_z=App.Vector(0, 0, 10),
- n_x=2,
- n_y=2,
- n_z=1,
- use_link=True):
+def make_ortho_array(
+ base_object,
+ v_x=App.Vector(10, 0, 0),
+ v_y=App.Vector(0, 10, 0),
+ v_z=App.Vector(0, 0, 10),
+ n_x=2,
+ n_y=2,
+ n_z=1,
+ use_link=True,
+):
"""Create an orthogonal array from the given object.
Parameters
@@ -248,8 +251,7 @@ def make_ortho_array(base_object,
"""
_name = "make_ortho_array"
- found, base_object = _find_object_in_doc(base_object,
- doc=App.activeDocument())
+ found, base_object = _find_object_in_doc(base_object, doc=App.activeDocument())
if not found:
return None
@@ -263,19 +265,15 @@ def make_ortho_array(base_object,
use_link = bool(use_link)
- new_obj = _make_ortho_array(base_object,
- v_x=v_x, v_y=v_y, v_z=v_z,
- n_x=n_x, n_y=n_y, n_z=n_z,
- use_link=use_link)
+ new_obj = _make_ortho_array(
+ base_object, v_x=v_x, v_y=v_y, v_z=v_z, n_x=n_x, n_y=n_y, n_z=n_z, use_link=use_link
+ )
return new_obj
-def make_ortho_array2d(base_object,
- v_x=App.Vector(10, 0, 0),
- v_y=App.Vector(0, 10, 0),
- n_x=2,
- n_y=2,
- use_link=True):
+def make_ortho_array2d(
+ base_object, v_x=App.Vector(10, 0, 0), v_y=App.Vector(0, 10, 0), n_x=2, n_y=2, use_link=True
+):
"""Create a 2D orthogonal array from the given object.
This works the same as `make_ortho_array`.
@@ -321,8 +319,7 @@ def make_ortho_array2d(base_object,
"""
_name = "make_ortho_array2d"
- found, base_object = _find_object_in_doc(base_object,
- doc=App.activeDocument())
+ found, base_object = _find_object_in_doc(base_object, doc=App.activeDocument())
if not found:
return None
@@ -336,21 +333,11 @@ def make_ortho_array2d(base_object,
use_link = bool(use_link)
- new_obj = _make_ortho_array(base_object,
- v_x=v_x, v_y=v_y,
- n_x=n_x, n_y=n_y,
- use_link=use_link)
+ new_obj = _make_ortho_array(base_object, v_x=v_x, v_y=v_y, n_x=n_x, n_y=n_y, use_link=use_link)
return new_obj
-def make_rect_array(base_object,
- d_x=10,
- d_y=10,
- d_z=10,
- n_x=2,
- n_y=2,
- n_z=1,
- use_link=True):
+def make_rect_array(base_object, d_x=10, d_y=10, d_z=10, n_x=2, n_y=2, n_z=1, use_link=True):
"""Create a rectangular array from the given object.
This function wraps around `make_ortho_array`
@@ -393,8 +380,7 @@ def make_rect_array(base_object,
"""
_name = "make_rect_array"
- found, base_object = _find_object_in_doc(base_object,
- doc=App.activeDocument())
+ found, base_object = _find_object_in_doc(base_object, doc=App.activeDocument())
if not found:
return None
@@ -408,23 +394,20 @@ def make_rect_array(base_object,
use_link = bool(use_link)
- new_obj = _make_ortho_array(base_object,
- v_x=App.Vector(d_x, 0, 0),
- v_y=App.Vector(0, d_y, 0),
- v_z=App.Vector(0, 0, d_z),
- n_x=n_x,
- n_y=n_y,
- n_z=n_z,
- use_link=use_link)
+ new_obj = _make_ortho_array(
+ base_object,
+ v_x=App.Vector(d_x, 0, 0),
+ v_y=App.Vector(0, d_y, 0),
+ v_z=App.Vector(0, 0, d_z),
+ n_x=n_x,
+ n_y=n_y,
+ n_z=n_z,
+ use_link=use_link,
+ )
return new_obj
-def make_rect_array2d(base_object,
- d_x=10,
- d_y=10,
- n_x=2,
- n_y=2,
- use_link=True):
+def make_rect_array2d(base_object, d_x=10, d_y=10, n_x=2, n_y=2, use_link=True):
"""Create a 2D rectangular array from the given object.
This function wraps around `make_ortho_array`,
@@ -468,8 +451,7 @@ def make_rect_array2d(base_object,
"""
_name = "make_rect_array2d"
- found, base_object = _find_object_in_doc(base_object,
- doc=App.activeDocument())
+ found, base_object = _find_object_in_doc(base_object, doc=App.activeDocument())
if not found:
return None
@@ -483,12 +465,15 @@ def make_rect_array2d(base_object,
use_link = bool(use_link)
- new_obj = _make_ortho_array(base_object,
- v_x=App.Vector(d_x, 0, 0),
- v_y=App.Vector(0, d_y, 0),
- n_x=n_x,
- n_y=n_y,
- use_link=use_link)
+ new_obj = _make_ortho_array(
+ base_object,
+ v_x=App.Vector(d_x, 0, 0),
+ v_y=App.Vector(0, d_y, 0),
+ n_x=n_x,
+ n_y=n_y,
+ use_link=use_link,
+ )
return new_obj
+
## @}
diff --git a/src/Mod/Draft/draftmake/make_patharray.py b/src/Mod/Draft/draftmake/make_patharray.py
index eb86cf3bf5..142ab7c608 100644
--- a/src/Mod/Draft/draftmake/make_patharray.py
+++ b/src/Mod/Draft/draftmake/make_patharray.py
@@ -50,14 +50,21 @@ if App.GuiUp:
from draftviewproviders.view_draftlink import ViewProviderDraftLink
-def make_path_array(base_object, path_object, count=4,
- extra=App.Vector(0, 0, 0), subelements=None,
- align=False, align_mode="Original",
- tan_vector=App.Vector(1, 0, 0),
- force_vertical=False,
- vertical_vector=App.Vector(0, 0, 1),
- start_offset=0.0, end_offset=0.0,
- use_link=True):
+def make_path_array(
+ base_object,
+ path_object,
+ count=4,
+ extra=App.Vector(0, 0, 0),
+ subelements=None,
+ align=False,
+ align_mode="Original",
+ tan_vector=App.Vector(1, 0, 0),
+ force_vertical=False,
+ vertical_vector=App.Vector(0, 0, 1),
+ start_offset=0.0,
+ end_offset=0.0,
+ use_link=True,
+):
"""Make a Draft PathArray object.
Distribute copies of a `base_object` along `path_object`
@@ -166,32 +173,30 @@ def make_path_array(base_object, path_object, count=4,
found, doc = utils.find_doc(App.activeDocument())
if not found:
- _err(translate("draft","No active document. Aborting."))
+ _err(translate("draft", "No active document. Aborting."))
return None
found, base_object = utils.find_object(base_object, doc)
if not found:
- _err(translate("draft","Wrong input: base_object not in document."))
+ _err(translate("draft", "Wrong input: base_object not in document."))
return None
found, path_object = utils.find_object(path_object, doc)
if not found:
- _err(translate("draft","Wrong input: path_object not in document."))
+ _err(translate("draft", "Wrong input: path_object not in document."))
return None
try:
- utils.type_check([(count, (int, float))],
- name=_name)
+ utils.type_check([(count, (int, float))], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a number."))
+ _err(translate("draft", "Wrong input: must be a number."))
return None
count = int(count)
try:
- utils.type_check([(extra, App.Vector)],
- name=_name)
+ utils.type_check([(extra, App.Vector)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a vector."))
+ _err(translate("draft", "Wrong input: must be a vector."))
return None
if subelements:
@@ -200,10 +205,13 @@ def make_path_array(base_object, path_object, count=4,
if isinstance(subelements, str):
subelements = [subelements]
- utils.type_check([(subelements, (list, tuple, str))],
- name=_name)
+ utils.type_check([(subelements, (list, tuple, str))], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a list or tuple of strings, or a single string."))
+ _err(
+ translate(
+ "draft", "Wrong input: must be a list or tuple of strings, or a single string."
+ )
+ )
return None
# The subelements list is used to build a special list
@@ -228,43 +236,38 @@ def make_path_array(base_object, path_object, count=4,
align = bool(align)
try:
- utils.type_check([(align_mode, str)],
- name=_name)
+ utils.type_check([(align_mode, str)], name=_name)
if align_mode not in ("Original", "Frenet", "Tangent"):
raise TypeError
except TypeError:
- _err(translate("draft","Wrong input: must be 'Original', 'Frenet', or 'Tangent'."))
+ _err(translate("draft", "Wrong input: must be 'Original', 'Frenet', or 'Tangent'."))
return None
try:
- utils.type_check([(tan_vector, App.Vector)],
- name=_name)
+ utils.type_check([(tan_vector, App.Vector)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a vector."))
+ _err(translate("draft", "Wrong input: must be a vector."))
return None
force_vertical = bool(force_vertical)
try:
- utils.type_check([(vertical_vector, App.Vector)],
- name=_name)
+ utils.type_check([(vertical_vector, App.Vector)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a vector."))
+ _err(translate("draft", "Wrong input: must be a vector."))
return None
try:
- utils.type_check([(start_offset, (int, float))],
- name=_name)
+ utils.type_check([(start_offset, (int, float))], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a number."))
+ _err(translate("draft", "Wrong input: must be a number."))
return None
start_offset = float(start_offset)
try:
- utils.type_check([(end_offset, (int, float))],
- name=_name)
+ utils.type_check([(end_offset, (int, float))], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a number."))
+ _err(translate("draft", "Wrong input: must be a number."))
return None
end_offset = float(end_offset)
@@ -273,8 +276,7 @@ def make_path_array(base_object, path_object, count=4,
if use_link:
# The PathArray class must be called in this special way
# to make it a PathLinkArray
- new_obj = doc.addObject("Part::FeaturePython", "PathArray",
- PathArray(None), None, True)
+ new_obj = doc.addObject("Part::FeaturePython", "PathArray", PathArray(None), None, True)
else:
new_obj = doc.addObject("Part::FeaturePython", "PathArray")
PathArray(new_obj)
@@ -305,44 +307,37 @@ def make_path_array(base_object, path_object, count=4,
return new_obj
-def makePathArray(baseobject, pathobject, count,
- xlate=None, align=False,
- pathobjsubs=[],
- use_link=False):
+def makePathArray(
+ baseobject, pathobject, count, xlate=None, align=False, pathobjsubs=[], use_link=False
+):
"""Create PathArray. DEPRECATED. Use 'make_path_array'."""
- utils.use_instead('make_path_array')
+ utils.use_instead("make_path_array")
- return make_path_array(baseobject, pathobject, count,
- xlate, pathobjsubs,
- align,
- use_link)
+ return make_path_array(baseobject, pathobject, count, xlate, pathobjsubs, align, use_link)
-def make_path_twisted_array(base_object, path_object,
- count=15, rot_factor=0.25,
- use_link=True):
+def make_path_twisted_array(base_object, path_object, count=15, rot_factor=0.25, use_link=True):
"""Create a Path twisted array."""
_name = "make_path_twisted_array"
found, doc = utils.find_doc(App.activeDocument())
if not found:
- _err(translate("draft","No active document. Aborting."))
+ _err(translate("draft", "No active document. Aborting."))
return None
found, base_object = utils.find_object(base_object, doc)
if not found:
- _err(translate("draft","Wrong input: base_object not in document."))
+ _err(translate("draft", "Wrong input: base_object not in document."))
return None
found, path_object = utils.find_object(path_object, doc)
if not found:
- _err(translate("draft","Wrong input: path_object not in document."))
+ _err(translate("draft", "Wrong input: path_object not in document."))
return None
try:
- utils.type_check([(count, (int, float))],
- name=_name)
+ utils.type_check([(count, (int, float))], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a number."))
+ _err(translate("draft", "Wrong input: must be a number."))
return None
count = int(count)
@@ -350,8 +345,9 @@ def make_path_twisted_array(base_object, path_object,
if use_link:
# The PathTwistedArray class must be called in this special way
# to make it a PathTwistLinkArray
- new_obj = doc.addObject("Part::FeaturePython", "PathTwistedArray",
- PathTwistedArray(None), None, True)
+ new_obj = doc.addObject(
+ "Part::FeaturePython", "PathTwistedArray", PathTwistedArray(None), None, True
+ )
else:
new_obj = doc.addObject("Part::FeaturePython", "PathTwistedArray")
PathTwistedArray(new_obj)
@@ -373,4 +369,5 @@ def make_path_twisted_array(base_object, path_object,
return new_obj
+
## @}
diff --git a/src/Mod/Draft/draftmake/make_point.py b/src/Mod/Draft/draftmake/make_point.py
index 71556d160a..12cf2db1ff 100644
--- a/src/Mod/Draft/draftmake/make_point.py
+++ b/src/Mod/Draft/draftmake/make_point.py
@@ -38,7 +38,7 @@ if App.GuiUp:
def make_point(X=0, Y=0, Z=0, color=None, name="Point", point_size=5):
- """ make_point(x, y, z, [color(r, g, b), point_size]) or
+ """make_point(x, y, z, [color(r, g, b), point_size]) or
make_point(Vector, color(r, g, b), point_size])
Creates a Draft Point in the current document.
diff --git a/src/Mod/Draft/draftmake/make_pointarray.py b/src/Mod/Draft/draftmake/make_pointarray.py
index 9deb017cd9..52dc4b0a6f 100644
--- a/src/Mod/Draft/draftmake/make_pointarray.py
+++ b/src/Mod/Draft/draftmake/make_pointarray.py
@@ -99,9 +99,11 @@ def make_point_array(base_object, point_object, extra=None, use_link=True):
_err(translate("draft", "Wrong input: point_object not in document."))
return None
- if not ((hasattr(point_object, "Shape") and hasattr(point_object.Shape, "Vertexes"))
- or hasattr(point_object, "Mesh")
- or hasattr(point_object, "Points")):
+ if not (
+ (hasattr(point_object, "Shape") and hasattr(point_object.Shape, "Vertexes"))
+ or hasattr(point_object, "Mesh")
+ or hasattr(point_object, "Points")
+ ):
_err(translate("draft", "Wrong input: object has the wrong type."))
return None
@@ -109,10 +111,7 @@ def make_point_array(base_object, point_object, extra=None, use_link=True):
extra = App.Placement()
try:
- utils.type_check([(extra, (App.Placement,
- App.Vector,
- App.Rotation))],
- name=_name)
+ utils.type_check([(extra, (App.Placement, App.Vector, App.Rotation))], name=_name)
except TypeError:
_err(translate("draft", "Wrong input: must be a placement, a vector, or a rotation."))
return None
@@ -126,8 +125,7 @@ def make_point_array(base_object, point_object, extra=None, use_link=True):
if use_link:
# The PointArray class must be called in this special way
# to make it a LinkArray
- new_obj = doc.addObject("Part::FeaturePython", "PointArray",
- PointArray(None), None, True)
+ new_obj = doc.addObject("Part::FeaturePython", "PointArray", PointArray(None), None, True)
else:
new_obj = doc.addObject("Part::FeaturePython", "PointArray")
PointArray(new_obj)
@@ -140,7 +138,9 @@ def make_point_array(base_object, point_object, extra=None, use_link=True):
if use_link:
ViewProviderDraftLink(new_obj.ViewObject)
else:
- new_obj.Proxy.execute(new_obj) # Updates Count which is required for correct DiffuseColor.
+ new_obj.Proxy.execute(
+ new_obj
+ ) # Updates Count which is required for correct DiffuseColor.
ViewProviderDraftArray(new_obj.ViewObject)
gui_utils.format_object(new_obj, new_obj.Base)
new_obj.ViewObject.Proxy.resetColors(new_obj.ViewObject)
@@ -152,8 +152,9 @@ def make_point_array(base_object, point_object, extra=None, use_link=True):
def makePointArray(base, ptlst):
"""Create PointArray. DEPRECATED. Use 'make_point_array'."""
- utils.use_instead('make_point_array')
+ utils.use_instead("make_point_array")
return make_point_array(base, ptlst)
+
## @}
diff --git a/src/Mod/Draft/draftmake/make_polararray.py b/src/Mod/Draft/draftmake/make_polararray.py
index c4e561567e..af332dc180 100644
--- a/src/Mod/Draft/draftmake/make_polararray.py
+++ b/src/Mod/Draft/draftmake/make_polararray.py
@@ -35,9 +35,7 @@ from draftutils.messages import _err
from draftutils.translate import translate
-def make_polar_array(base_object,
- number=5, angle=360, center=App.Vector(0, 0, 0),
- use_link=True):
+def make_polar_array(base_object, number=5, angle=360, center=App.Vector(0, 0, 0), use_link=True):
"""Create a polar array from the given object.
Parameters
@@ -94,31 +92,32 @@ def make_polar_array(base_object,
found, base_object = utils.find_object(base_object, doc=App.activeDocument())
if not found:
- _err(translate("draft","Wrong input: base_object not in document."))
+ _err(translate("draft", "Wrong input: base_object not in document."))
return None
try:
utils.type_check([(number, int)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be an integer number."))
+ _err(translate("draft", "Wrong input: must be an integer number."))
return None
try:
utils.type_check([(angle, (int, float))], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a number."))
+ _err(translate("draft", "Wrong input: must be a number."))
return None
try:
utils.type_check([(center, App.Vector)], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a vector."))
+ _err(translate("draft", "Wrong input: must be a vector."))
return None
use_link = bool(use_link)
- new_obj = make_array.make_array(base_object,
- arg1=center, arg2=angle, arg3=number,
- use_link=use_link)
+ new_obj = make_array.make_array(
+ base_object, arg1=center, arg2=angle, arg3=number, use_link=use_link
+ )
return new_obj
+
## @}
diff --git a/src/Mod/Draft/draftmake/make_polygon.py b/src/Mod/Draft/draftmake/make_polygon.py
index 4e146e839b..a35479f1c7 100644
--- a/src/Mod/Draft/draftmake/make_polygon.py
+++ b/src/Mod/Draft/draftmake/make_polygon.py
@@ -63,8 +63,9 @@ def make_polygon(nfaces, radius=1, inscribed=True, placement=None, face=None, su
if not App.ActiveDocument:
App.Console.PrintError("No active document. Aborting\n")
return
- if nfaces < 3: return None
- obj = App.ActiveDocument.addObject("Part::Part2DObjectPython","Polygon")
+ if nfaces < 3:
+ return None
+ obj = App.ActiveDocument.addObject("Part::Part2DObjectPython", "Polygon")
Polygon(obj)
obj.FacesNumber = nfaces
obj.Radius = radius
@@ -75,7 +76,8 @@ def make_polygon(nfaces, radius=1, inscribed=True, placement=None, face=None, su
else:
obj.DrawMode = "circumscribed"
obj.AttachmentSupport = support
- if placement: obj.Placement = placement
+ if placement:
+ obj.Placement = placement
if App.GuiUp:
ViewProviderDraft(obj.ViewObject)
gui_utils.format_object(obj)
diff --git a/src/Mod/Draft/draftmake/make_rectangle.py b/src/Mod/Draft/draftmake/make_rectangle.py
index d4b2c4946a..9fe1166b53 100644
--- a/src/Mod/Draft/draftmake/make_rectangle.py
+++ b/src/Mod/Draft/draftmake/make_rectangle.py
@@ -65,7 +65,7 @@ def make_rectangle(length, height=0, placement=None, face=None, support=None):
App.Console.PrintError("No active document. Aborting\n")
return
- if isinstance(length,(list,tuple)) and (len(length) == 4):
+ if isinstance(length, (list, tuple)) and (len(length) == 4):
verts = length
xv = verts[1].sub(verts[0])
yv = verts[3].sub(verts[0])
@@ -75,9 +75,9 @@ def make_rectangle(length, height=0, placement=None, face=None, support=None):
return make_rectangle(xv.Length, yv.Length, rp, face, support)
if placement:
- utils.type_check([(placement,App.Placement)], "make_rectangle")
+ utils.type_check([(placement, App.Placement)], "make_rectangle")
- obj = App.ActiveDocument.addObject("Part::Part2DObjectPython","Rectangle")
+ obj = App.ActiveDocument.addObject("Part::Part2DObjectPython", "Rectangle")
Rectangle(obj)
obj.Length = length
@@ -87,7 +87,8 @@ def make_rectangle(length, height=0, placement=None, face=None, support=None):
if face is not None:
obj.MakeFace = face
- if placement: obj.Placement = placement
+ if placement:
+ obj.Placement = placement
if App.GuiUp:
ViewProviderRectangle(obj.ViewObject)
diff --git a/src/Mod/Draft/draftmake/make_shape2dview.py b/src/Mod/Draft/draftmake/make_shape2dview.py
index 402b8ec3ba..50da4f2bc9 100644
--- a/src/Mod/Draft/draftmake/make_shape2dview.py
+++ b/src/Mod/Draft/draftmake/make_shape2dview.py
@@ -36,7 +36,7 @@ if App.GuiUp:
from draftviewproviders.view_base import ViewProviderDraftAlt
-def make_shape2dview(baseobj,projectionVector=None,facenumbers=[]):
+def make_shape2dview(baseobj, projectionVector=None, facenumbers=[]):
"""make_shape2dview(object, [projectionVector], [facenumbers])
Add a 2D shape to the document, which is a 2D projection of the given object.
@@ -55,7 +55,7 @@ def make_shape2dview(baseobj,projectionVector=None,facenumbers=[]):
if not App.ActiveDocument:
App.Console.PrintError("No active document. Aborting\n")
return
- obj = App.ActiveDocument.addObject("Part::Part2DObjectPython","Shape2DView")
+ obj = App.ActiveDocument.addObject("Part::Part2DObjectPython", "Shape2DView")
Shape2DView(obj)
if App.GuiUp:
ViewProviderDraftAlt(obj.ViewObject)
diff --git a/src/Mod/Draft/draftmake/make_shapestring.py b/src/Mod/Draft/draftmake/make_shapestring.py
index b413b39145..b1b465e088 100644
--- a/src/Mod/Draft/draftmake/make_shapestring.py
+++ b/src/Mod/Draft/draftmake/make_shapestring.py
@@ -51,8 +51,7 @@ def make_shapestring(String, FontFile, Size=100, Tracking=0):
App.Console.PrintError("No active document. Aborting\n")
return
- obj = App.ActiveDocument.addObject("Part::Part2DObjectPython",
- "ShapeString")
+ obj = App.ActiveDocument.addObject("Part::Part2DObjectPython", "ShapeString")
ShapeString(obj)
obj.String = String
obj.FontFile = FontFile
@@ -63,7 +62,8 @@ def make_shapestring(String, FontFile, Size=100, Tracking=0):
ViewProviderShapeString(obj.ViewObject)
gui_utils.format_object(obj)
obrep = obj.ViewObject
- if "PointSize" in obrep.PropertiesList: obrep.PointSize = 1 # hide the segment end points
+ if "PointSize" in obrep.PropertiesList:
+ obrep.PointSize = 1 # hide the segment end points
gui_utils.select(obj)
obj.recompute()
return obj
diff --git a/src/Mod/Draft/draftmake/make_sketch.py b/src/Mod/Draft/draftmake/make_sketch.py
index 88f7a8031b..39d6bce22a 100644
--- a/src/Mod/Draft/draftmake/make_sketch.py
+++ b/src/Mod/Draft/draftmake/make_sketch.py
@@ -38,8 +38,15 @@ from draftutils import utils
from draftutils.translate import translate
-def make_sketch(objects_list, autoconstraints=False, addTo=None,
- delete=False, name="Sketch", radiusPrecision=-1, tol=1e-3):
+def make_sketch(
+ objects_list,
+ autoconstraints=False,
+ addTo=None,
+ delete=False,
+ name="Sketch",
+ radiusPrecision=-1,
+ tol=1e-3,
+):
"""make_sketch(objects_list, [autoconstraints], [addTo], [delete],
[name], [radiusPrecision], [tol])
@@ -82,22 +89,20 @@ def make_sketch(objects_list, autoconstraints=False, addTo=None,
shape_norm_yes = list()
shape_norm_no = list()
- if not isinstance(objects_list,(list,tuple)):
+ if not isinstance(objects_list, (list, tuple)):
objects_list = [objects_list]
for obj in objects_list:
- if isinstance(obj,Part.Shape):
+ if isinstance(obj, Part.Shape):
shape = obj
elif not hasattr(obj, "Shape"):
- App.Console.PrintError(translate("draft",
- "No shape found") + "\n")
+ App.Console.PrintError(translate("draft", "No shape found") + "\n")
return None
else:
shape = obj.Shape
if not DraftGeomUtils.is_planar(shape, tol):
- App.Console.PrintError(translate("draft",
- "All shapes must be planar") + "\n")
+ App.Console.PrintError(translate("draft", "All shapes must be planar") + "\n")
return None
if DraftGeomUtils.get_normal(shape, tol):
@@ -105,15 +110,13 @@ def make_sketch(objects_list, autoconstraints=False, addTo=None,
else:
shape_norm_no.append(shape)
-
shapes_list = shape_norm_yes + shape_norm_no
# test if all shapes are coplanar
if len(shape_norm_yes) >= 1:
for shape in shapes_list[1:]:
if not DraftGeomUtils.are_coplanar(shapes_list[0], shape, tol):
- App.Console.PrintError(translate("draft",
- "All shapes must be coplanar") + "\n")
+ App.Console.PrintError(translate("draft", "All shapes must be coplanar") + "\n")
return None
# define sketch normal
normal = DraftGeomUtils.get_normal(shapes_list[0], tol)
@@ -129,8 +132,7 @@ def make_sketch(objects_list, autoconstraints=False, addTo=None,
normal = App.Vector(0, 0, 1)
else:
if not DraftGeomUtils.is_planar(poly, tol):
- App.Console.PrintError(translate("draft",
- "All shapes must be coplanar") + "\n")
+ App.Console.PrintError(translate("draft", "All shapes must be coplanar") + "\n")
return None
normal = DraftGeomUtils.get_shape_normal(poly)
else:
@@ -148,24 +150,22 @@ def make_sketch(objects_list, autoconstraints=False, addTo=None,
def addRadiusConstraint(edge):
try:
- if radiusPrecision<0:
+ if radiusPrecision < 0:
return
- if radiusPrecision==0:
- constraints.append(Constraint("Radius",
- nobj.GeometryCount-1, edge.Curve.Radius))
+ if radiusPrecision == 0:
+ constraints.append(Constraint("Radius", nobj.GeometryCount - 1, edge.Curve.Radius))
return
- r = round(edge.Curve.Radius,radiusPrecision)
- constraints.append(Constraint("Equal",
- radiuses[r], nobj.GeometryCount-1))
+ r = round(edge.Curve.Radius, radiusPrecision)
+ constraints.append(Constraint("Equal", radiuses[r], nobj.GeometryCount - 1))
except KeyError:
- radiuses[r] = nobj.GeometryCount-1
- constraints.append(Constraint("Radius", nobj.GeometryCount-1, r))
+ radiuses[r] = nobj.GeometryCount - 1
+ constraints.append(Constraint("Radius", nobj.GeometryCount - 1, r))
except AttributeError:
pass
def convertBezier(edge):
if DraftGeomUtils.geomType(edge) == "BezierCurve":
- return(edge.Curve.toBSpline(edge.FirstParameter,edge.LastParameter).toShape())
+ return edge.Curve.toBSpline(edge.FirstParameter, edge.LastParameter).toShape()
else:
return edge
@@ -181,7 +181,9 @@ def make_sketch(objects_list, autoconstraints=False, addTo=None,
point = shapes_list[0].Vertexes[0].Point
base = App.Vector(normal)
- base.Length = point.dot(base.normalize()) # See https://forum.freecad.org/viewtopic.php?f=22&t=69304#p601149
+ base.Length = point.dot(
+ base.normalize()
+ ) # See https://forum.freecad.org/viewtopic.php?f=22&t=69304#p601149
nobj.Placement = App.Placement(base, rotation)
@@ -204,18 +206,23 @@ def make_sketch(objects_list, autoconstraints=False, addTo=None,
shape = obj if tp == "Shape" else obj.Shape
for e in shape.Edges:
newedge = convertBezier(e)
- nobj.addGeometry(DraftGeomUtils.orientEdge(
- newedge, normal, make_arc=True))
+ nobj.addGeometry(DraftGeomUtils.orientEdge(newedge, normal, make_arc=True))
addRadiusConstraint(newedge)
ok = True
if ok and delete:
+
def delObj(obj):
if obj.InList:
- App.Console.PrintWarning(translate("draft",
- "Cannot delete object {} with dependency".format(obj.Label)) + "\n")
+ App.Console.PrintWarning(
+ translate(
+ "draft", "Cannot delete object {} with dependency".format(obj.Label)
+ )
+ + "\n"
+ )
else:
obj.Document.removeObject(obj.Name)
+
try:
if delete == "all":
objs = [obj]
@@ -226,8 +233,10 @@ def make_sketch(objects_list, autoconstraints=False, addTo=None,
else:
delObj(obj)
except Exception as ex:
- App.Console.PrintWarning(translate("draft",
- "Failed to delete object {}: {}".format(obj.Label, ex)) + "\n")
+ App.Console.PrintWarning(
+ translate("draft", "Failed to delete object {}: {}".format(obj.Label, ex))
+ + "\n"
+ )
nobj.addConstraint(constraints)
if autoconstraints:
diff --git a/src/Mod/Draft/draftmake/make_text.py b/src/Mod/Draft/draftmake/make_text.py
index 6248f7b215..4ca4813753 100644
--- a/src/Mod/Draft/draftmake/make_text.py
+++ b/src/Mod/Draft/draftmake/make_text.py
@@ -89,28 +89,25 @@ def make_text(string, placement=None, screen=False, height=None, line_spacing=1)
found, doc = utils.find_doc(App.activeDocument())
if not found:
- _err(translate("draft","No active document. Aborting."))
+ _err(translate("draft", "No active document. Aborting."))
return None
try:
utils.type_check([(string, (str, list))], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a list of strings or a single string."))
+ _err(translate("draft", "Wrong input: must be a list of strings or a single string."))
return None
- if (type(string) is list
- and not all(isinstance(element, str) for element in string)):
- _err(translate("draft","Wrong input: must be a list of strings or a single string."))
+ if type(string) is list and not all(isinstance(element, str) for element in string):
+ _err(translate("draft", "Wrong input: must be a list of strings or a single string."))
return None
if not placement:
placement = App.Placement()
try:
- utils.type_check([(placement, (App.Placement,
- App.Vector,
- App.Rotation))], name=_name)
+ utils.type_check([(placement, (App.Placement, App.Vector, App.Rotation))], name=_name)
except TypeError:
- _err(translate("draft","Wrong input: must be a placement, a vector, or a rotation."))
+ _err(translate("draft", "Wrong input: must be a placement, a vector, or a rotation."))
return None
# Convert the vector or rotation to a full placement
@@ -175,7 +172,7 @@ def convert_draft_texts(textslist=None):
found, doc = utils.find_doc(App.activeDocument())
if not found:
- _err(translate("draft","No active document. Aborting."))
+ _err(translate("draft", "No active document. Aborting."))
return None
if not textslist:
@@ -215,4 +212,5 @@ def convertDraftTexts(textslist=[]):
utils.use_instead("convert_draft_texts")
return convert_draft_texts(textslist)
+
## @}
diff --git a/src/Mod/Draft/draftmake/make_wire.py b/src/Mod/Draft/draftmake/make_wire.py
index d650e431d4..c8e1e9b57b 100644
--- a/src/Mod/Draft/draftmake/make_wire.py
+++ b/src/Mod/Draft/draftmake/make_wire.py
@@ -72,12 +72,12 @@ def make_wire(pointslist, closed=False, placement=None, face=None, support=None,
import Part
- if isinstance(pointslist, (list,tuple)):
+ if isinstance(pointslist, (list, tuple)):
for pnt in pointslist:
if not isinstance(pnt, App.Vector):
App.Console.PrintError(
- "Items must be Base.Vector objects, not {}\n".format(
- type(pnt)))
+ "Items must be Base.Vector objects, not {}\n".format(type(pnt))
+ )
return None
elif isinstance(pointslist, Part.Wire):
@@ -89,11 +89,9 @@ def make_wire(pointslist, closed=False, placement=None, face=None, support=None,
pointslist = [v.Point for v in pointslist.OrderedVertexes]
else:
- App.Console.PrintError("Can't make Draft Wire from {}\n".format(
- type(pointslist)))
+ App.Console.PrintError("Can't make Draft Wire from {}\n".format(type(pointslist)))
return None
-
if len(pointslist) == 0:
App.Console.PrintWarning("Draft Wire created with empty point list\n")
diff --git a/src/Mod/Draft/draftmake/make_wpproxy.py b/src/Mod/Draft/draftmake/make_wpproxy.py
index 62ae7dedf6..6fec1a9de7 100644
--- a/src/Mod/Draft/draftmake/make_wpproxy.py
+++ b/src/Mod/Draft/draftmake/make_wpproxy.py
@@ -46,7 +46,7 @@ def make_workingplaneproxy(placement):
specify the p.
"""
if App.ActiveDocument:
- obj = App.ActiveDocument.addObject("App::FeaturePython","WPProxy")
+ obj = App.ActiveDocument.addObject("App::FeaturePython", "WPProxy")
WorkingPlaneProxy(obj)
if App.GuiUp:
ViewProviderWorkingPlaneProxy(obj.ViewObject)
diff --git a/src/Mod/Draft/draftobjects/array.py b/src/Mod/Draft/draftobjects/array.py
index 15b106c37d..ce23aa6f31 100644
--- a/src/Mod/Draft/draftobjects/array.py
+++ b/src/Mod/Draft/draftobjects/array.py
@@ -75,7 +75,7 @@ class Array(DraftLink):
_log("v1.1, " + obj.Name + ", added hidden property 'PlacementList'")
self.set_general_properties(obj)
- self.execute(obj) # Required to update Count and/or PlacementList.
+ self.execute(obj) # Required to update Count and/or PlacementList.
def set_properties(self, obj):
"""Set properties only if they don't exist."""
@@ -94,67 +94,57 @@ class Array(DraftLink):
properties = obj.PropertiesList
if "Base" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The base object that will be duplicated")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The base object that will be duplicated")
obj.addProperty("App::PropertyLink", "Base", "Objects", _tip, locked=True)
obj.Base = None
if "ArrayType" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The type of array to create.\n"
- "- Ortho: places the copies "
- "in the direction of the global X, "
- "Y, Z axes.\n"
- "- Polar: places the copies along "
- "a circular arc, up to a specified "
- "angle, and with certain orientation "
- "defined by a center and an axis.\n"
- "- Circular: places the copies "
- "in concentric circles "
- "around the base object.")
- obj.addProperty("App::PropertyEnumeration",
- "ArrayType",
- "Objects",
- _tip,
- locked=True)
- obj.ArrayType = ['ortho', 'polar', 'circular']
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The type of array to create.\n"
+ "- Ortho: places the copies "
+ "in the direction of the global X, "
+ "Y, Z axes.\n"
+ "- Polar: places the copies along "
+ "a circular arc, up to a specified "
+ "angle, and with certain orientation "
+ "defined by a center and an axis.\n"
+ "- Circular: places the copies "
+ "in concentric circles "
+ "around the base object.",
+ )
+ obj.addProperty("App::PropertyEnumeration", "ArrayType", "Objects", _tip, locked=True)
+ obj.ArrayType = ["ortho", "polar", "circular"]
if "Fuse" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Specifies if the copies "
- "should be fused together "
- "if they touch each other (slower)")
- obj.addProperty("App::PropertyBool",
- "Fuse",
- "Objects",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Specifies if the copies "
+ "should be fused together "
+ "if they touch each other (slower)",
+ )
+ obj.addProperty("App::PropertyBool", "Fuse", "Objects", _tip, locked=True)
obj.Fuse = False
if "Count" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Total number of elements "
- "in the array.\n"
- "This property is read-only, "
- "as the number depends "
- "on the parameters of the array.")
- obj.addProperty("App::PropertyInteger",
- "Count",
- "Objects",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Total number of elements "
+ "in the array.\n"
+ "This property is read-only, "
+ "as the number depends "
+ "on the parameters of the array.",
+ )
+ obj.addProperty("App::PropertyInteger", "Count", "Objects", _tip, locked=True)
obj.Count = 0
obj.setEditorMode("Count", 1) # Read only
if not self.use_link:
if "PlacementList" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The placement for each array element")
- obj.addProperty("App::PropertyPlacementList",
- "PlacementList",
- "Objects",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The placement for each array element")
+ obj.addProperty(
+ "App::PropertyPlacementList", "PlacementList", "Objects", _tip, locked=True
+ )
obj.PlacementList = []
def set_ortho_properties(self, obj):
@@ -162,66 +152,51 @@ class Array(DraftLink):
properties = obj.PropertiesList
if "NumberX" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Number of copies in X-direction")
- obj.addProperty("App::PropertyInteger",
- "NumberX",
- "Orthogonal array",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Number of copies in X-direction")
+ obj.addProperty(
+ "App::PropertyInteger", "NumberX", "Orthogonal array", _tip, locked=True
+ )
obj.NumberX = 2
if "NumberY" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Number of copies in Y-direction")
- obj.addProperty("App::PropertyInteger",
- "NumberY",
- "Orthogonal array",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Number of copies in Y-direction")
+ obj.addProperty(
+ "App::PropertyInteger", "NumberY", "Orthogonal array", _tip, locked=True
+ )
obj.NumberY = 2
if "NumberZ" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Number of copies in Z-direction")
- obj.addProperty("App::PropertyInteger",
- "NumberZ",
- "Orthogonal array",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Number of copies in Z-direction")
+ obj.addProperty(
+ "App::PropertyInteger", "NumberZ", "Orthogonal array", _tip, locked=True
+ )
obj.NumberZ = 1
if "IntervalX" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Distance and orientation "
- "of intervals in X-direction")
- obj.addProperty("App::PropertyVectorDistance",
- "IntervalX",
- "Orthogonal array",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Distance and orientation " "of intervals in X-direction"
+ )
+ obj.addProperty(
+ "App::PropertyVectorDistance", "IntervalX", "Orthogonal array", _tip, locked=True
+ )
obj.IntervalX = App.Vector(50, 0, 0)
if "IntervalY" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Distance and orientation "
- "of intervals in Y-direction")
- obj.addProperty("App::PropertyVectorDistance",
- "IntervalY",
- "Orthogonal array",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Distance and orientation " "of intervals in Y-direction"
+ )
+ obj.addProperty(
+ "App::PropertyVectorDistance", "IntervalY", "Orthogonal array", _tip, locked=True
+ )
obj.IntervalY = App.Vector(0, 50, 0)
if "IntervalZ" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Distance and orientation "
- "of intervals in Z-direction")
- obj.addProperty("App::PropertyVectorDistance",
- "IntervalZ",
- "Orthogonal array",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Distance and orientation " "of intervals in Z-direction"
+ )
+ obj.addProperty(
+ "App::PropertyVectorDistance", "IntervalZ", "Orthogonal array", _tip, locked=True
+ )
obj.IntervalZ = App.Vector(0, 0, 50)
def set_polar_circular_properties(self, obj):
@@ -229,47 +204,47 @@ class Array(DraftLink):
properties = obj.PropertiesList
if "Axis" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The axis direction around which "
- "the elements in a polar or "
- "a circular array will be created")
- obj.addProperty("App::PropertyVector",
- "Axis",
- "Polar/circular array",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The axis direction around which "
+ "the elements in a polar or "
+ "a circular array will be created",
+ )
+ obj.addProperty(
+ "App::PropertyVector", "Axis", "Polar/circular array", _tip, locked=True
+ )
obj.Axis = App.Vector(0, 0, 1)
if "Center" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Center point for polar and "
- "circular arrays.\n"
- "The 'Axis' passes through this point.")
- obj.addProperty("App::PropertyVectorDistance",
- "Center",
- "Polar/circular array",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Center point for polar and "
+ "circular arrays.\n"
+ "The 'Axis' passes through this point.",
+ )
+ obj.addProperty(
+ "App::PropertyVectorDistance", "Center", "Polar/circular array", _tip, locked=True
+ )
obj.Center = App.Vector(0, 0, 0)
# The AxisReference property must be attached after Axis and Center
# so that onChanged works properly
if "AxisReference" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The axis object that overrides "
- "the value of 'Axis' and 'Center', "
- "for example, a datum line.\n"
- "Its placement, position and rotation, "
- "will be used when creating polar "
- "and circular arrays.\n"
- "Leave this property empty "
- "to be able to set 'Axis' and 'Center' "
- "manually.")
- obj.addProperty("App::PropertyLinkGlobal",
- "AxisReference",
- "Objects",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The axis object that overrides "
+ "the value of 'Axis' and 'Center', "
+ "for example, a datum line.\n"
+ "Its placement, position and rotation, "
+ "will be used when creating polar "
+ "and circular arrays.\n"
+ "Leave this property empty "
+ "to be able to set 'Axis' and 'Center' "
+ "manually.",
+ )
+ obj.addProperty(
+ "App::PropertyLinkGlobal", "AxisReference", "Objects", _tip, locked=True
+ )
obj.AxisReference = None
def set_polar_properties(self, obj):
@@ -277,34 +252,22 @@ class Array(DraftLink):
properties = obj.PropertiesList
if "NumberPolar" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Number of copies in the polar direction")
- obj.addProperty("App::PropertyInteger",
- "NumberPolar",
- "Polar array",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Number of copies in the polar direction")
+ obj.addProperty("App::PropertyInteger", "NumberPolar", "Polar array", _tip, locked=True)
obj.NumberPolar = 5
if "IntervalAxis" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Distance and orientation "
- "of intervals in 'Axis' direction")
- obj.addProperty("App::PropertyVectorDistance",
- "IntervalAxis",
- "Polar array",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Distance and orientation " "of intervals in 'Axis' direction"
+ )
+ obj.addProperty(
+ "App::PropertyVectorDistance", "IntervalAxis", "Polar array", _tip, locked=True
+ )
obj.IntervalAxis = App.Vector(0, 0, 0)
if "Angle" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Angle to cover with copies")
- obj.addProperty("App::PropertyAngle",
- "Angle",
- "Polar array",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Angle to cover with copies")
+ obj.addProperty("App::PropertyAngle", "Angle", "Polar array", _tip, locked=True)
obj.Angle = 360
def set_circular_properties(self, obj):
@@ -312,47 +275,39 @@ class Array(DraftLink):
properties = obj.PropertiesList
if "RadialDistance" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Distance between concentric circles")
- obj.addProperty("App::PropertyDistance",
- "RadialDistance",
- "Circular array",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Distance between concentric circles")
+ obj.addProperty(
+ "App::PropertyDistance", "RadialDistance", "Circular array", _tip, locked=True
+ )
obj.RadialDistance = 50
if "TangentialDistance" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Distance between copies "
- "in the same circle")
- obj.addProperty("App::PropertyDistance",
- "TangentialDistance",
- "Circular array",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Distance between copies " "in the same circle"
+ )
+ obj.addProperty(
+ "App::PropertyDistance", "TangentialDistance", "Circular array", _tip, locked=True
+ )
obj.TangentialDistance = 25
if "NumberCircles" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Number of concentric circle. "
- "The 'Base' object counts as one circle.")
- obj.addProperty("App::PropertyInteger",
- "NumberCircles",
- "Circular array",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Number of concentric circle. " "The 'Base' object counts as one circle.",
+ )
+ obj.addProperty(
+ "App::PropertyInteger", "NumberCircles", "Circular array", _tip, locked=True
+ )
obj.NumberCircles = 3
if "Symmetry" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "A parameter that determines "
- "how many symmetry planes "
- "the circular array will have")
- obj.addProperty("App::PropertyInteger",
- "Symmetry",
- "Circular array",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "A parameter that determines "
+ "how many symmetry planes "
+ "the circular array will have",
+ )
+ obj.addProperty("App::PropertyInteger", "Symmetry", "Circular array", _tip, locked=True)
obj.Symmetry = 1
def set_link_properties(self, obj):
@@ -361,21 +316,17 @@ class Array(DraftLink):
if self.use_link:
if "ExpandArray" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Show the individual array elements "
- "(only for Link arrays)")
- obj.addProperty("App::PropertyBool",
- "ExpandArray",
- "Objects",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Show the individual array elements " "(only for Link arrays)"
+ )
+ obj.addProperty("App::PropertyBool", "ExpandArray", "Objects", _tip, locked=True)
obj.ExpandArray = False
def linkSetup(self, obj):
"""Set up the object as a link object."""
super(Array, self).linkSetup(obj)
- obj.configLinkProperty(ElementCount='Count')
- obj.setPropertyStatus('Count', 'Hidden')
+ obj.configLinkProperty(ElementCount="Count")
+ obj.setPropertyStatus("Count", "Hidden")
def onChanged(self, obj, prop):
"""Execute when a property is changed."""
@@ -395,42 +346,67 @@ class Array(DraftLink):
if prop == "ArrayType":
if obj.ArrayType == "ortho":
- for pr in ("NumberX", "NumberY", "NumberZ",
- "IntervalX", "IntervalY", "IntervalZ"):
+ for pr in ("NumberX", "NumberY", "NumberZ", "IntervalX", "IntervalY", "IntervalZ"):
obj.setPropertyStatus(pr, "-Hidden")
- for pr in ("Axis", "Center", "NumberPolar", "Angle",
- "IntervalAxis", "NumberCircles",
- "RadialDistance", "TangentialDistance",
- "Symmetry"):
+ for pr in (
+ "Axis",
+ "Center",
+ "NumberPolar",
+ "Angle",
+ "IntervalAxis",
+ "NumberCircles",
+ "RadialDistance",
+ "TangentialDistance",
+ "Symmetry",
+ ):
obj.setPropertyStatus(pr, "Hidden")
if obj.ArrayType == "polar":
- for pr in ("Axis", "Center", "NumberPolar",
- "Angle", "IntervalAxis"):
+ for pr in ("Axis", "Center", "NumberPolar", "Angle", "IntervalAxis"):
obj.setPropertyStatus(pr, "-Hidden")
- for pr in ("NumberX", "NumberY", "NumberZ",
- "IntervalX", "IntervalY", "IntervalZ",
- "NumberCircles", "RadialDistance",
- "TangentialDistance", "Symmetry"):
+ for pr in (
+ "NumberX",
+ "NumberY",
+ "NumberZ",
+ "IntervalX",
+ "IntervalY",
+ "IntervalZ",
+ "NumberCircles",
+ "RadialDistance",
+ "TangentialDistance",
+ "Symmetry",
+ ):
obj.setPropertyStatus(pr, "Hidden")
if obj.ArrayType == "circular":
- for pr in ("Axis", "Center", "NumberCircles",
- "RadialDistance", "TangentialDistance",
- "Symmetry"):
+ for pr in (
+ "Axis",
+ "Center",
+ "NumberCircles",
+ "RadialDistance",
+ "TangentialDistance",
+ "Symmetry",
+ ):
obj.setPropertyStatus(pr, "-Hidden")
- for pr in ("NumberX", "NumberY", "NumberZ",
- "IntervalX", "IntervalY", "IntervalZ",
- "NumberPolar", "Angle", "IntervalAxis"):
+ for pr in (
+ "NumberX",
+ "NumberY",
+ "NumberZ",
+ "IntervalX",
+ "IntervalY",
+ "IntervalZ",
+ "NumberPolar",
+ "Angle",
+ "IntervalAxis",
+ ):
obj.setPropertyStatus(pr, "Hidden")
def execute(self, obj):
"""Execute when the object is created or recomputed."""
- if self.props_changed_placement_only(obj) \
- or not obj.Base:
+ if self.props_changed_placement_only(obj) or not obj.Base:
self.props_changed_clear()
return
@@ -444,43 +420,49 @@ class Array(DraftLink):
axis = reference.Rotation * App.Vector(0, 0, 1)
center = reference.Base
else:
- _info = ("'AxisReference' has no 'Placement' property. "
- "Please select a different object to use as "
- "reference.")
+ _info = (
+ "'AxisReference' has no 'Placement' property. "
+ "Please select a different object to use as "
+ "reference."
+ )
raise TypeError(_info)
if obj.ArrayType == "ortho":
- pls = rect_placements(obj.Base.Placement,
- obj.IntervalX,
- obj.IntervalY,
- obj.IntervalZ,
- obj.NumberX,
- obj.NumberY,
- obj.NumberZ)
+ pls = rect_placements(
+ obj.Base.Placement,
+ obj.IntervalX,
+ obj.IntervalY,
+ obj.IntervalZ,
+ obj.NumberX,
+ obj.NumberY,
+ obj.NumberZ,
+ )
elif obj.ArrayType == "polar":
av = obj.IntervalAxis if hasattr(obj, "IntervalAxis") else None
- pls = polar_placements(obj.Base.Placement,
- center, obj.Angle.Value,
- obj.NumberPolar, axis, av)
+ pls = polar_placements(
+ obj.Base.Placement, center, obj.Angle.Value, obj.NumberPolar, axis, av
+ )
elif obj.ArrayType == "circular":
- pls = circ_placements(obj.Base.Placement,
- obj.RadialDistance,
- obj.TangentialDistance,
- axis, center,
- obj.NumberCircles, obj.Symmetry)
+ pls = circ_placements(
+ obj.Base.Placement,
+ obj.RadialDistance,
+ obj.TangentialDistance,
+ axis,
+ center,
+ obj.NumberCircles,
+ obj.Symmetry,
+ )
self.buildShape(obj, pl, pls)
self.props_changed_clear()
- return (not self.use_link)
+ return not self.use_link
# Alias for compatibility with v0.18 and earlier
_Array = Array
-def rect_placements(base_placement,
- xvector, yvector, zvector,
- xnum, ynum, znum):
+def rect_placements(base_placement, xvector, yvector, zvector, xnum, ynum, znum):
"""Determine the placements where the rectangular copies will be."""
pl = base_placement
placements = [pl.copy()]
@@ -513,9 +495,7 @@ def rect_placements(base_placement,
return placements
-def polar_placements(base_placement,
- center, angle,
- number, axis, axisvector):
+def polar_placements(base_placement, center, angle, number, axis, axisvector):
"""Determine the placements where the polar copies will be."""
# print("angle ",angle," num ",num)
placements = [base_placement.copy()]
@@ -540,10 +520,9 @@ def polar_placements(base_placement,
return placements
-def circ_placements(base_placement,
- r_distance, tan_distance,
- axis, center,
- circle_number, symmetry):
+def circ_placements(
+ base_placement, r_distance, tan_distance, axis, center, circle_number, symmetry
+):
"""Determine the placements where the circular copies will be."""
symmetry = max(1, symmetry)
lead = (0, 1, 0)
@@ -572,4 +551,5 @@ def circ_placements(base_placement,
return placements
+
## @}
diff --git a/src/Mod/Draft/draftobjects/base.py b/src/Mod/Draft/draftobjects/base.py
index 507a92fec1..ecd4396d62 100644
--- a/src/Mod/Draft/draftobjects/base.py
+++ b/src/Mod/Draft/draftobjects/base.py
@@ -79,7 +79,7 @@ class DraftObject(object):
obj.Proxy = self
self.Type = tp
- def onDocumentRestored(self,obj):
+ def onDocumentRestored(self, obj):
# Object properties are updated when the document is opened.
self.props_changed_clear()
diff --git a/src/Mod/Draft/draftobjects/bezcurve.py b/src/Mod/Draft/draftobjects/bezcurve.py
index 24f8d4a4e3..6d1b89798f 100644
--- a/src/Mod/Draft/draftobjects/bezcurve.py
+++ b/src/Mod/Draft/draftobjects/bezcurve.py
@@ -41,39 +41,32 @@ class BezCurve(DraftObject):
def __init__(self, obj):
super().__init__(obj, "BezCurve")
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The points of the Bezier curve")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The points of the Bezier curve")
obj.addProperty("App::PropertyVectorList", "Points", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The degree of the Bezier function")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The degree of the Bezier function")
obj.addProperty("App::PropertyInteger", "Degree", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Continuity")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Continuity")
obj.addProperty("App::PropertyIntegerList", "Continuity", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "If the Bezier curve should be closed or not")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "If the Bezier curve should be closed or not")
obj.addProperty("App::PropertyBool", "Closed", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Create a face if this curve is closed")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Create a face if this curve is closed")
obj.addProperty("App::PropertyBool", "MakeFace", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The length of this object")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The length of this object")
obj.addProperty("App::PropertyLength", "Length", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The area of this object")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The area of this object")
obj.addProperty("App::PropertyArea", "Area", "Draft", _tip, locked=True)
obj.MakeFace = params.get_param("MakeFaceMode")
obj.Closed = False
obj.Degree = 3
obj.Continuity = []
- #obj.setEditorMode("Degree", 2)
+ # obj.setEditorMode("Degree", 2)
obj.setEditorMode("Continuity", 1)
def onDocumentRestored(self, obj):
@@ -92,67 +85,69 @@ class BezCurve(DraftObject):
fp.positionBySupport()
self.props_changed_clear()
- def _segpoleslst(self,fp):
+ def _segpoleslst(self, fp):
"""Split the points into segments."""
- if not fp.Closed and len(fp.Points) >= 2: #allow lower degree segment
- poles=fp.Points[1:]
- elif fp.Closed and len(fp.Points) >= fp.Degree: #drawable
- #poles=fp.Points[1:(fp.Degree*(len(fp.Points)//fp.Degree))]+fp.Points[0:1]
- poles=fp.Points[1:]+fp.Points[0:1]
+ if not fp.Closed and len(fp.Points) >= 2: # allow lower degree segment
+ poles = fp.Points[1:]
+ elif fp.Closed and len(fp.Points) >= fp.Degree: # drawable
+ # poles=fp.Points[1:(fp.Degree*(len(fp.Points)//fp.Degree))]+fp.Points[0:1]
+ poles = fp.Points[1:] + fp.Points[0:1]
else:
- poles=[]
- return [poles[x:x+fp.Degree] for x in \
- range(0, len(poles), (fp.Degree or 1))]
+ poles = []
+ return [poles[x : x + fp.Degree] for x in range(0, len(poles), (fp.Degree or 1))]
- def resetcontinuity(self,fp):
- fp.Continuity = [0]*(len(self._segpoleslst(fp))-1+1*fp.Closed)
- #nump= len(fp.Points)-1+fp.Closed*1
- #numsegments = (nump // fp.Degree) + 1 * (nump % fp.Degree > 0) -1
- #fp.Continuity = [0]*numsegments
+ def resetcontinuity(self, fp):
+ fp.Continuity = [0] * (len(self._segpoleslst(fp)) - 1 + 1 * fp.Closed)
+ # nump= len(fp.Points)-1+fp.Closed*1
+ # numsegments = (nump // fp.Degree) + 1 * (nump % fp.Degree > 0) -1
+ # fp.Continuity = [0]*numsegments
def onChanged(self, fp, prop):
self.props_changed_store(prop)
- if prop == 'Closed':
+ if prop == "Closed":
# if remove the last entry when curve gets opened
oldlen = len(fp.Continuity)
- newlen = (len(self._segpoleslst(fp))-1+1*fp.Closed)
+ newlen = len(self._segpoleslst(fp)) - 1 + 1 * fp.Closed
if oldlen > newlen:
fp.Continuity = fp.Continuity[:newlen]
if oldlen < newlen:
- fp.Continuity = fp.Continuity + [0]*(newlen-oldlen)
+ fp.Continuity = fp.Continuity + [0] * (newlen - oldlen)
- if (hasattr(fp,'Closed') and
- fp.Closed and
- prop in ['Points','Degree','Closed'] and
- len(fp.Points) % fp.Degree):
+ if (
+ hasattr(fp, "Closed")
+ and fp.Closed
+ and prop in ["Points", "Degree", "Closed"]
+ and len(fp.Points) % fp.Degree
+ ):
# the curve editing tools can't handle extra points
- fp.Points=fp.Points[:(fp.Degree*(len(fp.Points)//fp.Degree))]
- #for closed curves
+ fp.Points = fp.Points[: (fp.Degree * (len(fp.Points) // fp.Degree))]
+ # for closed curves
if prop in ["Degree"] and fp.Degree >= 1:
self.resetcontinuity(fp)
- if prop in ["Points","Degree","Continuity","Closed"]:
+ if prop in ["Points", "Degree", "Continuity", "Closed"]:
self.createGeometry(fp)
- def createGeometry(self,fp):
+ def createGeometry(self, fp):
import Part
+
plm = fp.Placement
if fp.Points:
startpoint = fp.Points[0]
edges = []
for segpoles in self._segpoleslst(fp):
-# if len(segpoles) == fp.Degree # would skip additional poles
- c = Part.BezierCurve() #last segment may have lower degree
+ # if len(segpoles) == fp.Degree # would skip additional poles
+ c = Part.BezierCurve() # last segment may have lower degree
c.increase(len(segpoles))
- c.setPoles([startpoint]+segpoles)
+ c.setPoles([startpoint] + segpoles)
edges.append(Part.Edge(c))
startpoint = segpoles[-1]
w = Part.Wire(edges)
if fp.Closed and w.isClosed():
try:
- if hasattr(fp,"MakeFace"):
+ if hasattr(fp, "MakeFace"):
if fp.MakeFace:
w = Part.Face(w)
else:
@@ -160,31 +155,31 @@ class BezCurve(DraftObject):
except Part.OCCError:
pass
fp.Shape = w
- if hasattr(fp,"Area") and hasattr(w,"Area"):
+ if hasattr(fp, "Area") and hasattr(w, "Area"):
fp.Area = w.Area
- if hasattr(fp,"Length") and hasattr(w,"Length"):
+ if hasattr(fp, "Length") and hasattr(w, "Length"):
fp.Length = w.Length
fp.Placement = plm
@classmethod
- def symmetricpoles(cls,knot, p1, p2):
+ def symmetricpoles(cls, knot, p1, p2):
"""Make two poles symmetric respective to the knot."""
p1h = App.Vector(p1)
p2h = App.Vector(p2)
p1h.multiply(0.5)
p2h.multiply(0.5)
- return ( knot+p1h-p2h , knot+p2h-p1h )
+ return (knot + p1h - p2h, knot + p2h - p1h)
@classmethod
- def tangentpoles(cls,knot, p1, p2,allowsameside=False):
+ def tangentpoles(cls, knot, p1, p2, allowsameside=False):
"""Make two poles have the same tangent at knot."""
p12n = p2.sub(p1)
p12n.normalize()
- p1k = knot-p1
- p2k = knot-p2
- p1k_= App.Vector(p12n)
- kon12=(p1k * p12n)
- if allowsameside or not (kon12 < 0 or p2k * p12n > 0):# instead of moving
+ p1k = knot - p1
+ p2k = knot - p2
+ p1k_ = App.Vector(p12n)
+ kon12 = p1k * p12n
+ if allowsameside or not (kon12 < 0 or p2k * p12n > 0): # instead of moving
p1k_.multiply(kon12)
pk_k = knot - p1 - p1k_
return (p1 + pk_k, p2 + pk_k)
@@ -192,13 +187,13 @@ class BezCurve(DraftObject):
return cls.symmetricpoles(knot, p1, p2)
@staticmethod
- def modifysymmetricpole(knot,p1):
+ def modifysymmetricpole(knot, p1):
"""calculate the coordinates of the opposite pole
of a symmetric knot"""
return knot + knot - p1
@staticmethod
- def modifytangentpole(knot,p1,oldp2):
+ def modifytangentpole(knot, p1, oldp2):
"""calculate the coordinates of the opposite pole
of a tangent knot"""
pn = knot - p1
diff --git a/src/Mod/Draft/draftobjects/block.py b/src/Mod/Draft/draftobjects/block.py
index 478d5674d6..5ac385b41f 100644
--- a/src/Mod/Draft/draftobjects/block.py
+++ b/src/Mod/Draft/draftobjects/block.py
@@ -39,9 +39,8 @@ class Block(DraftObject):
def __init__(self, obj):
super().__init__(obj, "Block")
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The components of this block")
- obj.addProperty("App::PropertyLinkList","Components", "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The components of this block")
+ obj.addProperty("App::PropertyLinkList", "Components", "Draft", _tip, locked=True)
def onDocumentRestored(self, obj):
super().onDocumentRestored(obj)
@@ -56,6 +55,7 @@ class Block(DraftObject):
return
import Part
+
plm = obj.Placement
shps = []
for c in obj.Components:
diff --git a/src/Mod/Draft/draftobjects/bspline.py b/src/Mod/Draft/draftobjects/bspline.py
index 56c8ef6feb..41292dc8d1 100644
--- a/src/Mod/Draft/draftobjects/bspline.py
+++ b/src/Mod/Draft/draftobjects/bspline.py
@@ -41,20 +41,17 @@ class BSpline(DraftObject):
def __init__(self, obj):
super().__init__(obj, "BSpline")
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The points of the B-spline")
- obj.addProperty("App::PropertyVectorList","Points", "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The points of the B-spline")
+ obj.addProperty("App::PropertyVectorList", "Points", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "If the B-spline is closed or not")
- obj.addProperty("App::PropertyBool","Closed", "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "If the B-spline is closed or not")
+ obj.addProperty("App::PropertyBool", "Closed", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Create a face if this B-spline is closed")
- obj.addProperty("App::PropertyBool","MakeFace", "Draft",_tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Create a face if this B-spline is closed")
+ obj.addProperty("App::PropertyBool", "MakeFace", "Draft", _tip, locked=True)
_tip = QT_TRANSLATE_NOOP("App::Property", "The area of this object")
- obj.addProperty("App::PropertyArea","Area", "Draft", _tip, locked=True)
+ obj.addProperty("App::PropertyArea", "Area", "Draft", _tip, locked=True)
obj.MakeFace = params.get_param("MakeFaceMode")
obj.Closed = False
@@ -63,28 +60,26 @@ class BSpline(DraftObject):
def onDocumentRestored(self, obj):
super().onDocumentRestored(obj)
- gui_utils.restore_view_object(
- obj, vp_module="view_bspline", vp_class="ViewProviderBSpline"
- )
+ gui_utils.restore_view_object(obj, vp_module="view_bspline", vp_class="ViewProviderBSpline")
- def assureProperties(self, obj): # for Compatibility with older versions
+ def assureProperties(self, obj): # for Compatibility with older versions
if not hasattr(obj, "Parameterization"):
- _tip = QT_TRANSLATE_NOOP("App::Property","Parameterization factor")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Parameterization factor")
obj.addProperty("App::PropertyFloat", "Parameterization", "Draft", _tip, locked=True)
obj.Parameterization = 1.0
self.knotSeq = []
- def parameterization (self, pts, a, closed):
+ def parameterization(self, pts, a, closed):
"""Computes a knot Sequence for a set of points.
fac (0-1) : parameterization factor
fac = 0 -> Uniform / fac=0.5 -> Centripetal / fac=1.0 -> Chord-Length
"""
- if closed: # we need to add the first point as the end point
+ if closed: # we need to add the first point as the end point
pts.append(pts[0])
params = [0]
- for i in range(1,len(pts)):
- p = pts[i].sub(pts[i-1])
- pl = pow(p.Length,a)
+ for i in range(1, len(pts)):
+ p = pts[i].sub(pts[i - 1])
+ pl = pow(p.Length, a)
params.append(params[-1] + pl)
return params
@@ -92,14 +87,13 @@ class BSpline(DraftObject):
self.props_changed_store(prop)
if prop == "Parameterization":
- if fp.Parameterization < 0.:
- fp.Parameterization = 0.
+ if fp.Parameterization < 0.0:
+ fp.Parameterization = 0.0
if fp.Parameterization > 1.0:
fp.Parameterization = 1.0
def execute(self, obj):
- if self.props_changed_placement_only() \
- or not obj.Points:
+ if self.props_changed_placement_only() or not obj.Points:
obj.positionBySupport()
self.props_changed_clear()
return
@@ -112,18 +106,21 @@ class BSpline(DraftObject):
plm = obj.Placement
if obj.Closed and (len(obj.Points) > 2):
if obj.Points[0] == obj.Points[-1]: # should not occur, but OCC will crash
- _err = QT_TRANSLATE_NOOP('Draft', "_BSpline.createGeometry: "
- "Closed with same first/last Point. Geometry not updated.")
- App.Console.PrintError(_err+"\n")
+ _err = QT_TRANSLATE_NOOP(
+ "Draft",
+ "_BSpline.createGeometry: "
+ "Closed with same first/last Point. Geometry not updated.",
+ )
+ App.Console.PrintError(_err + "\n")
return
spline = Part.BSplineCurve()
- spline.interpolate(obj.Points, PeriodicFlag = True, Parameters = self.knotSeq)
+ spline.interpolate(obj.Points, PeriodicFlag=True, Parameters=self.knotSeq)
# DNC: bug fix: convert to face if closed
shape = Part.Wire(spline.toShape())
# Creating a face from a closed spline cannot be expected to always work
# Usually, if the spline is not flat the call of Part.Face() fails
try:
- if hasattr(obj,"MakeFace"):
+ if hasattr(obj, "MakeFace"):
if obj.MakeFace:
shape = Part.Face(shape)
else:
@@ -131,14 +128,14 @@ class BSpline(DraftObject):
except Part.OCCError:
pass
obj.Shape = shape
- if hasattr(obj,"Area") and hasattr(shape,"Area"):
+ if hasattr(obj, "Area") and hasattr(shape, "Area"):
obj.Area = shape.Area
else:
spline = Part.BSplineCurve()
- spline.interpolate(obj.Points, PeriodicFlag = False, Parameters = self.knotSeq)
+ spline.interpolate(obj.Points, PeriodicFlag=False, Parameters=self.knotSeq)
shape = spline.toShape()
obj.Shape = shape
- if hasattr(obj,"Area") and hasattr(shape,"Area"):
+ if hasattr(obj, "Area") and hasattr(shape, "Area"):
obj.Area = shape.Area
obj.Placement = plm
obj.positionBySupport()
diff --git a/src/Mod/Draft/draftobjects/circle.py b/src/Mod/Draft/draftobjects/circle.py
index ec4e0c54e1..65c4183519 100644
--- a/src/Mod/Draft/draftobjects/circle.py
+++ b/src/Mod/Draft/draftobjects/circle.py
@@ -42,25 +42,23 @@ class Circle(DraftObject):
super().__init__(obj, "Circle")
_tip = QT_TRANSLATE_NOOP("App::Property", "Start angle of the arc")
- obj.addProperty("App::PropertyAngle", "FirstAngle",
- "Draft", _tip, locked=True)
+ obj.addProperty("App::PropertyAngle", "FirstAngle", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property", "End angle of the arc (for a full circle, \
- give it same value as First Angle)")
- obj.addProperty("App::PropertyAngle","LastAngle",
- "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "End angle of the arc (for a full circle, \
+ give it same value as First Angle)",
+ )
+ obj.addProperty("App::PropertyAngle", "LastAngle", "Draft", _tip, locked=True)
_tip = QT_TRANSLATE_NOOP("App::Property", "Radius of the circle")
- obj.addProperty("App::PropertyLength", "Radius",
- "Draft", _tip, locked=True)
+ obj.addProperty("App::PropertyLength", "Radius", "Draft", _tip, locked=True)
_tip = QT_TRANSLATE_NOOP("App::Property", "Create a face")
- obj.addProperty("App::PropertyBool", "MakeFace",
- "Draft", _tip, locked=True)
+ obj.addProperty("App::PropertyBool", "MakeFace", "Draft", _tip, locked=True)
_tip = QT_TRANSLATE_NOOP("App::Property", "The area of this object")
- obj.addProperty("App::PropertyArea", "Area",
- "Draft", _tip, locked=True)
+ obj.addProperty("App::PropertyArea", "Area", "Draft", _tip, locked=True)
obj.MakeFace = params.get_param("MakeFaceMode")
@@ -79,20 +77,22 @@ class Circle(DraftObject):
plm = obj.Placement
- shape = Part.makeCircle(obj.Radius.Value,
- App.Vector(0,0,0),
- App.Vector(0,0,1),
- obj.FirstAngle.Value,
- obj.LastAngle.Value)
+ shape = Part.makeCircle(
+ obj.Radius.Value,
+ App.Vector(0, 0, 0),
+ App.Vector(0, 0, 1),
+ obj.FirstAngle.Value,
+ obj.LastAngle.Value,
+ )
if obj.FirstAngle.Value == obj.LastAngle.Value:
shape = Part.Wire(shape)
- if getattr(obj,"MakeFace",True):
+ if getattr(obj, "MakeFace", True):
shape = Part.Face(shape)
obj.Shape = shape
- if hasattr(obj,"Area") and hasattr(shape,"Area"):
+ if hasattr(obj, "Area") and hasattr(shape, "Area"):
obj.Area = shape.Area
obj.Placement = plm
diff --git a/src/Mod/Draft/draftobjects/clone.py b/src/Mod/Draft/draftobjects/clone.py
index af1b65b474..6858f6f83a 100644
--- a/src/Mod/Draft/draftobjects/clone.py
+++ b/src/Mod/Draft/draftobjects/clone.py
@@ -43,7 +43,6 @@ class Clone(DraftObject):
self.set_properties(obj)
super().__init__(obj, "Clone")
-
def set_properties(self, obj):
pl = obj.PropertiesList
if not "Objects" in pl:
@@ -54,9 +53,10 @@ class Clone(DraftObject):
obj.addProperty("App::PropertyVector", "Scale", "Draft", _tip, locked=True)
obj.Scale = App.Vector(1, 1, 1)
if not "Fuse" in pl:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "If Clones includes several objects,\n"
- "set True for fusion or False for compound")
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "If Clones includes several objects,\n" "set True for fusion or False for compound",
+ )
obj.addProperty("App::PropertyBool", "Fuse", "Draft", _tip, locked=True)
if not "ForceCompound" in pl:
_tip = QT_TRANSLATE_NOOP("App::Property", "Always create a compound")
@@ -88,6 +88,7 @@ class Clone(DraftObject):
tmps += s.Edges
shapes = tmps
import Part
+
if len(shapes) == 1:
if force_compound:
return Part.makeCompound([shapes[0]])
@@ -106,21 +107,24 @@ class Clone(DraftObject):
return sh
return Part.makeCompound(shapes)
- def execute(self,obj):
+ def execute(self, obj):
if self.props_changed_placement_only(obj):
- if hasattr(obj,"positionBySupport"):
+ if hasattr(obj, "positionBySupport"):
obj.positionBySupport()
self.props_changed_clear()
return
import Part
+
pl = obj.Placement
shapes = []
if obj.isDerivedFrom("Part::Part2DObject"):
# if our clone is 2D, make sure all its linked geometry is 2D too
for o in obj.Objects:
if not o.getLinkedObject(True).isDerivedFrom("Part::Part2DObject"):
- App.Console.PrintWarning("Warning 2D Clone "+obj.Name+" contains 3D geometry")
+ App.Console.PrintWarning(
+ "Warning 2D Clone " + obj.Name + " contains 3D geometry"
+ )
return
for o in obj.Objects:
sh = Part.getShape(o)
@@ -129,7 +133,7 @@ class Clone(DraftObject):
if shapes:
sh = self.join(obj, shapes)
m = App.Matrix()
- if hasattr(obj,"Scale") and not sh.isNull():
+ if hasattr(obj, "Scale") and not sh.isNull():
if not DraftVecUtils.equals(obj.Scale, App.Vector(1, 1, 1)):
op = sh.Placement
sh.Placement = App.Placement()
@@ -139,17 +143,17 @@ class Clone(DraftObject):
obj.Shape = sh
obj.Placement = pl
- if hasattr(obj,"positionBySupport"):
+ if hasattr(obj, "positionBySupport"):
obj.positionBySupport()
self.props_changed_clear()
def onChanged(self, obj, prop):
self.props_changed_store(prop)
- def getSubVolume(self,obj,placement=None):
+ def getSubVolume(self, obj, placement=None):
# this allows clones of arch windows to return a subvolume too
if obj.Objects:
- if hasattr(obj.Objects[0],"Proxy"):
+ if hasattr(obj.Objects[0], "Proxy"):
if hasattr(obj.Objects[0].Proxy, "getSubVolume"):
if not placement:
# clones must displace the original subvolume too
diff --git a/src/Mod/Draft/draftobjects/dimension.py b/src/Mod/Draft/draftobjects/dimension.py
index ecc56ede10..7177ed5a39 100644
--- a/src/Mod/Draft/draftobjects/dimension.py
+++ b/src/Mod/Draft/draftobjects/dimension.py
@@ -1,4 +1,4 @@
-#
+#
# ***************************************************************************
# * Copyright (c) 2009, 2010 Yorik van Havre *
# * Copyright (c) 2009, 2010 Ken Cline *
@@ -128,69 +128,60 @@ class DimensionBase(DraftAnnotation):
properties = obj.PropertiesList
if "Normal" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The normal direction of the text "
- "of the dimension")
- obj.addProperty("App::PropertyVector",
- "Normal",
- "Dimension",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "The normal direction of the text " "of the dimension"
+ )
+ obj.addProperty("App::PropertyVector", "Normal", "Dimension", _tip, locked=True)
obj.Normal = App.Vector(0, 0, 1)
# TODO: remove Support property as it is not used at all.
# It is just set at creation time by the make_dimension function
# but it is not used.
if "Support" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The object measured by this dimension")
- obj.addProperty("App::PropertyLink",
- "Support",
- "Dimension",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The object measured by this dimension")
+ obj.addProperty("App::PropertyLink", "Support", "Dimension", _tip, locked=True)
obj.Support = None
if "LinkedGeometry" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The object, and specific subelements "
- "of it,\n"
- "that this dimension "
- "is measuring.\n"
- "\n"
- "There are various possibilities:\n"
- "- An object, and one of its edges.\n"
- "- An object, and two of its vertices.\n"
- "- An arc object, and its edge.")
- obj.addProperty("App::PropertyLinkSubList",
- "LinkedGeometry",
- "Dimension",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The object, and specific subelements "
+ "of it,\n"
+ "that this dimension "
+ "is measuring.\n"
+ "\n"
+ "There are various possibilities:\n"
+ "- An object, and one of its edges.\n"
+ "- An object, and two of its vertices.\n"
+ "- An arc object, and its edge.",
+ )
+ obj.addProperty(
+ "App::PropertyLinkSubList", "LinkedGeometry", "Dimension", _tip, locked=True
+ )
obj.LinkedGeometry = []
if "Dimline" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "A point through which the dimension "
- "line, or an extrapolation of it, "
- "will pass.\n"
- "\n"
- "- For linear dimensions, this property "
- "controls how close the dimension line\n"
- "is to the measured object.\n"
- "- For radial dimensions, this controls "
- "the direction of the dimension line\n"
- "that displays the measured radius or "
- "diameter.\n"
- "- For angular dimensions, "
- "this controls the radius of the "
- "dimension arc\n"
- "that displays the measured angle.")
- obj.addProperty("App::PropertyVectorDistance",
- "Dimline",
- "Dimension",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "A point through which the dimension "
+ "line, or an extrapolation of it, "
+ "will pass.\n"
+ "\n"
+ "- For linear dimensions, this property "
+ "controls how close the dimension line\n"
+ "is to the measured object.\n"
+ "- For radial dimensions, this controls "
+ "the direction of the dimension line\n"
+ "that displays the measured radius or "
+ "diameter.\n"
+ "- For angular dimensions, "
+ "this controls the radius of the "
+ "dimension arc\n"
+ "that displays the measured angle.",
+ )
+ obj.addProperty(
+ "App::PropertyVectorDistance", "Dimline", "Dimension", _tip, locked=True
+ )
obj.Dimline = App.Vector(0, 1, 0)
def update_properties_0v21(self, obj, vobj):
@@ -223,77 +214,75 @@ class LinearDimension(DimensionBase):
properties = obj.PropertiesList
if "Start" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Starting point of the dimension line.\n"
- "\n"
- "If it is a radius dimension it will be "
- "the center of the arc.\n"
- "If it is a diameter dimension "
- "it will be a point that lies "
- "on the arc.")
- obj.addProperty("App::PropertyVectorDistance",
- "Start",
- "Linear/radial dimension",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Starting point of the dimension line.\n"
+ "\n"
+ "If it is a radius dimension it will be "
+ "the center of the arc.\n"
+ "If it is a diameter dimension "
+ "it will be a point that lies "
+ "on the arc.",
+ )
+ obj.addProperty(
+ "App::PropertyVectorDistance", "Start", "Linear/radial dimension", _tip, locked=True
+ )
obj.Start = App.Vector(0, 0, 0)
if "End" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Ending point of the dimension line.\n"
- "\n"
- "If it is a radius or diameter "
- "dimension\n"
- "it will be a point that lies "
- "on the arc.")
- obj.addProperty("App::PropertyVectorDistance",
- "End",
- "Linear/radial dimension",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Ending point of the dimension line.\n"
+ "\n"
+ "If it is a radius or diameter "
+ "dimension\n"
+ "it will be a point that lies "
+ "on the arc.",
+ )
+ obj.addProperty(
+ "App::PropertyVectorDistance", "End", "Linear/radial dimension", _tip, locked=True
+ )
obj.End = App.Vector(1, 0, 0)
if "Direction" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The direction of the dimension line.\n"
- "If this remains '(0,0,0)', "
- "the direction will be calculated "
- "automatically.")
- obj.addProperty("App::PropertyVector",
- "Direction",
- "Linear/radial dimension",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The direction of the dimension line.\n"
+ "If this remains '(0,0,0)', "
+ "the direction will be calculated "
+ "automatically.",
+ )
+ obj.addProperty(
+ "App::PropertyVector", "Direction", "Linear/radial dimension", _tip, locked=True
+ )
if "Distance" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The value of the measurement.\n"
- "\n"
- "This property is read-only because "
- "the value is calculated\n"
- "from the 'Start' and 'End' properties.\n"
- "\n"
- "If the 'Linked Geometry' "
- "is an arc or circle, this 'Distance'\n"
- "is the radius or diameter, depending "
- "on the 'Diameter' property.")
- obj.addProperty("App::PropertyLength",
- "Distance",
- "Linear/radial dimension",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The value of the measurement.\n"
+ "\n"
+ "This property is read-only because "
+ "the value is calculated\n"
+ "from the 'Start' and 'End' properties.\n"
+ "\n"
+ "If the 'Linked Geometry' "
+ "is an arc or circle, this 'Distance'\n"
+ "is the radius or diameter, depending "
+ "on the 'Diameter' property.",
+ )
+ obj.addProperty(
+ "App::PropertyLength", "Distance", "Linear/radial dimension", _tip, locked=True
+ )
obj.Distance = 0
if "Diameter" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "When measuring circular arcs, "
- "it determines whether to display\n"
- "the radius or the diameter value")
- obj.addProperty("App::PropertyBool",
- "Diameter",
- "Radial dimension",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "When measuring circular arcs, "
+ "it determines whether to display\n"
+ "the radius or the diameter value",
+ )
+ obj.addProperty("App::PropertyBool", "Diameter", "Radial dimension", _tip, locked=True)
obj.Diameter = False
def onDocumentRestored(self, obj):
@@ -320,12 +309,12 @@ class LinearDimension(DimensionBase):
as they aren't used.
"""
if hasattr(obj, "Distance"):
- obj.setPropertyStatus('Distance', 'ReadOnly')
+ obj.setPropertyStatus("Distance", "ReadOnly")
# if hasattr(obj, "Normal"):
# obj.setPropertyStatus('Normal', 'Hidden')
if hasattr(obj, "Support"):
- obj.setPropertyStatus('Support', 'Hidden')
+ obj.setPropertyStatus("Support", "Hidden")
def transform(self, obj, pla):
"""Transform the object by applying a placement."""
@@ -353,24 +342,20 @@ class LinearDimension(DimensionBase):
# If it has one subelement, we assume an edge
# that can be a straight line, or a circular edge
subelement = sub_list[0]
- (obj.Start,
- obj.End) = measure_one_obj_edge(linked_obj,
- subelement,
- obj.Dimline,
- obj.Diameter)
+ (obj.Start, obj.End) = measure_one_obj_edge(
+ linked_obj, subelement, obj.Dimline, obj.Diameter
+ )
elif len(sub_list) == 2:
# If it has two subelements, we assume a straight edge
# that is measured by two vertices
- (obj.Start,
- obj.End) = measure_one_obj_vertices(linked_obj,
- sub_list)
+ (obj.Start, obj.End) = measure_one_obj_vertices(linked_obj, sub_list)
elif len(obj.LinkedGeometry) == 2:
# If the list has two objects, it measures the distance
# between the two vertices in those two objects
- (obj.Start,
- obj.End) = measure_two_objects(obj.LinkedGeometry[0],
- obj.LinkedGeometry[1])
+ (obj.Start, obj.End) = measure_two_objects(
+ obj.LinkedGeometry[0], obj.LinkedGeometry[1]
+ )
# Update the distance property by comparing the floats
# with the precision
@@ -521,58 +506,56 @@ class AngularDimension(DimensionBase):
properties = obj.PropertiesList
if "FirstAngle" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Starting angle of the dimension line "
- "(circular arc).\n"
- "The arc is drawn counter-clockwise.")
- obj.addProperty("App::PropertyAngle",
- "FirstAngle",
- "Angular dimension",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Starting angle of the dimension line "
+ "(circular arc).\n"
+ "The arc is drawn counter-clockwise.",
+ )
+ obj.addProperty(
+ "App::PropertyAngle", "FirstAngle", "Angular dimension", _tip, locked=True
+ )
obj.FirstAngle = 0
if "LastAngle" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Ending angle of the dimension line "
- "(circular arc).\n"
- "The arc is drawn counter-clockwise.")
- obj.addProperty("App::PropertyAngle",
- "LastAngle",
- "Angular dimension",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Ending angle of the dimension line "
+ "(circular arc).\n"
+ "The arc is drawn counter-clockwise.",
+ )
+ obj.addProperty(
+ "App::PropertyAngle", "LastAngle", "Angular dimension", _tip, locked=True
+ )
obj.LastAngle = 90
if "Center" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The center point of the dimension "
- "line, which is a circular arc.\n"
- "\n"
- "This is normally the point where two "
- "line segments, or their extensions\n"
- "intersect, resulting in the "
- "measured 'Angle' between them.")
- obj.addProperty("App::PropertyVectorDistance",
- "Center",
- "Angular dimension",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The center point of the dimension "
+ "line, which is a circular arc.\n"
+ "\n"
+ "This is normally the point where two "
+ "line segments, or their extensions\n"
+ "intersect, resulting in the "
+ "measured 'Angle' between them.",
+ )
+ obj.addProperty(
+ "App::PropertyVectorDistance", "Center", "Angular dimension", _tip, locked=True
+ )
obj.Center = App.Vector(0, 0, 0)
if "Angle" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The value of the measurement.\n"
- "\n"
- "This property is read-only because "
- "the value is calculated from\n"
- "the 'First Angle' and "
- "'Last Angle' properties.")
- obj.addProperty("App::PropertyAngle",
- "Angle",
- "Angular dimension",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The value of the measurement.\n"
+ "\n"
+ "This property is read-only because "
+ "the value is calculated from\n"
+ "the 'First Angle' and "
+ "'Last Angle' properties.",
+ )
+ obj.addProperty("App::PropertyAngle", "Angle", "Angular dimension", _tip, locked=True)
obj.Angle = 0
def onDocumentRestored(self, obj):
@@ -644,14 +627,14 @@ class AngularDimension(DimensionBase):
as they aren't used.
"""
if hasattr(obj, "Angle"):
- obj.setPropertyStatus('Angle', 'ReadOnly')
+ obj.setPropertyStatus("Angle", "ReadOnly")
if hasattr(obj, "Normal"):
- obj.setPropertyStatus('Normal', 'Hidden')
+ obj.setPropertyStatus("Normal", "Hidden")
if hasattr(obj, "Support"):
- obj.setPropertyStatus('Support', 'Hidden')
+ obj.setPropertyStatus("Support", "Hidden")
if hasattr(obj, "LinkedGeometry"):
- obj.setPropertyStatus('LinkedGeometry', 'Hidden')
+ obj.setPropertyStatus("LinkedGeometry", "Hidden")
def measure_two_obj_angles(link_sub_1, link_sub_2):
diff --git a/src/Mod/Draft/draftobjects/draft_annotation.py b/src/Mod/Draft/draftobjects/draft_annotation.py
index cbd7e621b5..849c6745e2 100644
--- a/src/Mod/Draft/draftobjects/draft_annotation.py
+++ b/src/Mod/Draft/draftobjects/draft_annotation.py
@@ -92,9 +92,7 @@ class DraftAnnotation(object):
typ = obj.Proxy.Type
if typ == "Label":
vobj.ArrowTypeStart = vobj.ArrowType
- elif typ == "AngularDimension" \
- or obj.Diameter \
- or not vobj.Proxy.is_linked_to_circle():
+ elif typ == "AngularDimension" or obj.Diameter or not vobj.Proxy.is_linked_to_circle():
vobj.ArrowTypeStart = vobj.ArrowType
vobj.ArrowTypeEnd = vobj.ArrowType
else: # Radial dimension
@@ -115,7 +113,7 @@ class DraftAnnotation(object):
return
- def loads(self,state):
+ def loads(self, state):
return
diff --git a/src/Mod/Draft/draftobjects/draftlink.py b/src/Mod/Draft/draftobjects/draftlink.py
index 3d86fa578b..ab9eee10da 100644
--- a/src/Mod/Draft/draftobjects/draftlink.py
+++ b/src/Mod/Draft/draftobjects/draftlink.py
@@ -80,7 +80,7 @@ class DraftLink(DraftObject):
def attach(self, obj):
"""Set up the properties when the object is attached."""
if self.use_link:
- obj.addExtension('App::LinkExtensionPython')
+ obj.addExtension("App::LinkExtensionPython")
self.linkSetup(obj)
def canLinkProperties(self, _obj):
@@ -92,68 +92,55 @@ class DraftLink(DraftObject):
def linkSetup(self, obj):
"""Set up the link properties on attachment."""
- obj.configLinkProperty('Placement', LinkedObject='Base')
+ obj.configLinkProperty("Placement", LinkedObject="Base")
- if not hasattr(obj, 'AlwaysSyncPlacement'):
- _tip = QT_TRANSLATE_NOOP("App::Property",
- 'Force sync pattern placements even when array elements are expanded')
- obj.addProperty("App::PropertyBool",
- "AlwaysSyncPlacement",
- "Draft",
- _tip,
- locked=True)
+ if not hasattr(obj, "AlwaysSyncPlacement"):
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Force sync pattern placements even when array elements are expanded",
+ )
+ obj.addProperty("App::PropertyBool", "AlwaysSyncPlacement", "Draft", _tip, locked=True)
- if hasattr(obj, 'ShowElement'):
+ if hasattr(obj, "ShowElement"):
# Rename 'ShowElement' property to 'ExpandArray' to avoid conflict
# with native App::Link
- obj.configLinkProperty('ShowElement')
+ obj.configLinkProperty("ShowElement")
showElement = obj.ShowElement
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Show the individual array elements")
- obj.addProperty("App::PropertyBool",
- "ExpandArray",
- "Draft",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Show the individual array elements")
+ obj.addProperty("App::PropertyBool", "ExpandArray", "Draft", _tip, locked=True)
obj.ExpandArray = showElement
- obj.configLinkProperty(ShowElement='ExpandArray')
- obj.removeProperty('ShowElement')
+ obj.configLinkProperty(ShowElement="ExpandArray")
+ obj.removeProperty("ShowElement")
else:
- obj.configLinkProperty(ShowElement='ExpandArray')
+ obj.configLinkProperty(ShowElement="ExpandArray")
- if getattr(obj, 'ExpandArray', False):
- obj.setPropertyStatus('PlacementList', 'Immutable')
+ if getattr(obj, "ExpandArray", False):
+ obj.setPropertyStatus("PlacementList", "Immutable")
else:
- obj.setPropertyStatus('PlacementList', '-Immutable')
+ obj.setPropertyStatus("PlacementList", "-Immutable")
- if not hasattr(obj, 'LinkTransform'):
- obj.addProperty('App::PropertyBool',
- 'LinkTransform',
- ' Link',
- locked=True)
+ if not hasattr(obj, "LinkTransform"):
+ obj.addProperty("App::PropertyBool", "LinkTransform", " Link", locked=True)
- if not hasattr(obj, 'ColoredElements'):
- obj.addProperty('App::PropertyLinkSubHidden',
- 'ColoredElements',
- ' Link',
- locked=True)
- obj.setPropertyStatus('ColoredElements', 'Hidden')
+ if not hasattr(obj, "ColoredElements"):
+ obj.addProperty("App::PropertyLinkSubHidden", "ColoredElements", " Link", locked=True)
+ obj.setPropertyStatus("ColoredElements", "Hidden")
- if not hasattr(obj,'LinkCopyOnChange'):
- obj.addProperty("App::PropertyEnumeration","LinkCopyOnChange"," Link",locked=True)
+ if not hasattr(obj, "LinkCopyOnChange"):
+ obj.addProperty("App::PropertyEnumeration", "LinkCopyOnChange", " Link", locked=True)
- obj.configLinkProperty('LinkCopyOnChange','LinkTransform','ColoredElements')
+ obj.configLinkProperty("LinkCopyOnChange", "LinkTransform", "ColoredElements")
- if not getattr(obj, 'Fuse', False):
- obj.setPropertyStatus('Shape', 'Transient')
+ if not getattr(obj, "Fuse", False):
+ obj.setPropertyStatus("Shape", "Transient")
def getViewProviderName(self, _obj):
"""Override the view provider name."""
if self.use_link:
- return 'Gui::ViewProviderLinkPython'
- return ''
+ return "Gui::ViewProviderLinkPython"
+ return ""
def migrate_attributes(self, obj):
"""Migrate old attribute names to new names if they exist.
@@ -177,10 +164,10 @@ class DraftLink(DraftObject):
if self.use_link:
self.linkSetup(obj)
else:
- obj.setPropertyStatus('Shape', '-Transient')
+ obj.setPropertyStatus("Shape", "-Transient")
if obj.Shape.isNull():
- if getattr(obj, 'PlacementList', None):
+ if getattr(obj, "PlacementList", None):
self.buildShape(obj, obj.Placement, obj.PlacementList)
else:
self.execute(obj)
@@ -198,14 +185,13 @@ class DraftLink(DraftObject):
def buildShape(self, obj, pl, pls):
"""Build the shape of the link object."""
if self.use_link:
- if not getattr(obj, 'ExpandArray', False) or obj.Count != len(pls):
- obj.setPropertyStatus('PlacementList', '-Immutable')
+ if not getattr(obj, "ExpandArray", False) or obj.Count != len(pls):
+ obj.setPropertyStatus("PlacementList", "-Immutable")
obj.PlacementList = pls
- obj.setPropertyStatus('PlacementList', 'Immutable')
+ obj.setPropertyStatus("PlacementList", "Immutable")
obj.Count = len(pls)
- if getattr(obj, 'ExpandArray', False) \
- and getattr(obj, 'AlwaysSyncPlacement', False):
- for pla,child in zip(pls,obj.ElementList):
+ if getattr(obj, "ExpandArray", False) and getattr(obj, "AlwaysSyncPlacement", False):
+ for pla, child in zip(pls, obj.ElementList):
child.Placement = pla
else:
obj.PlacementList = pls
@@ -213,12 +199,13 @@ class DraftLink(DraftObject):
obj.Count = len(pls)
if obj.Base:
- shape = getattr(obj.Base, 'Shape', None)
+ shape = getattr(obj.Base, "Shape", None)
if not isinstance(shape, Part.Shape):
obj.Shape = Part.Shape()
elif shape.isNull():
- _err_msg = ("'{}' cannot build shape "
- "from '{}'\n".format(obj.Label, obj.Base.Label))
+ _err_msg = "'{}' cannot build shape " "from '{}'\n".format(
+ obj.Label, obj.Base.Label
+ )
raise RuntimeError(_err_msg)
else:
# Resetting the Placement of the copied shape does not work for
@@ -228,13 +215,13 @@ class DraftLink(DraftObject):
shape.transformShape(place.Matrix.inverse())
base = []
for i, pla in enumerate(pls):
- vis = getattr(obj, 'VisibilityList', [])
+ vis = getattr(obj, "VisibilityList", [])
if len(vis) > i and not vis[i]:
continue
base.append(shape.transformed(pla.toMatrix()))
- if getattr(obj, 'Fuse', False) and len(base) > 1:
+ if getattr(obj, "Fuse", False) and len(base) > 1:
obj.Shape = base[0].multiFuse(base[1:]).removeSplitter()
else:
obj.Shape = Part.makeCompound(base)
@@ -249,20 +236,20 @@ class DraftLink(DraftObject):
"""Execute when a property changes."""
self.props_changed_store(prop)
- if not getattr(self, 'use_link', False):
+ if not getattr(self, "use_link", False):
return
- if prop == 'Fuse':
+ if prop == "Fuse":
if obj.Fuse:
- obj.setPropertyStatus('Shape', '-Transient')
+ obj.setPropertyStatus("Shape", "-Transient")
else:
- obj.setPropertyStatus('Shape', 'Transient')
- elif prop == 'ExpandArray':
- if hasattr(obj, 'PlacementList'):
+ obj.setPropertyStatus("Shape", "Transient")
+ elif prop == "ExpandArray":
+ if hasattr(obj, "PlacementList"):
if obj.ExpandArray:
- obj.setPropertyStatus('PlacementList', '-Immutable')
+ obj.setPropertyStatus("PlacementList", "-Immutable")
else:
- obj.setPropertyStatus('PlacementList', 'Immutable')
+ obj.setPropertyStatus("PlacementList", "Immutable")
# Alias for compatibility with old versions of v0.19
diff --git a/src/Mod/Draft/draftobjects/ellipse.py b/src/Mod/Draft/draftobjects/ellipse.py
index e8e31d224e..b413793380 100644
--- a/src/Mod/Draft/draftobjects/ellipse.py
+++ b/src/Mod/Draft/draftobjects/ellipse.py
@@ -41,24 +41,27 @@ class Ellipse(DraftObject):
def __init__(self, obj):
super().__init__(obj, "Ellipse")
- _tip = QT_TRANSLATE_NOOP("App::Property","Start angle of the elliptical arc")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Start angle of the elliptical arc")
obj.addProperty("App::PropertyAngle", "FirstAngle", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property","End angle of the elliptical arc \n\
- (for a full circle, give it same value as First Angle)")
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "End angle of the elliptical arc \n\
+ (for a full circle, give it same value as First Angle)",
+ )
obj.addProperty("App::PropertyAngle", "LastAngle", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property","Minor radius of the ellipse")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Minor radius of the ellipse")
obj.addProperty("App::PropertyLength", "MinorRadius", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property","Major radius of the ellipse")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Major radius of the ellipse")
obj.addProperty("App::PropertyLength", "MajorRadius", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property","Create a face")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Create a face")
obj.addProperty("App::PropertyBool", "MakeFace", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property","Area of this object")
- obj.addProperty("App::PropertyArea", "Area","Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Area of this object")
+ obj.addProperty("App::PropertyArea", "Area", "Draft", _tip, locked=True)
obj.MakeFace = params.get_param("MakeFaceMode")
@@ -73,24 +76,23 @@ class Ellipse(DraftObject):
return
import Part
+
plm = obj.Placement
if obj.MajorRadius.Value < obj.MinorRadius.Value:
_err = "Error: Major radius is smaller than the minor radius"
App.Console.PrintMessage(QT_TRANSLATE_NOOP("Draft", _err))
return
if obj.MajorRadius.Value and obj.MinorRadius.Value:
- ell = Part.Ellipse(App.Vector(0, 0, 0),
- obj.MajorRadius.Value,
- obj.MinorRadius.Value)
+ ell = Part.Ellipse(App.Vector(0, 0, 0), obj.MajorRadius.Value, obj.MinorRadius.Value)
shape = ell.toShape()
- if hasattr(obj,"FirstAngle"):
+ if hasattr(obj, "FirstAngle"):
if obj.FirstAngle.Value != obj.LastAngle.Value:
a1 = obj.FirstAngle.getValueAs(App.Units.Radian)
a2 = obj.LastAngle.getValueAs(App.Units.Radian)
shape = Part.ArcOfEllipse(ell, a1, a2).toShape()
shape = Part.Wire(shape)
if shape.isClosed():
- if hasattr(obj,"MakeFace"):
+ if hasattr(obj, "MakeFace"):
if obj.MakeFace:
shape = Part.Face(shape)
else:
diff --git a/src/Mod/Draft/draftobjects/facebinder.py b/src/Mod/Draft/draftobjects/facebinder.py
index 09562c9f4c..d3d647d054 100644
--- a/src/Mod/Draft/draftobjects/facebinder.py
+++ b/src/Mod/Draft/draftobjects/facebinder.py
@@ -40,26 +40,31 @@ from draftutils.translate import translate
class Facebinder(DraftObject):
"""The Draft Facebinder object"""
- def __init__(self,obj):
+
+ def __init__(self, obj):
super().__init__(obj, "Facebinder")
- _tip = QT_TRANSLATE_NOOP("App::Property","Linked faces")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Linked faces")
obj.addProperty("App::PropertyLinkSubList", "Faces", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property","Specifies if splitter lines must be removed")
- obj.addProperty("App::PropertyBool","RemoveSplitter", "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Specifies if splitter lines must be removed")
+ obj.addProperty("App::PropertyBool", "RemoveSplitter", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property","An optional extrusion value to be applied to all faces")
- obj.addProperty("App::PropertyDistance","Extrusion", "Draft" , _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "An optional extrusion value to be applied to all faces"
+ )
+ obj.addProperty("App::PropertyDistance", "Extrusion", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property","An optional offset value to be applied to all faces")
- obj.addProperty("App::PropertyDistance","Offset", "Draft" , _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "An optional offset value to be applied to all faces"
+ )
+ obj.addProperty("App::PropertyDistance", "Offset", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property","This specifies if the shapes sew")
- obj.addProperty("App::PropertyBool","Sew", "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "This specifies if the shapes sew")
+ obj.addProperty("App::PropertyBool", "Sew", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property","The area of the faces of this Facebinder")
- obj.addProperty("App::PropertyArea","Area", "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The area of the faces of this Facebinder")
+ obj.addProperty("App::PropertyArea", "Area", "Draft", _tip, locked=True)
obj.setEditorMode("Area", 1)
def onDocumentRestored(self, obj):
@@ -78,6 +83,7 @@ class Facebinder(DraftObject):
return
import Part
+
faces = []
try:
for sel in obj.Faces:
@@ -131,11 +137,16 @@ class Facebinder(DraftObject):
_wrn(obj.Label + ": " + translate("draft", "No valid faces for facebinder"))
def _report_sew_error(self, obj):
- _wrn(obj.Label + ": " + translate("draft", "Unable to build facebinder, resuming with sew disabled"))
+ _wrn(
+ obj.Label
+ + ": "
+ + translate("draft", "Unable to build facebinder, resuming with sew disabled")
+ )
def _build_shape(self, obj, faces, sew=False):
"""returns the built shape and the area of the offset faces"""
import Part
+
offs_val = getattr(obj, "Offset", 0)
extr_val = getattr(obj, "Extrusion", 0)
@@ -175,6 +186,7 @@ class Facebinder(DraftObject):
def _convert_to_planar(self, obj, shp):
"""convert flat B-spline faces to planar faces if possible"""
import Part
+
faces = []
for face in shp.Faces:
if face.Surface.TypeId == "Part::GeomPlane":
@@ -196,9 +208,13 @@ class Facebinder(DraftObject):
solid = Part.makeSolid(Part.makeShell(faces))
if solid.isValid():
return solid
- _msg(obj.Label + ": " + translate("draft",
- "Converting flat B-spline faces of facebinder to planar faces failed"
- ))
+ _msg(
+ obj.Label
+ + ": "
+ + translate(
+ "draft", "Converting flat B-spline faces of facebinder to planar faces failed"
+ )
+ )
return shp
def onChanged(self, obj, prop):
diff --git a/src/Mod/Draft/draftobjects/fillet.py b/src/Mod/Draft/draftobjects/fillet.py
index 5cb9ccdf97..4e5e3c2631 100644
--- a/src/Mod/Draft/draftobjects/fillet.py
+++ b/src/Mod/Draft/draftobjects/fillet.py
@@ -47,38 +47,22 @@ class Fillet(DraftObject):
"""Set the properties of objects if they don't exist."""
if not hasattr(obj, "Start"):
_tip = QT_TRANSLATE_NOOP("App::Property", "The start point of this line.")
- obj.addProperty("App::PropertyVectorDistance",
- "Start",
- "Draft",
- _tip,
- locked=True)
+ obj.addProperty("App::PropertyVectorDistance", "Start", "Draft", _tip, locked=True)
obj.Start = App.Vector(0, 0, 0)
if not hasattr(obj, "End"):
_tip = QT_TRANSLATE_NOOP("App::Property", "The end point of this line.")
- obj.addProperty("App::PropertyVectorDistance",
- "End",
- "Draft",
- _tip,
- locked=True)
+ obj.addProperty("App::PropertyVectorDistance", "End", "Draft", _tip, locked=True)
obj.End = App.Vector(0, 0, 0)
if not hasattr(obj, "Length"):
_tip = QT_TRANSLATE_NOOP("App::Property", "The length of this line.")
- obj.addProperty("App::PropertyLength",
- "Length",
- "Draft",
- _tip,
- locked=True)
+ obj.addProperty("App::PropertyLength", "Length", "Draft", _tip, locked=True)
obj.Length = 0
if not hasattr(obj, "FilletRadius"):
_tip = QT_TRANSLATE_NOOP("App::Property", "Radius to use to fillet the corner.")
- obj.addProperty("App::PropertyLength",
- "FilletRadius",
- "Draft",
- _tip,
- locked=True)
+ obj.addProperty("App::PropertyLength", "FilletRadius", "Draft", _tip, locked=True)
obj.FilletRadius = 0
# TODO: these two properties should link two straight lines
@@ -117,7 +101,7 @@ class Fillet(DraftObject):
obj.End = obj.Shape.Vertexes[-1].Point
def _update_radius(self, obj, radius):
- #if (hasattr(obj, "Line1") and hasattr(obj, "Line2")
+ # if (hasattr(obj, "Line1") and hasattr(obj, "Line2")
# and obj.Line1 and obj.Line2):
# do the unimplemented work
pass
@@ -131,4 +115,5 @@ class Fillet(DraftObject):
if prop in "FilletRadius":
self._update_radius(obj, obj.FilletRadius)
+
## @}
diff --git a/src/Mod/Draft/draftobjects/hatch.py b/src/Mod/Draft/draftobjects/hatch.py
index 5645dd2aeb..933e8e1fb9 100644
--- a/src/Mod/Draft/draftobjects/hatch.py
+++ b/src/Mod/Draft/draftobjects/hatch.py
@@ -1,24 +1,24 @@
-#***************************************************************************
-#* *
-#* Copyright (c) 2021 Yorik van Havre *
-#* *
-#* This program is free software; you can redistribute it and/or modify *
-#* it under the terms of the GNU Lesser General Public License (LGPL) *
-#* as published by the Free Software Foundation; either version 2 of *
-#* the License, or (at your option) any later version. *
-#* for detail see the LICENCE text file. *
-#* *
-#* This program is distributed in the hope that it will be useful, *
-#* but WITHOUT ANY WARRANTY; without even the implied warranty of *
-#* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
-#* GNU Library General Public License for more details. *
-#* *
-#* You should have received a copy of the GNU Library General Public *
-#* License along with this program; if not, write to the Free Software *
-#* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 *
-#* USA *
-#* *
-#***************************************************************************
+# ***************************************************************************
+# * *
+# * Copyright (c) 2021 Yorik van Havre *
+# * *
+# * This program is free software; you can redistribute it and/or modify *
+# * it under the terms of the GNU Lesser General Public License (LGPL) *
+# * as published by the Free Software Foundation; either version 2 of *
+# * the License, or (at your option) any later version. *
+# * for detail see the LICENCE text file. *
+# * *
+# * This program is distributed in the hope that it will be useful, *
+# * but WITHOUT ANY WARRANTY; without even the implied warranty of *
+# * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
+# * GNU Library General Public License for more details. *
+# * *
+# * You should have received a copy of the GNU Library General Public *
+# * License along with this program; if not, write to the Free Software *
+# * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 *
+# * USA *
+# * *
+# ***************************************************************************
"""This module contains FreeCAD commands for the Draft workbench"""
@@ -36,37 +36,69 @@ from draftutils.translate import translate
class Hatch(DraftObject):
-
- def __init__(self,obj):
+ def __init__(self, obj):
obj.Proxy = self
self.Type = "Hatch"
self.setProperties(obj)
- def setProperties(self,obj):
+ def setProperties(self, obj):
pl = obj.PropertiesList
if not "Base" in pl:
- obj.addProperty("App::PropertyLink","Base","Hatch",
- QT_TRANSLATE_NOOP("App::Property","The base object used by this object"), locked=True)
+ obj.addProperty(
+ "App::PropertyLink",
+ "Base",
+ "Hatch",
+ QT_TRANSLATE_NOOP("App::Property", "The base object used by this object"),
+ locked=True,
+ )
if not "File" in pl:
- obj.addProperty("App::PropertyFile","File","Hatch",
- QT_TRANSLATE_NOOP("App::Property","The PAT file used by this object"), locked=True)
+ obj.addProperty(
+ "App::PropertyFile",
+ "File",
+ "Hatch",
+ QT_TRANSLATE_NOOP("App::Property", "The PAT file used by this object"),
+ locked=True,
+ )
if not "Pattern" in pl:
- obj.addProperty("App::PropertyString","Pattern","Hatch",
- QT_TRANSLATE_NOOP("App::Property","The pattern name used by this object"), locked=True)
+ obj.addProperty(
+ "App::PropertyString",
+ "Pattern",
+ "Hatch",
+ QT_TRANSLATE_NOOP("App::Property", "The pattern name used by this object"),
+ locked=True,
+ )
if not "Scale" in pl:
- obj.addProperty("App::PropertyFloat","Scale","Hatch",
- QT_TRANSLATE_NOOP("App::Property","The pattern scale used by this object"), locked=True)
+ obj.addProperty(
+ "App::PropertyFloat",
+ "Scale",
+ "Hatch",
+ QT_TRANSLATE_NOOP("App::Property", "The pattern scale used by this object"),
+ locked=True,
+ )
if not "Rotation" in pl:
- obj.addProperty("App::PropertyAngle","Rotation","Hatch",
- QT_TRANSLATE_NOOP("App::Property","The pattern rotation used by this object"), locked=True)
+ obj.addProperty(
+ "App::PropertyAngle",
+ "Rotation",
+ "Hatch",
+ QT_TRANSLATE_NOOP("App::Property", "The pattern rotation used by this object"),
+ locked=True,
+ )
if not "Translate" in pl:
- obj.addProperty("App::PropertyBool","Translate","Hatch",
- QT_TRANSLATE_NOOP("App::Property","If set to False, hatch is applied as is to the faces, without translation (this might give wrong results for non-XY faces)"), locked=True)
+ obj.addProperty(
+ "App::PropertyBool",
+ "Translate",
+ "Hatch",
+ QT_TRANSLATE_NOOP(
+ "App::Property",
+ "If set to False, hatch is applied as is to the faces, without translation (this might give wrong results for non-XY faces)",
+ ),
+ locked=True,
+ )
obj.Translate = True
- def onDocumentRestored(self,obj):
+ def onDocumentRestored(self, obj):
self.setProperties(obj)
super().onDocumentRestored(obj)
gui_utils.restore_view_object(
@@ -79,15 +111,17 @@ class Hatch(DraftObject):
def loads(self, state):
self.Type = "Hatch"
- def execute(self,obj):
+ def execute(self, obj):
- if self.props_changed_placement_only(obj) \
- or not obj.Base \
- or not obj.File \
- or not obj.Pattern \
- or not obj.Scale \
- or not obj.Base.isDerivedFrom("Part::Feature") \
- or not obj.Base.Shape.Faces:
+ if (
+ self.props_changed_placement_only(obj)
+ or not obj.Base
+ or not obj.File
+ or not obj.Pattern
+ or not obj.Scale
+ or not obj.Base.isDerivedFrom("Part::Feature")
+ or not obj.Base.Shape.Faces
+ ):
self.props_changed_clear()
return
@@ -131,7 +165,7 @@ class Hatch(DraftObject):
shapes = []
for face in obj.Base.Shape.Faces:
- if face.findPlane(): # Only planar faces.
+ if face.findPlane(): # Only planar faces.
face = face.copy()
if obj.Translate:
mtx = None
@@ -183,8 +217,7 @@ class Hatch(DraftObject):
self.props_changed_store(prop)
- def getPatterns(self,filename):
-
+ def getPatterns(self, filename):
"""returns a list of pattern names found in a PAT file"""
patterns = []
if os.path.exists(filename):
diff --git a/src/Mod/Draft/draftobjects/label.py b/src/Mod/Draft/draftobjects/label.py
index 5f843db283..a3b0e868df 100644
--- a/src/Mod/Draft/draftobjects/label.py
+++ b/src/Mod/Draft/draftobjects/label.py
@@ -58,31 +58,27 @@ class Label(DraftAnnotation):
properties = obj.PropertiesList
if "TargetPoint" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The position of the tip of the leader "
- "line.\n"
- "This point can be decorated "
- "with an arrow or another symbol.")
- obj.addProperty("App::PropertyVector",
- "TargetPoint",
- "Target",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The position of the tip of the leader "
+ "line.\n"
+ "This point can be decorated "
+ "with an arrow or another symbol.",
+ )
+ obj.addProperty("App::PropertyVector", "TargetPoint", "Target", _tip, locked=True)
obj.TargetPoint = App.Vector(2, -1, 0)
if "Target" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Object, and optionally subelement, "
- "whose properties will be displayed\n"
- "as 'Text', depending on 'Label Type'.\n"
- "\n"
- "'Target' won't be used "
- "if 'Label Type' is set to 'Custom'.")
- obj.addProperty("App::PropertyLinkSub",
- "Target",
- "Target",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Object, and optionally subelement, "
+ "whose properties will be displayed\n"
+ "as 'Text', depending on 'Label Type'.\n"
+ "\n"
+ "'Target' won't be used "
+ "if 'Label Type' is set to 'Custom'.",
+ )
+ obj.addProperty("App::PropertyLinkSub", "Target", "Target", _tip, locked=True)
obj.Target = None
def set_leader_properties(self, obj):
@@ -90,65 +86,63 @@ class Label(DraftAnnotation):
properties = obj.PropertiesList
if "Points" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The list of points defining the leader "
- "line; normally a list of three points.\n"
- "\n"
- "The first point should be the position "
- "of the text, that is, the 'Placement',\n"
- "and the last point should be "
- "the tip of the line, that is, "
- "the 'Target Point'.\n"
- "The middle point is calculated "
- "automatically depending on the chosen\n"
- "'Straight Direction' "
- "and the 'Straight Distance' value "
- "and sign.\n"
- "\n"
- "If 'Straight Direction' is set to "
- "'Custom', the 'Points' property\n"
- "can be set as a list "
- "of arbitrary points.")
- obj.addProperty("App::PropertyVectorList",
- "Points",
- "Leader",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The list of points defining the leader "
+ "line; normally a list of three points.\n"
+ "\n"
+ "The first point should be the position "
+ "of the text, that is, the 'Placement',\n"
+ "and the last point should be "
+ "the tip of the line, that is, "
+ "the 'Target Point'.\n"
+ "The middle point is calculated "
+ "automatically depending on the chosen\n"
+ "'Straight Direction' "
+ "and the 'Straight Distance' value "
+ "and sign.\n"
+ "\n"
+ "If 'Straight Direction' is set to "
+ "'Custom', the 'Points' property\n"
+ "can be set as a list "
+ "of arbitrary points.",
+ )
+ obj.addProperty("App::PropertyVectorList", "Points", "Leader", _tip, locked=True)
obj.Points = []
if "StraightDirection" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The direction of the straight segment "
- "of the leader line.\n"
- "\n"
- "If 'Custom' is chosen, the points "
- "of the leader can be specified by\n"
- "assigning a custom list "
- "to the 'Points' attribute.")
- obj.addProperty("App::PropertyEnumeration",
- "StraightDirection",
- "Leader",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The direction of the straight segment "
+ "of the leader line.\n"
+ "\n"
+ "If 'Custom' is chosen, the points "
+ "of the leader can be specified by\n"
+ "assigning a custom list "
+ "to the 'Points' attribute.",
+ )
+ obj.addProperty(
+ "App::PropertyEnumeration", "StraightDirection", "Leader", _tip, locked=True
+ )
obj.StraightDirection = ["Horizontal", "Vertical", "Custom"]
if "StraightDistance" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The length of the straight segment "
- "of the leader line.\n"
- "\n"
- "This is an oriented distance; "
- "if it is negative, the line will "
- "be drawn\n"
- "to the left or below the 'Text', "
- "otherwise to the right or above it,\n"
- "depending on the value of "
- "'Straight Direction'.")
- obj.addProperty("App::PropertyDistance",
- "StraightDistance",
- "Leader",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The length of the straight segment "
+ "of the leader line.\n"
+ "\n"
+ "This is an oriented distance; "
+ "if it is negative, the line will "
+ "be drawn\n"
+ "to the left or below the 'Text', "
+ "otherwise to the right or above it,\n"
+ "depending on the value of "
+ "'Straight Direction'.",
+ )
+ obj.addProperty(
+ "App::PropertyDistance", "StraightDistance", "Leader", _tip, locked=True
+ )
obj.StraightDistance = 1
def set_label_properties(self, obj):
@@ -156,41 +150,31 @@ class Label(DraftAnnotation):
properties = obj.PropertiesList
if "Placement" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The placement of the 'Text' element "
- "in 3D space")
- obj.addProperty("App::PropertyPlacement",
- "Placement",
- "Label",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "The placement of the 'Text' element " "in 3D space"
+ )
+ obj.addProperty("App::PropertyPlacement", "Placement", "Label", _tip, locked=True)
obj.Placement = App.Placement()
if "CustomText" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The text to display when 'Label Type' "
- "is set to 'Custom'")
- obj.addProperty("App::PropertyStringList",
- "CustomText",
- "Label",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "The text to display when 'Label Type' " "is set to 'Custom'"
+ )
+ obj.addProperty("App::PropertyStringList", "CustomText", "Label", _tip, locked=True)
obj.CustomText = "Label"
if "Text" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The text displayed by this label.\n"
- "\n"
- "This property is read-only, as the "
- "final text depends on 'Label Type',\n"
- "and the object defined in 'Target'.\n"
- "The 'Custom Text' is displayed only "
- "if 'Label Type' is set to 'Custom'.")
- obj.addProperty("App::PropertyStringList",
- "Text",
- "Label",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The text displayed by this label.\n"
+ "\n"
+ "This property is read-only, as the "
+ "final text depends on 'Label Type',\n"
+ "and the object defined in 'Target'.\n"
+ "The 'Custom Text' is displayed only "
+ "if 'Label Type' is set to 'Custom'.",
+ )
+ obj.addProperty("App::PropertyStringList", "Text", "Label", _tip, locked=True)
obj.setEditorMode("Text", 1) # Read only
# TODO: maybe here we can define a second and third 'label type'
@@ -203,30 +187,28 @@ class Label(DraftAnnotation):
# This would also require updating the `return_info` function
# to handle any combination that we want.
if "LabelType" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The type of information displayed "
- "by this label.\n"
- "\n"
- "If 'Custom' is chosen, the contents of "
- "'Custom Text' will be used.\n"
- "For other types, the string will be "
- "calculated automatically from the "
- "object defined in 'Target'.\n"
- "'Tag' and 'Material' only work "
- "for objects that have these properties, "
- "like BIM objects.\n"
- "\n"
- "For 'Position', 'Length', and 'Area' "
- "these properties will be extracted "
- "from the main object in 'Target',\n"
- "or from the subelement "
- "'VertexN', 'EdgeN', or 'FaceN', "
- "respectively, if it is specified.")
- obj.addProperty("App::PropertyEnumeration",
- "LabelType",
- "Label",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The type of information displayed "
+ "by this label.\n"
+ "\n"
+ "If 'Custom' is chosen, the contents of "
+ "'Custom Text' will be used.\n"
+ "For other types, the string will be "
+ "calculated automatically from the "
+ "object defined in 'Target'.\n"
+ "'Tag' and 'Material' only work "
+ "for objects that have these properties, "
+ "like BIM objects.\n"
+ "\n"
+ "For 'Position', 'Length', and 'Area' "
+ "these properties will be extracted "
+ "from the main object in 'Target',\n"
+ "or from the subelement "
+ "'VertexN', 'EdgeN', or 'FaceN', "
+ "respectively, if it is specified.",
+ )
+ obj.addProperty("App::PropertyEnumeration", "LabelType", "Label", _tip, locked=True)
obj.LabelType = get_label_types()
def onDocumentRestored(self, obj):
@@ -327,20 +309,22 @@ DraftLabel = Label
def get_label_types():
- return [QT_TRANSLATE_NOOP("Draft","Custom"),
- QT_TRANSLATE_NOOP("Draft","Name"),
- QT_TRANSLATE_NOOP("Draft","Label"),
- QT_TRANSLATE_NOOP("Draft","Position"),
- QT_TRANSLATE_NOOP("Draft","Length"),
- QT_TRANSLATE_NOOP("Draft","Area"),
- QT_TRANSLATE_NOOP("Draft","Volume"),
- QT_TRANSLATE_NOOP("Draft","Tag"),
- QT_TRANSLATE_NOOP("Draft","Material"),
- QT_TRANSLATE_NOOP("Draft","Label + Position"),
- QT_TRANSLATE_NOOP("Draft","Label + Length"),
- QT_TRANSLATE_NOOP("Draft","Label + Area"),
- QT_TRANSLATE_NOOP("Draft","Label + Volume"),
- QT_TRANSLATE_NOOP("Draft","Label + Material")]
+ return [
+ QT_TRANSLATE_NOOP("Draft", "Custom"),
+ QT_TRANSLATE_NOOP("Draft", "Name"),
+ QT_TRANSLATE_NOOP("Draft", "Label"),
+ QT_TRANSLATE_NOOP("Draft", "Position"),
+ QT_TRANSLATE_NOOP("Draft", "Length"),
+ QT_TRANSLATE_NOOP("Draft", "Area"),
+ QT_TRANSLATE_NOOP("Draft", "Volume"),
+ QT_TRANSLATE_NOOP("Draft", "Tag"),
+ QT_TRANSLATE_NOOP("Draft", "Material"),
+ QT_TRANSLATE_NOOP("Draft", "Label + Position"),
+ QT_TRANSLATE_NOOP("Draft", "Label + Length"),
+ QT_TRANSLATE_NOOP("Draft", "Label + Area"),
+ QT_TRANSLATE_NOOP("Draft", "Label + Volume"),
+ QT_TRANSLATE_NOOP("Draft", "Label + Material"),
+ ]
def return_info(target, typ, subelement=None):
@@ -420,7 +404,7 @@ def _get_tag(target):
def _get_material(target):
- if (hasattr(target, "Material") and hasattr(target.Material, "Label")):
+ if hasattr(target, "Material") and hasattr(target.Material, "Label"):
return [target.Material.Label]
else:
return [translate("draft", "Material not available for object")]
diff --git a/src/Mod/Draft/draftobjects/layer.py b/src/Mod/Draft/draftobjects/layer.py
index 70844d5d52..fdd03f59cc 100644
--- a/src/Mod/Draft/draftobjects/layer.py
+++ b/src/Mod/Draft/draftobjects/layer.py
@@ -52,16 +52,11 @@ class Layer:
def set_properties(self, obj):
"""Set properties only if they don't exist."""
if "Group" not in obj.PropertiesList:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The objects that are part of this layer")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The objects that are part of this layer")
# "App::PropertyLinkListHidden" instead of "App::PropertyLinkList" has 2 advantages:
# 1. No 'might break' warning when deleting an object nested in a layer.
# 2. No 'out of scope' warning for objects also nested in f.e. a Std_Part.
- obj.addProperty("App::PropertyLinkListHidden",
- "Group",
- "Layer",
- _tip,
- locked=True)
+ obj.addProperty("App::PropertyLinkListHidden", "Group", "Layer", _tip, locked=True)
def onDocumentRestored(self, obj):
"""Execute code when the document is restored."""
@@ -93,7 +88,7 @@ class Layer:
material = App.Material() # Material with default v0.21 properties.
material.DiffuseColor = vobj.ShapeColor
material.Transparency = vobj.Transparency / 100
- vobj.ShapeAppearance = (material, )
+ vobj.ShapeAppearance = (material,)
vobj.setPropertyStatus("ShapeColor", "Hidden")
if hasattr(vobj, "OverrideShapeColorChildren"): # v0.19 - v0.21
vobj.OverrideShapeAppearanceChildren = vobj.OverrideShapeColorChildren
@@ -214,4 +209,5 @@ def get_layer(obj):
return find
return None
+
## @}
diff --git a/src/Mod/Draft/draftobjects/patharray.py b/src/Mod/Draft/draftobjects/patharray.py
index 3273740fae..69d10f38c5 100644
--- a/src/Mod/Draft/draftobjects/patharray.py
+++ b/src/Mod/Draft/draftobjects/patharray.py
@@ -69,7 +69,12 @@ import lazy_loader.lazy_loader as lz
from draftutils.messages import _err, _log, _wrn
from draftutils.translate import translate
-def QT_TRANSLATE_NOOP(ctx,txt): return txt
+
+
+def QT_TRANSLATE_NOOP(ctx, txt):
+ return txt
+
+
from draftobjects.base import DraftObject
from draftobjects.draftlink import DraftLink
@@ -212,21 +217,16 @@ class PathArray(DraftLink):
def set_general_properties(self, obj, properties):
"""Set general properties only if they don't exist."""
if "Base" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property","The base object that will be duplicated")
- obj.addProperty("App::PropertyLinkGlobal",
- "Base",
- "Objects",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The base object that will be duplicated")
+ obj.addProperty("App::PropertyLinkGlobal", "Base", "Objects", _tip, locked=True)
obj.Base = None
if "PathObject" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property","The object along which the copies will be distributed. It must contain 'Edges'.")
- obj.addProperty("App::PropertyLinkGlobal",
- "PathObject",
- "Objects",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The object along which the copies will be distributed. It must contain 'Edges'.",
+ )
+ obj.addProperty("App::PropertyLinkGlobal", "PathObject", "Objects", _tip, locked=True)
obj.PathObject = None
# TODO: the 'PathSubelements' property must be changed,
@@ -237,199 +237,161 @@ class PathArray(DraftLink):
# as this property can be used to select a single object,
# or a single object with its subelements.
if "PathSubelements" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property","List of connected edges in the 'Path Object'.\nIf these are present, the copies will be created along these subelements only.\nLeave this property empty to create copies along the entire 'Path Object'.")
- obj.addProperty("App::PropertyLinkSubListGlobal",
- "PathSubelements",
- "Objects",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "List of connected edges in the 'Path Object'.\nIf these are present, the copies will be created along these subelements only.\nLeave this property empty to create copies along the entire 'Path Object'.",
+ )
+ obj.addProperty(
+ "App::PropertyLinkSubListGlobal", "PathSubelements", "Objects", _tip, locked=True
+ )
obj.PathSubelements = []
if "Fuse" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Specifies if the copies "
- "should be fused together "
- "if they touch each other (slower)")
- obj.addProperty("App::PropertyBool",
- "Fuse",
- "Objects",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Specifies if the copies "
+ "should be fused together "
+ "if they touch each other (slower)",
+ )
+ obj.addProperty("App::PropertyBool", "Fuse", "Objects", _tip, locked=True)
obj.Fuse = False
if self.use_link and "ExpandArray" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property","Show the individual array elements (only for Link arrays)")
- obj.addProperty("App::PropertyBool",
- "ExpandArray",
- "Objects",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Show the individual array elements (only for Link arrays)"
+ )
+ obj.addProperty("App::PropertyBool", "ExpandArray", "Objects", _tip, locked=True)
obj.ExpandArray = False
- obj.setPropertyStatus('Shape', 'Transient')
+ obj.setPropertyStatus("Shape", "Transient")
if not self.use_link:
if "PlacementList" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The placement for each array element")
- obj.addProperty("App::PropertyPlacementList",
- "PlacementList",
- "Objects",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The placement for each array element")
+ obj.addProperty(
+ "App::PropertyPlacementList", "PlacementList", "Objects", _tip, locked=True
+ )
obj.PlacementList = []
def set_align_properties(self, obj, properties):
"""Set general properties only if they don't exist."""
if "ExtraTranslation" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property","Additional translation that will be applied to each copy.\nThis is useful to adjust for the difference between shape centre and shape reference point.")
- obj.addProperty("App::PropertyVectorDistance",
- "ExtraTranslation",
- "Alignment",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Additional translation that will be applied to each copy.\nThis is useful to adjust for the difference between shape centre and shape reference point.",
+ )
+ obj.addProperty(
+ "App::PropertyVectorDistance", "ExtraTranslation", "Alignment", _tip, locked=True
+ )
obj.ExtraTranslation = App.Vector(0, 0, 0)
if "TangentVector" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property","Alignment vector for 'Tangent' mode")
- obj.addProperty("App::PropertyVector",
- "TangentVector",
- "Alignment",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Alignment vector for 'Tangent' mode")
+ obj.addProperty("App::PropertyVector", "TangentVector", "Alignment", _tip, locked=True)
obj.TangentVector = App.Vector(1, 0, 0)
if "ForceVertical" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property","Force use of 'Vertical Vector' as local Z-direction when using 'Original' or 'Tangent' alignment mode")
- obj.addProperty("App::PropertyBool",
- "ForceVertical",
- "Alignment",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Force use of 'Vertical Vector' as local Z-direction when using 'Original' or 'Tangent' alignment mode",
+ )
+ obj.addProperty("App::PropertyBool", "ForceVertical", "Alignment", _tip, locked=True)
obj.ForceVertical = False
if "VerticalVector" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property","Direction of the local Z axis when 'Force Vertical' is true")
- obj.addProperty("App::PropertyVector",
- "VerticalVector",
- "Alignment",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Direction of the local Z axis when 'Force Vertical' is true"
+ )
+ obj.addProperty("App::PropertyVector", "VerticalVector", "Alignment", _tip, locked=True)
obj.VerticalVector = App.Vector(0, 0, 1)
if "AlignMode" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property","Method to orient the copies along the path.\n- Original: X is curve tangent, Y is normal, and Z is the cross product.\n- Frenet: aligns the object following the local coordinate system along the path.\n- Tangent: similar to 'Original' but the local X axis is pre-aligned to 'Tangent Vector'.\n\nTo get better results with 'Original' or 'Tangent' you may have to set 'Force Vertical' to true.")
- obj.addProperty("App::PropertyEnumeration",
- "AlignMode",
- "Alignment",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Method to orient the copies along the path.\n- Original: X is curve tangent, Y is normal, and Z is the cross product.\n- Frenet: aligns the object following the local coordinate system along the path.\n- Tangent: similar to 'Original' but the local X axis is pre-aligned to 'Tangent Vector'.\n\nTo get better results with 'Original' or 'Tangent' you may have to set 'Force Vertical' to true.",
+ )
+ obj.addProperty("App::PropertyEnumeration", "AlignMode", "Alignment", _tip, locked=True)
obj.AlignMode = ["Original", "Frenet", "Tangent"]
obj.AlignMode = "Original"
if "ReversePath" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property","Walk the path backwards.")
- obj.addProperty("App::PropertyBool",
- "ReversePath",
- "Alignment",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Walk the path backwards.")
+ obj.addProperty("App::PropertyBool", "ReversePath", "Alignment", _tip, locked=True)
obj.ReversePath = False
# The Align property must be attached after other align properties
# so that onChanged works properly
if "Align" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property","Orient the copies along the path depending on the 'Align Mode'.\nOtherwise the copies will have the same orientation as the original Base object.")
- obj.addProperty("App::PropertyBool",
- "Align",
- "Alignment",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Orient the copies along the path depending on the 'Align Mode'.\nOtherwise the copies will have the same orientation as the original Base object.",
+ )
+ obj.addProperty("App::PropertyBool", "Align", "Alignment", _tip, locked=True)
obj.Align = False
def set_spacing_properties(self, obj, properties):
if "Count" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property","Number of copies to create")
- obj.addProperty("App::PropertyInteger",
- "Count",
- "Spacing",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Number of copies to create")
+ obj.addProperty("App::PropertyInteger", "Count", "Spacing", _tip, locked=True)
obj.Count = 4
if "SpacingMode" not in properties:
_tip = QT_TRANSLATE_NOOP(
"App::Property",
- "How copies are spaced.\n" +
- " - Fixed count: available path length (minus start and end offsets) is evenly divided into n.\n" +
- " - Fixed spacing: start at \"Start offset\" and place new copies after traveling a fixed distance along the path.\n" +
- " - Fixed count and spacing: same as \"Fixed spacing\", but also stop at given number of copies."
- )
- obj.addProperty("App::PropertyEnumeration",
- "SpacingMode",
- "Spacing",
- _tip,
- locked=True)
+ "How copies are spaced.\n"
+ + " - Fixed count: available path length (minus start and end offsets) is evenly divided into n.\n"
+ + ' - Fixed spacing: start at "Start offset" and place new copies after traveling a fixed distance along the path.\n'
+ + ' - Fixed count and spacing: same as "Fixed spacing", but also stop at given number of copies.',
+ )
+ obj.addProperty("App::PropertyEnumeration", "SpacingMode", "Spacing", _tip, locked=True)
obj.SpacingMode = ["Fixed count", "Fixed spacing", "Fixed count and spacing"]
obj.SpacingMode = "Fixed count"
if "SpacingUnit" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property","Base fixed distance between elements.")
- obj.addProperty("App::PropertyLength",
- "SpacingUnit",
- "Spacing",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Base fixed distance between elements.")
+ obj.addProperty("App::PropertyLength", "SpacingUnit", "Spacing", _tip, locked=True)
obj.SpacingUnit = 20.0
obj.setPropertyStatus("SpacingUnit", "Hidden")
if "UseSpacingPattern" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property","Use repeating spacing patterns instead of uniform spacing.")
- obj.addProperty("App::PropertyBool",
- "UseSpacingPattern",
- "Spacing",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Use repeating spacing patterns instead of uniform spacing."
+ )
+ obj.addProperty("App::PropertyBool", "UseSpacingPattern", "Spacing", _tip, locked=True)
obj.UseSpacingPattern = False
if "SpacingPattern" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property","Spacing is multiplied by a corresponding number in this sequence.")
- obj.addProperty("App::PropertyFloatList",
- "SpacingPattern",
- "Spacing",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Spacing is multiplied by a corresponding number in this sequence."
+ )
+ obj.addProperty(
+ "App::PropertyFloatList", "SpacingPattern", "Spacing", _tip, locked=True
+ )
obj.SpacingPattern = [1, 2]
obj.setPropertyStatus("SpacingPattern", "Hidden")
if "StartOffset" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property","Length from the start of the path to the first copy.")
- obj.addProperty("App::PropertyLength",
- "StartOffset",
- "Spacing",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Length from the start of the path to the first copy."
+ )
+ obj.addProperty("App::PropertyLength", "StartOffset", "Spacing", _tip, locked=True)
obj.StartOffset = 0.0
if "EndOffset" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property","Length from the end of the path to the last copy.")
- obj.addProperty("App::PropertyLength",
- "EndOffset",
- "Spacing",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Length from the end of the path to the last copy."
+ )
+ obj.addProperty("App::PropertyLength", "EndOffset", "Spacing", _tip, locked=True)
obj.EndOffset = 0.0
def linkSetup(self, obj):
"""Set up the object as a link object."""
super().linkSetup(obj)
- obj.configLinkProperty(ElementCount='Count')
+ obj.configLinkProperty(ElementCount="Count")
def execute(self, obj):
"""Execute when the object is created or recomputed."""
- if self.props_changed_placement_only(obj) \
- or not obj.Base \
- or not obj.PathObject:
+ if self.props_changed_placement_only(obj) or not obj.Base or not obj.PathObject:
self.props_changed_clear()
return
@@ -438,15 +400,13 @@ class PathArray(DraftLink):
w = self.get_wires(obj.PathObject, obj.PathSubelements)
if not w:
- _err(obj.PathObject.Label
- + translate("draft",", path object does not have 'Edges'."))
+ _err(obj.PathObject.Label + translate("draft", ", path object does not have 'Edges'."))
return
base_rotation = obj.Base.Shape.Placement.Rotation
final_rotation = base_rotation
- if (obj.Align and obj.AlignMode == "Tangent"
- and hasattr(obj, "TangentVector")):
+ if obj.Align and obj.AlignMode == "Tangent" and hasattr(obj, "TangentVector"):
Xaxis = App.Vector(1.0, 0.0, 0.0) # default TangentVector
if not DraftVecUtils.equals(Xaxis, obj.TangentVector):
@@ -454,30 +414,33 @@ class PathArray(DraftLink):
pre_rotation = App.Rotation(obj.TangentVector, Xaxis)
final_rotation = base_rotation.multiply(pre_rotation)
- copy_placements = placements_on_path(final_rotation,
- w, obj.Count,
- obj.ExtraTranslation,
- obj.Align, obj.AlignMode,
- obj.ForceVertical,
- obj.VerticalVector,
- obj.StartOffset.Value,
- obj.EndOffset.Value,
- obj.ReversePath,
- obj.SpacingMode,
- obj.SpacingUnit.Value,
- obj.UseSpacingPattern,
- obj.SpacingPattern)
+ copy_placements = placements_on_path(
+ final_rotation,
+ w,
+ obj.Count,
+ obj.ExtraTranslation,
+ obj.Align,
+ obj.AlignMode,
+ obj.ForceVertical,
+ obj.VerticalVector,
+ obj.StartOffset.Value,
+ obj.EndOffset.Value,
+ obj.ReversePath,
+ obj.SpacingMode,
+ obj.SpacingUnit.Value,
+ obj.UseSpacingPattern,
+ obj.SpacingPattern,
+ )
self.buildShape(obj, array_placement, copy_placements)
self.props_changed_clear()
- return (not self.use_link)
+ return not self.use_link
def get_wires(self, path_object, subelements):
"""Get wires from the path object."""
if subelements:
w = self.get_wire_from_subelements(subelements)
- elif (hasattr(path_object.Shape, 'Wires')
- and path_object.Shape.Wires):
+ elif hasattr(path_object.Shape, "Wires") and path_object.Shape.Wires:
w = path_object.Shape.Wires[0]
elif path_object.Shape.Edges:
w = Part.Wire(path_object.Shape.Edges)
@@ -511,10 +474,7 @@ class PathArray(DraftLink):
if prop == "SpacingMode":
# Check if all referenced properties are available:
- for pr in ("SpacingMode",
- "SpacingUnit",
- "UseSpacingPattern",
- "SpacingPattern"):
+ for pr in ("SpacingMode", "SpacingUnit", "UseSpacingPattern", "SpacingPattern"):
if not hasattr(obj, pr):
return
@@ -544,8 +504,7 @@ class PathArray(DraftLink):
if prop in ("Align", "AlignMode"):
# Check if all referenced properties are available:
- for pr in ("Align", "AlignMode", "ForceVertical",
- "VerticalVector", "TangentVector"):
+ for pr in ("Align", "AlignMode", "ForceVertical", "VerticalVector", "TangentVector"):
if not hasattr(obj, pr):
return
@@ -565,8 +524,7 @@ class PathArray(DraftLink):
obj.setPropertyStatus("TangentVector", "Hidden")
else:
- for pr in ("AlignMode", "ForceVertical",
- "VerticalVector", "TangentVector"):
+ for pr in ("AlignMode", "ForceVertical", "VerticalVector", "TangentVector"):
obj.setPropertyStatus(pr, "Hidden")
def onDocumentRestored(self, obj):
@@ -609,22 +567,30 @@ class PathArray(DraftLink):
if hasattr(obj, "Xlate"):
obj.ExtraTranslation = obj.Xlate
obj.removeProperty("Xlate")
- self.execute(obj) # Required to update PlacementList.
+ self.execute(obj) # Required to update PlacementList.
# Alias for compatibility with v0.18 and earlier
_PathArray = PathArray
-def placements_on_path(shapeRotation, pathwire, count, xlate, align,
- mode="Original", forceNormal=False,
- normalOverride=None,
- startOffset=0.0, endOffset=0.0,
- reversePath=False,
- spacingMode="Fixed count",
- spacingUnit=20.0,
- useSpacingPattern=False,
- spacingPattern=[1, 1, 1, 1]):
+def placements_on_path(
+ shapeRotation,
+ pathwire,
+ count,
+ xlate,
+ align,
+ mode="Original",
+ forceNormal=False,
+ normalOverride=None,
+ startOffset=0.0,
+ endOffset=0.0,
+ reversePath=False,
+ spacingMode="Fixed count",
+ spacingUnit=20.0,
+ useSpacingPattern=False,
+ spacingPattern=[1, 1, 1, 1],
+):
"""Calculate the placements of a shape along a given path.
Copies will be distributed according to spacing mode - evenly or in fixed offsets.
@@ -658,12 +624,7 @@ def placements_on_path(shapeRotation, pathwire, count, xlate, align,
if startOffset > (totalDist - minLength):
if startOffset != 0:
- _wrn(
- translate(
- "draft",
- "Start Offset too large for path length. Using 0 instead."
- )
- )
+ _wrn(translate("draft", "Start Offset too large for path length. Using 0 instead."))
startOffset = 0
if endOffset > (totalDist - startOffset - minLength):
@@ -671,7 +632,7 @@ def placements_on_path(shapeRotation, pathwire, count, xlate, align,
_wrn(
translate(
"draft",
- "End Offset too large for path length minus Start Offset. Using 0 instead."
+ "End Offset too large for path length minus Start Offset. Using 0 instead.",
)
)
endOffset = 0
@@ -728,7 +689,6 @@ def placements_on_path(shapeRotation, pathwire, count, xlate, align,
# Each interval will be the same:
steps = [spacingUnit]
-
remains = 0
travel = startOffset
endTravel = startOffset + totalDist
@@ -750,18 +710,27 @@ def placements_on_path(shapeRotation, pathwire, count, xlate, align,
# place shape at proper spot on proper edge
pt = path[iend].valueAt(get_parameter_from_v0(path[iend], offset))
- place = calculate_placement(shapeRotation,
- path[iend], offset,
- pt, xlate, align, normal,
- mode, forceNormal,
- reversePath)
+ place = calculate_placement(
+ shapeRotation,
+ path[iend],
+ offset,
+ pt,
+ xlate,
+ align,
+ normal,
+ mode,
+ forceNormal,
+ reversePath,
+ )
placements.append(place)
travel += steps[i % len(steps)]
i = i + 1
# End conditions:
- if stopAfterDistance and travel > endTravel: break
- if stopAfterCount and i >= count: break
+ if stopAfterDistance and travel > endTravel:
+ break
+ if stopAfterCount and i >= count:
+ break
# Failsafe:
if i > 10_000:
@@ -774,11 +743,18 @@ def placements_on_path(shapeRotation, pathwire, count, xlate, align,
calculatePlacementsOnPath = placements_on_path
-def calculate_placement(globalRotation,
- edge, offset, RefPt, xlate, align,
- normal=App.Vector(0.0, 0.0, 1.0),
- mode="Original", overrideNormal=False,
- reversePath=False):
+def calculate_placement(
+ globalRotation,
+ edge,
+ offset,
+ RefPt,
+ xlate,
+ align,
+ normal=App.Vector(0.0, 0.0, 1.0),
+ mode="Original",
+ overrideNormal=False,
+ reversePath=False,
+):
"""Orient shape in the local coordinate system at parameter offset.
http://en.wikipedia.org/wiki/Euler_angles (previous version)
@@ -792,7 +768,7 @@ def calculate_placement(globalRotation,
if not align:
return placement
- tol = 1e-6 # App.Rotation() tolerance is 1e-7. Shorter vectors are ignored.
+ tol = 1e-6 # App.Rotation() tolerance is 1e-7. Shorter vectors are ignored.
nullv = App.Vector()
t = edge.tangentAt(get_parameter_from_v0(edge, offset))
@@ -821,19 +797,28 @@ def calculate_placement(globalRotation,
n_nor = n.normalize()
t_nor = t.normalize()
if n_nor.isEqual(t_nor, tol) or n_nor.isEqual(t_nor.negative(), tol):
- _wrn(translate("draft", "Tangent and normal vectors are parallel. Normal replaced by a default axis."))
+ _wrn(
+ translate(
+ "draft",
+ "Tangent and normal vectors are parallel. Normal replaced by a default axis.",
+ )
+ )
n = t
if overrideNormal:
- onPathRotation = App.Rotation(t, nullv, n, "XZY") # priority = "XZY"
+ onPathRotation = App.Rotation(t, nullv, n, "XZY") # priority = "XZY"
else:
- onPathRotation = App.Rotation(t, n, nullv, "XYZ") # priority = "XYZ"
+ onPathRotation = App.Rotation(t, n, nullv, "XYZ") # priority = "XYZ"
elif mode == "Frenet":
try:
n = edge.normalAt(get_parameter_from_v0(edge, offset))
- except App.Base.FreeCADError: # no/infinite normals here
- _wrn(translate("draft", "Cannot calculate normal vector. Using the default normal instead."))
+ except App.Base.FreeCADError: # no/infinite normals here
+ _wrn(
+ translate(
+ "draft", "Cannot calculate normal vector. Using the default normal instead."
+ )
+ )
n = normal
if n.isEqual(nullv, tol):
@@ -843,10 +828,15 @@ def calculate_placement(globalRotation,
n_nor = n.normalize()
t_nor = t.normalize()
if n_nor.isEqual(t_nor, tol) or n_nor.isEqual(t_nor.negative(), tol):
- _wrn(translate("draft", "Tangent and normal vectors are parallel. Normal replaced by a default axis."))
+ _wrn(
+ translate(
+ "draft",
+ "Tangent and normal vectors are parallel. Normal replaced by a default axis.",
+ )
+ )
n = t
- onPathRotation = App.Rotation(t, n, nullv, "XYZ") # priority = "XYZ"
+ onPathRotation = App.Rotation(t, n, nullv, "XYZ") # priority = "XYZ"
else:
_err(translate("draft", "AlignMode {} is not implemented").format(mode))
@@ -860,6 +850,7 @@ def calculate_placement(globalRotation,
calculatePlacement = calculate_placement
+
def get_parameter_from_v0(edge, offset):
"""Return parameter at distance offset from edge.Vertexes[0].
diff --git a/src/Mod/Draft/draftobjects/pathtwistedarray.py b/src/Mod/Draft/draftobjects/pathtwistedarray.py
index 52cb6efdc9..7b200d8a67 100644
--- a/src/Mod/Draft/draftobjects/pathtwistedarray.py
+++ b/src/Mod/Draft/draftobjects/pathtwistedarray.py
@@ -49,7 +49,12 @@ object in the Arch Workbench.
import draftgeoutils.geo_arrays as geo
from draftutils.messages import _log
-def QT_TRANSLATE_NOOP(ctx,txt): return txt
+
+
+def QT_TRANSLATE_NOOP(ctx, txt):
+ return txt
+
+
from draftobjects.draftlink import DraftLink
## \addtogroup draftobjects
@@ -80,73 +85,83 @@ class PathTwistedArray(DraftLink):
properties = []
if "Base" not in properties:
- obj.addProperty("App::PropertyLink",
- "Base",
- "Objects",
- QT_TRANSLATE_NOOP("App::Property","The base object that will be duplicated."),
- locked=True)
+ obj.addProperty(
+ "App::PropertyLink",
+ "Base",
+ "Objects",
+ QT_TRANSLATE_NOOP("App::Property", "The base object that will be duplicated."),
+ locked=True,
+ )
obj.Base = None
if "PathObject" not in properties:
- obj.addProperty("App::PropertyLink",
- "PathObject",
- "Objects",
- QT_TRANSLATE_NOOP("App::Property","The object along which the copies will be distributed. It must contain 'Edges'."),
- locked=True)
+ obj.addProperty(
+ "App::PropertyLink",
+ "PathObject",
+ "Objects",
+ QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The object along which the copies will be distributed. It must contain 'Edges'.",
+ ),
+ locked=True,
+ )
obj.PathObject = None
if "Fuse" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Specifies if the copies "
- "should be fused together "
- "if they touch each other (slower)")
- obj.addProperty("App::PropertyBool",
- "Fuse",
- "Objects",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Specifies if the copies "
+ "should be fused together "
+ "if they touch each other (slower)",
+ )
+ obj.addProperty("App::PropertyBool", "Fuse", "Objects", _tip, locked=True)
obj.Fuse = False
if "Count" not in properties:
- obj.addProperty("App::PropertyInteger",
- "Count",
- "Objects",
- QT_TRANSLATE_NOOP("App::Property","Number of copies to create."),
- locked=True)
+ obj.addProperty(
+ "App::PropertyInteger",
+ "Count",
+ "Objects",
+ QT_TRANSLATE_NOOP("App::Property", "Number of copies to create."),
+ locked=True,
+ )
obj.Count = 15
if "RotationFactor" not in properties:
- obj.addProperty("App::PropertyFloat",
- "RotationFactor",
- "Objects",
- QT_TRANSLATE_NOOP("App::Property","Rotation factor of the twisted array."),
- locked=True)
+ obj.addProperty(
+ "App::PropertyFloat",
+ "RotationFactor",
+ "Objects",
+ QT_TRANSLATE_NOOP("App::Property", "Rotation factor of the twisted array."),
+ locked=True,
+ )
obj.RotationFactor = 0.25
if self.use_link and "ExpandArray" not in properties:
- obj.addProperty("App::PropertyBool",
- "ExpandArray",
- "Objects",
- QT_TRANSLATE_NOOP("App::Property","Show the individual array elements (only for Link arrays)"),
- locked=True)
+ obj.addProperty(
+ "App::PropertyBool",
+ "ExpandArray",
+ "Objects",
+ QT_TRANSLATE_NOOP(
+ "App::Property", "Show the individual array elements (only for Link arrays)"
+ ),
+ locked=True,
+ )
obj.ExpandArray = False
- obj.setPropertyStatus('Shape', 'Transient')
+ obj.setPropertyStatus("Shape", "Transient")
if not self.use_link:
if "PlacementList" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The placement for each array element")
- obj.addProperty("App::PropertyPlacementList",
- "PlacementList",
- "Objects",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The placement for each array element")
+ obj.addProperty(
+ "App::PropertyPlacementList", "PlacementList", "Objects", _tip, locked=True
+ )
obj.PlacementList = []
def linkSetup(self, obj):
"""Set up the object as a link object."""
super().linkSetup(obj)
- obj.configLinkProperty(ElementCount='Count')
+ obj.configLinkProperty(ElementCount="Count")
def onDocumentRestored(self, obj):
super().onDocumentRestored(obj)
@@ -161,13 +176,11 @@ class PathTwistedArray(DraftLink):
_log("v1.1, " + obj.Name + ", added hidden property 'PlacementList'")
self.set_properties(obj)
- self.execute(obj) # Required to update PlacementList.
+ self.execute(obj) # Required to update PlacementList.
def execute(self, obj):
"""Execute when the object is created or recomputed."""
- if self.props_changed_placement_only(obj) \
- or not obj.Base \
- or not obj.PathObject:
+ if self.props_changed_placement_only(obj) or not obj.Base or not obj.PathObject:
self.props_changed_clear()
return
@@ -178,12 +191,11 @@ class PathTwistedArray(DraftLink):
count = obj.Count
rot_factor = obj.RotationFactor
- copy_placements, _ = geo.get_twisted_placements(path,
- count=count,
- rot_factor=rot_factor)
+ copy_placements, _ = geo.get_twisted_placements(path, count=count, rot_factor=rot_factor)
self.buildShape(obj, array_placement, copy_placements)
self.props_changed_clear()
- return (not self.use_link)
+ return not self.use_link
+
## @}
diff --git a/src/Mod/Draft/draftobjects/point.py b/src/Mod/Draft/draftobjects/point.py
index 3f64712b86..0412e21ef5 100644
--- a/src/Mod/Draft/draftobjects/point.py
+++ b/src/Mod/Draft/draftobjects/point.py
@@ -54,7 +54,7 @@ class Point(DraftObject):
obj.Y = y
obj.Z = z
- obj.setPropertyStatus('Placement', 'Hidden')
+ obj.setPropertyStatus("Placement", "Hidden")
def onDocumentRestored(self, obj):
super().onDocumentRestored(obj)
@@ -73,6 +73,7 @@ class Point(DraftObject):
return
import Part
+
obj.Shape = Part.Vertex(App.Vector(0, 0, 0))
if base != xyz_vec:
obj.Placement.Base = xyz_vec
diff --git a/src/Mod/Draft/draftobjects/pointarray.py b/src/Mod/Draft/draftobjects/pointarray.py
index 0cd5793c11..d4e59a5538 100644
--- a/src/Mod/Draft/draftobjects/pointarray.py
+++ b/src/Mod/Draft/draftobjects/pointarray.py
@@ -22,8 +22,7 @@
# * USA *
# * *
# ***************************************************************************
-"""Provides the object code for the PointArray object.
-"""
+"""Provides the object code for the PointArray object."""
## @package pointarray
# \ingroup draftobjects
# \brief Provides the object code for the PointArray object.
@@ -56,7 +55,7 @@ class PointArray(DraftLink):
def linkSetup(self, obj):
"""Set up the object as a link object."""
super().linkSetup(obj)
- obj.configLinkProperty(ElementCount='Count')
+ obj.configLinkProperty(ElementCount="Count")
def set_properties(self, obj):
"""Set properties only if they don't exist."""
@@ -64,78 +63,63 @@ class PointArray(DraftLink):
if "Base" not in properties:
_tip = QT_TRANSLATE_NOOP("App::Property", "Base object that will be duplicated")
- obj.addProperty("App::PropertyLink",
- "Base",
- "Objects",
- _tip,
- locked=True)
+ obj.addProperty("App::PropertyLink", "Base", "Objects", _tip, locked=True)
obj.Base = None
if "PointObject" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property", "Object containing points used to distribute the copies.")
- obj.addProperty("App::PropertyLink",
- "PointObject",
- "Objects",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Object containing points used to distribute the copies."
+ )
+ obj.addProperty("App::PropertyLink", "PointObject", "Objects", _tip, locked=True)
obj.PointObject = None
if "Fuse" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Specifies if the copies "
- "should be fused together "
- "if they touch each other (slower)")
- obj.addProperty("App::PropertyBool",
- "Fuse",
- "Objects",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Specifies if the copies "
+ "should be fused together "
+ "if they touch each other (slower)",
+ )
+ obj.addProperty("App::PropertyBool", "Fuse", "Objects", _tip, locked=True)
obj.Fuse = False
if "Count" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property", "Number of copies in the array.\nThis property is read-only, as the number depends on the points in 'Point Object'.")
- obj.addProperty("App::PropertyInteger",
- "Count",
- "Objects",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Number of copies in the array.\nThis property is read-only, as the number depends on the points in 'Point Object'.",
+ )
+ obj.addProperty("App::PropertyInteger", "Count", "Objects", _tip, locked=True)
obj.Count = 0
obj.setEditorMode("Count", 1) # Read only
if "ExtraPlacement" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property", "Additional placement, shift and rotation, that will be applied to each copy")
- obj.addProperty("App::PropertyPlacement",
- "ExtraPlacement",
- "Objects",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Additional placement, shift and rotation, that will be applied to each copy",
+ )
+ obj.addProperty(
+ "App::PropertyPlacement", "ExtraPlacement", "Objects", _tip, locked=True
+ )
obj.ExtraPlacement = App.Placement()
if self.use_link and "ExpandArray" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property", "Show the individual array elements (only for Link arrays)")
- obj.addProperty("App::PropertyBool",
- "ExpandArray",
- "Objects",
- _tip,
- locked=True)
- obj.setPropertyStatus('Shape', 'Transient')
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Show the individual array elements (only for Link arrays)"
+ )
+ obj.addProperty("App::PropertyBool", "ExpandArray", "Objects", _tip, locked=True)
+ obj.setPropertyStatus("Shape", "Transient")
if not self.use_link:
if "PlacementList" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The placement for each array element")
- obj.addProperty("App::PropertyPlacementList",
- "PlacementList",
- "Objects",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The placement for each array element")
+ obj.addProperty(
+ "App::PropertyPlacementList", "PlacementList", "Objects", _tip, locked=True
+ )
obj.PlacementList = []
def execute(self, obj):
"""Run when the object is created or recomputed."""
- if self.props_changed_placement_only(obj) \
- or not obj.Base \
- or not obj.PointObject:
+ if self.props_changed_placement_only(obj) or not obj.Base or not obj.PointObject:
self.props_changed_clear()
return
@@ -145,7 +129,7 @@ class PointArray(DraftLink):
self.buildShape(obj, obj.Placement, pls)
self.props_changed_clear()
- return (not self.use_link)
+ return not self.use_link
def onDocumentRestored(self, obj):
super().onDocumentRestored(obj)
@@ -167,9 +151,10 @@ class PointArray(DraftLink):
if hasattr(obj, "PointList"):
obj.PointObject = obj.PointList
obj.removeProperty("PointList")
- self.execute(obj) # Required to update PlacementList.
+ self.execute(obj) # Required to update PlacementList.
-def remove_equal_vecs (vec_list):
+
+def remove_equal_vecs(vec_list):
"""Remove equal vectors from a list.
Parameters
@@ -189,6 +174,7 @@ def remove_equal_vecs (vec_list):
res_list.append(vec)
return res_list
+
def get_point_list(point_object):
"""Extract a list of points from a point object.
@@ -205,7 +191,7 @@ def get_point_list(point_object):
if hasattr(point_object, "Shape") and hasattr(point_object.Shape, "Vertexes"):
pt_list = [v.Point for v in point_object.Shape.Vertexes]
# For compatibility with previous versions: add all points from sketch (including construction geometry):
- if hasattr(point_object, 'Geometry'):
+ if hasattr(point_object, "Geometry"):
place = point_object.Placement
for geo in point_object.Geometry:
if geo.TypeId == "Part::GeomPoint":
@@ -219,6 +205,7 @@ def get_point_list(point_object):
return remove_equal_vecs(pt_list)
+
def build_placements(base_object, pt_list=None, placement=App.Placement()):
"""Build a placements from the base object and list of points.
@@ -227,9 +214,12 @@ def build_placements(base_object, pt_list=None, placement=App.Placement()):
list of App.Placements
"""
if not pt_list:
- _err(translate("Draft",
- "Point object does not have a discrete point, "
- "it cannot be used for an array"))
+ _err(
+ translate(
+ "Draft",
+ "Point object does not have a discrete point, " "it cannot be used for an array",
+ )
+ )
return []
pls = list()
diff --git a/src/Mod/Draft/draftobjects/polygon.py b/src/Mod/Draft/draftobjects/polygon.py
index ebbf62f455..50f5bf204c 100644
--- a/src/Mod/Draft/draftobjects/polygon.py
+++ b/src/Mod/Draft/draftobjects/polygon.py
@@ -43,36 +43,31 @@ class Polygon(DraftObject):
def __init__(self, obj):
super().__init__(obj, "Polygon")
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Number of faces")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Number of faces")
obj.addProperty("App::PropertyInteger", "FacesNumber", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Radius of the control circle")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Radius of the control circle")
obj.addProperty("App::PropertyLength", "Radius", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "How the polygon must be drawn from the control circle")
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "How the polygon must be drawn from the control circle"
+ )
obj.addProperty("App::PropertyEnumeration", "DrawMode", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Radius to use to fillet the corners")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Radius to use to fillet the corners")
obj.addProperty("App::PropertyLength", "FilletRadius", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Size of the chamfer to give to the corners")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Size of the chamfer to give to the corners")
obj.addProperty("App::PropertyLength", "ChamferSize", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Create a face")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Create a face")
obj.addProperty("App::PropertyBool", "MakeFace", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The area of this object")
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The area of this object")
obj.addProperty("App::PropertyArea", "Area", "Draft", _tip, locked=True)
obj.MakeFace = params.get_param("MakeFaceMode")
- obj.DrawMode = ['inscribed','circumscribed']
+ obj.DrawMode = ["inscribed", "circumscribed"]
obj.FacesNumber = 0
obj.Radius = 1
@@ -88,33 +83,30 @@ class Polygon(DraftObject):
if (obj.FacesNumber >= 3) and (obj.Radius.Value > 0):
import Part
+
plm = obj.Placement
angle = (math.pi * 2) / obj.FacesNumber
- if obj.DrawMode == 'inscribed':
+ if obj.DrawMode == "inscribed":
delta = obj.Radius.Value
else:
delta = obj.Radius.Value / math.cos(angle / 2.0)
pts = [App.Vector(delta, 0, 0)]
for i in range(obj.FacesNumber - 1):
ang = (i + 1) * angle
- pts.append(App.Vector(delta * math.cos(ang),
- delta*math.sin(ang),
- 0))
+ pts.append(App.Vector(delta * math.cos(ang), delta * math.sin(ang), 0))
pts.append(pts[0])
shape = Part.makePolygon(pts)
if "ChamferSize" in obj.PropertiesList:
if obj.ChamferSize.Value != 0:
- w = DraftGeomUtils.filletWire(shape,obj.ChamferSize.Value,
- chamfer=True)
+ w = DraftGeomUtils.filletWire(shape, obj.ChamferSize.Value, chamfer=True)
if w:
shape = w
if "FilletRadius" in obj.PropertiesList:
if obj.FilletRadius.Value != 0:
- w = DraftGeomUtils.filletWire(shape,
- obj.FilletRadius.Value)
+ w = DraftGeomUtils.filletWire(shape, obj.FilletRadius.Value)
if w:
shape = w
- if hasattr(obj,"MakeFace"):
+ if hasattr(obj, "MakeFace"):
if obj.MakeFace:
shape = Part.Face(shape)
else:
diff --git a/src/Mod/Draft/draftobjects/rectangle.py b/src/Mod/Draft/draftobjects/rectangle.py
index 1bf4fcd108..d9ea64d6b5 100644
--- a/src/Mod/Draft/draftobjects/rectangle.py
+++ b/src/Mod/Draft/draftobjects/rectangle.py
@@ -67,10 +67,10 @@ class Rectangle(DraftObject):
obj.addProperty("App::PropertyArea", "Area", "Draft", _tip, locked=True)
obj.MakeFace = params.get_param("MakeFaceMode")
- obj.Length=1
- obj.Height=1
- obj.Rows=1
- obj.Columns=1
+ obj.Length = 1
+ obj.Height = 1
+ obj.Rows = 1
+ obj.Columns = 1
def onDocumentRestored(self, obj):
super().onDocumentRestored(obj)
@@ -95,7 +95,7 @@ class Rectangle(DraftObject):
shape = None
- if hasattr(obj,"Rows") and hasattr(obj,"Columns"):
+ if hasattr(obj, "Rows") and hasattr(obj, "Columns"):
# TODO: verify if this is needed:
if obj.Rows > 1:
rows = obj.Rows
@@ -109,29 +109,28 @@ class Rectangle(DraftObject):
if (rows > 1) or (columns > 1):
shapes = []
- l = obj.Length.Value/columns
- h = obj.Height.Value/rows
+ l = obj.Length.Value / columns
+ h = obj.Height.Value / rows
for i in range(columns):
for j in range(rows):
- p1 = App.Vector(i*l,j*h,0)
- p2 = App.Vector(p1.x+l,p1.y,p1.z)
- p3 = App.Vector(p1.x+l,p1.y+h,p1.z)
- p4 = App.Vector(p1.x,p1.y+h,p1.z)
- p = Part.makePolygon([p1,p2,p3,p4,p1])
+ p1 = App.Vector(i * l, j * h, 0)
+ p2 = App.Vector(p1.x + l, p1.y, p1.z)
+ p3 = App.Vector(p1.x + l, p1.y + h, p1.z)
+ p4 = App.Vector(p1.x, p1.y + h, p1.z)
+ p = Part.makePolygon([p1, p2, p3, p4, p1])
if "ChamferSize" in obj.PropertiesList:
if obj.ChamferSize.Value != 0:
- w = DraftGeomUtils.filletWire(p,
- obj.ChamferSize.Value,
- chamfer=True)
+ w = DraftGeomUtils.filletWire(
+ p, obj.ChamferSize.Value, chamfer=True
+ )
if w:
p = w
if "FilletRadius" in obj.PropertiesList:
if obj.FilletRadius.Value != 0:
- w = DraftGeomUtils.filletWire(p,
- obj.FilletRadius.Value)
+ w = DraftGeomUtils.filletWire(p, obj.FilletRadius.Value)
if w:
p = w
- if hasattr(obj,"MakeFace"):
+ if hasattr(obj, "MakeFace"):
if obj.MakeFace:
p = Part.Face(p)
shapes.append(p)
@@ -139,31 +138,22 @@ class Rectangle(DraftObject):
shape = Part.makeCompound(shapes)
if not shape:
- p1 = App.Vector(0,0,0)
- p2 = App.Vector(p1.x+obj.Length.Value,
- p1.y,
- p1.z)
- p3 = App.Vector(p1.x+obj.Length.Value,
- p1.y+obj.Height.Value,
- p1.z)
- p4 = App.Vector(p1.x,
- p1.y+obj.Height.Value,
- p1.z)
+ p1 = App.Vector(0, 0, 0)
+ p2 = App.Vector(p1.x + obj.Length.Value, p1.y, p1.z)
+ p3 = App.Vector(p1.x + obj.Length.Value, p1.y + obj.Height.Value, p1.z)
+ p4 = App.Vector(p1.x, p1.y + obj.Height.Value, p1.z)
shape = Part.makePolygon([p1, p2, p3, p4, p1])
if "ChamferSize" in obj.PropertiesList:
if obj.ChamferSize.Value != 0:
- w = DraftGeomUtils.filletWire(shape,
- obj.ChamferSize.Value,
- chamfer=True)
+ w = DraftGeomUtils.filletWire(shape, obj.ChamferSize.Value, chamfer=True)
if w:
shape = w
if "FilletRadius" in obj.PropertiesList:
if obj.FilletRadius.Value != 0:
- w = DraftGeomUtils.filletWire(shape,
- obj.FilletRadius.Value)
+ w = DraftGeomUtils.filletWire(shape, obj.FilletRadius.Value)
if w:
shape = w
- if hasattr(obj,"MakeFace"):
+ if hasattr(obj, "MakeFace"):
if obj.MakeFace:
shape = Part.Face(shape)
else:
@@ -171,7 +161,7 @@ class Rectangle(DraftObject):
obj.Shape = shape
- if hasattr(obj,"Area") and hasattr(shape,"Area"):
+ if hasattr(obj, "Area") and hasattr(shape, "Area"):
obj.Area = shape.Area
obj.Placement = plm
diff --git a/src/Mod/Draft/draftobjects/shape2dview.py b/src/Mod/Draft/draftobjects/shape2dview.py
index a04da16891..496dd84d55 100644
--- a/src/Mod/Draft/draftobjects/shape2dview.py
+++ b/src/Mod/Draft/draftobjects/shape2dview.py
@@ -41,7 +41,7 @@ from draftutils.translate import translate
class Shape2DView(DraftObject):
"""The Shape2DView object"""
- def __init__(self,obj):
+ def __init__(self, obj):
self.setProperties(obj)
super().__init__(obj, "Shape2DView")
@@ -53,101 +53,108 @@ class Shape2DView(DraftObject):
obj, vp_module="view_base", vp_class="ViewProviderDraftAlt", format=False
)
- def setProperties(self,obj):
+ def setProperties(self, obj):
pl = obj.PropertiesList
if not "Base" in pl:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The base object this 2D view must represent")
- obj.addProperty("App::PropertyLink", "Base",
- "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The base object this 2D view must represent")
+ obj.addProperty("App::PropertyLink", "Base", "Draft", _tip, locked=True)
if not "Projection" in pl:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The projection vector of this object")
- obj.addProperty("App::PropertyVector", "Projection",
- "Draft", _tip, locked=True)
- obj.Projection = App.Vector(0,0,1)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The projection vector of this object")
+ obj.addProperty("App::PropertyVector", "Projection", "Draft", _tip, locked=True)
+ obj.Projection = App.Vector(0, 0, 1)
if not "ProjectionMode" in pl:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The way the viewed object must be projected")
- obj.addProperty("App::PropertyEnumeration", "ProjectionMode",
- "Draft", _tip, locked=True)
- obj.ProjectionMode = ["Solid", "Individual Faces",
- "Cutlines", "Cutfaces","Solid faces"]
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The way the viewed object must be projected")
+ obj.addProperty(
+ "App::PropertyEnumeration", "ProjectionMode", "Draft", _tip, locked=True
+ )
+ obj.ProjectionMode = [
+ "Solid",
+ "Individual Faces",
+ "Cutlines",
+ "Cutfaces",
+ "Solid faces",
+ ]
if not "FaceNumbers" in pl:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The indices of the faces to be projected in Individual Faces mode")
- obj.addProperty("App::PropertyIntegerList", "FaceNumbers",
- "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "The indices of the faces to be projected in Individual Faces mode"
+ )
+ obj.addProperty("App::PropertyIntegerList", "FaceNumbers", "Draft", _tip, locked=True)
if not "HiddenLines" in pl:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Show hidden lines")
- obj.addProperty("App::PropertyBool", "HiddenLines",
- "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Show hidden lines")
+ obj.addProperty("App::PropertyBool", "HiddenLines", "Draft", _tip, locked=True)
obj.HiddenLines = False
if not "FuseArch" in pl:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Fuse wall and structure objects of same type and material")
- obj.addProperty("App::PropertyBool", "FuseArch",
- "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Fuse wall and structure objects of same type and material"
+ )
+ obj.addProperty("App::PropertyBool", "FuseArch", "Draft", _tip, locked=True)
if not "Tessellation" in pl:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Tessellate Ellipses and B-splines into line segments")
- obj.addProperty("App::PropertyBool", "Tessellation",
- "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Tessellate Ellipses and B-splines into line segments"
+ )
+ obj.addProperty("App::PropertyBool", "Tessellation", "Draft", _tip, locked=True)
obj.Tessellation = False
if not "InPlace" in pl:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "For Cutlines and Cutfaces modes, this leaves the faces at the cut location")
- obj.addProperty("App::PropertyBool", "InPlace",
- "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "For Cutlines and Cutfaces modes, this leaves the faces at the cut location",
+ )
+ obj.addProperty("App::PropertyBool", "InPlace", "Draft", _tip, locked=True)
obj.InPlace = True
if not "SegmentLength" in pl:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Length of line segments if tessellating Ellipses or B-splines into line segments")
- obj.addProperty("App::PropertyFloat", "SegmentLength",
- "Draft", _tip, locked=True)
- obj.SegmentLength = .05
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Length of line segments if tessellating Ellipses or B-splines into line segments",
+ )
+ obj.addProperty("App::PropertyFloat", "SegmentLength", "Draft", _tip, locked=True)
+ obj.SegmentLength = 0.05
if not "VisibleOnly" in pl:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "If this is True, this object will include only visible objects")
- obj.addProperty("App::PropertyBool", "VisibleOnly",
- "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "If this is True, this object will include only visible objects"
+ )
+ obj.addProperty("App::PropertyBool", "VisibleOnly", "Draft", _tip, locked=True)
obj.VisibleOnly = False
if not "ExclusionPoints" in pl:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "A list of exclusion points. Any edge touching any of those points will not be drawn.")
- obj.addProperty("App::PropertyVectorList", "ExclusionPoints",
- "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "A list of exclusion points. Any edge touching any of those points will not be drawn.",
+ )
+ obj.addProperty(
+ "App::PropertyVectorList", "ExclusionPoints", "Draft", _tip, locked=True
+ )
if not "ExclusionNames" in pl:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "A list of exclusion object names. Any object viewed that matches a name from the list will not be drawn.")
- obj.addProperty("App::PropertyStringList", "ExclusionNames",
- "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "A list of exclusion object names. Any object viewed that matches a name from the list will not be drawn.",
+ )
+ obj.addProperty("App::PropertyStringList", "ExclusionNames", "Draft", _tip, locked=True)
if not "OnlySolids" in pl:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "If this is True, only solid geometry is handled. This overrides the base object's Only Solids property")
- obj.addProperty("App::PropertyBool", "OnlySolids",
- "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "If this is True, only solid geometry is handled. This overrides the base object's Only Solids property",
+ )
+ obj.addProperty("App::PropertyBool", "OnlySolids", "Draft", _tip, locked=True)
if not "Clip" in pl:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "If this is True, the contents are clipped to the borders of the section plane, if applicable. This overrides the base object's Clip property")
- obj.addProperty("App::PropertyBool", "Clip",
- "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "If this is True, the contents are clipped to the borders of the section plane, if applicable. This overrides the base object's Clip property",
+ )
+ obj.addProperty("App::PropertyBool", "Clip", "Draft", _tip, locked=True)
if not "AutoUpdate" in pl:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "This object will be recomputed only if this is True.")
- obj.addProperty("App::PropertyBool", "AutoUpdate",
- "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "This object will be recomputed only if this is True."
+ )
+ obj.addProperty("App::PropertyBool", "AutoUpdate", "Draft", _tip, locked=True)
obj.AutoUpdate = True
- def getProjected(self,obj,shape,direction):
-
+ def getProjected(self, obj, shape, direction):
"returns projected edges from a shape and a direction"
import Part
import TechDraw
import DraftGeomUtils
+
edges = []
_groups = TechDraw.projectEx(shape, direction)
for g in _groups[0:5]:
@@ -157,22 +164,22 @@ class Shape2DView(DraftObject):
for g in _groups[5:]:
if not g.isNull():
edges.append(g)
- edges = self.cleanExcluded(obj,edges)
+ edges = self.cleanExcluded(obj, edges)
if getattr(obj, "Tessellation", False):
- return DraftGeomUtils.cleanProjection(Part.makeCompound(edges),
- obj.Tessellation,
- obj.SegmentLength)
+ return DraftGeomUtils.cleanProjection(
+ Part.makeCompound(edges), obj.Tessellation, obj.SegmentLength
+ )
else:
return Part.makeCompound(edges)
- def cleanExcluded(self,obj,shapes):
-
+ def cleanExcluded(self, obj, shapes):
"""removes any edge touching exclusion points"""
import Part
+
MAXDIST = 0.0001
- if (not hasattr(obj,"ExclusionPoints")) or (not obj.ExclusionPoints):
+ if (not hasattr(obj, "ExclusionPoints")) or (not obj.ExclusionPoints):
return shapes
- #verts = [Part.Vertex(obj.Placement.multVec(p)) for p in obj.ExclusionPoints]
+ # verts = [Part.Vertex(obj.Placement.multVec(p)) for p in obj.ExclusionPoints]
verts = [Part.Vertex(p) for p in obj.ExclusionPoints]
nedges = []
for s in shapes:
@@ -183,14 +190,16 @@ class Shape2DView(DraftObject):
if d and (d[0] <= MAXDIST):
break
except RuntimeError:
- print("FIXME: shape2dview: distance unavailable for edge",e,"in",obj.Label)
+ print(
+ "FIXME: shape2dview: distance unavailable for edge", e, "in", obj.Label
+ )
else:
nedges.append(e)
return nedges
- def excludeNames(self,obj,objs):
- if hasattr(obj,"ExclusionNames"):
- objs = [o for o in objs if not(o.Name in obj.ExclusionNames)]
+ def excludeNames(self, obj, objs):
+ if hasattr(obj, "ExclusionNames"):
+ objs = [o for o in objs if not (o.Name in obj.ExclusionNames)]
return objs
def _get_shapes(self, shape, onlysolids=False):
@@ -203,39 +212,39 @@ class Shape2DView(DraftObject):
return [shape.copy()]
def execute(self, obj):
- if self.props_changed_placement_only(obj) \
- or not getattr(obj, "AutoUpdate", True):
+ if self.props_changed_placement_only(obj) or not getattr(obj, "AutoUpdate", True):
obj.positionBySupport()
self.props_changed_clear()
return
import Part
import DraftGeomUtils
+
pl = obj.Placement
if obj.Base:
- if utils.get_type(obj.Base) in ["BuildingPart","SectionPlane","IfcAnnotation"]:
+ if utils.get_type(obj.Base) in ["BuildingPart", "SectionPlane", "IfcAnnotation"]:
objs = []
if utils.get_type(obj.Base) == "SectionPlane":
- objs = self.excludeNames(obj,obj.Base.Objects)
+ objs = self.excludeNames(obj, obj.Base.Objects)
cutplane = obj.Base.Shape
elif utils.get_type(obj.Base) == "IfcAnnotation":
# this is a NativeIFC section plane
objs, cutplane = obj.Base.Proxy.get_section_data(obj.Base)
objs = self.excludeNames(obj, objs)
else:
- objs = self.excludeNames(obj,obj.Base.Group)
+ objs = self.excludeNames(obj, obj.Base.Group)
cutplane = Part.makePlane(1000, 1000, App.Vector(-500, -500, 0))
m = 1
- if obj.Base.ViewObject and hasattr(obj.Base.ViewObject,"CutMargin"):
+ if obj.Base.ViewObject and hasattr(obj.Base.ViewObject, "CutMargin"):
m = obj.Base.ViewObject.CutMargin.Value
- cutplane.translate(App.Vector(0,0,m))
+ cutplane.translate(App.Vector(0, 0, m))
cutplane.Placement = cutplane.Placement.multiply(obj.Base.Placement)
if objs:
onlysolids = True
# TODO Fix this : 2025.1.26, why test obj.Base.OnlySolids if override by obj.OnlySolids
- if hasattr(obj.Base,"OnlySolids"):
+ if hasattr(obj.Base, "OnlySolids"):
onlysolids = obj.Base.OnlySolids
- if hasattr(obj,"OnlySolids"): # override base object
+ if hasattr(obj, "OnlySolids"): # override base object
onlysolids = obj.OnlySolids
try:
import Arch
@@ -243,17 +252,20 @@ class Shape2DView(DraftObject):
print("Shape2DView: BIM not present, unable to recompute")
return
objs = groups.get_group_contents(objs, walls=True)
- if getattr(obj,"VisibleOnly",True):
+ if getattr(obj, "VisibleOnly", True):
objs = gui_utils.remove_hidden(objs)
shapes = []
- if getattr(obj,"FuseArch", False):
+ if getattr(obj, "FuseArch", False):
shtypes = {}
for o in objs:
- if utils.get_type(o) in ["Wall","Structure"]:
+ if utils.get_type(o) in ["Wall", "Structure"]:
shtypes.setdefault(
- o.Material.Name
- if (hasattr(o,"Material") and o.Material) else "None",
- []
+ (
+ o.Material.Name
+ if (hasattr(o, "Material") and o.Material)
+ else "None"
+ ),
+ [],
).extend(self._get_shapes(o.Shape, onlysolids))
elif hasattr(o, "Shape"):
shapes.extend(self._get_shapes(o.Shape, onlysolids))
@@ -281,18 +293,18 @@ class Shape2DView(DraftObject):
shapes.extend(self._get_shapes(o.Shape, onlysolids))
clip = False
# TODO Fix this : 2025.1.26, why test obj.Base.Clip if override by obj.Clip
- if hasattr(obj.Base,"Clip"):
+ if hasattr(obj.Base, "Clip"):
clip = obj.Base.Clip
- if hasattr(obj,"Clip"): #override base object
+ if hasattr(obj, "Clip"): # override base object
clip = obj.Clip
depth = None
- if hasattr(obj.Base,"Depth"):
+ if hasattr(obj.Base, "Depth"):
depth = obj.Base.Depth.Value
cutp, cutv, iv = Arch.getCutVolume(cutplane, shapes, clip, depth)
cuts = []
opl = App.Placement(obj.Base.Placement)
proj = opl.Rotation.multVec(App.Vector(0, 0, 1))
- if obj.ProjectionMode in ["Solid","Solid faces"]:
+ if obj.ProjectionMode in ["Solid", "Solid faces"]:
shapes_to_cut = shapes
if obj.ProjectionMode == "Solid faces":
shapes_to_cut = []
@@ -302,9 +314,9 @@ class Shape2DView(DraftObject):
if cutv and (not cutv.isNull()) and (not sh.isNull()):
if sh.Volume < 0:
sh.reverse()
- #if cutv.BoundBox.intersect(sh.BoundBox):
+ # if cutv.BoundBox.intersect(sh.BoundBox):
# c = sh.cut(cutv)
- #else:
+ # else:
# c = sh.copy()
try:
c = sh.cut(cutv)
@@ -316,7 +328,7 @@ class Shape2DView(DraftObject):
else:
cuts.extend(self._get_shapes(sh, onlysolids))
comp = Part.makeCompound(cuts)
- obj.Shape = self.getProjected(obj,comp,proj)
+ obj.Shape = self.getProjected(obj, comp, proj)
elif obj.ProjectionMode in ["Cutlines", "Cutfaces"]:
if not cutp: # Cutfaces and Cutlines needs cutp
obj.Shape = Part.Shape()
@@ -332,7 +344,7 @@ class Shape2DView(DraftObject):
facesOrg = sc.Faces
if not facesOrg:
continue
- if hasattr(obj,"InPlace"):
+ if hasattr(obj, "InPlace"):
if obj.InPlace:
faces = facesOrg
# Alternative approach in https://forum.freecad.org/viewtopic.php?p=807314#p807314, not adopted
@@ -340,7 +352,7 @@ class Shape2DView(DraftObject):
for faceOrg in facesOrg:
if len(faceOrg.Wires) == 1:
wireProj = self.getProjected(obj, faceOrg, proj)
- #return Compound
+ # return Compound
wireProjWire = Part.Wire(wireProj.Edges)
faceProj = Part.Face(wireProjWire)
elif len(faceOrg.Wires) == 2:
@@ -349,22 +361,28 @@ class Shape2DView(DraftObject):
if not w.isEqual(wireClosedOuter):
wireClosedInner = w
break
- wireProjOuter = self.getProjected(obj, wireClosedOuter, proj)
- #return Compound
+ wireProjOuter = self.getProjected(
+ obj, wireClosedOuter, proj
+ )
+ # return Compound
wireProjOuterWire = Part.Wire(wireProjOuter.Edges)
faceProj = Part.Face(wireProjOuterWire)
- wireProjInner = self.getProjected(obj, wireClosedInner, proj)
- #return Compound
+ wireProjInner = self.getProjected(
+ obj, wireClosedInner, proj
+ )
+ # return Compound
wireProjInnerWire = Part.Wire(wireProjInner.Edges)
- faceProj.cutHoles([wireProjInnerWire]) # (list of wires)
+ faceProj.cutHoles(
+ [wireProjInnerWire]
+ ) # (list of wires)
faces.append(faceProj)
else:
c = sh.section(cutp)
- if hasattr(obj,"InPlace"):
+ if hasattr(obj, "InPlace"):
if not obj.InPlace:
c = self.getProjected(obj, c, proj)
- #faces = []
- #if (obj.ProjectionMode == "Cutfaces") and (sh.ShapeType == "Solid"):
+ # faces = []
+ # if (obj.ProjectionMode == "Cutfaces") and (sh.ShapeType == "Solid"):
# wires = DraftGeomUtils.findWires(c.Edges)
# for w in wires:
# if w.isClosed():
@@ -381,21 +399,23 @@ class Shape2DView(DraftObject):
elif obj.Base.isDerivedFrom("App::DocumentObjectGroup"):
shapes = []
- objs = self.excludeNames(obj,groups.get_group_contents(obj.Base))
+ objs = self.excludeNames(obj, groups.get_group_contents(obj.Base))
for o in objs:
if hasattr(o, "Shape"):
shapes.extend(self._get_shapes(o.Shape))
if shapes:
import Part
+
comp = Part.makeCompound(shapes)
- obj.Shape = self.getProjected(obj,comp,obj.Projection)
+ obj.Shape = self.getProjected(obj, comp, obj.Projection)
elif hasattr(obj.Base, "Shape"):
if not DraftVecUtils.isNull(obj.Projection):
if obj.ProjectionMode == "Solid":
- obj.Shape = self.getProjected(obj,obj.Base.Shape,obj.Projection)
+ obj.Shape = self.getProjected(obj, obj.Base.Shape, obj.Projection)
elif obj.ProjectionMode == "Individual Faces":
import Part
+
if obj.FaceNumbers:
faces = []
for i in obj.FaceNumbers:
@@ -403,11 +423,11 @@ class Shape2DView(DraftObject):
faces.append(obj.Base.Shape.Faces[i])
views = []
for f in faces:
- views.append(self.getProjected(obj,f,obj.Projection))
+ views.append(self.getProjected(obj, f, obj.Projection))
if views:
obj.Shape = Part.makeCompound(views)
else:
- App.Console.PrintWarning(obj.ProjectionMode+" mode not implemented\n")
+ App.Console.PrintWarning(obj.ProjectionMode + " mode not implemented\n")
obj.Placement = pl
obj.positionBySupport()
diff --git a/src/Mod/Draft/draftobjects/shapestring.py b/src/Mod/Draft/draftobjects/shapestring.py
index f2cf266898..70bf1ffba0 100644
--- a/src/Mod/Draft/draftobjects/shapestring.py
+++ b/src/Mod/Draft/draftobjects/shapestring.py
@@ -66,24 +66,41 @@ class ShapeString(DraftObject):
if "Justification" not in properties:
_tip = QT_TRANSLATE_NOOP("App::Property", "Horizontal and vertical alignment")
obj.addProperty("App::PropertyEnumeration", "Justification", "Draft", _tip, locked=True)
- obj.Justification = ["Top-Left", "Top-Center", "Top-Right",
- "Middle-Left", "Middle-Center", "Middle-Right",
- "Bottom-Left", "Bottom-Center", "Bottom-Right"]
+ obj.Justification = [
+ "Top-Left",
+ "Top-Center",
+ "Top-Right",
+ "Middle-Left",
+ "Middle-Center",
+ "Middle-Right",
+ "Bottom-Left",
+ "Bottom-Center",
+ "Bottom-Right",
+ ]
obj.Justification = "Bottom-Left"
if "JustificationReference" not in properties:
_tip = QT_TRANSLATE_NOOP("App::Property", "Height reference used for justification")
- obj.addProperty("App::PropertyEnumeration", "JustificationReference", "Draft", _tip, locked=True)
+ obj.addProperty(
+ "App::PropertyEnumeration", "JustificationReference", "Draft", _tip, locked=True
+ )
obj.JustificationReference = ["Cap Height", "Shape Height"]
obj.JustificationReference = "Cap Height"
if "KeepLeftMargin" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property", "Keep left margin and leading white space when justification is left")
- obj.addProperty("App::PropertyBool", "KeepLeftMargin", "Draft", _tip, locked=True).KeepLeftMargin = False
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Keep left margin and leading white space when justification is left",
+ )
+ obj.addProperty(
+ "App::PropertyBool", "KeepLeftMargin", "Draft", _tip, locked=True
+ ).KeepLeftMargin = False
if "ScaleToSize" not in properties:
_tip = QT_TRANSLATE_NOOP("App::Property", "Scale to ensure cap height is equal to size")
- obj.addProperty("App::PropertyBool", "ScaleToSize", "Draft", _tip, locked=True).ScaleToSize = True
+ obj.addProperty(
+ "App::PropertyBool", "ScaleToSize", "Draft", _tip, locked=True
+ ).ScaleToSize = True
if "Tracking" not in properties:
_tip = QT_TRANSLATE_NOOP("App::Property", "Inter-character spacing")
@@ -95,10 +112,15 @@ class ShapeString(DraftObject):
if "MakeFace" not in properties:
_tip = QT_TRANSLATE_NOOP("App::Property", "Fill letters with faces")
- obj.addProperty("App::PropertyBool", "MakeFace", "Draft", _tip, locked=True).MakeFace = True
+ obj.addProperty(
+ "App::PropertyBool", "MakeFace", "Draft", _tip, locked=True
+ ).MakeFace = True
if "Fuse" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property", "Fuse faces if faces overlap, usually not required (can be very slow)")
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Fuse faces if faces overlap, usually not required (can be very slow)",
+ )
obj.addProperty("App::PropertyBool", "Fuse", "Draft", _tip, locked=True).Fuse = False
def onDocumentRestored(self, obj):
@@ -106,12 +128,12 @@ class ShapeString(DraftObject):
gui_utils.restore_view_object(
obj, vp_module="view_shapestring", vp_class="ViewProviderShapeString"
)
- if not hasattr(obj, "ObliqueAngle"): # several more properties were added
+ if not hasattr(obj, "ObliqueAngle"): # several more properties were added
self.update_properties_1v0(obj)
def update_properties_1v0(self, obj):
"""Update view properties."""
- old_tracking = obj.Tracking # no need for obj.getTypeIdOfProperty("Tracking")
+ old_tracking = obj.Tracking # no need for obj.getTypeIdOfProperty("Tracking")
obj.removeProperty("Tracking")
self.set_properties(obj)
obj.KeepLeftMargin = True
@@ -123,13 +145,11 @@ class ShapeString(DraftObject):
+ ", "
+ "added 'Fuse', 'Justification', 'JustificationReference', 'KeepLeftMargin', "
+ "'ObliqueAngle' and 'ScaleToSize' properties"
- )
+ )
_log("v1.0, " + obj.Name + ", changed 'Tracking' property type")
def execute(self, obj):
- if self.props_changed_placement_only() \
- or not obj.String \
- or not obj.FontFile:
+ if self.props_changed_placement_only() or not obj.String or not obj.FontFile:
obj.positionBySupport()
self.props_changed_clear()
return
@@ -174,10 +194,11 @@ class ShapeString(DraftObject):
# https://github.com/FreeCAD/FreeCAD/issues/21501
char_comp = Part.Compound(char)
factor = 1 / char_comp.BoundBox.YLength
- fill = sum([shape.Area for shape in shapes]) > (0.03 / factor ** 2) \
- and math.isclose(char_comp.BoundBox.DiagonalLength,
- Part.Compound(shapes).BoundBox.DiagonalLength,
- rel_tol=1e-7)
+ fill = sum([shape.Area for shape in shapes]) > (0.03 / factor**2) and math.isclose(
+ char_comp.BoundBox.DiagonalLength,
+ Part.Compound(shapes).BoundBox.DiagonalLength,
+ rel_tol=1e-7,
+ )
chars = Part.makeWireString(obj.String, font_file, obj.Size, obj.Tracking)
shapes = []
@@ -208,13 +229,21 @@ class ShapeString(DraftObject):
mtx.A12 = math.tan(math.radians(obj.ObliqueAngle))
ss_shape = ss_shape.transformGeometry(mtx)
else:
- wrn = translate("draft", "ShapeString: oblique angle must be in the -80 to +80 degree range") + "\n"
+ wrn = (
+ translate(
+ "draft",
+ "ShapeString: oblique angle must be in the -80 to +80 degree range",
+ )
+ + "\n"
+ )
App.Console.PrintWarning(wrn)
- just_vec = self.justification_vector(ss_shape,
- cap_height,
- obj.Justification,
- obj.JustificationReference,
- obj.KeepLeftMargin)
+ just_vec = self.justification_vector(
+ ss_shape,
+ cap_height,
+ obj.Justification,
+ obj.JustificationReference,
+ obj.KeepLeftMargin,
+ )
shapes = ss_shape.SubShapes
for shape in shapes:
shape.translate(just_vec)
@@ -229,13 +258,17 @@ class ShapeString(DraftObject):
def onChanged(self, obj, prop):
self.props_changed_store(prop)
- def justification_vector(self, ss_shape, cap_height, just, just_ref, keep_left_margin): # ss_shape is a compound
+ def justification_vector(
+ self, ss_shape, cap_height, just, just_ref, keep_left_margin
+ ): # ss_shape is a compound
box = ss_shape.optimalBoundingBox()
if keep_left_margin is True and "Left" in just:
vec = App.Vector(0, 0, 0)
else:
- vec = App.Vector(-box.XMin, 0, 0) # remove left margin caused by kerning and white space characters
- width = box.XLength
+ vec = App.Vector(
+ -box.XMin, 0, 0
+ ) # remove left margin caused by kerning and white space characters
+ width = box.XLength
if "Shape" in just_ref:
vec = vec + App.Vector(0, -box.YMin, 0)
height = box.YLength
@@ -244,11 +277,11 @@ class ShapeString(DraftObject):
if "Top" in just:
vec = vec + App.Vector(0, -height, 0)
elif "Middle" in just:
- vec = vec + App.Vector(0, -height/2, 0)
+ vec = vec + App.Vector(0, -height / 2, 0)
if "Right" in just:
vec = vec + App.Vector(-width, 0, 0)
elif "Center" in just:
- vec = vec + App.Vector(-width/2, 0, 0)
+ vec = vec + App.Vector(-width / 2, 0, 0)
return vec
def make_faces(self, wireChar):
@@ -307,7 +340,7 @@ class ShapeString(DraftObject):
for face in faces:
try:
# some fonts fail here
- if face.normalAt(0, 0).z < 0: # Does not seem to occur for FaceMakerBullseye.
+ if face.normalAt(0, 0).z < 0: # Does not seem to occur for FaceMakerBullseye.
face.reverse()
except Exception:
pass
diff --git a/src/Mod/Draft/draftobjects/text.py b/src/Mod/Draft/draftobjects/text.py
index 5f173b2594..27b800f7a2 100644
--- a/src/Mod/Draft/draftobjects/text.py
+++ b/src/Mod/Draft/draftobjects/text.py
@@ -49,30 +49,24 @@ class Text(DraftAnnotation):
properties = obj.PropertiesList
if "Placement" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The placement of the base point "
- "of the first line")
- obj.addProperty("App::PropertyPlacement",
- "Placement",
- "Base",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "The placement of the base point " "of the first line"
+ )
+ obj.addProperty("App::PropertyPlacement", "Placement", "Base", _tip, locked=True)
obj.Placement = App.Placement()
if "Text" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The text displayed by this object.\n"
- "It is a list of strings; each element "
- "in the list will be displayed "
- "in its own line.")
- obj.addProperty("App::PropertyStringList",
- "Text",
- "Base",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The text displayed by this object.\n"
+ "It is a list of strings; each element "
+ "in the list will be displayed "
+ "in its own line.",
+ )
+ obj.addProperty("App::PropertyStringList", "Text", "Base", _tip, locked=True)
obj.Text = []
- def onDocumentRestored(self,obj):
+ def onDocumentRestored(self, obj):
"""Execute code when the document is restored."""
super().onDocumentRestored(obj)
gui_utils.restore_view_object(obj, vp_module="view_text", vp_class="ViewProviderText")
diff --git a/src/Mod/Draft/draftobjects/wire.py b/src/Mod/Draft/draftobjects/wire.py
index e04fe8c3a1..e7e2745002 100644
--- a/src/Mod/Draft/draftobjects/wire.py
+++ b/src/Mod/Draft/draftobjects/wire.py
@@ -45,53 +45,45 @@ class Wire(DraftObject):
def __init__(self, obj):
super().__init__(obj, "Wire")
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The vertices of the wire")
- obj.addProperty("App::PropertyVectorList","Points", "Draft",_tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The vertices of the wire")
+ obj.addProperty("App::PropertyVectorList", "Points", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "If the wire is closed or not")
- obj.addProperty("App::PropertyBool","Closed", "Draft",_tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "If the wire is closed or not")
+ obj.addProperty("App::PropertyBool", "Closed", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The base object is the wire, it's formed from 2 objects")
- obj.addProperty("App::PropertyLink","Base", "Draft",_tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "The base object is the wire, it's formed from 2 objects"
+ )
+ obj.addProperty("App::PropertyLink", "Base", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The tool object is the wire, it's formed from 2 objects")
- obj.addProperty("App::PropertyLink","Tool", "Draft",_tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "The tool object is the wire, it's formed from 2 objects"
+ )
+ obj.addProperty("App::PropertyLink", "Tool", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The start point of this line")
- obj.addProperty("App::PropertyVectorDistance","Start", "Draft",_tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The start point of this line")
+ obj.addProperty("App::PropertyVectorDistance", "Start", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The end point of this line")
- obj.addProperty("App::PropertyVectorDistance","End", "Draft",_tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The end point of this line")
+ obj.addProperty("App::PropertyVectorDistance", "End", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The length of this line")
- obj.addProperty("App::PropertyLength","Length", "Draft",_tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The length of this line")
+ obj.addProperty("App::PropertyLength", "Length", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Radius to use to fillet the corners")
- obj.addProperty("App::PropertyLength","FilletRadius", "Draft",_tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Radius to use to fillet the corners")
+ obj.addProperty("App::PropertyLength", "FilletRadius", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Size of the chamfer to give to the corners")
- obj.addProperty("App::PropertyLength","ChamferSize", "Draft",_tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Size of the chamfer to give to the corners")
+ obj.addProperty("App::PropertyLength", "ChamferSize", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Create a face if this object is closed")
- obj.addProperty("App::PropertyBool","MakeFace", "Draft",_tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Create a face if this object is closed")
+ obj.addProperty("App::PropertyBool", "MakeFace", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The number of subdivisions of each edge")
- obj.addProperty("App::PropertyInteger","Subdivisions", "Draft",_tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The number of subdivisions of each edge")
+ obj.addProperty("App::PropertyInteger", "Subdivisions", "Draft", _tip, locked=True)
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The area of this object")
- obj.addProperty("App::PropertyArea","Area", "Draft",_tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The area of this object")
+ obj.addProperty("App::PropertyArea", "Area", "Draft", _tip, locked=True)
obj.MakeFace = params.get_param("MakeFaceMode")
obj.Closed = False
@@ -126,23 +118,26 @@ class Wire(DraftObject):
_log("v1.1, " + obj.Name + ", migrated view properties")
def execute(self, obj):
- if self.props_changed_placement_only(obj): # Supplying obj is required because of `Base` and `Tool`.
+ if self.props_changed_placement_only(
+ obj
+ ): # Supplying obj is required because of `Base` and `Tool`.
obj.positionBySupport()
self.update_start_end(obj)
self.props_changed_clear()
return
import Part
+
plm = obj.Placement
if obj.Base and (not obj.Tool):
if obj.Base.isDerivedFrom("Sketcher::SketchObject"):
shape = obj.Base.Shape.copy()
if obj.Base.Shape.isClosed():
- if getattr(obj,"MakeFace",True):
+ if getattr(obj, "MakeFace", True):
shape = Part.Face(shape)
obj.Shape = shape
elif obj.Base and obj.Tool:
- if hasattr(obj.Base,'Shape') and hasattr(obj.Tool,'Shape'):
+ if hasattr(obj.Base, "Shape") and hasattr(obj.Tool, "Shape"):
if (not obj.Base.Shape.isNull()) and (not obj.Tool.Shape.isNull()):
sh1 = obj.Base.Shape.copy()
sh2 = obj.Tool.Shape.copy()
@@ -151,41 +146,44 @@ class Wire(DraftObject):
shape = DraftGeomUtils.concatenate(shape)
obj.Shape = shape
p = []
- for v in shape.Vertexes: p.append(v.Point)
- if obj.Points != p: obj.Points = p
+ for v in shape.Vertexes:
+ p.append(v.Point)
+ if obj.Points != p:
+ obj.Points = p
elif obj.Points:
if obj.Points[0] == obj.Points[-1]:
- if not obj.Closed: obj.Closed = True
+ if not obj.Closed:
+ obj.Closed = True
obj.Points.pop()
if obj.Closed and (len(obj.Points) > 2):
pts = obj.Points
- if getattr(obj,"Subdivisions",0) > 0:
+ if getattr(obj, "Subdivisions", 0) > 0:
npts = []
for i in range(len(pts)):
p1 = pts[i]
npts.append(pts[i])
- if i == len(pts)-1:
+ if i == len(pts) - 1:
p2 = pts[0]
else:
- p2 = pts[i+1]
+ p2 = pts[i + 1]
v = p2.sub(p1)
- v = DraftVecUtils.scaleTo(v,v.Length/(obj.Subdivisions+1))
+ v = DraftVecUtils.scaleTo(v, v.Length / (obj.Subdivisions + 1))
for j in range(obj.Subdivisions):
- npts.append(p1.add(App.Vector(v).multiply(j+1)))
+ npts.append(p1.add(App.Vector(v).multiply(j + 1)))
pts = npts
- shape = Part.makePolygon(pts+[pts[0]])
+ shape = Part.makePolygon(pts + [pts[0]])
if "ChamferSize" in obj.PropertiesList:
if obj.ChamferSize.Value != 0:
- w = DraftGeomUtils.filletWire(shape,obj.ChamferSize.Value,chamfer=True)
+ w = DraftGeomUtils.filletWire(shape, obj.ChamferSize.Value, chamfer=True)
if w:
shape = w
if "FilletRadius" in obj.PropertiesList:
if obj.FilletRadius.Value != 0:
- w = DraftGeomUtils.filletWire(shape,obj.FilletRadius.Value)
+ w = DraftGeomUtils.filletWire(shape, obj.FilletRadius.Value)
if w:
shape = w
try:
- if getattr(obj,"MakeFace",True):
+ if getattr(obj, "MakeFace", True):
shape = Part.Face(shape)
except Part.OCCError:
pass
@@ -194,18 +192,18 @@ class Wire(DraftObject):
pts = obj.Points[1:]
lp = obj.Points[0]
for p in pts:
- if not DraftVecUtils.equals(lp,p):
- if getattr(obj,"Subdivisions",0) > 0:
+ if not DraftVecUtils.equals(lp, p):
+ if getattr(obj, "Subdivisions", 0) > 0:
npts = []
v = p.sub(lp)
- v = DraftVecUtils.scaleTo(v,v.Length/(obj.Subdivisions+1))
- edges.append(Part.LineSegment(lp,lp.add(v)).toShape())
+ v = DraftVecUtils.scaleTo(v, v.Length / (obj.Subdivisions + 1))
+ edges.append(Part.LineSegment(lp, lp.add(v)).toShape())
lv = lp.add(v)
for j in range(obj.Subdivisions):
- edges.append(Part.LineSegment(lv,lv.add(v)).toShape())
+ edges.append(Part.LineSegment(lv, lv.add(v)).toShape())
lv = lv.add(v)
else:
- edges.append(Part.LineSegment(lp,p).toShape())
+ edges.append(Part.LineSegment(lp, p).toShape())
lp = p
try:
shape = Part.Wire(edges)
@@ -214,19 +212,19 @@ class Wire(DraftObject):
shape = None
if "ChamferSize" in obj.PropertiesList:
if obj.ChamferSize.Value != 0:
- w = DraftGeomUtils.filletWire(shape,obj.ChamferSize.Value,chamfer=True)
+ w = DraftGeomUtils.filletWire(shape, obj.ChamferSize.Value, chamfer=True)
if w:
shape = w
if "FilletRadius" in obj.PropertiesList:
if obj.FilletRadius.Value != 0:
- w = DraftGeomUtils.filletWire(shape,obj.FilletRadius.Value)
+ w = DraftGeomUtils.filletWire(shape, obj.FilletRadius.Value)
if w:
shape = w
if shape:
obj.Shape = shape
- if hasattr(obj,"Area") and hasattr(shape,"Area"):
+ if hasattr(obj, "Area") and hasattr(shape, "Area"):
obj.Area = shape.Area
- if hasattr(obj,"Length"):
+ if hasattr(obj, "Length"):
obj.Length = shape.Length
obj.Placement = plm
diff --git a/src/Mod/Draft/draftobjects/wpproxy.py b/src/Mod/Draft/draftobjects/wpproxy.py
index 110da0b18b..3e1d5c5a1b 100644
--- a/src/Mod/Draft/draftobjects/wpproxy.py
+++ b/src/Mod/Draft/draftobjects/wpproxy.py
@@ -36,13 +36,13 @@ from draftutils import gui_utils
class WorkingPlaneProxy:
"""The Draft working plane proxy object"""
- def __init__(self,obj):
+ def __init__(self, obj):
obj.Proxy = self
_tip = QT_TRANSLATE_NOOP("App::Property", "The placement of this object")
obj.addProperty("App::PropertyPlacement", "Placement", "Base", _tip, locked=True)
- obj.addProperty("Part::PropertyPartShape","Shape","Base","", locked=True)
+ obj.addProperty("Part::PropertyPartShape", "Shape", "Base", "", locked=True)
obj.addExtension("Part::AttachExtensionPython")
obj.changeAttacherType("Attacher::AttachEnginePlane")
@@ -54,33 +54,32 @@ class WorkingPlaneProxy:
obj, vp_module="view_wpproxy", vp_class="ViewProviderWorkingPlaneProxy", format=False
)
- def execute(self,obj):
+ def execute(self, obj):
import Part
+
l = 1
if obj.ViewObject:
- if hasattr(obj.ViewObject,"DisplaySize"):
+ if hasattr(obj.ViewObject, "DisplaySize"):
l = obj.ViewObject.DisplaySize.Value
- p = Part.makePlane(l,
- l,
- App.Vector(l/2, -l/2, 0),
- App.Vector(0, 0, -1))
+ p = Part.makePlane(l, l, App.Vector(l / 2, -l / 2, 0), App.Vector(0, 0, -1))
# make sure the normal direction is pointing outwards, you never know what OCC will decide...
- if p.normalAt(0,0).getAngle(obj.Placement.Rotation.multVec(App.Vector(0,0,1))) > 1:
+ if p.normalAt(0, 0).getAngle(obj.Placement.Rotation.multVec(App.Vector(0, 0, 1))) > 1:
p.reverse()
p.Placement = obj.Placement
obj.Shape = p
- def onChanged(self,obj,prop):
+ def onChanged(self, obj, prop):
pass
- def getNormal(self,obj):
- return obj.Shape.Faces[0].normalAt(0,0)
+ def getNormal(self, obj):
+ return obj.Shape.Faces[0].normalAt(0, 0)
def dumps(self):
return self.Type
- def loads(self,state):
+ def loads(self, state):
if state:
self.Type = state
+
## @}
diff --git a/src/Mod/Draft/drafttaskpanels/task_circulararray.py b/src/Mod/Draft/drafttaskpanels/task_circulararray.py
index 7fcceb2957..09b6145d74 100644
--- a/src/Mod/Draft/drafttaskpanels/task_circulararray.py
+++ b/src/Mod/Draft/drafttaskpanels/task_circulararray.py
@@ -96,11 +96,11 @@ class TaskPanelCircularArray:
self.fuse = params.get_param("Draft_array_fuse")
self.use_link = params.get_param("Draft_array_Link")
- self.form.input_c_x.setProperty('rawValue', self.center.x)
- self.form.input_c_y.setProperty('rawValue', self.center.y)
- self.form.input_c_z.setProperty('rawValue', self.center.z)
- self.form.spinbox_r_distance.setProperty('rawValue', self.r_distance)
- self.form.spinbox_tan_distance.setProperty('rawValue', self.tan_distance)
+ self.form.input_c_x.setProperty("rawValue", self.center.x)
+ self.form.input_c_y.setProperty("rawValue", self.center.y)
+ self.form.input_c_z.setProperty("rawValue", self.center.z)
+ self.form.spinbox_r_distance.setProperty("rawValue", self.r_distance)
+ self.form.spinbox_tan_distance.setProperty("rawValue", self.tan_distance)
self.form.spinbox_number.setValue(self.number)
self.form.spinbox_symmetry.setValue(self.symmetry)
self.form.checkbox_fuse.setChecked(self.fuse)
@@ -129,75 +129,77 @@ class TaskPanelCircularArray:
self.form.button_reset.clicked.connect(self.reset_point)
# When the checkbox changes, change the internal value
- if hasattr(self.form.checkbox_fuse, "checkStateChanged"): # Qt version >= 6.7.0
+ if hasattr(self.form.checkbox_fuse, "checkStateChanged"): # Qt version >= 6.7.0
self.form.checkbox_fuse.checkStateChanged.connect(self.set_fuse)
self.form.checkbox_link.checkStateChanged.connect(self.set_link)
- else: # Qt version < 6.7.0
+ else: # Qt version < 6.7.0
self.form.checkbox_fuse.stateChanged.connect(self.set_fuse)
self.form.checkbox_link.stateChanged.connect(self.set_link)
-
def accept(self):
"""Execute when clicking the OK button or Enter key."""
self.selection = Gui.Selection.getSelection()
- (self.r_distance,
- self.tan_distance) = self.get_distances()
+ (self.r_distance, self.tan_distance) = self.get_distances()
- (self.number,
- self.symmetry) = self.get_number_symmetry()
+ (self.number, self.symmetry) = self.get_number_symmetry()
self.axis = self.get_axis()
self.center = self.get_center()
- self.valid_input = self.validate_input(self.selection,
- self.r_distance,
- self.tan_distance,
- self.number,
- self.symmetry,
- self.axis,
- self.center)
+ self.valid_input = self.validate_input(
+ self.selection,
+ self.r_distance,
+ self.tan_distance,
+ self.number,
+ self.symmetry,
+ self.axis,
+ self.center,
+ )
if self.valid_input:
self.create_object()
# The internal function already displays messages
self.finish()
- def validate_input(self, selection,
- r_distance, tan_distance,
- number, symmetry,
- axis, center):
+ def validate_input(self, selection, r_distance, tan_distance, number, symmetry, axis, center):
"""Check that the input is valid.
Some values may not need to be checked because
the interface may not allow one to input wrong data.
"""
if not selection:
- _err(translate("draft","At least 1 element must be selected"))
+ _err(translate("draft", "At least 1 element must be selected"))
return False
if number < 2:
- _err(translate("draft","Number of layers must be at least 2"))
+ _err(translate("draft", "Number of layers must be at least 2"))
return False
# TODO: this should handle multiple objects.
# Each of the elements of the selection should be tested.
obj = selection[0]
if obj.isDerivedFrom("App::FeaturePython"):
- _err(translate("draft","Selection is not suitable for array"))
- _err(translate("draft","Object:") + " {}".format(selection[0].Label))
+ _err(translate("draft", "Selection is not suitable for array"))
+ _err(translate("draft", "Object:") + " {}".format(selection[0].Label))
return False
if r_distance == 0:
- _wrn(translate("draft","Radial distance is zero. Resulting array may not look correct."))
+ _wrn(
+ translate("draft", "Radial distance is zero. Resulting array may not look correct.")
+ )
elif r_distance < 0:
- _wrn(translate("draft","Radial distance is negative. It is made positive to proceed."))
+ _wrn(translate("draft", "Radial distance is negative. It is made positive to proceed."))
self.r_distance = abs(r_distance)
if tan_distance == 0:
- _err(translate("draft","Tangential distance cannot be 0"))
+ _err(translate("draft", "Tangential distance cannot be 0"))
return False
elif tan_distance < 0:
- _wrn(translate("draft","Tangential distance is negative. It is made positive to proceed."))
+ _wrn(
+ translate(
+ "draft", "Tangential distance is negative. It is made positive to proceed."
+ )
+ )
self.tan_distance = abs(tan_distance)
# The other arguments are not tested but they should be present.
@@ -246,22 +248,23 @@ class TaskPanelCircularArray:
_cmd += "use_link=" + str(self.use_link)
_cmd += ")"
- Gui.addModule('Draft')
+ Gui.addModule("Draft")
- _cmd_list = ["_obj_ = " + _cmd,
- "_obj_.Fuse = " + str(self.fuse),
- "Draft.autogroup(_obj_)",
- "App.ActiveDocument.recompute()"]
+ _cmd_list = [
+ "_obj_ = " + _cmd,
+ "_obj_.Fuse = " + str(self.fuse),
+ "Draft.autogroup(_obj_)",
+ "App.ActiveDocument.recompute()",
+ ]
# We commit the command list through the parent command
- self.source_command.commit(translate("draft","Create Circular Array"), _cmd_list)
+ self.source_command.commit(translate("draft", "Create Circular Array"), _cmd_list)
def get_distances(self):
"""Get the distance parameters from the widgets."""
r_d_str = self.form.spinbox_r_distance.text()
tan_d_str = self.form.spinbox_tan_distance.text()
- return (U.Quantity(r_d_str).Value,
- U.Quantity(tan_d_str).Value)
+ return (U.Quantity(r_d_str).Value, U.Quantity(tan_d_str).Value)
def get_number_symmetry(self):
"""Get the number and symmetry parameters from the widgets."""
@@ -274,9 +277,9 @@ class TaskPanelCircularArray:
c_x_str = self.form.input_c_x.text()
c_y_str = self.form.input_c_y.text()
c_z_str = self.form.input_c_z.text()
- center = App.Vector(U.Quantity(c_x_str).Value,
- U.Quantity(c_y_str).Value,
- U.Quantity(c_z_str).Value)
+ center = App.Vector(
+ U.Quantity(c_x_str).Value, U.Quantity(c_y_str).Value, U.Quantity(c_z_str).Value
+ )
return center
def get_axis(self):
@@ -289,9 +292,9 @@ class TaskPanelCircularArray:
def reset_point(self):
"""Reset the center point to the original distance."""
- self.form.input_c_x.setProperty('rawValue', 0)
- self.form.input_c_y.setProperty('rawValue', 0)
- self.form.input_c_z.setProperty('rawValue', 0)
+ self.form.input_c_x.setProperty("rawValue", 0)
+ self.form.input_c_y.setProperty("rawValue", 0)
+ self.form.input_c_z.setProperty("rawValue", 0)
self.center = self.get_center()
@@ -301,7 +304,7 @@ class TaskPanelCircularArray:
state = self.tr_true
else:
state = self.tr_false
- _msg(translate("draft","Fuse:") + " {}".format(state))
+ _msg(translate("draft", "Fuse:") + " {}".format(state))
def set_fuse(self):
"""Execute as a callback when the fuse checkbox changes."""
@@ -314,14 +317,13 @@ class TaskPanelCircularArray:
state = self.tr_true
else:
state = self.tr_false
- _msg(translate("draft","Create Link array:") + " {}".format(state))
+ _msg(translate("draft", "Create Link array:") + " {}".format(state))
def set_link(self):
"""Execute as a callback when the link checkbox changes."""
self.use_link = self.form.checkbox_link.isChecked()
params.set_param("Draft_array_Link", self.use_link)
-
def print_messages(self):
"""Print messages about the operation."""
if len(self.selection) == 1:
@@ -331,15 +333,15 @@ class TaskPanelCircularArray:
# For example, it could take the shapes of all objects,
# make a compound and then use it as input for the array function.
sel_obj = self.selection[0]
- _msg(translate("draft","Object:") + " {}".format(sel_obj.Label))
- _msg(translate("draft","Radial distance:") + " {}".format(self.r_distance))
- _msg(translate("draft","Tangential distance:") + " {}".format(self.tan_distance))
- _msg(translate("draft","Number of concentric circles:") + " {}".format(self.number))
- _msg(translate("draft","Symmetry parameter:") + " {}".format(self.symmetry))
- _msg(translate("draft","Center of rotation:")
- + " ({0}, {1}, {2})".format(self.center.x,
- self.center.y,
- self.center.z))
+ _msg(translate("draft", "Object:") + " {}".format(sel_obj.Label))
+ _msg(translate("draft", "Radial distance:") + " {}".format(self.r_distance))
+ _msg(translate("draft", "Tangential distance:") + " {}".format(self.tan_distance))
+ _msg(translate("draft", "Number of concentric circles:") + " {}".format(self.number))
+ _msg(translate("draft", "Symmetry parameter:") + " {}".format(self.symmetry))
+ _msg(
+ translate("draft", "Center of rotation:")
+ + " ({0}, {1}, {2})".format(self.center.x, self.center.y, self.center.z)
+ )
self.print_fuse_state(self.fuse)
self.print_link_state(self.use_link)
@@ -380,24 +382,24 @@ class TaskPanelCircularArray:
# sby = self.form.spinbox_c_y
# sbz = self.form.spinbox_c_z
if d_p:
- if self.mask in ('y', 'z'):
+ if self.mask in ("y", "z"):
# sbx.setText(displayExternal(d_p.x, None, 'Length'))
- self.form.input_c_x.setProperty('rawValue', d_p.x)
+ self.form.input_c_x.setProperty("rawValue", d_p.x)
else:
# sbx.setText(displayExternal(d_p.x, None, 'Length'))
- self.form.input_c_x.setProperty('rawValue', d_p.x)
- if self.mask in ('x', 'z'):
+ self.form.input_c_x.setProperty("rawValue", d_p.x)
+ if self.mask in ("x", "z"):
# sby.setText(displayExternal(d_p.y, None, 'Length'))
- self.form.input_c_y.setProperty('rawValue', d_p.y)
+ self.form.input_c_y.setProperty("rawValue", d_p.y)
else:
# sby.setText(displayExternal(d_p.y, None, 'Length'))
- self.form.input_c_y.setProperty('rawValue', d_p.y)
- if self.mask in ('x', 'y'):
+ self.form.input_c_y.setProperty("rawValue", d_p.y)
+ if self.mask in ("x", "y"):
# sbz.setText(displayExternal(d_p.z, None, 'Length'))
- self.form.input_c_z.setProperty('rawValue', d_p.z)
+ self.form.input_c_z.setProperty("rawValue", d_p.z)
else:
# sbz.setText(displayExternal(d_p.z, None, 'Length'))
- self.form.input_c_z.setProperty('rawValue', d_p.z)
+ self.form.input_c_z.setProperty("rawValue", d_p.z)
if plane:
pass
@@ -452,4 +454,5 @@ class TaskPanelCircularArray:
# Runs the parent command to complete the call
self.source_command.completed()
+
## @}
diff --git a/src/Mod/Draft/drafttaskpanels/task_orthoarray.py b/src/Mod/Draft/drafttaskpanels/task_orthoarray.py
index 619c9f3f50..14cfba6bbf 100644
--- a/src/Mod/Draft/drafttaskpanels/task_orthoarray.py
+++ b/src/Mod/Draft/drafttaskpanels/task_orthoarray.py
@@ -94,17 +94,17 @@ class TaskPanelOrthoArray:
self.v_y = App.Vector(0, start_y, 0)
self.v_z = App.Vector(0, 0, start_z)
- self.form.input_X_x.setProperty('rawValue', self.v_x.x)
- self.form.input_X_y.setProperty('rawValue', self.v_x.y)
- self.form.input_X_z.setProperty('rawValue', self.v_x.z)
+ self.form.input_X_x.setProperty("rawValue", self.v_x.x)
+ self.form.input_X_y.setProperty("rawValue", self.v_x.y)
+ self.form.input_X_z.setProperty("rawValue", self.v_x.z)
- self.form.input_Y_x.setProperty('rawValue', self.v_y.x)
- self.form.input_Y_y.setProperty('rawValue', self.v_y.y)
- self.form.input_Y_z.setProperty('rawValue', self.v_y.z)
+ self.form.input_Y_x.setProperty("rawValue", self.v_y.x)
+ self.form.input_Y_y.setProperty("rawValue", self.v_y.y)
+ self.form.input_Y_z.setProperty("rawValue", self.v_y.z)
- self.form.input_Z_x.setProperty('rawValue', self.v_z.x)
- self.form.input_Z_y.setProperty('rawValue', self.v_z.y)
- self.form.input_Z_z.setProperty('rawValue', self.v_z.z)
+ self.form.input_Z_x.setProperty("rawValue", self.v_z.x)
+ self.form.input_Z_y.setProperty("rawValue", self.v_z.y)
+ self.form.input_Z_z.setProperty("rawValue", self.v_z.z)
self.n_x = params.get_param("XNumOfElements", "Mod/Draft/OrthoArrayLinearMode")
self.n_y = params.get_param("YNumOfElements", "Mod/Draft/OrthoArrayLinearMode")
@@ -154,10 +154,10 @@ class TaskPanelOrthoArray:
self.form.button_reset_Z.clicked.connect(lambda: self.reset_v("Z"))
# When the checkbox changes, change the internal value
- if hasattr(self.form.checkbox_fuse, "checkStateChanged"): # Qt version >= 6.7.0
+ if hasattr(self.form.checkbox_fuse, "checkStateChanged"): # Qt version >= 6.7.0
self.form.checkbox_fuse.checkStateChanged.connect(self.set_fuse)
self.form.checkbox_link.checkStateChanged.connect(self.set_link)
- else: # Qt version < 6.7.0
+ else: # Qt version < 6.7.0
self.form.checkbox_fuse.stateChanged.connect(self.set_fuse)
self.form.checkbox_link.stateChanged.connect(self.set_link)
@@ -167,71 +167,72 @@ class TaskPanelOrthoArray:
self.form.radiobutton_y_axis.clicked.connect(lambda: self.set_active_axis("Y"))
self.form.radiobutton_z_axis.clicked.connect(lambda: self.set_active_axis("Z"))
-
def accept(self):
"""Execute when clicking the OK button or Enter key."""
self.selection = Gui.Selection.getSelection()
- (self.v_x,
- self.v_y,
- self.v_z) = self.get_intervals()
+ (self.v_x, self.v_y, self.v_z) = self.get_intervals()
- (self.n_x,
- self.n_y,
- self.n_z) = self.get_numbers()
+ (self.n_x, self.n_y, self.n_z) = self.get_numbers()
- self.valid_input = self.validate_input(self.selection,
- self.v_x, self.v_y, self.v_z,
- self.n_x, self.n_y, self.n_z)
+ self.valid_input = self.validate_input(
+ self.selection, self.v_x, self.v_y, self.v_z, self.n_x, self.n_y, self.n_z
+ )
if self.valid_input:
axis_values = {
- 'X': (self.v_x.x, self.n_x),
- 'Y': (self.v_y.y, self.n_y),
- 'Z': (self.v_z.z, self.n_z),
+ "X": (self.v_x.x, self.n_x),
+ "Y": (self.v_y.y, self.n_y),
+ "Z": (self.v_z.z, self.n_z),
}
values = axis_values.get(self.active_axis)
if values is not None:
interval, num_elements = values
# Set interval
- params.set_param(f"{self.active_axis}Interval", interval, "Mod/Draft/OrthoArrayLinearMode")
+ params.set_param(
+ f"{self.active_axis}Interval", interval, "Mod/Draft/OrthoArrayLinearMode"
+ )
# Set number of elements
- params.set_param(f"{self.active_axis}NumOfElements", num_elements, "Mod/Draft/OrthoArrayLinearMode")
+ params.set_param(
+ f"{self.active_axis}NumOfElements",
+ num_elements,
+ "Mod/Draft/OrthoArrayLinearMode",
+ )
self.create_object()
# The internal function already displays messages
self.finish()
- def validate_input(self, selection,
- v_x, v_y, v_z,
- n_x, n_y, n_z):
+ def validate_input(self, selection, v_x, v_y, v_z, n_x, n_y, n_z):
"""Check that the input is valid.
Some values may not need to be checked because
the interface may not allow one to input wrong data.
"""
if not selection:
- _err(translate("draft","At least 1 element must be selected"))
+ _err(translate("draft", "At least 1 element must be selected"))
return False
if n_x < 1 or n_y < 1 or n_z < 1:
- _err(translate("draft","Number of elements must be at least 1"))
+ _err(translate("draft", "Number of elements must be at least 1"))
return False
# TODO: this should handle multiple objects.
# Each of the elements of the selection should be tested.
obj = selection[0]
if obj.isDerivedFrom("App::FeaturePython"):
- _err(translate("draft","Selection is not suitable for array"))
- _err(translate("draft","Object:") + " {0} ({1})".format(obj.Label, obj.TypeId))
+ _err(translate("draft", "Selection is not suitable for array"))
+ _err(translate("draft", "Object:") + " {0} ({1})".format(obj.Label, obj.TypeId))
return False
# we should not ever do this but maybe a sanity check here?
if self.linear_mode:
- if not (self.form.radiobutton_x_axis.isChecked() or
- self.form.radiobutton_y_axis.isChecked() or
- self.form.radiobutton_z_axis.isChecked()):
- _err(translate("draft","In linear mode, at least 1 axis must be selected"))
+ if not (
+ self.form.radiobutton_x_axis.isChecked()
+ or self.form.radiobutton_y_axis.isChecked()
+ or self.form.radiobutton_z_axis.isChecked()
+ ):
+ _err(translate("draft", "In linear mode, at least 1 axis must be selected"))
return False
# The other arguments are not tested but they should be present.
@@ -293,44 +294,48 @@ class TaskPanelOrthoArray:
_cmd += "use_link=" + str(self.use_link)
_cmd += ")"
- Gui.addModule('Draft')
+ Gui.addModule("Draft")
- _cmd_list = ["_obj_ = " + _cmd,
- "_obj_.Fuse = " + str(self.fuse),
- "Draft.autogroup(_obj_)",
- "App.ActiveDocument.recompute()"]
+ _cmd_list = [
+ "_obj_ = " + _cmd,
+ "_obj_.Fuse = " + str(self.fuse),
+ "Draft.autogroup(_obj_)",
+ "App.ActiveDocument.recompute()",
+ ]
# We commit the command list through the parent command
- self.source_command.commit(translate("draft","Create Orthogonal Array"), _cmd_list)
+ self.source_command.commit(translate("draft", "Create Orthogonal Array"), _cmd_list)
def get_numbers(self):
"""Get the number of elements from the widgets."""
- return (self.form.spinbox_n_X.value(),
- self.form.spinbox_n_Y.value(),
- self.form.spinbox_n_Z.value())
+ return (
+ self.form.spinbox_n_X.value(),
+ self.form.spinbox_n_Y.value(),
+ self.form.spinbox_n_Z.value(),
+ )
def get_intervals(self):
"""Get the interval vectors from the widgets."""
v_x_x_str = self.form.input_X_x.text()
v_x_y_str = self.form.input_X_y.text()
v_x_z_str = self.form.input_X_z.text()
- v_x = App.Vector(U.Quantity(v_x_x_str).Value,
- U.Quantity(v_x_y_str).Value,
- U.Quantity(v_x_z_str).Value)
+ v_x = App.Vector(
+ U.Quantity(v_x_x_str).Value, U.Quantity(v_x_y_str).Value, U.Quantity(v_x_z_str).Value
+ )
v_y_x_str = self.form.input_Y_x.text()
v_y_y_str = self.form.input_Y_y.text()
v_y_z_str = self.form.input_Y_z.text()
- v_y = App.Vector(U.Quantity(v_y_x_str).Value,
- U.Quantity(v_y_y_str).Value,
- U.Quantity(v_y_z_str).Value)
+ v_y = App.Vector(
+ U.Quantity(v_y_x_str).Value, U.Quantity(v_y_y_str).Value, U.Quantity(v_y_z_str).Value
+ )
v_z_x_str = self.form.input_Z_x.text()
v_z_y_str = self.form.input_Z_y.text()
v_z_z_str = self.form.input_Z_z.text()
- v_z = App.Vector(U.Quantity(v_z_x_str).Value,
- U.Quantity(v_z_y_str).Value,
- U.Quantity(v_z_z_str).Value)
+ v_z = App.Vector(
+ U.Quantity(v_z_x_str).Value, U.Quantity(v_z_y_str).Value, U.Quantity(v_z_z_str).Value
+ )
return v_x, v_y, v_z
def reset_v(self, interval):
@@ -343,19 +348,19 @@ class TaskPanelOrthoArray:
for that direction.
"""
if interval == "X":
- self.form.input_X_x.setProperty('rawValue', 100)
- self.form.input_X_y.setProperty('rawValue', 0)
- self.form.input_X_z.setProperty('rawValue', 0)
+ self.form.input_X_x.setProperty("rawValue", 100)
+ self.form.input_X_y.setProperty("rawValue", 0)
+ self.form.input_X_z.setProperty("rawValue", 0)
self.v_x, self.v_y, self.v_z = self.get_intervals()
elif interval == "Y":
- self.form.input_Y_x.setProperty('rawValue', 0)
- self.form.input_Y_y.setProperty('rawValue', 100)
- self.form.input_Y_z.setProperty('rawValue', 0)
+ self.form.input_Y_x.setProperty("rawValue", 0)
+ self.form.input_Y_y.setProperty("rawValue", 100)
+ self.form.input_Y_z.setProperty("rawValue", 0)
self.v_x, self.v_y, self.v_z = self.get_intervals()
elif interval == "Z":
- self.form.input_Z_x.setProperty('rawValue', 0)
- self.form.input_Z_y.setProperty('rawValue', 0)
- self.form.input_Z_z.setProperty('rawValue', 100)
+ self.form.input_Z_x.setProperty("rawValue", 0)
+ self.form.input_Z_y.setProperty("rawValue", 0)
+ self.form.input_Z_z.setProperty("rawValue", 100)
self.v_x, self.v_y, self.v_z = self.get_intervals()
def print_fuse_state(self, fuse):
@@ -364,7 +369,7 @@ class TaskPanelOrthoArray:
state = self.tr_true
else:
state = self.tr_false
- _msg(translate("draft","Fuse:") + " {}".format(state))
+ _msg(translate("draft", "Fuse:") + " {}".format(state))
def set_fuse(self):
"""Execute as a callback when the fuse checkbox changes."""
@@ -377,7 +382,7 @@ class TaskPanelOrthoArray:
state = self.tr_true
else:
state = self.tr_false
- _msg(translate("draft","Create link array:") + " {}".format(state))
+ _msg(translate("draft", "Create link array:") + " {}".format(state))
def set_link(self):
"""Execute as a callback when the link checkbox changes."""
@@ -393,23 +398,23 @@ class TaskPanelOrthoArray:
# For example, it could take the shapes of all objects,
# make a compound and then use it as input for the array function.
sel_obj = self.selection[0]
- _msg(translate("draft","Object:") + " {}".format(sel_obj.Label))
+ _msg(translate("draft", "Object:") + " {}".format(sel_obj.Label))
- _msg(translate("draft","Number of X elements:") + " {}".format(self.n_x))
- _msg(translate("draft","Interval X:")
- + " ({0}, {1}, {2})".format(self.v_x.x,
- self.v_x.y,
- self.v_x.z))
- _msg(translate("draft","Number of Y elements:") + " {}".format(self.n_y))
- _msg(translate("draft","Interval Y:")
- + " ({0}, {1}, {2})".format(self.v_y.x,
- self.v_y.y,
- self.v_y.z))
- _msg(translate("draft","Number of Z elements:") + " {}".format(self.n_z))
- _msg(translate("draft","Interval Z:")
- + " ({0}, {1}, {2})".format(self.v_z.x,
- self.v_z.y,
- self.v_z.z))
+ _msg(translate("draft", "Number of X elements:") + " {}".format(self.n_x))
+ _msg(
+ translate("draft", "Interval X:")
+ + " ({0}, {1}, {2})".format(self.v_x.x, self.v_x.y, self.v_x.z)
+ )
+ _msg(translate("draft", "Number of Y elements:") + " {}".format(self.n_y))
+ _msg(
+ translate("draft", "Interval Y:")
+ + " ({0}, {1}, {2})".format(self.v_y.x, self.v_y.y, self.v_y.z)
+ )
+ _msg(translate("draft", "Number of Z elements:") + " {}".format(self.n_z))
+ _msg(
+ translate("draft", "Interval Z:")
+ + " ({0}, {1}, {2})".format(self.v_z.x, self.v_z.y, self.v_z.z)
+ )
self.print_fuse_state(self.fuse)
self.print_link_state(self.use_link)
@@ -421,7 +426,7 @@ class TaskPanelOrthoArray:
"""Toggle between Linear mode and Orthogonal mode."""
self.linear_mode = self.form.button_linear_mode.isChecked()
self.toggle_axis_radiobuttons(self.linear_mode)
- params.set_param("LinearModeOn" , self.linear_mode, "Mod/Draft/OrthoArrayLinearMode")
+ params.set_param("LinearModeOn", self.linear_mode, "Mod/Draft/OrthoArrayLinearMode")
if self.linear_mode:
self.form.button_linear_mode.setText(translate("draft", "Switch to Ortho Mode"))
@@ -446,7 +451,7 @@ class TaskPanelOrthoArray:
case "Z":
title = translate("draft", "Z-Axis")
self.form.group_linearmode.setTitle(title)
- else: # ortho mode
+ else: # ortho mode
self.form.button_linear_mode.setText(translate("draft", "Switch to Linear Mode"))
# For ortho mode we're showing back default groupboxes and we reparent everything
@@ -458,9 +463,11 @@ class TaskPanelOrthoArray:
def toggle_axis_radiobuttons(self, show):
"""Show or hide the axis radio buttons."""
- for radiobutton in [self.form.radiobutton_x_axis,
- self.form.radiobutton_y_axis,
- self.form.radiobutton_z_axis]:
+ for radiobutton in [
+ self.form.radiobutton_x_axis,
+ self.form.radiobutton_y_axis,
+ self.form.radiobutton_z_axis,
+ ]:
radiobutton.setVisible(show)
def set_active_axis(self, axis):
@@ -483,7 +490,6 @@ class TaskPanelOrthoArray:
title = translate("draft", "Z-Axis")
self.form.group_linearmode.setTitle(title)
-
def update_axis_ui(self):
"""Update the UI to reflect the current axis selection."""
# Make sure only one axis is selected
@@ -494,9 +500,9 @@ class TaskPanelOrthoArray:
def _get_axis_widgets(self, axis):
"""Get all widgets for a specific axis."""
return {
- 'spinbox_elements': getattr(self.form, f"spinbox_n_{axis}", None),
- 'spinbox_interval': getattr(self.form, f"input_{axis}_{axis.lower()}", None),
- 'button_reset': getattr(self.form, f"button_reset_{axis}", None)
+ "spinbox_elements": getattr(self.form, f"spinbox_n_{axis}", None),
+ "spinbox_interval": getattr(self.form, f"input_{axis}_{axis.lower()}", None),
+ "button_reset": getattr(self.form, f"button_reset_{axis}", None),
}
def _clear_linear_mode_layout(self):
@@ -525,8 +531,8 @@ class TaskPanelOrthoArray:
# Add widgets to layout
widget_pairs = [
- (label_elements, widgets['spinbox_elements']),
- (label_interval, widgets['spinbox_interval'])
+ (label_elements, widgets["spinbox_elements"]),
+ (label_interval, widgets["spinbox_interval"]),
]
for row_index, (label, widget) in enumerate(widget_pairs):
@@ -536,8 +542,8 @@ class TaskPanelOrthoArray:
group_layout.addWidget(widget, row_index, 1)
# Add reset button spanning both columns
- widgets['button_reset'].setParent(self.form.group_linearmode)
- group_layout.addWidget(widgets['button_reset'], 2, 0, 1, 2)
+ widgets["button_reset"].setParent(self.form.group_linearmode)
+ group_layout.addWidget(widgets["button_reset"], 2, 0, 1, 2)
def _restore_axis_to_ortho_layout(self, axis, row_index):
"""Restore widgets for a specific axis back to their original Ortho layout positions."""
@@ -545,16 +551,16 @@ class TaskPanelOrthoArray:
# Restore spinbox elements to grid layout
grid_number_layout = self.form.findChild(QtWidgets.QGridLayout, "grid_number")
- grid_number_layout.addWidget(widgets['spinbox_elements'], row_index, 1)
+ grid_number_layout.addWidget(widgets["spinbox_elements"], row_index, 1)
# Restore interval input to its axis-specific inner grid layout
inner_grid_layout = self.form.findChild(QtWidgets.QGridLayout, f"grid_{axis}")
- inner_grid_layout.addWidget(widgets['spinbox_interval'], row_index, 1)
+ inner_grid_layout.addWidget(widgets["spinbox_interval"], row_index, 1)
# Restore reset button to its axis group
group_box = self.form.findChild(QtWidgets.QGroupBox, f"group_{axis}")
group_axis_layout = group_box.layout()
- group_axis_layout.addWidget(widgets['button_reset'], 1, 0)
+ group_axis_layout.addWidget(widgets["button_reset"], 1, 0)
def _setup_ortho_mode_layout(self):
"""Restore all widgets back to their original Ortho mode layout positions."""
@@ -592,4 +598,5 @@ class TaskPanelOrthoArray:
# Runs the parent command to complete the call
self.source_command.completed()
+
## @}
diff --git a/src/Mod/Draft/drafttaskpanels/task_polararray.py b/src/Mod/Draft/drafttaskpanels/task_polararray.py
index 7952741409..0c426d0b2d 100644
--- a/src/Mod/Draft/drafttaskpanels/task_polararray.py
+++ b/src/Mod/Draft/drafttaskpanels/task_polararray.py
@@ -91,10 +91,10 @@ class TaskPanelPolarArray:
self.fuse = params.get_param("Draft_array_fuse")
self.use_link = params.get_param("Draft_array_Link")
- self.form.input_c_x.setProperty('rawValue', self.center.x)
- self.form.input_c_y.setProperty('rawValue', self.center.y)
- self.form.input_c_z.setProperty('rawValue', self.center.z)
- self.form.spinbox_angle.setProperty('rawValue', self.angle)
+ self.form.input_c_x.setProperty("rawValue", self.center.x)
+ self.form.input_c_y.setProperty("rawValue", self.center.y)
+ self.form.input_c_z.setProperty("rawValue", self.center.z)
+ self.form.spinbox_angle.setProperty("rawValue", self.angle)
self.form.spinbox_number.setValue(self.number)
self.form.checkbox_fuse.setChecked(self.fuse)
self.form.checkbox_link.setChecked(self.use_link)
@@ -122,61 +122,63 @@ class TaskPanelPolarArray:
self.form.button_reset.clicked.connect(self.reset_point)
# When the checkbox changes, change the internal value
- if hasattr(self.form.checkbox_fuse, "checkStateChanged"): # Qt version >= 6.7.0
+ if hasattr(self.form.checkbox_fuse, "checkStateChanged"): # Qt version >= 6.7.0
self.form.checkbox_fuse.checkStateChanged.connect(self.set_fuse)
self.form.checkbox_link.checkStateChanged.connect(self.set_link)
- else: # Qt version < 6.7.0
+ else: # Qt version < 6.7.0
self.form.checkbox_fuse.stateChanged.connect(self.set_fuse)
self.form.checkbox_link.stateChanged.connect(self.set_link)
-
def accept(self):
"""Execute when clicking the OK button or Enter key."""
self.selection = Gui.Selection.getSelection()
- (self.number,
- self.angle) = self.get_number_angle()
+ (self.number, self.angle) = self.get_number_angle()
self.center = self.get_center()
- self.valid_input = self.validate_input(self.selection,
- self.number,
- self.angle,
- self.center)
+ self.valid_input = self.validate_input(self.selection, self.number, self.angle, self.center)
if self.valid_input:
self.create_object()
# The internal function already displays messages
# self.print_messages()
self.finish()
- def validate_input(self, selection,
- number, angle, center):
+ def validate_input(self, selection, number, angle, center):
"""Check that the input is valid.
Some values may not need to be checked because
the interface may not allow one to input wrong data.
"""
if not selection:
- _err(translate("draft","At least 1 element must be selected"))
+ _err(translate("draft", "At least 1 element must be selected"))
return False
# TODO: this should handle multiple objects.
# Each of the elements of the selection should be tested.
obj = selection[0]
if obj.isDerivedFrom("App::FeaturePython"):
- _err(translate("draft","Selection is not suitable for array"))
- _err(translate("draft","Object:") + " {}".format(selection[0].Label))
+ _err(translate("draft", "Selection is not suitable for array"))
+ _err(translate("draft", "Object:") + " {}".format(selection[0].Label))
return False
if number < 2:
- _err(translate("draft","Number of elements must be at least 2"))
+ _err(translate("draft", "Number of elements must be at least 2"))
return False
if angle > 360:
- _wrn(translate("draft","The angle is above 360 degrees. It is set to this value to proceed."))
+ _wrn(
+ translate(
+ "draft", "The angle is above 360 degrees. It is set to this value to proceed."
+ )
+ )
self.angle = 360
elif angle < -360:
- _wrn(translate("draft","The angle is below -360 degrees. It is set to this value to proceed."))
+ _wrn(
+ translate(
+ "draft", "The angle is below -360 degrees. It is set to this value to proceed."
+ )
+ )
self.angle = -360
# The other arguments are not tested but they should be present.
@@ -220,15 +222,17 @@ class TaskPanelPolarArray:
_cmd += "use_link=" + str(self.use_link)
_cmd += ")"
- Gui.addModule('Draft')
+ Gui.addModule("Draft")
- _cmd_list = ["_obj_ = " + _cmd,
- "_obj_.Fuse = " + str(self.fuse),
- "Draft.autogroup(_obj_)",
- "App.ActiveDocument.recompute()"]
+ _cmd_list = [
+ "_obj_ = " + _cmd,
+ "_obj_.Fuse = " + str(self.fuse),
+ "Draft.autogroup(_obj_)",
+ "App.ActiveDocument.recompute()",
+ ]
# We commit the command list through the parent command
- self.source_command.commit(translate("draft","Create Polar Array"), _cmd_list)
+ self.source_command.commit(translate("draft", "Create Polar Array"), _cmd_list)
def get_number_angle(self):
"""Get the number and angle parameters from the widgets."""
@@ -243,16 +247,16 @@ class TaskPanelPolarArray:
c_x_str = self.form.input_c_x.text()
c_y_str = self.form.input_c_y.text()
c_z_str = self.form.input_c_z.text()
- center = App.Vector(U.Quantity(c_x_str).Value,
- U.Quantity(c_y_str).Value,
- U.Quantity(c_z_str).Value)
+ center = App.Vector(
+ U.Quantity(c_x_str).Value, U.Quantity(c_y_str).Value, U.Quantity(c_z_str).Value
+ )
return center
def reset_point(self):
"""Reset the center point to the original distance."""
- self.form.input_c_x.setProperty('rawValue', 0)
- self.form.input_c_y.setProperty('rawValue', 0)
- self.form.input_c_z.setProperty('rawValue', 0)
+ self.form.input_c_x.setProperty("rawValue", 0)
+ self.form.input_c_y.setProperty("rawValue", 0)
+ self.form.input_c_z.setProperty("rawValue", 0)
self.center = self.get_center()
@@ -262,7 +266,7 @@ class TaskPanelPolarArray:
state = self.tr_true
else:
state = self.tr_false
- _msg(translate("draft","Fuse:") + " {}".format(state))
+ _msg(translate("draft", "Fuse:") + " {}".format(state))
def set_fuse(self):
"""Execute as a callback when the fuse checkbox changes."""
@@ -275,7 +279,7 @@ class TaskPanelPolarArray:
state = self.tr_true
else:
state = self.tr_false
- _msg(translate("draft","Create link array:") + " {}".format(state))
+ _msg(translate("draft", "Create link array:") + " {}".format(state))
def set_link(self):
"""Execute as a callback when the link checkbox changes."""
@@ -291,13 +295,13 @@ class TaskPanelPolarArray:
# For example, it could take the shapes of all objects,
# make a compound and then use it as input for the array function.
sel_obj = self.selection[0]
- _msg(translate("draft","Object:") + " {}".format(sel_obj.Label))
- _msg(translate("draft","Number of elements:") + " {}".format(self.number))
- _msg(translate("draft","Polar angle:") + " {}".format(self.angle))
- _msg(translate("draft","Center of rotation:")
- + " ({0}, {1}, {2})".format(self.center.x,
- self.center.y,
- self.center.z))
+ _msg(translate("draft", "Object:") + " {}".format(sel_obj.Label))
+ _msg(translate("draft", "Number of elements:") + " {}".format(self.number))
+ _msg(translate("draft", "Polar angle:") + " {}".format(self.angle))
+ _msg(
+ translate("draft", "Center of rotation:")
+ + " ({0}, {1}, {2})".format(self.center.x, self.center.y, self.center.z)
+ )
self.print_fuse_state(self.fuse)
self.print_link_state(self.use_link)
@@ -338,24 +342,24 @@ class TaskPanelPolarArray:
# sby = self.form.spinbox_c_y
# sbz = self.form.spinbox_c_z
if dp:
- if self.mask in ('y', 'z'):
+ if self.mask in ("y", "z"):
# sbx.setText(displayExternal(dp.x, None, 'Length'))
- self.form.input_c_x.setProperty('rawValue', dp.x)
+ self.form.input_c_x.setProperty("rawValue", dp.x)
else:
# sbx.setText(displayExternal(dp.x, None, 'Length'))
- self.form.input_c_x.setProperty('rawValue', dp.x)
- if self.mask in ('x', 'z'):
+ self.form.input_c_x.setProperty("rawValue", dp.x)
+ if self.mask in ("x", "z"):
# sby.setText(displayExternal(dp.y, None, 'Length'))
- self.form.input_c_y.setProperty('rawValue', dp.y)
+ self.form.input_c_y.setProperty("rawValue", dp.y)
else:
# sby.setText(displayExternal(dp.y, None, 'Length'))
- self.form.input_c_y.setProperty('rawValue', dp.y)
- if self.mask in ('x', 'y'):
+ self.form.input_c_y.setProperty("rawValue", dp.y)
+ if self.mask in ("x", "y"):
# sbz.setText(displayExternal(dp.z, None, 'Length'))
- self.form.input_c_z.setProperty('rawValue', dp.z)
+ self.form.input_c_z.setProperty("rawValue", dp.z)
else:
# sbz.setText(displayExternal(dp.z, None, 'Length'))
- self.form.input_c_z.setProperty('rawValue', dp.z)
+ self.form.input_c_z.setProperty("rawValue", dp.z)
if plane:
pass
@@ -410,4 +414,5 @@ class TaskPanelPolarArray:
# Runs the parent command to complete the call
self.source_command.completed()
+
## @}
diff --git a/src/Mod/Draft/drafttaskpanels/task_scale.py b/src/Mod/Draft/drafttaskpanels/task_scale.py
index 89c6159ab1..d92efb9b1c 100644
--- a/src/Mod/Draft/drafttaskpanels/task_scale.py
+++ b/src/Mod/Draft/drafttaskpanels/task_scale.py
@@ -57,32 +57,32 @@ class ScaleTaskPanel:
self.xValue.setRange(-1000000.0, 1000000.0)
self.xValue.setDecimals(decimals)
self.xValue.setValue(1)
- layout.addWidget(self.xValue,0,1,1,1)
+ layout.addWidget(self.xValue, 0, 1, 1, 1)
self.yLabel = QtWidgets.QLabel()
self.yLabel.setText(translate("Draft", "Y-factor"))
- layout.addWidget(self.yLabel,1,0,1,1)
+ layout.addWidget(self.yLabel, 1, 0, 1, 1)
self.yValue = QtWidgets.QDoubleSpinBox()
self.yValue.setRange(-1000000.0, 1000000.0)
self.yValue.setDecimals(decimals)
self.yValue.setValue(1)
- layout.addWidget(self.yValue,1,1,1,1)
+ layout.addWidget(self.yValue, 1, 1, 1, 1)
self.zLabel = QtWidgets.QLabel()
self.zLabel.setText(translate("Draft", "Z-factor"))
- layout.addWidget(self.zLabel,2,0,1,1)
+ layout.addWidget(self.zLabel, 2, 0, 1, 1)
self.zValue = QtWidgets.QDoubleSpinBox()
self.zValue.setRange(-1000000.0, 1000000.0)
self.zValue.setDecimals(decimals)
self.zValue.setValue(1)
- layout.addWidget(self.zValue,2,1,1,1)
+ layout.addWidget(self.zValue, 2, 1, 1, 1)
self.lock = QtWidgets.QCheckBox()
self.lock.setText(translate("Draft", "Uniform scaling"))
self.lock.setChecked(params.get_param("ScaleUniform"))
- layout.addWidget(self.lock,3,0,1,2)
+ layout.addWidget(self.lock, 3, 0, 1, 2)
- QtCore.QObject.connect(self.xValue,QtCore.SIGNAL("valueChanged(double)"),self.setValue)
- QtCore.QObject.connect(self.yValue,QtCore.SIGNAL("valueChanged(double)"),self.setValue)
- QtCore.QObject.connect(self.zValue,QtCore.SIGNAL("valueChanged(double)"),self.setValue)
- QtCore.QObject.connect(self.lock,QtCore.SIGNAL("toggled(bool)"),self.setLock)
+ QtCore.QObject.connect(self.xValue, QtCore.SIGNAL("valueChanged(double)"), self.setValue)
+ QtCore.QObject.connect(self.yValue, QtCore.SIGNAL("valueChanged(double)"), self.setValue)
+ QtCore.QObject.connect(self.zValue, QtCore.SIGNAL("valueChanged(double)"), self.setValue)
+ QtCore.QObject.connect(self.lock, QtCore.SIGNAL("toggled(bool)"), self.setLock)
if self.__class__.__name__ != "ScaleTaskPanelEdit":
# ScaleRelative option removed in v1.1 as it does not work properly:
@@ -93,24 +93,26 @@ class ScaleTaskPanel:
self.isCopy = QtWidgets.QCheckBox()
self.isCopy.setText(translate("Draft", "Copy"))
self.isCopy.setChecked(params.get_param("ScaleCopy"))
- layout.addWidget(self.isCopy,5,0,1,2)
+ layout.addWidget(self.isCopy, 5, 0, 1, 2)
self.isSubelementMode = QtWidgets.QCheckBox()
self.isSubelementMode.setText(translate("Draft", "Modify subelements"))
self.isSubelementMode.setChecked(params.get_param("SubelementMode"))
- layout.addWidget(self.isSubelementMode,6,0,1,2)
+ layout.addWidget(self.isSubelementMode, 6, 0, 1, 2)
self.isClone = QtWidgets.QCheckBox()
self.isClone.setText(translate("Draft", "Create a clone"))
self.isClone.setChecked(params.get_param("ScaleClone"))
- layout.addWidget(self.isClone,7,0,1,2)
+ layout.addWidget(self.isClone, 7, 0, 1, 2)
self.pickrefButton = QtWidgets.QPushButton()
self.pickrefButton.setText(translate("Draft", "Pick From/To Points"))
- layout.addWidget(self.pickrefButton,8,0,1,2)
+ layout.addWidget(self.pickrefButton, 8, 0, 1, 2)
# QtCore.QObject.connect(self.relative,QtCore.SIGNAL("toggled(bool)"),self.setRelative)
- QtCore.QObject.connect(self.isCopy,QtCore.SIGNAL("toggled(bool)"),self.setCopy)
- QtCore.QObject.connect(self.isSubelementMode,QtCore.SIGNAL("toggled(bool)"),self.setSubelementMode)
- QtCore.QObject.connect(self.isClone,QtCore.SIGNAL("toggled(bool)"),self.setClone)
- QtCore.QObject.connect(self.pickrefButton,QtCore.SIGNAL("clicked()"),self.pickRef)
+ QtCore.QObject.connect(self.isCopy, QtCore.SIGNAL("toggled(bool)"), self.setCopy)
+ QtCore.QObject.connect(
+ self.isSubelementMode, QtCore.SIGNAL("toggled(bool)"), self.setSubelementMode
+ )
+ QtCore.QObject.connect(self.isClone, QtCore.SIGNAL("toggled(bool)"), self.setClone)
+ QtCore.QObject.connect(self.pickrefButton, QtCore.SIGNAL("clicked()"), self.pickRef)
def setValue(self, val=None):
"""Set the value of the scale factors."""
@@ -226,7 +228,7 @@ class ScaleTaskPanelEdit(ScaleTaskPanel):
mtx = mtx * self.global_place.Matrix.inverse()
delta = self.global_place.inverse().Rotation.multVec(self.global_place.Base)
- delta = -App.Vector(delta.x*x, delta.y*y, delta.z*z)
+ delta = -App.Vector(delta.x * x, delta.y * y, delta.z * z)
delta = self.global_place.multVec(delta)
self.ghost.setMatrix(mtx)
@@ -266,4 +268,5 @@ class ScaleTaskPanelEdit(ScaleTaskPanel):
Gui.Control.closeDialog()
return None
+
## @}
diff --git a/src/Mod/Draft/drafttaskpanels/task_selectplane.py b/src/Mod/Draft/drafttaskpanels/task_selectplane.py
index a841572cb4..d391d951b9 100644
--- a/src/Mod/Draft/drafttaskpanels/task_selectplane.py
+++ b/src/Mod/Draft/drafttaskpanels/task_selectplane.py
@@ -53,4 +53,5 @@ class SelectPlaneTaskPanel:
"""Execute to set the standard buttons."""
return QtWidgets.QDialogButtonBox.Close
+
## @}
diff --git a/src/Mod/Draft/drafttaskpanels/task_shapestring.py b/src/Mod/Draft/drafttaskpanels/task_shapestring.py
index 30384656a8..d8ed5d9cc1 100644
--- a/src/Mod/Draft/drafttaskpanels/task_shapestring.py
+++ b/src/Mod/Draft/drafttaskpanels/task_shapestring.py
@@ -86,9 +86,9 @@ class ShapeStringTaskPanel:
self.form.sbX.valueChanged.connect(self.set_point_x)
self.form.sbY.valueChanged.connect(self.set_point_y)
self.form.sbZ.valueChanged.connect(self.set_point_z)
- if hasattr(self.form.cbGlobalMode, "checkStateChanged"): # Qt version >= 6.7.0
+ if hasattr(self.form.cbGlobalMode, "checkStateChanged"): # Qt version >= 6.7.0
self.form.cbGlobalMode.checkStateChanged.connect(self.set_global_mode)
- else: # Qt version < 6.7.0
+ else: # Qt version < 6.7.0
self.form.cbGlobalMode.stateChanged.connect(self.set_global_mode)
self.form.pbReset.clicked.connect(self.reset_point)
self.form.sbHeight.valueChanged.connect(self.set_height)
@@ -132,7 +132,7 @@ class ShapeStringTaskPanel:
self.display_point_active = False
def escape_string(self, string):
- return string.replace("\\", "\\\\").replace("\"", "\\\"")
+ return string.replace("\\", "\\\\").replace('"', '\\"')
def platform_win_dialog(self, flag):
"""Handle the type of dialog depending on the platform."""
@@ -207,10 +207,7 @@ class ShapeStringTaskPanel:
Gui.HintManager.hide()
else:
Gui.HintManager.show(
- Gui.InputHint(
- translate("draft", "%1 pick point"),
- Gui.UserInput.MouseLeft
- )
+ Gui.InputHint(translate("draft", "%1 pick point"), Gui.UserInput.MouseLeft)
)
@@ -232,20 +229,22 @@ class ShapeStringTaskPanelCmd(ShapeStringTaskPanel):
Gui.addModule("Draft")
Gui.addModule("WorkingPlane")
cmd = "Draft.make_shapestring("
- cmd += "String=\"" + self.escape_string(self.text) + "\", "
- cmd += "FontFile=\"" + self.escape_string(self.font_file) + "\", "
+ cmd += 'String="' + self.escape_string(self.text) + '", '
+ cmd += 'FontFile="' + self.escape_string(self.font_file) + '", '
cmd += "Size=" + str(self.height) + ", "
cmd += "Tracking=0.0"
cmd += ")"
self.sourceCmd.commit(
translate("draft", "Create ShapeString"),
- ["ss = " + cmd,
- "pl = FreeCAD.Placement()",
- "pl.Base = " + toString(self.point),
- "pl.Rotation = WorkingPlane.get_working_plane().get_placement().Rotation",
- "ss.Placement = pl",
- "Draft.autogroup(ss)",
- "FreeCAD.ActiveDocument.recompute()"]
+ [
+ "ss = " + cmd,
+ "pl = FreeCAD.Placement()",
+ "pl.Base = " + toString(self.point),
+ "pl.Rotation = WorkingPlane.get_working_plane().get_placement().Rotation",
+ "ss.Placement = pl",
+ "Draft.autogroup(ss)",
+ "FreeCAD.ActiveDocument.recompute()",
+ ],
)
def reject(self):
@@ -269,9 +268,9 @@ class ShapeStringTaskPanelEdit(ShapeStringTaskPanel):
def accept(self):
- Gui.doCommand("ss = FreeCAD.ActiveDocument.getObject(\"" + self.obj.Name + "\")")
- Gui.doCommand("ss.String=\"" + self.escape_string(self.text) + "\"")
- Gui.doCommand("ss.FontFile=\"" + self.escape_string(self.font_file) + "\"")
+ Gui.doCommand('ss = FreeCAD.ActiveDocument.getObject("' + self.obj.Name + '")')
+ Gui.doCommand('ss.String="' + self.escape_string(self.text) + '"')
+ Gui.doCommand('ss.FontFile="' + self.escape_string(self.font_file) + '"')
Gui.doCommand("ss.Size=" + str(self.height))
Gui.doCommand("ss.Placement.Base=" + toString(self.point))
Gui.doCommand("FreeCAD.ActiveDocument.recompute()")
diff --git a/src/Mod/Draft/drafttests/auxiliary.py b/src/Mod/Draft/drafttests/auxiliary.py
index e058007857..de9d40607b 100644
--- a/src/Mod/Draft/drafttests/auxiliary.py
+++ b/src/Mod/Draft/drafttests/auxiliary.py
@@ -39,7 +39,7 @@ from draftutils.messages import _msg
def draw_header():
"""Draw a header for the tests."""
_msg("")
- _msg(78*"-")
+ _msg(78 * "-")
def import_test(module):
@@ -56,18 +56,22 @@ def import_test(module):
def no_gui(module):
"""Print a message that there is no user interface."""
- _msg(" #-----------------------------------------------------#\n"
- " # No GUI; cannot test for '{}'\n"
- " #-----------------------------------------------------#\n"
- " Automatic PASS".format(module))
+ _msg(
+ " #-----------------------------------------------------#\n"
+ " # No GUI; cannot test for '{}'\n"
+ " #-----------------------------------------------------#\n"
+ " Automatic PASS".format(module)
+ )
def no_test():
"""Print a message that the test is not currently implemented."""
- _msg(" #-----------------------------------------------------#\n"
- " # This test is not implemented currently\n"
- " #-----------------------------------------------------#\n"
- " Automatic PASS")
+ _msg(
+ " #-----------------------------------------------------#\n"
+ " # This test is not implemented currently\n"
+ " #-----------------------------------------------------#\n"
+ " Automatic PASS"
+ )
def fake_function(p1=None, p2=None, p3=None, p4=None, p5=None):
@@ -79,4 +83,5 @@ def fake_function(p1=None, p2=None, p3=None, p4=None, p5=None):
no_test()
return True
+
## @}
diff --git a/src/Mod/Draft/drafttests/draft_test_objects.py b/src/Mod/Draft/drafttests/draft_test_objects.py
index 3283a657f1..d0fa073a7d 100644
--- a/src/Mod/Draft/drafttests/draft_test_objects.py
+++ b/src/Mod/Draft/drafttests/draft_test_objects.py
@@ -78,12 +78,14 @@ def _create_frame(doc=None):
version = App.Version()
now = datetime.datetime.now().strftime("%Y/%m/%dT%H:%M:%S")
- _text = ["Draft test file",
- "Created: {}".format(now),
- "\n",
- "Version: " + ".".join(version[0:3]),
- "Release: " + " ".join(version[3:5]),
- "Branch: " + " ".join(version[5:])]
+ _text = [
+ "Draft test file",
+ "Created: {}".format(now),
+ "\n",
+ "Version: " + ".".join(version[0:3]),
+ "Release: " + " ".join(version[3:5]),
+ "Branch: " + " ".join(version[5:]),
+ ]
record = doc.addObject("App::Annotation", "Description")
record.LabelText = _text
@@ -104,10 +106,7 @@ def _create_frame(doc=None):
frame.Shape = poly
-def _create_objects(doc=None,
- font_file=None,
- hatch_file=None,
- hatch_name=None):
+def _create_objects(doc=None, font_file=None, hatch_file=None, hatch_name=None):
"""Create the objects of the test file."""
if not doc:
doc = App.activeDocument()
@@ -125,9 +124,7 @@ def _create_objects(doc=None,
# Wire
_msg(16 * "-")
_msg("Wire")
- Draft.make_wire([Vector(1000, 0, 0),
- Vector(1500, 250, 0),
- Vector(1500, 500, 0)])
+ Draft.make_wire([Vector(1000, 0, 0), Vector(1500, 250, 0), Vector(1500, 500, 0)])
_set_text(["Wire"], Vector(1000, -200, 0))
# Fillet
@@ -152,9 +149,7 @@ def _create_objects(doc=None,
# Circular arc 3 points
_msg(16 * "-")
_msg("Circular arc 3 points")
- Draft.make_arc_3points([Vector(4250, 0, 0),
- Vector(4000, 250, 0),
- Vector(4250, 500, 0)])
+ Draft.make_arc_3points([Vector(4250, 0, 0), Vector(4000, 250, 0), Vector(4250, 500, 0)])
_set_text(["Circular arc 3 points"], Vector(4000, -200, 0))
# Circle
@@ -188,29 +183,32 @@ def _create_objects(doc=None,
# BSpline
_msg(16 * "-")
_msg("BSpline")
- Draft.make_bspline([Vector(9000, 0, 0),
- Vector(9100, 200, 0),
- Vector(9400, 300, 0),
- Vector(9500, 500, 0)])
+ Draft.make_bspline(
+ [Vector(9000, 0, 0), Vector(9100, 200, 0), Vector(9400, 300, 0), Vector(9500, 500, 0)]
+ )
_set_text(["BSpline"], Vector(9000, -200, 0))
# Cubic bezier
_msg(16 * "-")
_msg("Cubic bezier")
- Draft.make_bezcurve([Vector(10000, 0, 0),
- Vector(10000, 500, 0),
- Vector(10500, 0, 0),
- Vector(10500, 500, 0)], degree=3)
+ Draft.make_bezcurve(
+ [Vector(10000, 0, 0), Vector(10000, 500, 0), Vector(10500, 0, 0), Vector(10500, 500, 0)],
+ degree=3,
+ )
_set_text(["Cubic bezier"], Vector(10000, -200, 0))
# N-degree bezier
_msg(16 * "-")
_msg("N-degree bezier")
- Draft.make_bezcurve([Vector (11000, 0, 0),
- Vector (11100, 400, 0),
- Vector (11250, 250, 0),
- Vector (11400, 100, 0),
- Vector (11500, 500, 0)])
+ Draft.make_bezcurve(
+ [
+ Vector(11000, 0, 0),
+ Vector(11100, 400, 0),
+ Vector(11250, 250, 0),
+ Vector(11400, 100, 0),
+ Vector(11500, 500, 0),
+ ]
+ )
_set_text(["N-degree bezier"], Vector(11000, -200, 0))
# Point
@@ -239,9 +237,7 @@ def _create_objects(doc=None,
_msg(16 * "-")
_msg("Shapestring")
try:
- shape_string = Draft.make_shapestring("Testing",
- font_file,
- 100)
+ shape_string = Draft.make_shapestring("Testing", font_file, 100)
shape_string.Placement.Base = Vector(14000, 0)
except Exception:
_wrn("Shapestring could not be created")
@@ -259,11 +255,7 @@ def _create_objects(doc=None,
rectangle.ViewObject.Visibility = False
doc.recompute()
try:
- Draft.make_hatch(rectangle,
- hatch_file,
- hatch_name,
- scale=10,
- rotation=45)
+ Draft.make_hatch(rectangle, hatch_file, hatch_name, scale=10, rotation=45)
except Exception:
_wrn("Hatch could not be created")
_wrn("Possible cause: the hatch file may not exist")
@@ -283,9 +275,9 @@ def _create_objects(doc=None,
# Linear dimension
_msg(16 * "-")
_msg("Linear dimension")
- dimension = Draft.make_linear_dimension(Vector(1500, 2000, 0),
- Vector(1500, 2400, 0),
- Vector(1000, 2200, 0))
+ dimension = Draft.make_linear_dimension(
+ Vector(1500, 2000, 0), Vector(1500, 2400, 0), Vector(1000, 2200, 0)
+ )
if App.GuiUp:
dimension.ViewObject.ArrowSizeStart = 15
dimension.ViewObject.ArrowSizeEnd = 15
@@ -296,11 +288,9 @@ def _create_objects(doc=None,
dimension.ViewObject.Decimals = 1
dimension.ViewObject.ShowUnit = False
- line = Draft.make_wire([Vector(1500, 2600, 0),
- Vector(1500, 3000, 0)])
+ line = Draft.make_wire([Vector(1500, 2600, 0), Vector(1500, 3000, 0)])
doc.recompute()
- dimension = Draft.make_linear_dimension_obj(line, 1, 2,
- Vector(1000, 2800, 0))
+ dimension = Draft.make_linear_dimension_obj(line, 1, 2, Vector(1000, 2800, 0))
if App.GuiUp:
dimension.ViewObject.ArrowSizeStart = 15
dimension.ViewObject.ArrowSizeEnd = 15
@@ -322,10 +312,7 @@ def _create_objects(doc=None,
circle.Placement.Base = Vector(2200, 2200, 0)
circle.MakeFace = False
doc.recompute()
- dimension = Draft.make_radial_dimension_obj(circle,
- 1,
- "radius",
- Vector(2300, 2300, 0))
+ dimension = Draft.make_radial_dimension_obj(circle, 1, "radius", Vector(2300, 2300, 0))
if App.GuiUp:
dimension.ViewObject.ArrowSizeStart = 15
dimension.ViewObject.ArrowSizeEnd = 15
@@ -337,27 +324,21 @@ def _create_objects(doc=None,
circle.Placement.Base = Vector(2200, 2800, 0)
circle.MakeFace = False
doc.recompute()
- dimension = Draft.make_radial_dimension_obj(circle,
- 1,
- "diameter",
- Vector(2300, 2900, 0))
+ dimension = Draft.make_radial_dimension_obj(circle, 1, "diameter", Vector(2300, 2900, 0))
if App.GuiUp:
dimension.ViewObject.ArrowSizeStart = 15
dimension.ViewObject.ArrowSizeEnd = 15
dimension.ViewObject.FontSize = 50
dimension.ViewObject.Decimals = 1
dimension.ViewObject.ShowUnit = False
- _set_text(["Radius dimension",
- "Diameter dimension"], Vector(2000, 1800, 0))
+ _set_text(["Radius dimension", "Diameter dimension"], Vector(2000, 1800, 0))
# Angular dimension
_msg(16 * "-")
_msg("Angular dimension")
Draft.make_line(Vector(3000, 2000, 0), Vector(3500, 2000, 0))
Draft.make_line(Vector(3000, 2000, 0), Vector(3500, 2500, 0))
- dimension = Draft.make_angular_dimension(Vector(3000, 2000, 0),
- [0, 45],
- Vector(3250, 2250, 0))
+ dimension = Draft.make_angular_dimension(Vector(3000, 2000, 0), [0, 45], Vector(3250, 2250, 0))
if App.GuiUp:
dimension.ViewObject.ArrowSizeStart = 15
dimension.ViewObject.ArrowSizeEnd = 15
@@ -369,10 +350,12 @@ def _create_objects(doc=None,
_msg(16 * "-")
_msg("Label")
place = App.Placement(Vector(4250, 2250, 0), App.Rotation())
- label = Draft.make_label(target_point=Vector(4000, 2000, 0),
- placement=place,
- custom_text="Example label",
- distance=-100)
+ label = Draft.make_label(
+ target_point=Vector(4000, 2000, 0),
+ placement=place,
+ custom_text="Example label",
+ distance=-100,
+ )
label.Text = "Testing"
if App.GuiUp:
label.ViewObject.ArrowSizeStart = 15
@@ -389,14 +372,9 @@ def _create_objects(doc=None,
if App.GuiUp:
rectangle.ViewObject.Visibility = False
doc.recompute()
- Draft.make_ortho_array(rectangle,
- Vector(200, 0, 0),
- Vector(0, 150, 0),
- Vector(0, 0, 0),
- 3,
- 2,
- 1,
- use_link=False)
+ Draft.make_ortho_array(
+ rectangle, Vector(200, 0, 0), Vector(0, 150, 0), Vector(0, 0, 0), 3, 2, 1, use_link=False
+ )
_set_text(["Orthogonal array"], Vector(0, 3800, 0))
# Orthogonal link array
@@ -407,46 +385,29 @@ def _create_objects(doc=None,
if App.GuiUp:
rectangle.ViewObject.Visibility = False
doc.recompute()
- Draft.make_ortho_array(rectangle,
- Vector(200, 0, 0),
- Vector(0, 150, 0),
- Vector(0, 0, 0),
- 3,
- 2,
- 1,
- use_link=True)
+ Draft.make_ortho_array(
+ rectangle, Vector(200, 0, 0), Vector(0, 150, 0), Vector(0, 0, 0), 3, 2, 1, use_link=True
+ )
_set_text(["Orthogonal link array"], Vector(1000, 3800, 0))
# Polar array
_msg(16 * "-")
_msg("Polar array")
- wire = Draft.make_wire([Vector(2000, 4050, 0),
- Vector(2000, 4000, 0),
- Vector(2100, 4000, 0)])
+ wire = Draft.make_wire([Vector(2000, 4050, 0), Vector(2000, 4000, 0), Vector(2100, 4000, 0)])
if App.GuiUp:
wire.ViewObject.Visibility = False
doc.recompute()
- Draft.make_polar_array(wire,
- 4,
- 90,
- Vector(2000, 4250, 0),
- use_link=False)
+ Draft.make_polar_array(wire, 4, 90, Vector(2000, 4250, 0), use_link=False)
_set_text(["Polar array"], Vector(2000, 3800, 0))
# Polar link array
_msg(16 * "-")
_msg("Polar link array")
- wire = Draft.make_wire([Vector(3000, 4050, 0),
- Vector(3000, 4000, 0),
- Vector(3050, 4000, 0)])
+ wire = Draft.make_wire([Vector(3000, 4050, 0), Vector(3000, 4000, 0), Vector(3050, 4000, 0)])
if App.GuiUp:
wire.ViewObject.Visibility = False
doc.recompute()
- Draft.make_polar_array(wire,
- 4,
- 90,
- Vector(3000, 4250, 0),
- use_link=True)
+ Draft.make_polar_array(wire, 4, 90, Vector(3000, 4250, 0), use_link=True)
_set_text(["Polar link array"], Vector(3000, 3800, 0))
# Circular array
@@ -457,14 +418,9 @@ def _create_objects(doc=None,
if App.GuiUp:
polygon.ViewObject.Visibility = False
doc.recompute()
- Draft.make_circular_array(polygon,
- 110,
- 100,
- 3,
- 1,
- Vector(0, 0, 1),
- Vector(4250, 4250, 0),
- use_link=False)
+ Draft.make_circular_array(
+ polygon, 110, 100, 3, 1, Vector(0, 0, 1), Vector(4250, 4250, 0), use_link=False
+ )
_set_text(["Circular array"], Vector(4000, 3800, 0))
# Circular link array
@@ -475,14 +431,9 @@ def _create_objects(doc=None,
if App.GuiUp:
polygon.ViewObject.Visibility = False
doc.recompute()
- Draft.make_circular_array(polygon,
- 110,
- 100,
- 3,
- 1,
- Vector(0, 0, 1),
- Vector(5250, 4250, 0),
- use_link=True)
+ Draft.make_circular_array(
+ polygon, 110, 100, 3, 1, Vector(0, 0, 1), Vector(5250, 4250, 0), use_link=True
+ )
_set_text(["Circular link array"], Vector(5000, 3800, 0))
# Path array
@@ -492,10 +443,9 @@ def _create_objects(doc=None,
polygon.Placement.Base = Vector(6000, 4000, 0)
if App.GuiUp:
polygon.ViewObject.Visibility = False
- spline = Draft.make_bspline([Vector(6000, 4000, 0),
- Vector(6100, 4200, 0),
- Vector(6400, 4300, 0),
- Vector(6500, 4500, 0)])
+ spline = Draft.make_bspline(
+ [Vector(6000, 4000, 0), Vector(6100, 4200, 0), Vector(6400, 4300, 0), Vector(6500, 4500, 0)]
+ )
doc.recompute()
Draft.make_path_array(polygon, spline, 5, use_link=False)
_set_text(["Path array"], Vector(6000, 3800, 0))
@@ -507,10 +457,9 @@ def _create_objects(doc=None,
polygon.Placement.Base = Vector(7000, 4000, 0)
if App.GuiUp:
polygon.ViewObject.Visibility = False
- spline = Draft.make_bspline([Vector(7000, 4000, 0),
- Vector(7100, 4200, 0),
- Vector(7400, 4300, 0),
- Vector(7500, 4500, 0)])
+ spline = Draft.make_bspline(
+ [Vector(7000, 4000, 0), Vector(7100, 4200, 0), Vector(7400, 4300, 0), Vector(7500, 4500, 0)]
+ )
doc.recompute()
Draft.make_path_array(polygon, spline, 5, use_link=True)
_set_text(["Path link array"], Vector(7000, 3800, 0))
@@ -524,8 +473,7 @@ def _create_objects(doc=None,
point_2 = Draft.make_point(8030, 4250, 0)
point_3 = Draft.make_point(8470, 4250, 0)
point_4 = Draft.make_point(8470, 4470, 0)
- add_list, delete_list = Draft.upgrade([point_1, point_2,
- point_3, point_4])
+ add_list, delete_list = Draft.upgrade([point_1, point_2, point_3, point_4])
compound = add_list[0]
if App.GuiUp:
compound.ViewObject.PointSize = 5
@@ -542,8 +490,7 @@ def _create_objects(doc=None,
point_2 = Draft.make_point(9030, 4250, 0)
point_3 = Draft.make_point(9470, 4250, 0)
point_4 = Draft.make_point(9470, 4470, 0)
- add_list, delete_list = Draft.upgrade([point_1, point_2,
- point_3, point_4])
+ add_list, delete_list = Draft.upgrade([point_1, point_2, point_3, point_4])
compound = add_list[0]
if App.GuiUp:
compound.ViewObject.PointSize = 5
@@ -556,28 +503,21 @@ def _create_objects(doc=None,
# Mirror
_msg(16 * "-")
_msg("Mirror")
- wire = Draft.make_wire([Vector(0, 6000, 0),
- Vector(150, 6200, 0),
- Vector(500, 6000, 0)])
- Draft.mirror(wire,
- Vector(0, 6250, 0),
- Vector(500, 6250, 0))
+ wire = Draft.make_wire([Vector(0, 6000, 0), Vector(150, 6200, 0), Vector(500, 6000, 0)])
+ Draft.mirror(wire, Vector(0, 6250, 0), Vector(500, 6250, 0))
_set_text(["Mirror"], Vector(0, 5800, 0))
# Clone
_msg(16 * "-")
_msg("Clone")
- wire = Draft.make_wire([Vector(1000, 6000, 0),
- Vector(1150, 6200, 0),
- Vector(1500, 6000, 0)])
+ wire = Draft.make_wire([Vector(1000, 6000, 0), Vector(1150, 6200, 0), Vector(1500, 6000, 0)])
Draft.make_clone(wire, Vector(0, 300, 0))
_set_text(["Clone"], Vector(1000, 5800, 0))
# Shape2DView
_msg(16 * "-")
_msg("Shape2DView")
- place = App.Placement(Vector(2000, 6000, 0),
- App.Rotation(Vector(0, 0, 1), Vector(1, 2, 3)))
+ place = App.Placement(Vector(2000, 6000, 0), App.Rotation(Vector(0, 0, 1), Vector(1, 2, 3)))
box = doc.addObject("Part::Box", "Box")
box.Length = 200
box.Width = 500
@@ -601,12 +541,14 @@ def _create_objects(doc=None,
# Layer
_msg(16 * "-")
_msg("Layer")
- layer = Draft.make_layer("Custom layer",
- line_color=(0.33, 0.0, 0.49),
- shape_color=(0.56, 0.89, 0.56),
- line_width=4,
- draw_style="Solid",
- transparency=50)
+ layer = Draft.make_layer(
+ "Custom layer",
+ line_color=(0.33, 0.0, 0.49),
+ shape_color=(0.56, 0.89, 0.56),
+ line_width=4,
+ draw_style="Solid",
+ transparency=50,
+ )
box = doc.addObject("Part::Box", "Box")
box.Length = 200
box.Width = 500
@@ -622,9 +564,11 @@ def _create_objects(doc=None,
doc.recompute()
-def create_test_file(font_file=App.getResourceDir()+"Mod/TechDraw/Resources/fonts/osifont-lgpl3fe.ttf",
- hatch_file=App.getResourceDir()+"Mod/TechDraw/PAT/FCPAT.pat",
- hatch_name="Horizontal5"):
+def create_test_file(
+ font_file=App.getResourceDir() + "Mod/TechDraw/Resources/fonts/osifont-lgpl3fe.ttf",
+ hatch_file=App.getResourceDir() + "Mod/TechDraw/PAT/FCPAT.pat",
+ hatch_name="Horizontal5",
+):
"""Create a complete test file of Draft objects.
It draws a frame with information on the software used to create
@@ -664,6 +608,7 @@ def create_test_file(font_file=App.getResourceDir()+"Mod/TechDraw/Resources/font
return doc
+
## @}
diff --git a/src/Mod/Draft/drafttests/test_airfoildat.py b/src/Mod/Draft/drafttests/test_airfoildat.py
index eaf409c3df..b1e6e166ed 100644
--- a/src/Mod/Draft/drafttests/test_airfoildat.py
+++ b/src/Mod/Draft/drafttests/test_airfoildat.py
@@ -71,4 +71,5 @@ class DraftAirfoilDAT(test_base.DraftTestCaseDoc):
obj = aux.fake_function(out_file)
self.assertTrue(obj, "'{}' failed".format(operation))
+
## @}
diff --git a/src/Mod/Draft/drafttests/test_array.py b/src/Mod/Draft/drafttests/test_array.py
index 1e49cb4d66..016b002348 100644
--- a/src/Mod/Draft/drafttests/test_array.py
+++ b/src/Mod/Draft/drafttests/test_array.py
@@ -43,10 +43,16 @@ class DraftArray(test_base.DraftTestCaseDoc):
box.Label = "Box"
self.doc.recompute()
- array = Draft.make_ortho_array(box, v_x=Vector(100.0, 0.0, 0.0),
- v_y=Vector(0.0, 100.0, 0.0),
- v_z=Vector(0.0, 0.0, 100.0),
- n_x=12, n_y=1, n_z=1, use_link=True)
+ array = Draft.make_ortho_array(
+ box,
+ v_x=Vector(100.0, 0.0, 0.0),
+ v_y=Vector(0.0, 100.0, 0.0),
+ v_z=Vector(0.0, 0.0, 100.0),
+ n_x=12,
+ n_y=1,
+ n_z=1,
+ use_link=True,
+ )
Draft.autogroup(array)
array.ExpandArray = True
@@ -64,4 +70,5 @@ class DraftArray(test_base.DraftTestCaseDoc):
self.doc.recompute(None, True, True)
self.assertEqual(array.Count, array.NumberX)
+
## @}
diff --git a/src/Mod/Draft/drafttests/test_creation.py b/src/Mod/Draft/drafttests/test_creation.py
index 0a224a8dd8..2fcbbfbf6f 100644
--- a/src/Mod/Draft/drafttests/test_creation.py
+++ b/src/Mod/Draft/drafttests/test_creation.py
@@ -103,10 +103,8 @@ class DraftCreation(test_base.DraftTestCaseDoc):
start_angle = 0
end_angle = 90
_msg(" radius={}".format(radius))
- _msg(" startangle={0}, endangle={1}".format(start_angle,
- end_angle))
- obj = Draft.make_circle(radius,
- startangle=start_angle, endangle=end_angle)
+ _msg(" startangle={0}, endangle={1}".format(start_angle, end_angle))
+ obj = Draft.make_circle(radius, startangle=start_angle, endangle=end_angle)
self.assertTrue(obj, "'{}' failed".format(operation))
def test_arc_3points(self):
@@ -185,9 +183,7 @@ class DraftCreation(test_base.DraftTestCaseDoc):
line = Draft.make_line(a, b)
self.doc.recompute()
- obj = Draft.make_linear_dimension_obj(line,
- i1=1, i2=2,
- dim_line=Vector(5, 3, 0))
+ obj = Draft.make_linear_dimension_obj(line, i1=1, i2=2, dim_line=Vector(5, 3, 0))
self.assertTrue(obj, "'{}' failed".format(operation))
def test_dimension_radial_obj(self):
@@ -198,18 +194,16 @@ class DraftCreation(test_base.DraftTestCaseDoc):
start_angle = 0
end_angle = 90
_msg(" radius={}".format(radius))
- _msg(" startangle={0}, endangle={1}".format(start_angle,
- end_angle))
- circ = Draft.make_circle(radius,
- startangle=start_angle, endangle=end_angle)
+ _msg(" startangle={0}, endangle={1}".format(start_angle, end_angle))
+ circ = Draft.make_circle(radius, startangle=start_angle, endangle=end_angle)
self.doc.recompute()
- obj1 = Draft.make_radial_dimension_obj(circ, index=1,
- mode="radius",
- dim_line=Vector(1, 1, 0))
- obj2 = Draft.make_radial_dimension_obj(circ, index=1,
- mode="diameter",
- dim_line=Vector(3, 1, 0))
+ obj1 = Draft.make_radial_dimension_obj(
+ circ, index=1, mode="radius", dim_line=Vector(1, 1, 0)
+ )
+ obj2 = Draft.make_radial_dimension_obj(
+ circ, index=1, mode="diameter", dim_line=Vector(3, 1, 0)
+ )
self.assertTrue(obj1 and obj2, "'{}' failed".format(operation))
def test_dimension_angular(self):
@@ -322,12 +316,9 @@ class DraftCreation(test_base.DraftTestCaseDoc):
target_point = Vector(0, 0, 0)
distance = -25
placement = App.Placement(Vector(50, 50, 0), App.Rotation())
- _msg(" target_point={0}, "
- "distance={1}".format(target_point, distance))
+ _msg(" target_point={0}, " "distance={1}".format(target_point, distance))
_msg(" placement={}".format(placement))
- obj = Draft.make_label(target_point=target_point,
- distance=distance,
- placement=placement)
+ obj = Draft.make_label(target_point=target_point, distance=distance, placement=placement)
self.doc.recompute()
self.assertTrue(obj, "'{}' failed".format(operation))
@@ -374,9 +365,12 @@ class DraftCreation(test_base.DraftTestCaseDoc):
box = obj.Shape.BoundBox
# A rather high tolerance is required.
- obj_is_ok = (box.Center.isEqual(Vector(length/2, width/2, 0), 1e-6)
- and math.isclose(box.XLength, length, rel_tol=0, abs_tol=1e-6)
- and math.isclose(box.YLength, width, rel_tol=0, abs_tol=1e-6))
+ obj_is_ok = (
+ box.Center.isEqual(Vector(length / 2, width / 2, 0), 1e-6)
+ and math.isclose(box.XLength, length, rel_tol=0, abs_tol=1e-6)
+ and math.isclose(box.YLength, width, rel_tol=0, abs_tol=1e-6)
+ )
self.assertTrue(obj_is_ok, "'{}' failed".format(operation))
+
## @}
diff --git a/src/Mod/Draft/drafttests/test_draftgeomutils.py b/src/Mod/Draft/drafttests/test_draftgeomutils.py
index 3523ba086a..4960a5d491 100644
--- a/src/Mod/Draft/drafttests/test_draftgeomutils.py
+++ b/src/Mod/Draft/drafttests/test_draftgeomutils.py
@@ -43,18 +43,38 @@ class TestDraftGeomUtils(test_base.DraftTestCaseNoDoc):
try:
extended = DraftGeomUtils.get_extended_wire(wire, offset_start, offset_end)
# Test that the extended wire's length is correctly changed
- self.assertAlmostEqual(extended.Length, wire.Length + offset_start + offset_end,
- DraftGeomUtils.precision(), "'start={0}, end={1}' failed".format(offset_start, offset_end))
+ self.assertAlmostEqual(
+ extended.Length,
+ wire.Length + offset_start + offset_end,
+ DraftGeomUtils.precision(),
+ "'start={0}, end={1}' failed".format(offset_start, offset_end),
+ )
if offset_start == 0.0:
# If offset_start is 0.0, check that the wire's start point is unchanged
- self.assertAlmostEqual(extended.OrderedVertexes[0].Point.distanceToPoint(wire.OrderedVertexes[0].Point), 0.0,
- DraftGeomUtils.precision(), "'start={0}, end={1}' failed".format(offset_start, offset_end))
+ self.assertAlmostEqual(
+ extended.OrderedVertexes[0].Point.distanceToPoint(
+ wire.OrderedVertexes[0].Point
+ ),
+ 0.0,
+ DraftGeomUtils.precision(),
+ "'start={0}, end={1}' failed".format(offset_start, offset_end),
+ )
if offset_end == 0.0:
# If offset_end is 0.0, check that the wire's end point is unchanged
- self.assertAlmostEqual(extended.OrderedVertexes[-1].Point.distanceToPoint(wire.OrderedVertexes[-1].Point), 0.0,
- DraftGeomUtils.precision(), "'start={0}, end={1}' failed".format(offset_start, offset_end))
+ self.assertAlmostEqual(
+ extended.OrderedVertexes[-1].Point.distanceToPoint(
+ wire.OrderedVertexes[-1].Point
+ ),
+ 0.0,
+ DraftGeomUtils.precision(),
+ "'start={0}, end={1}' failed".format(offset_start, offset_end),
+ )
except Exception as exc:
- print ("get_extended_wire failed for 'start={0}, end={1}'".format(offset_start, offset_end))
+ print(
+ "get_extended_wire failed for 'start={0}, end={1}'".format(
+ offset_start, offset_end
+ )
+ )
raise exc
def test_get_extended_wire1(self):
@@ -63,10 +83,12 @@ class TestDraftGeomUtils(test_base.DraftTestCaseNoDoc):
_msg(" Test '{}'".format(operation))
# Build wires made with straight edges and various combination of Orientation: the wires 1-4 are all equivalent
- points = [Vector(0.0, 0.0, 0.0),
- Vector(1500.0, 2000.0, 0.0),
- Vector(4500.0, 2000.0, 0.0),
- Vector(4500.0, 2000.0, 2500.0)]
+ points = [
+ Vector(0.0, 0.0, 0.0),
+ Vector(1500.0, 2000.0, 0.0),
+ Vector(4500.0, 2000.0, 0.0),
+ Vector(4500.0, 2000.0, 2500.0),
+ ]
edges = []
for start, end in zip(points[:-1], points[1:]):
@@ -81,10 +103,12 @@ class TestDraftGeomUtils(test_base.DraftTestCaseNoDoc):
_msg(" Test '{}'".format(operation))
# Build wires made with straight edges and various combination of Orientation: the wires 1-4 are all equivalent
- points = [Vector(0.0, 0.0, 0.0),
- Vector(1500.0, 2000.0, 0.0),
- Vector(4500.0, 2000.0, 0.0),
- Vector(4500.0, 2000.0, 2500.0)]
+ points = [
+ Vector(0.0, 0.0, 0.0),
+ Vector(1500.0, 2000.0, 0.0),
+ Vector(4500.0, 2000.0, 0.0),
+ Vector(4500.0, 2000.0, 2500.0),
+ ]
edges = []
for start, end in zip(points[:-1], points[1:]):
@@ -100,10 +124,12 @@ class TestDraftGeomUtils(test_base.DraftTestCaseNoDoc):
_msg(" Test '{}'".format(operation))
# Build wires made with straight edges and various combination of Orientation: the wires 1-4 are all equivalent
- points = [Vector(0.0, 0.0, 0.0),
- Vector(1500.0, 2000.0, 0.0),
- Vector(4500.0, 2000.0, 0.0),
- Vector(4500.0, 2000.0, 2500.0)]
+ points = [
+ Vector(0.0, 0.0, 0.0),
+ Vector(1500.0, 2000.0, 0.0),
+ Vector(4500.0, 2000.0, 0.0),
+ Vector(4500.0, 2000.0, 2500.0),
+ ]
edges = []
for start, end in zip(points[:-1], points[1:]):
@@ -120,10 +146,12 @@ class TestDraftGeomUtils(test_base.DraftTestCaseNoDoc):
_msg(" Test '{}'".format(operation))
# Build wires made with straight edges and various combination of Orientation: the wires 1-4 are all equivalent
- points = [Vector(0.0, 0.0, 0.0),
- Vector(1500.0, 2000.0, 0.0),
- Vector(4500.0, 2000.0, 0.0),
- Vector(4500.0, 2000.0, 2500.0)]
+ points = [
+ Vector(0.0, 0.0, 0.0),
+ Vector(1500.0, 2000.0, 0.0),
+ Vector(4500.0, 2000.0, 0.0),
+ Vector(4500.0, 2000.0, 2500.0),
+ ]
edges = []
for start, end in zip(points[:-1], points[1:]):
@@ -139,11 +167,13 @@ class TestDraftGeomUtils(test_base.DraftTestCaseNoDoc):
_msg(" Test '{}'".format(operation))
# Build wires made with arcs and various combination of Orientation: the wires 5-8 are all equivalent
- points = [Vector(0.0, 0.0, 0.0),
- Vector(1000.0, 1000.0, 0.0),
- Vector(2000.0, 0.0, 0.0),
- Vector(3000.0, 0.0, 1000.0),
- Vector(4000.0, 0.0, 0.0)]
+ points = [
+ Vector(0.0, 0.0, 0.0),
+ Vector(1000.0, 1000.0, 0.0),
+ Vector(2000.0, 0.0, 0.0),
+ Vector(3000.0, 0.0, 1000.0),
+ Vector(4000.0, 0.0, 0.0),
+ ]
edges = []
for start, mid, end in zip(points[:-2], points[1:-1], points[2:]):
@@ -158,11 +188,13 @@ class TestDraftGeomUtils(test_base.DraftTestCaseNoDoc):
_msg(" Test '{}'".format(operation))
# Build wires made with arcs and various combination of Orientation: the wires 5-8 are all equivalent
- points = [Vector(0.0, 0.0, 0.0),
- Vector(1000.0, 1000.0, 0.0),
- Vector(2000.0, 0.0, 0.0),
- Vector(3000.0, 0.0, 1000.0),
- Vector(4000.0, 0.0, 0.0)]
+ points = [
+ Vector(0.0, 0.0, 0.0),
+ Vector(1000.0, 1000.0, 0.0),
+ Vector(2000.0, 0.0, 0.0),
+ Vector(3000.0, 0.0, 1000.0),
+ Vector(4000.0, 0.0, 0.0),
+ ]
edges = []
for start, mid, end in zip(points[:-2], points[1:-1], points[2:]):
@@ -178,11 +210,13 @@ class TestDraftGeomUtils(test_base.DraftTestCaseNoDoc):
_msg(" Test '{}'".format(operation))
# Build wires made with arcs and various combination of Orientation: the wires 5-8 are all equivalent
- points = [Vector(0.0, 0.0, 0.0),
- Vector(1000.0, 1000.0, 0.0),
- Vector(2000.0, 0.0, 0.0),
- Vector(3000.0, 0.0, 1000.0),
- Vector(4000.0, 0.0, 0.0)]
+ points = [
+ Vector(0.0, 0.0, 0.0),
+ Vector(1000.0, 1000.0, 0.0),
+ Vector(2000.0, 0.0, 0.0),
+ Vector(3000.0, 0.0, 1000.0),
+ Vector(4000.0, 0.0, 0.0),
+ ]
edges = []
for start, mid, end in zip(points[:-2], points[1:-1], points[2:]):
@@ -199,11 +233,13 @@ class TestDraftGeomUtils(test_base.DraftTestCaseNoDoc):
_msg(" Test '{}'".format(operation))
# Build wires made with arcs and various combination of Orientation: the wires 5-8 are all equivalent
- points = [Vector(0.0, 0.0, 0.0),
- Vector(1000.0, 1000.0, 0.0),
- Vector(2000.0, 0.0, 0.0),
- Vector(3000.0, 0.0, 1000.0),
- Vector(4000.0, 0.0, 0.0)]
+ points = [
+ Vector(0.0, 0.0, 0.0),
+ Vector(1000.0, 1000.0, 0.0),
+ Vector(2000.0, 0.0, 0.0),
+ Vector(3000.0, 0.0, 1000.0),
+ Vector(4000.0, 0.0, 0.0),
+ ]
edges = []
for start, mid, end in zip(points[:-2], points[1:-1], points[2:]):
@@ -213,5 +249,6 @@ class TestDraftGeomUtils(test_base.DraftTestCaseNoDoc):
wire.Orientation = "Reversed"
self.check_wire(wire)
+
# suite = unittest.defaultTestLoader.loadTestsFromTestCase(TestDraftGeomUtils)
# unittest.TextTestRunner().run(suite)
diff --git a/src/Mod/Draft/drafttests/test_dwg.py b/src/Mod/Draft/drafttests/test_dwg.py
index b77293a395..2af415ab9d 100644
--- a/src/Mod/Draft/drafttests/test_dwg.py
+++ b/src/Mod/Draft/drafttests/test_dwg.py
@@ -70,4 +70,5 @@ class DraftDWG(test_base.DraftTestCaseDoc):
obj = aux.fake_function(out_file)
self.assertTrue(obj, "'{}' failed".format(operation))
+
## @}
diff --git a/src/Mod/Draft/drafttests/test_dxf.py b/src/Mod/Draft/drafttests/test_dxf.py
index e29f28606b..cdf70f1565 100644
--- a/src/Mod/Draft/drafttests/test_dxf.py
+++ b/src/Mod/Draft/drafttests/test_dxf.py
@@ -71,4 +71,5 @@ class DraftDXF(test_base.DraftTestCaseDoc):
obj = aux.fake_function(out_file)
self.assertTrue(obj, "'{}' failed".format(operation))
+
## @}
diff --git a/src/Mod/Draft/drafttests/test_import.py b/src/Mod/Draft/drafttests/test_import.py
index 9a5007295f..d60ceb351b 100644
--- a/src/Mod/Draft/drafttests/test_import.py
+++ b/src/Mod/Draft/drafttests/test_import.py
@@ -63,4 +63,5 @@ class DraftImport(test_base.DraftTestCaseNoDoc):
imported = aux.import_test(module)
self.assertTrue(imported, "Problem importing '{}'".format(module))
+
## @}
diff --git a/src/Mod/Draft/drafttests/test_import_gui.py b/src/Mod/Draft/drafttests/test_import_gui.py
index eb686eb702..2e40a2a571 100644
--- a/src/Mod/Draft/drafttests/test_import_gui.py
+++ b/src/Mod/Draft/drafttests/test_import_gui.py
@@ -63,4 +63,5 @@ class DraftGuiImport(test_base.DraftTestCaseNoDoc):
imported = aux.import_test(module)
self.assertTrue(imported, "Problem importing '{}'".format(module))
+
## @}
diff --git a/src/Mod/Draft/drafttests/test_import_tools.py b/src/Mod/Draft/drafttests/test_import_tools.py
index 757bacc583..449f4e2e71 100644
--- a/src/Mod/Draft/drafttests/test_import_tools.py
+++ b/src/Mod/Draft/drafttests/test_import_tools.py
@@ -56,4 +56,5 @@ class DraftImportTools(test_base.DraftTestCaseNoDoc):
imported = aux.import_test(module)
self.assertTrue(imported, "Problem importing '{}'".format(module))
+
## @}
diff --git a/src/Mod/Draft/drafttests/test_modification.py b/src/Mod/Draft/drafttests/test_modification.py
index 105cba52d0..bdebbfc2ea 100644
--- a/src/Mod/Draft/drafttests/test_modification.py
+++ b/src/Mod/Draft/drafttests/test_modification.py
@@ -60,8 +60,7 @@ class DraftModification(test_base.DraftTestCaseDoc):
_msg(" c={}".format(c))
Draft.move(obj, c)
self.doc.recompute()
- self.assertTrue(obj.Start.isEqual(Vector(3, 3, 0), 1e-6),
- "'{}' failed".format(operation))
+ self.assertTrue(obj.Start.isEqual(Vector(3, 3, 0), 1e-6), "'{}' failed".format(operation))
def test_copy(self):
"""Create a line, then copy and move it."""
@@ -96,8 +95,7 @@ class DraftModification(test_base.DraftTestCaseDoc):
_msg(" angle={} degrees".format(rot))
Draft.rotate(obj, rot)
self.doc.recompute()
- self.assertTrue(obj.Start.isEqual(c, 1e-6),
- "'{}' failed".format(operation))
+ self.assertTrue(obj.Start.isEqual(c, 1e-6), "'{}' failed".format(operation))
def test_offset_open(self):
"""Create an open wire, then produce an offset copy."""
@@ -129,10 +127,7 @@ class DraftModification(test_base.DraftTestCaseDoc):
b = Vector(10, 0, 0)
c = Vector(10, 4, 0)
d = Vector(0, 4, 0)
- edges = [Part.makeLine(a, b),
- Part.makeLine(b, c),
- Part.makeLine(c, d),
- Part.makeLine(a, d)]
+ edges = [Part.makeLine(a, b), Part.makeLine(b, c), Part.makeLine(c, d), Part.makeLine(a, d)]
wire = Part.Wire(edges)
obj = self.doc.addObject("Part::Feature")
obj.Shape = wire
@@ -160,9 +155,9 @@ class DraftModification(test_base.DraftTestCaseDoc):
_msg(" vector={}".format(offset))
obj = Draft.offset(rect, offset, copy=True)
self.doc.recompute()
- obj_is_ok = (obj.Shape.CenterOfGravity == Vector(5, 2, 0)
- and obj.Length == 12
- and obj.Height == 6)
+ obj_is_ok = (
+ obj.Shape.CenterOfGravity == Vector(5, 2, 0) and obj.Length == 12 and obj.Height == 6
+ )
self.assertTrue(obj_is_ok, "'{}' failed".format(operation))
def test_trim(self):
@@ -335,8 +330,7 @@ class DraftModification(test_base.DraftTestCaseDoc):
obj3 = Draft.downgrade(obj2[0], delete=True)
self.doc.recompute()
s3 = obj3[0][0]
- _msg(" 3: Result 3 x '{0}' ({1})".format(s3.Shape.ShapeType,
- s3.TypeId))
+ _msg(" 3: Result 3 x '{0}' ({1})".format(s3.Shape.ShapeType, s3.TypeId))
self.assertTrue(len(obj3[0]) == 3, "'{}' failed".format(operation))
# edges cannot be downgraded
@@ -376,7 +370,7 @@ class DraftModification(test_base.DraftTestCaseDoc):
prism.Polygon = 5
# Rotate the prism 45 degrees around the Y axis
prism.Placement.Rotation.Axis = Vector(0, 1, 0)
- prism.Placement.Rotation.Angle = 45 * (3.14159/180)
+ prism.Placement.Rotation.Angle = 45 * (3.14159 / 180)
_msg(" Prism")
_msg(" n_sides={}".format(prism.Polygon))
_msg(" placement={}".format(prism.Placement))
@@ -402,14 +396,12 @@ class DraftModification(test_base.DraftTestCaseDoc):
obj = Draft.make_sketch(wire, autoconstraints=True)
self.doc.recompute()
- _msg(" 1: Result '{0}' ({1})".format(obj.Shape.ShapeType,
- obj.TypeId))
+ _msg(" 1: Result '{0}' ({1})".format(obj.Shape.ShapeType, obj.TypeId))
self.assertTrue(obj, "'{}' failed".format(operation))
obj2 = Draft.draftify(obj, delete=False)
self.doc.recompute()
- _msg(" 2: Result '{0}' ({1})".format(obj2.Proxy.Type,
- obj2.TypeId))
+ _msg(" 2: Result '{0}' ({1})".format(obj2.Proxy.Type, obj2.TypeId))
self.assertTrue(obj2, "'{}' failed".format(operation))
def test_rectangular_array(self):
@@ -433,12 +425,8 @@ class DraftModification(test_base.DraftTestCaseDoc):
_msg(" direction_x={}".format(dir_x))
_msg(" direction_y={}".format(dir_y))
_msg(" direction_z={}".format(dir_z))
- _msg(" number_x={0}, number_y={1}, number_z={2}".format(number_x,
- number_y,
- number_z))
- obj = Draft.make_ortho_array(rect,
- dir_x, dir_y, dir_z,
- number_x, number_y, number_z)
+ _msg(" number_x={0}, number_y={1}, number_z={2}".format(number_x, number_y, number_z))
+ obj = Draft.make_ortho_array(rect, dir_x, dir_y, dir_z, number_x, number_y, number_z)
self.assertTrue(obj, "'{}' failed".format(operation))
def test_polar_array(self):
@@ -458,8 +446,7 @@ class DraftModification(test_base.DraftTestCaseDoc):
_msg(" Array")
_msg(" number={0}, polar_angle={1}".format(number, angle))
_msg(" center={}".format(center))
- obj = Draft.make_polar_array(rect,
- number, angle, center)
+ obj = Draft.make_polar_array(rect, number, angle, center)
self.assertTrue(obj, "'{}' failed".format(operation))
def test_circular_array(self):
@@ -480,15 +467,13 @@ class DraftModification(test_base.DraftTestCaseDoc):
number = 3
symmetry = 1
_msg(" Array")
- _msg(" radial_distance={0}, "
- "tangential_distance={1}".format(rad_distance, tan_distance))
+ _msg(" radial_distance={0}, " "tangential_distance={1}".format(rad_distance, tan_distance))
_msg(" number={0}, symmetry={1}".format(number, symmetry))
_msg(" axis={}".format(axis))
_msg(" center={}".format(center))
- obj = Draft.make_circular_array(rect,
- rad_distance, tan_distance,
- number, symmetry,
- axis, center)
+ obj = Draft.make_circular_array(
+ rect, rad_distance, tan_distance, number, symmetry, axis, center
+ )
self.assertTrue(obj, "'{}' failed".format(operation))
def test_path_array(self):
@@ -517,8 +502,7 @@ class DraftModification(test_base.DraftTestCaseDoc):
_msg(" Path Array")
_msg(" number={}, translation={}".format(number, translation))
_msg(" subelements={}, align={}".format(subelements, align))
- obj = Draft.make_path_array(poly, wire, number,
- translation, subelements, align)
+ obj = Draft.make_path_array(poly, wire, number, translation, subelements, align)
self.assertTrue(obj, "'{}' failed".format(operation))
def test_point_array(self):
@@ -532,10 +516,12 @@ class DraftModification(test_base.DraftTestCaseDoc):
_msg(" Points")
_msg(" a={0}, b={1}".format(a, b))
_msg(" c={0}, d={1}".format(c, d))
- points = [Draft.make_point(a),
- Draft.make_point(b),
- Draft.make_point(c),
- Draft.make_point(d)]
+ points = [
+ Draft.make_point(a),
+ Draft.make_point(b),
+ Draft.make_point(c),
+ Draft.make_point(d),
+ ]
_msg(" Upgrade")
add, delete = Draft.upgrade(points)
@@ -565,8 +551,7 @@ class DraftModification(test_base.DraftTestCaseDoc):
obj = Draft.make_clone(box)
_msg(" clone: '{0}' ({1})".format(obj.Proxy.Type, obj.TypeId))
self.assertTrue(obj, "'{}' failed".format(operation))
- self.assertTrue(obj.hasExtension("Part::AttachExtension"),
- "'{}' failed".format(operation))
+ self.assertTrue(obj.hasExtension("Part::AttachExtension"), "'{}' failed".format(operation))
def test_attached_clone_behavior(self):
"""Check if an attached clone behaves correctly.
@@ -599,7 +584,7 @@ class DraftModification(test_base.DraftTestCaseDoc):
prism.Polygon = 5
# Rotate the prism 45 degrees around the Y axis
prism.Placement.Rotation.Axis = Vector(0, 1, 0)
- prism.Placement.Rotation.Angle = 45 * (3.14159/180)
+ prism.Placement.Rotation.Angle = 45 * (3.14159 / 180)
_msg(" Prism")
_msg(" n_sides={}".format(prism.Polygon))
_msg(" placement={}".format(prism.Placement))
@@ -607,8 +592,9 @@ class DraftModification(test_base.DraftTestCaseDoc):
page = self.doc.addObject("TechDraw::DrawPage")
_msg(" page={}".format(page.TypeId))
template = self.doc.addObject("TechDraw::DrawSVGTemplate")
- template.Template = App.getResourceDir() \
- + "Mod/TechDraw/Templates/ISO/A3_Landscape_blank.svg"
+ template.Template = (
+ App.getResourceDir() + "Mod/TechDraw/Templates/ISO/A3_Landscape_blank.svg"
+ )
page.Template = template
_msg(" template={}".format(template.TypeId))
view = self.doc.addObject("TechDraw::DrawViewDraft")
@@ -659,21 +645,29 @@ class DraftModification(test_base.DraftTestCaseDoc):
_msg(" Test '{}'".format(operation))
base = Vector(3.5, 2.5, 0.0)
- cen = Vector(2.0, 1.0, 0.0) # center for scaling
+ cen = Vector(2.0, 1.0, 0.0) # center for scaling
sca = Vector(2.0, 3.0, 1.0)
- ends = [Vector(0.0, 0.0, 0.0),
- Vector(4.0, 0.0, 0.0),
- Vector(4.0, 3.0, 0.0),
- Vector(0.0, 3.0, 0.0)]
- mids = [Vector( 2.0, -0.5, 0.0),
- Vector( 4.5, 1.5, 0.0),
- Vector( 2.0, 3.5, 0.0),
- Vector(-0.5, 1.5, 0.0)] # arc midpoints
+ ends = [
+ Vector(0.0, 0.0, 0.0),
+ Vector(4.0, 0.0, 0.0),
+ Vector(4.0, 3.0, 0.0),
+ Vector(0.0, 3.0, 0.0),
+ ]
+ mids = [
+ Vector(2.0, -0.5, 0.0),
+ Vector(4.5, 1.5, 0.0),
+ Vector(2.0, 3.5, 0.0),
+ Vector(-0.5, 1.5, 0.0),
+ ] # arc midpoints
- shp = Part.Shape([Part.Arc(ends[0], mids[0], ends[1]),
- Part.Arc(ends[1], mids[1], ends[2]),
- Part.Arc(ends[2], mids[2], ends[3]),
- Part.Arc(ends[3], mids[3], ends[0])])
+ shp = Part.Shape(
+ [
+ Part.Arc(ends[0], mids[0], ends[1]),
+ Part.Arc(ends[1], mids[1], ends[2]),
+ Part.Arc(ends[2], mids[2], ends[3]),
+ Part.Arc(ends[3], mids[3], ends[0]),
+ ]
+ )
obj = self.doc.addObject("Part::Feature")
obj.Shape = shp
obj.Placement.Base = base
@@ -682,24 +676,30 @@ class DraftModification(test_base.DraftTestCaseDoc):
self.doc.recompute()
# check endpoints of arcs:
- newEnds = [Vector( 5.0, 5.5, 0.0),
- Vector(13.0, 5.5, 0.0),
- Vector(13.0, 14.5, 0.0),
- Vector( 5.0, 14.5, 0.0)]
+ newEnds = [
+ Vector(5.0, 5.5, 0.0),
+ Vector(13.0, 5.5, 0.0),
+ Vector(13.0, 14.5, 0.0),
+ Vector(5.0, 14.5, 0.0),
+ ]
vrts = obj.Shape.Vertexes
for i in range(4):
- self.assertTrue(vrts[i].Point.isEqual(newEnds[i], 1e-6),
- "'{}' failed".format(operation))
+ self.assertTrue(
+ vrts[i].Point.isEqual(newEnds[i], 1e-6), "'{}' failed".format(operation)
+ )
# check midpoints of arcs:
- newMids = [Vector( 9.0, 4.0, 0.0),
- Vector(14.0, 10.0, 0.0),
- Vector( 9.0, 16.0, 0.0),
- Vector( 4.0, 10.0, 0.0)]
+ newMids = [
+ Vector(9.0, 4.0, 0.0),
+ Vector(14.0, 10.0, 0.0),
+ Vector(9.0, 16.0, 0.0),
+ Vector(4.0, 10.0, 0.0),
+ ]
for i in range(4):
edge = obj.Shape.Edges[i]
par = (edge.LastParameter - edge.FirstParameter) / 2.0
- self.assertTrue(edge.valueAt(par).isEqual(newMids[i], 1e-6),
- "'{}' failed".format(operation))
+ self.assertTrue(
+ edge.valueAt(par).isEqual(newMids[i], 1e-6), "'{}' failed".format(operation)
+ )
def test_scale_part_feature_lines(self):
"""Create and scale a part feature (lines)."""
@@ -707,17 +707,23 @@ class DraftModification(test_base.DraftTestCaseDoc):
_msg(" Test '{}'".format(operation))
base = Vector(3.5, 2.5, 0.0)
- cen = Vector(2.0, 1.0, 0.0) # center for scaling
+ cen = Vector(2.0, 1.0, 0.0) # center for scaling
sca = Vector(2.0, 3.0, 1.0)
- pts = [Vector(0.0, 0.0, 0.0),
- Vector(4.0, 0.0, 0.0),
- Vector(4.0, 3.0, 0.0),
- Vector(0.0, 3.0, 0.0)]
+ pts = [
+ Vector(0.0, 0.0, 0.0),
+ Vector(4.0, 0.0, 0.0),
+ Vector(4.0, 3.0, 0.0),
+ Vector(0.0, 3.0, 0.0),
+ ]
- shp = Part.Shape([Part.LineSegment(pts[0], pts[1]),
- Part.LineSegment(pts[1], pts[2]),
- Part.LineSegment(pts[2], pts[3]),
- Part.LineSegment(pts[3], pts[0])])
+ shp = Part.Shape(
+ [
+ Part.LineSegment(pts[0], pts[1]),
+ Part.LineSegment(pts[1], pts[2]),
+ Part.LineSegment(pts[2], pts[3]),
+ Part.LineSegment(pts[3], pts[0]),
+ ]
+ )
obj = self.doc.addObject("Part::Feature")
obj.Shape = shp
obj.Placement.Base = base
@@ -725,14 +731,15 @@ class DraftModification(test_base.DraftTestCaseDoc):
obj = Draft.scale(obj, sca, cen, False)
self.doc.recompute()
- newPts = [Vector( 5.0, 5.5, 0.0),
- Vector(13.0, 5.5, 0.0),
- Vector(13.0, 14.5, 0.0),
- Vector( 5.0, 14.5, 0.0)]
+ newPts = [
+ Vector(5.0, 5.5, 0.0),
+ Vector(13.0, 5.5, 0.0),
+ Vector(13.0, 14.5, 0.0),
+ Vector(5.0, 14.5, 0.0),
+ ]
vrts = obj.Shape.Vertexes
for i in range(4):
- self.assertTrue(vrts[i].Point.isEqual(newPts[i], 1e-6),
- "'{}' failed".format(operation))
+ self.assertTrue(vrts[i].Point.isEqual(newPts[i], 1e-6), "'{}' failed".format(operation))
def test_scale_rectangle(self):
"""Create and scale a rectangle."""
@@ -740,7 +747,7 @@ class DraftModification(test_base.DraftTestCaseDoc):
_msg(" Test '{}'".format(operation))
base = Vector(3.5, 2.5, 0.0)
- cen = Vector(2.0, 1.0, 0.0) # center for scaling
+ cen = Vector(2.0, 1.0, 0.0) # center for scaling
sca = Vector(2.0, 3.0, 1.0)
len = 4.0
hgt = 3.0
@@ -754,16 +761,9 @@ class DraftModification(test_base.DraftTestCaseDoc):
newBase = Vector(5.0, 5.5, 0.0)
newLen = 8.0
newHgt = 9.0
- self.assertTrue(obj.Placement.Base.isEqual(newBase, 1e-6),
- "'{}' failed".format(operation))
- self.assertAlmostEqual(obj.Length,
- newLen,
- delta = 1e-6,
- msg = "'{}' failed".format(operation))
- self.assertAlmostEqual(obj.Height,
- newHgt,
- delta = 1e-6,
- msg = "'{}' failed".format(operation))
+ self.assertTrue(obj.Placement.Base.isEqual(newBase, 1e-6), "'{}' failed".format(operation))
+ self.assertAlmostEqual(obj.Length, newLen, delta=1e-6, msg="'{}' failed".format(operation))
+ self.assertAlmostEqual(obj.Height, newHgt, delta=1e-6, msg="'{}' failed".format(operation))
def test_scale_spline(self):
"""Create and scale a spline."""
@@ -771,11 +771,9 @@ class DraftModification(test_base.DraftTestCaseDoc):
_msg(" Test '{}'".format(operation))
base = Vector(3.5, 2.5, 0.0)
- cen = Vector(2.0, 1.0, 0.0) # center for scaling
+ cen = Vector(2.0, 1.0, 0.0) # center for scaling
sca = Vector(2.0, 3.0, 1.0)
- pts = [Vector(0.0, 0.0, 0.0),
- Vector(2.0, 3.0, 0.0),
- Vector(4.0, 0.0, 0.0)]
+ pts = [Vector(0.0, 0.0, 0.0), Vector(2.0, 3.0, 0.0), Vector(4.0, 0.0, 0.0)]
obj = Draft.make_bspline(pts, False)
obj.Placement.Base = base
@@ -784,12 +782,11 @@ class DraftModification(test_base.DraftTestCaseDoc):
self.doc.recompute()
pla = obj.Placement
- newPts = [Vector( 5.0, 5.5, 0.0),
- Vector( 9.0, 14.5, 0.0),
- Vector(13.0, 5.5, 0.0)]
+ newPts = [Vector(5.0, 5.5, 0.0), Vector(9.0, 14.5, 0.0), Vector(13.0, 5.5, 0.0)]
for i in range(3):
- self.assertTrue(pla.multVec(obj.Points[i]).isEqual(newPts[i], 1e-6),
- "'{}' failed".format(operation))
+ self.assertTrue(
+ pla.multVec(obj.Points[i]).isEqual(newPts[i], 1e-6), "'{}' failed".format(operation)
+ )
def test_scale_wire(self):
"""Create and scale a wire."""
@@ -797,12 +794,14 @@ class DraftModification(test_base.DraftTestCaseDoc):
_msg(" Test '{}'".format(operation))
base = Vector(3.5, 2.5, 0.0)
- cen = Vector(2.0, 1.0, 0.0) # center for scaling
+ cen = Vector(2.0, 1.0, 0.0) # center for scaling
sca = Vector(2.0, 3.0, 1.0)
- pts = [Vector(0.0, 0.0, 0.0),
- Vector(4.0, 0.0, 0.0),
- Vector(4.0, 3.0, 0.0),
- Vector(0.0, 3.0, 0.0)]
+ pts = [
+ Vector(0.0, 0.0, 0.0),
+ Vector(4.0, 0.0, 0.0),
+ Vector(4.0, 3.0, 0.0),
+ Vector(0.0, 3.0, 0.0),
+ ]
obj = Draft.make_wire(pts, True)
obj.Placement.Base = base
@@ -810,13 +809,15 @@ class DraftModification(test_base.DraftTestCaseDoc):
obj = Draft.scale(obj, sca, cen, False)
self.doc.recompute()
- newPts = [Vector( 5.0, 5.5, 0.0),
- Vector(13.0, 5.5, 0.0),
- Vector(13.0, 14.5, 0.0),
- Vector( 5.0, 14.5, 0.0)]
+ newPts = [
+ Vector(5.0, 5.5, 0.0),
+ Vector(13.0, 5.5, 0.0),
+ Vector(13.0, 14.5, 0.0),
+ Vector(5.0, 14.5, 0.0),
+ ]
vrts = obj.Shape.Vertexes
for i in range(4):
- self.assertTrue(vrts[i].Point.isEqual(newPts[i], 1e-6),
- "'{}' failed".format(operation))
+ self.assertTrue(vrts[i].Point.isEqual(newPts[i], 1e-6), "'{}' failed".format(operation))
+
## @}
diff --git a/src/Mod/Draft/drafttests/test_oca.py b/src/Mod/Draft/drafttests/test_oca.py
index 4595e9e306..1964e44d39 100644
--- a/src/Mod/Draft/drafttests/test_oca.py
+++ b/src/Mod/Draft/drafttests/test_oca.py
@@ -71,4 +71,5 @@ class DraftOCA(test_base.DraftTestCaseDoc):
obj = aux.fake_function(out_file)
self.assertTrue(obj, "'{}' failed".format(operation))
+
## @}
diff --git a/src/Mod/Draft/drafttests/test_pivy.py b/src/Mod/Draft/drafttests/test_pivy.py
index 8adcf3bd10..1b9f89c0d1 100644
--- a/src/Mod/Draft/drafttests/test_pivy.py
+++ b/src/Mod/Draft/drafttests/test_pivy.py
@@ -50,10 +50,12 @@ class DraftPivy(test_base.DraftTestCaseDoc):
def test_pivy_draw(self):
"""Use Coin (pivy.coin) to draw a cube on the active view."""
import pivy.coin as coin
+
cube = coin.SoCube()
_msg(" Draw cube")
Gui.getDocument(self.doc).ActiveView.getSceneGraph().addChild(cube)
_msg(" Adding cube to the active view scene")
self.assertTrue(cube, "Pivy is not working properly.")
+
## @}
diff --git a/src/Mod/Draft/drafttests/test_svg.py b/src/Mod/Draft/drafttests/test_svg.py
index 49c890315a..c8e218b509 100644
--- a/src/Mod/Draft/drafttests/test_svg.py
+++ b/src/Mod/Draft/drafttests/test_svg.py
@@ -100,4 +100,5 @@ class DraftSVG(test_base.DraftTestCaseDoc):
else:
self.fail("no exception thrown")
+
## @}
diff --git a/src/Mod/Draft/draftutils/grid_observer.py b/src/Mod/Draft/draftutils/grid_observer.py
index b873810393..5a55ec3b99 100644
--- a/src/Mod/Draft/draftutils/grid_observer.py
+++ b/src/Mod/Draft/draftutils/grid_observer.py
@@ -20,8 +20,7 @@
# * USA *
# * *
# ***************************************************************************
-"""Provide the grid observer for the Draft and BIM workbenches.
-"""
+"""Provide the grid observer for the Draft and BIM workbenches."""
import FreeCAD
diff --git a/src/Mod/Draft/draftutils/groups.py b/src/Mod/Draft/draftutils/groups.py
index 38615ab813..2393bd4e3b 100644
--- a/src/Mod/Draft/draftutils/groups.py
+++ b/src/Mod/Draft/draftutils/groups.py
@@ -63,10 +63,14 @@ def is_group(obj):
Otherwise returns `False`.
"""
typ = utils.get_type(obj)
- return ((obj.isDerivedFrom("App::DocumentObjectGroup")
- and typ != "LayerContainer")
- or typ in ("Project", "Site", "Building",
- "Floor", "BuildingPart", "Space"))
+ return (obj.isDerivedFrom("App::DocumentObjectGroup") and typ != "LayerContainer") or typ in (
+ "Project",
+ "Site",
+ "Building",
+ "Floor",
+ "BuildingPart",
+ "Space",
+ )
def get_group_names(doc=None):
@@ -171,26 +175,23 @@ def get_windows(obj):
for o in obj.OutList:
out.extend(get_windows(o))
for i in obj.InList:
- if (utils.get_type(i.getLinkedObject()) == "Window"
- or utils.is_clone(obj, "Window")):
+ if utils.get_type(i.getLinkedObject()) == "Window" or utils.is_clone(obj, "Window"):
if hasattr(i, "Hosts"):
if obj in i.Hosts:
out.append(i)
- elif (utils.get_type(i) == "Rebar"
- or utils.is_clone(obj, "Rebar")):
+ elif utils.get_type(i) == "Rebar" or utils.is_clone(obj, "Rebar"):
if hasattr(i, "Host"):
if obj == i.Host:
out.append(i)
- elif (utils.get_type(obj.getLinkedObject()) in ("Window", "Rebar")
- or utils.is_clone(obj, ["Window", "Rebar"])):
+ elif utils.get_type(obj.getLinkedObject()) in ("Window", "Rebar") or utils.is_clone(
+ obj, ["Window", "Rebar"]
+ ):
out.append(obj)
return out
-def get_group_contents(objectslist,
- walls=False, addgroups=False,
- spaces=False, noarchchild=False):
+def get_group_contents(objectslist, walls=False, addgroups=False, spaces=False, noarchchild=False):
"""Return a list of objects from expanding the input groups.
The function accepts any type of object, although it is most useful
@@ -239,15 +240,12 @@ def get_group_contents(objectslist,
for obj in objectslist:
if obj:
if is_group(obj):
- if addgroups or (spaces
- and utils.get_type(obj) == "Space"):
+ if addgroups or (spaces and utils.get_type(obj) == "Space"):
newlist.append(obj)
- if not (noarchchild
- and utils.get_type(obj) in ("Building",
- "BuildingPart")):
- newlist.extend(get_group_contents(obj.Group,
- walls, addgroups,
- spaces, noarchchild))
+ if not (noarchchild and utils.get_type(obj) in ("Building", "BuildingPart")):
+ newlist.extend(
+ get_group_contents(obj.Group, walls, addgroups, spaces, noarchchild)
+ )
else:
# print("adding ", obj.Name)
newlist.append(obj)
@@ -263,15 +261,11 @@ def get_group_contents(objectslist,
return cleanlist
-def getGroupContents(objectslist,
- walls=False, addgroups=False,
- spaces=False, noarchchild=False):
+def getGroupContents(objectslist, walls=False, addgroups=False, spaces=False, noarchchild=False):
"""Return a list of objects from groups. DEPRECATED."""
utils.use_instead("get_group_contents")
- return get_group_contents(objectslist,
- walls, addgroups,
- spaces, noarchchild)
+ return get_group_contents(objectslist, walls, addgroups, spaces, noarchchild)
def get_movable_children(objectslist, recursive=True, _donelist=[]):
@@ -313,19 +307,28 @@ def get_movable_children(objectslist, recursive=True, _donelist=[]):
_donelist.append(obj.Name)
# Skips some objects that should never move their children
- if utils.get_type(obj) not in ("App::Part", "PartDesign::Body",
- "Clone", "SectionPlane",
- "Facebinder", "BuildingPart", "App::Link"):
+ if utils.get_type(obj) not in (
+ "App::Part",
+ "PartDesign::Body",
+ "Clone",
+ "SectionPlane",
+ "Facebinder",
+ "BuildingPart",
+ "App::Link",
+ ):
children = obj.OutList
- if (hasattr(obj, "Proxy") and obj.Proxy
- and hasattr(obj.Proxy, "getSiblings")
- and utils.get_type(obj) != "Window"):
+ if (
+ hasattr(obj, "Proxy")
+ and obj.Proxy
+ and hasattr(obj.Proxy, "getSiblings")
+ and utils.get_type(obj) != "Window"
+ ):
# children.extend(obj.Proxy.getSiblings(obj))
pass
for child in children:
if hasattr(child, "MoveWithHost") and child.MoveWithHost:
- if hasattr(obj, "CloneOf") and obj.CloneOf:
+ if hasattr(obj, "CloneOf") and obj.CloneOf:
if obj.CloneOf.Name != child.Name:
added.append(child)
else:
@@ -342,4 +345,5 @@ def getMovableChildren(objectslist, recursive=True):
utils.use_instead("get_movable_children")
return get_movable_children(objectslist, recursive)
+
## @}
diff --git a/src/Mod/Draft/draftutils/gui_utils.py b/src/Mod/Draft/draftutils/gui_utils.py
index 34137815fb..6c0c13b897 100644
--- a/src/Mod/Draft/draftutils/gui_utils.py
+++ b/src/Mod/Draft/draftutils/gui_utils.py
@@ -51,6 +51,7 @@ if App.GuiUp:
from pivy import coin
from PySide import QtCore
from PySide import QtGui
+
# from PySide import QtSvg # for load_texture
@@ -105,9 +106,9 @@ def autogroup(obj):
# check for required conditions for autogroup to work
if not App.GuiUp:
return
- if not hasattr(Gui,"draftToolBar"):
+ if not hasattr(Gui, "draftToolBar"):
return
- if not hasattr(Gui.draftToolBar,"autogroup"):
+ if not hasattr(Gui.draftToolBar, "autogroup"):
return
if Gui.draftToolBar.isConstructionMode():
return
@@ -115,8 +116,8 @@ def autogroup(obj):
# check first for objects that do autogroup themselves
# at the moment only Arch_BuildingPart, which is an App::GeometryPython
for par in App.ActiveDocument.findObjects(Type="App::GeometryPython"):
- if hasattr(par.Proxy,"autogroup"):
- if par.Proxy.autogroup(par,obj):
+ if hasattr(par.Proxy, "autogroup"):
+ if par.Proxy.autogroup(par, obj):
return
# autogroup code
@@ -135,6 +136,7 @@ def autogroup(obj):
# NativeIFC handling
try:
from nativeifc import ifc_tools
+
parent = Gui.ActiveDocument.ActiveView.getActiveObject("NativeIFC")
ifc_tools.aggregate(obj, parent)
except:
@@ -158,13 +160,11 @@ def autogroup(obj):
return
matrix = parent.getSubObject(sub, retType=4)
if matrix.hasScale() == App.ScaleType.Uniform:
- err = translate("draft",
- "Unable to insert new object into "
- "a scaled part")
+ err = translate("draft", "Unable to insert new object into " "a scaled part")
App.Console.PrintMessage(err)
return
inverse_placement = App.Placement(matrix.inverse())
- if utils.get_type(obj) == 'Point':
+ if utils.get_type(obj) == "Point":
point_vector = App.Vector(obj.X, obj.Y, obj.Z)
real_point = inverse_placement.multVec(point_vector)
obj.X = real_point.x
@@ -179,7 +179,7 @@ def autogroup(obj):
elif utils.get_type(obj) in ["Label"]:
obj.Placement = App.Placement(inverse_placement.multiply(obj.Placement))
obj.TargetPoint = inverse_placement.multVec(obj.TargetPoint)
- elif hasattr(obj,"Placement"):
+ elif hasattr(obj, "Placement"):
# every object that have a placement is processed here
obj.Placement = App.Placement(inverse_placement.multiply(obj.Placement))
@@ -244,9 +244,9 @@ def dim_symbol(symbol=None, invert=False):
t.translation.setValue((0, -2, 0))
t.center.setValue((0, 2, 0))
if invert:
- t.rotation.setValue(coin.SbVec3f((0, 0, 1)), -math.pi/2)
+ t.rotation.setValue(coin.SbVec3f((0, 0, 1)), -math.pi / 2)
else:
- t.rotation.setValue(coin.SbVec3f((0, 0, 1)), math.pi/2)
+ t.rotation.setValue(coin.SbVec3f((0, 0, 1)), math.pi / 2)
c = coin.SoCone()
c.height.setValue(4)
marker.addChild(t)
@@ -258,8 +258,7 @@ def dim_symbol(symbol=None, invert=False):
h = coin.SoShapeHints()
h.vertexOrdering = h.COUNTERCLOCKWISE
c = coin.SoCoordinate3()
- c.point.setValues([(-1, -2, 0), (0, 2, 0),
- (1, 2, 0), (0, -2, 0)])
+ c.point.setValues([(-1, -2, 0), (0, 2, 0), (1, 2, 0), (0, -2, 0)])
f = coin.SoFaceSet()
marker.addChild(h)
marker.addChild(c)
@@ -359,6 +358,7 @@ def get_diffuse_color(objs):
list of tuples
The list will be empty if no valid object is found.
"""
+
def _get_color(obj):
if hasattr(obj, "ColoredElements"):
if hasattr(obj, "Count") or hasattr(obj, "ElementCount"):
@@ -376,7 +376,9 @@ def get_diffuse_color(objs):
return cols
face_num = len(base.Shape.Faces)
for elm, override in zip(obj.ColoredElements[1], obj.ViewObject.OverrideColorList):
- if "Face" in elm: # Examples: "Face3" and "1.Face6". Int before "." is zero-based, other int is 1-based.
+ if (
+ "Face" in elm
+ ): # Examples: "Face3" and "1.Face6". Int before "." is zero-based, other int is 1-based.
if "." in elm:
elm0, elm1 = elm.split(".")
i = (int(elm0) * face_num) + int(elm1[4:]) - 1
@@ -394,9 +396,11 @@ def get_diffuse_color(objs):
if obj.ColoredElements is None:
cols += sub_cols
else:
- for elm, override in zip(obj.ColoredElements[1], obj.ViewObject.OverrideColorList):
+ for elm, override in zip(
+ obj.ColoredElements[1], obj.ViewObject.OverrideColorList
+ ):
if sub.Name + ".Face" in elm:
- i = int(elm[(len(sub.Name) + 5):]) - 1
+ i = int(elm[(len(sub.Name) + 5) :]) - 1
sub_cols[i] = override
cols += sub_cols
return cols
@@ -420,10 +424,14 @@ def get_diffuse_color(objs):
if not isinstance(objs, list):
# Quick check to avoid processing a single object:
obj = objs
- if not hasattr(obj, "ColoredElements") \
- and hasattr(obj.ViewObject, "DiffuseColor") \
- and (len(obj.ViewObject.DiffuseColor) == 1 \
- or len(obj.ViewObject.DiffuseColor) == len(obj.Shape.Faces)):
+ if (
+ not hasattr(obj, "ColoredElements")
+ and hasattr(obj.ViewObject, "DiffuseColor")
+ and (
+ len(obj.ViewObject.DiffuseColor) == 1
+ or len(obj.ViewObject.DiffuseColor) == len(obj.Shape.Faces)
+ )
+ ):
return obj.ViewObject.DiffuseColor
# Create a list for further processing:
objs = [objs]
@@ -454,7 +462,7 @@ def apply_current_style(objs):
anno_style = utils.get_default_annotation_style()
shape_style = utils.get_default_shape_style()
for obj in objs:
- if not hasattr(obj, 'ViewObject'):
+ if not hasattr(obj, "ViewObject"):
continue
vobj = obj.ViewObject
props = vobj.PropertiesList
@@ -554,7 +562,7 @@ def format_object(target, origin=None, ignore_construction=False):
val = getattr(matchrep, p)
if isinstance(val, tuple):
if len(val) != len_faces:
- val = (val[0], )
+ val = (val[0],)
elif hasattr(val, "Value"):
val = val.Value
try:
@@ -778,11 +786,14 @@ def load_texture(filename, size=None, gui=App.GuiUp):
_wrn("load_texture: " + translate("draft", "image is Null"))
if not os.path.exists(filename):
- raise FileNotFoundError(-1,
- translate("draft", "filename does not exist "
- "on the system or "
- "in the resource file"),
- filename)
+ raise FileNotFoundError(
+ -1,
+ translate(
+ "draft",
+ "filename does not exist " "on the system or " "in the resource file",
+ ),
+ filename,
+ )
# This is buggy so it was de-activated.
#
@@ -835,8 +846,7 @@ def load_texture(filename, size=None, gui=App.GuiUp):
_bytes = bytes(byteList)
img.setValue(size, numcomponents, _bytes)
except FileNotFoundError as exc:
- _wrn("load_texture: {0}, {1}".format(exc.strerror,
- exc.filename))
+ _wrn("load_texture: {0}, {1}".format(exc.strerror, exc.filename))
return None
except Exception as exc:
_wrn(str(exc))
@@ -902,9 +912,11 @@ def get_bbox(obj, debug=False):
_err(translate("draft", "Wrong input: object {} not in document.").format(obj_str))
return None
- if (not hasattr(obj, "ViewObject")
- or not obj.ViewObject
- or not hasattr(obj.ViewObject, "RootNode")):
+ if (
+ not hasattr(obj, "ViewObject")
+ or not obj.ViewObject
+ or not hasattr(obj.ViewObject, "RootNode")
+ ):
_err(translate("draft", "Does not have 'ViewObject.RootNode'."))
# For Draft Dimensions
@@ -941,21 +953,27 @@ def end_all_events():
if view is None:
return
if view.getNavigationType() in (
- "Gui::GestureNavigationStyle", "Gui::MayaGestureNavigationStyle"
+ "Gui::GestureNavigationStyle",
+ "Gui::MayaGestureNavigationStyle",
):
return
class DelayEnder:
def __init__(self):
self.delay_is_done = False
+
def stop(self):
self.delay_is_done = True
+
ender = DelayEnder()
timer = QtCore.QTimer()
timer.timeout.connect(ender.stop)
timer.setSingleShot(True)
- timer.start(100) # 100ms (50ms is too short) timer guarantees the loop below runs at least that long
+ timer.start(
+ 100
+ ) # 100ms (50ms is too short) timer guarantees the loop below runs at least that long
while not ender.delay_is_done:
QtCore.QCoreApplication.processEvents(QtCore.QEventLoop.AllEvents)
+
## @}
diff --git a/src/Mod/Draft/draftutils/init_draft_statusbar.py b/src/Mod/Draft/draftutils/init_draft_statusbar.py
index a7c0c85e17..79a47e760b 100644
--- a/src/Mod/Draft/draftutils/init_draft_statusbar.py
+++ b/src/Mod/Draft/draftutils/init_draft_statusbar.py
@@ -41,32 +41,61 @@ from draftutils import params
from draftutils.init_tools import get_draft_snap_commands
from draftutils.translate import translate
-#----------------------------------------------------------------------------
+# ----------------------------------------------------------------------------
# SCALE WIDGET FUNCTIONS
-#----------------------------------------------------------------------------
+# ----------------------------------------------------------------------------
-draft_scales_metrics = ["1:1000", "1:500", "1:250", "1:200", "1:100",
- "1:50", "1:25","1:20", "1:10", "1:5","1:2",
- "1:1",
- "2:1", "5:1", "10:1", "20:1",
- translate("draft", "Custom"),
- ]
+draft_scales_metrics = [
+ "1:1000",
+ "1:500",
+ "1:250",
+ "1:200",
+ "1:100",
+ "1:50",
+ "1:25",
+ "1:20",
+ "1:10",
+ "1:5",
+ "1:2",
+ "1:1",
+ "2:1",
+ "5:1",
+ "10:1",
+ "20:1",
+ translate("draft", "Custom"),
+]
-draft_scales_arch_imperial = ["1/16in=1ft", "3/32in=1ft", "1/8in=1ft",
- "3/16in=1ft", "1/4in=1ft","3/8in=1ft",
- "1/2in=1ft", "3/4in=1ft", "1in=1ft",
- "1.5in=1ft", "3in=1ft",
- translate("draft", "Custom"),
- ]
+draft_scales_arch_imperial = [
+ "1/16in=1ft",
+ "3/32in=1ft",
+ "1/8in=1ft",
+ "3/16in=1ft",
+ "1/4in=1ft",
+ "3/8in=1ft",
+ "1/2in=1ft",
+ "3/4in=1ft",
+ "1in=1ft",
+ "1.5in=1ft",
+ "3in=1ft",
+ translate("draft", "Custom"),
+]
-draft_scales_eng_imperial = ["1in=10ft", "1in=20ft", "1in=30ft",
- "1in=40ft", "1in=50ft", "1in=60ft",
- "1in=70ft", "1in=80ft", "1in=90ft",
- "1in=100ft",
- translate("draft", "Custom"),
- ]
+draft_scales_eng_imperial = [
+ "1in=10ft",
+ "1in=20ft",
+ "1in=30ft",
+ "1in=40ft",
+ "1in=50ft",
+ "1in=60ft",
+ "1in=70ft",
+ "1in=80ft",
+ "1in=90ft",
+ "1in=100ft",
+ translate("draft", "Custom"),
+]
-def get_scales(unit_system = 0):
+
+def get_scales(unit_system=0):
"""
returns the list of preset scales according to unit system.
@@ -107,17 +136,18 @@ def scale_to_label(scale):
if f[1] == 1:
return str(f[0]) + ":1"
return str(scale)
- f = round(1/scale, 2)
+ f = round(1 / scale, 2)
f = f.as_integer_ratio()
if f[1] == 1:
return "1:" + str(f[0])
return str(scale)
+
def label_to_scale(label):
"""
transform a scale string into scale factor as float
"""
- try :
+ try:
scale = float(label)
return scale
except Exception:
@@ -131,14 +161,14 @@ def label_to_scale(label):
try:
num = App.Units.Quantity(f[0]).Value
den = App.Units.Quantity(f[1]).Value
- scale = num/den
+ scale = num / den
return scale
except Exception:
- err = translate("draft",
- "Unable to convert input into a scale factor")
+ err = translate("draft", "Unable to convert input into a scale factor")
App.Console.PrintWarning(err)
return None
+
def _set_scale(action):
"""
triggered by scale pushbutton, set DefaultAnnoScaleMultiplier in preferences
@@ -146,12 +176,11 @@ def _set_scale(action):
mw = Gui.getMainWindow()
sb = mw.statusBar()
- scale_widget = sb.findChild(QtWidgets.QToolBar,"draft_scale_widget")
+ scale_widget = sb.findChild(QtWidgets.QToolBar, "draft_scale_widget")
if action.text() == translate("draft", "Custom"):
title_text = translate("draft", "Set Custom Scale")
- dialog_text = translate("draft",
- "Set custom annotation scale in format x:x, x=x")
+ dialog_text = translate("draft", "Set custom annotation scale in format x:x, x=x")
custom_scale = QtWidgets.QInputDialog.getText(None, title_text, dialog_text)
if custom_scale[1]:
print(custom_scale[0])
@@ -169,9 +198,11 @@ def _set_scale(action):
scale = label_to_scale(text_scale)
params.set_param("DefaultAnnoScaleMultiplier", 1 / scale)
-#----------------------------------------------------------------------------
+
+# ----------------------------------------------------------------------------
# MAIN DRAFT STATUSBAR FUNCTIONS
-#----------------------------------------------------------------------------
+# ----------------------------------------------------------------------------
+
def init_draft_statusbar_scale():
"""
@@ -184,8 +215,11 @@ def init_draft_statusbar_scale():
# prevent the widget from showing up in the toolbar area context menu:
scale_widget.toggleViewAction().setVisible(False)
scale_widget.setObjectName("draft_scale_widget")
- text = translate("draft", "Draft Scale Widget",
- "A context menu action used to show or hide this toolbar widget")
+ text = translate(
+ "draft",
+ "Draft Scale Widget",
+ "A context menu action used to show or hide this toolbar widget",
+ )
scale_widget.setWindowTitle(text)
# get scales list according to system units
@@ -210,8 +244,7 @@ def init_draft_statusbar_scale():
gUnits.triggered.connect(_set_scale)
scale_label = scale_to_label(annotation_scale)
scaleLabel.setText(scale_label)
- scaleLabel.setToolTip(translate("draft",
- "Set the scale used by Draft annotation tools"))
+ scaleLabel.setToolTip(translate("draft", "Set the scale used by Draft annotation tools"))
scale_widget.addWidget(scaleLabel)
scale_widget.scaleLabel = scaleLabel
@@ -246,8 +279,11 @@ def init_draft_statusbar_snap():
# prevent the widget from showing up in the toolbar area context menu:
snap_widget.toggleViewAction().setVisible(False)
snap_widget.setObjectName("draft_snap_widget")
- text = translate("draft", "Draft Snap Widget",
- "A context menu action used to show or hide this toolbar widget")
+ text = translate(
+ "draft",
+ "Draft Snap Widget",
+ "A context menu action used to show or hide this toolbar widget",
+ )
snap_widget.setWindowTitle(text)
snap_widget.setOrientation(QtCore.Qt.Orientation.Horizontal)
snap_widget.setIconSize(QtCore.QSize(16, 16))
@@ -261,7 +297,7 @@ def init_draft_statusbar_snap():
# lock button:
snap_widget.addAction(Gui.Command.get("Draft_Snap_Lock").getAction()[0])
snap_action = snap_widget.children()[-1]
- snap_action.setFixedWidth(40) # Widen the button.
+ snap_action.setFixedWidth(40) # Widen the button.
snap_widget.addWidget(_spacer())
@@ -280,12 +316,14 @@ def init_draft_statusbar_snap():
# menu for lock button:
for cmd in get_draft_snap_commands():
- if cmd not in ["Separator",
- "Draft_ToggleGrid",
- "Draft_Snap_Lock", # Is automatically added to the menu anyway.
- "Draft_Snap_Dimensions",
- "Draft_Snap_Ortho",
- "Draft_Snap_WorkingPlane"]:
+ if cmd not in [
+ "Separator",
+ "Draft_ToggleGrid",
+ "Draft_Snap_Lock", # Is automatically added to the menu anyway.
+ "Draft_Snap_Dimensions",
+ "Draft_Snap_Ortho",
+ "Draft_Snap_WorkingPlane",
+ ]:
snap_action.addAction(Gui.Command.get(cmd).getAction()[0])
@@ -352,11 +390,11 @@ def hide_draft_statusbar_snap():
mw = Gui.getMainWindow()
sb = mw.statusBar()
- snap_widget = sb.findChild(QtWidgets.QToolBar,"draft_snap_widget")
+ snap_widget = sb.findChild(QtWidgets.QToolBar, "draft_snap_widget")
if snap_widget is None:
# when switching workbenches, the toolbar sometimes "jumps"
# out of the status bar to any other dock area...
- snap_widget = mw.findChild(QtWidgets.QToolBar,"draft_snap_widget")
+ snap_widget = mw.findChild(QtWidgets.QToolBar, "draft_snap_widget")
if snap_widget:
snap_widget.hide()
@@ -380,4 +418,5 @@ def hide_draft_statusbar():
QtCore.QTimer().singleShot(500, hide_draft_statusbar_scale)
QtCore.QTimer().singleShot(500, hide_draft_statusbar_snap)
+
## @}
diff --git a/src/Mod/Draft/draftutils/init_tools.py b/src/Mod/Draft/draftutils/init_tools.py
index 62762e6f5b..bb24bb595a 100644
--- a/src/Mod/Draft/draftutils/init_tools.py
+++ b/src/Mod/Draft/draftutils/init_tools.py
@@ -41,150 +41,164 @@ def get_draft_drawing_commands():
"""Return the drawing commands list."""
from draftguitools import gui_arcs
from draftguitools import gui_beziers
+
arc_group = gui_arcs.ArcGroup
bez_group = gui_beziers.BezierGroup
- return ["Draft_Line",
- "Draft_Wire",
- "Draft_Fillet",
- ([QT_TRANSLATE_NOOP("Workbench", "Arc Tools")],
- list(arc_group.GetCommands(arc_group))), # tuple len=2: submenu
- ("Draft_ArcTools", ), # tuple len=1: toolbar flyout
- "Draft_Circle",
- "Draft_Ellipse",
- "Draft_Rectangle",
- "Draft_Polygon",
- "Draft_BSpline",
- ([QT_TRANSLATE_NOOP("Workbench", "Bézier Tools")],
- list(bez_group.GetCommands(bez_group))),
- ("Draft_BezierTools", ),
- "Draft_Point",
- "Draft_Facebinder",
- "Draft_ShapeString",
- "Draft_Hatch"]
+ return [
+ "Draft_Line",
+ "Draft_Wire",
+ "Draft_Fillet",
+ (
+ [QT_TRANSLATE_NOOP("Workbench", "Arc Tools")],
+ list(arc_group.GetCommands(arc_group)),
+ ), # tuple len=2: submenu
+ ("Draft_ArcTools",), # tuple len=1: toolbar flyout
+ "Draft_Circle",
+ "Draft_Ellipse",
+ "Draft_Rectangle",
+ "Draft_Polygon",
+ "Draft_BSpline",
+ ([QT_TRANSLATE_NOOP("Workbench", "Bézier Tools")], list(bez_group.GetCommands(bez_group))),
+ ("Draft_BezierTools",),
+ "Draft_Point",
+ "Draft_Facebinder",
+ "Draft_ShapeString",
+ "Draft_Hatch",
+ ]
def get_draft_annotation_commands():
"""Return the annotation commands list."""
- return ["Draft_Text",
- "Draft_Dimension",
- "Draft_Label",
- "Draft_AnnotationStyleEditor"]
+ return ["Draft_Text", "Draft_Dimension", "Draft_Label", "Draft_AnnotationStyleEditor"]
def get_draft_modification_commands():
"""Return the modification commands list."""
from draftguitools import gui_arrays
+
arr_group = gui_arrays.ArrayGroup
- return ["Draft_Move",
- "Draft_Rotate",
- "Draft_Scale",
- "Draft_Mirror",
- "Draft_Offset",
- "Draft_Trimex",
- "Draft_Stretch",
- "Separator",
- "Draft_Clone",
- ([QT_TRANSLATE_NOOP("Workbench", "Array Tools")],
- list(arr_group.GetCommands(arr_group))), # tuple len=2: submenu
- ("Draft_ArrayTools", ), # tuple len=1: toolbar flyout
- "Separator",
- "Draft_Edit",
- "Draft_SubelementHighlight",
- "Separator",
- "Draft_Join",
- "Draft_Split",
- "Draft_Upgrade",
- "Draft_Downgrade",
- "Separator",
- "Draft_WireToBSpline",
- "Draft_Draft2Sketch",
- "Draft_Slope",
- "Draft_FlipDimension",
- "Separator",
- "Draft_Shape2DView"]
+ return [
+ "Draft_Move",
+ "Draft_Rotate",
+ "Draft_Scale",
+ "Draft_Mirror",
+ "Draft_Offset",
+ "Draft_Trimex",
+ "Draft_Stretch",
+ "Separator",
+ "Draft_Clone",
+ (
+ [QT_TRANSLATE_NOOP("Workbench", "Array Tools")],
+ list(arr_group.GetCommands(arr_group)),
+ ), # tuple len=2: submenu
+ ("Draft_ArrayTools",), # tuple len=1: toolbar flyout
+ "Separator",
+ "Draft_Edit",
+ "Draft_SubelementHighlight",
+ "Separator",
+ "Draft_Join",
+ "Draft_Split",
+ "Draft_Upgrade",
+ "Draft_Downgrade",
+ "Separator",
+ "Draft_WireToBSpline",
+ "Draft_Draft2Sketch",
+ "Draft_Slope",
+ "Draft_FlipDimension",
+ "Separator",
+ "Draft_Shape2DView",
+ ]
def get_draft_utility_commands_menu():
"""Return the utility commands list for the menu."""
- return ["Draft_SetStyle",
- "Draft_ApplyStyle",
- "Separator",
- "Draft_Layer",
- "Draft_LayerManager",
- "Draft_AddNamedGroup",
- "Draft_SelectGroup",
- "Draft_ToggleConstructionMode",
- "Separator",
- "Draft_AddToLayer",
- "Draft_AddToGroup",
- "Draft_AddConstruction",
- "Separator",
- "Draft_ToggleDisplayMode",
- "Draft_ToggleGrid",
- "Draft_SelectPlane",
- "Draft_WorkingPlaneProxy",
- "Separator",
- "Draft_Heal",
- "Draft_ShowSnapBar"]
+ return [
+ "Draft_SetStyle",
+ "Draft_ApplyStyle",
+ "Separator",
+ "Draft_Layer",
+ "Draft_LayerManager",
+ "Draft_AddNamedGroup",
+ "Draft_SelectGroup",
+ "Draft_ToggleConstructionMode",
+ "Separator",
+ "Draft_AddToLayer",
+ "Draft_AddToGroup",
+ "Draft_AddConstruction",
+ "Separator",
+ "Draft_ToggleDisplayMode",
+ "Draft_ToggleGrid",
+ "Draft_SelectPlane",
+ "Draft_WorkingPlaneProxy",
+ "Separator",
+ "Draft_Heal",
+ "Draft_ShowSnapBar",
+ ]
def get_draft_utility_commands_toolbar():
"""Return the utility commands list for the toolbar."""
- return ["Draft_LayerManager",
- "Draft_AddNamedGroup",
- "Draft_SelectGroup",
- "Draft_AddToLayer",
- "Draft_AddToGroup",
- "Draft_AddConstruction",
- "Draft_ToggleDisplayMode",
- "Draft_WorkingPlaneProxy"]
+ return [
+ "Draft_LayerManager",
+ "Draft_AddNamedGroup",
+ "Draft_SelectGroup",
+ "Draft_AddToLayer",
+ "Draft_AddToGroup",
+ "Draft_AddConstruction",
+ "Draft_ToggleDisplayMode",
+ "Draft_WorkingPlaneProxy",
+ ]
def get_draft_snap_commands():
"""Return the snapping commands list."""
- return ["Draft_Snap_Lock",
- "Draft_Snap_Endpoint",
- "Draft_Snap_Midpoint",
- "Draft_Snap_Center",
- "Draft_Snap_Angle",
- "Draft_Snap_Intersection",
- "Draft_Snap_Perpendicular",
- "Draft_Snap_Extension",
- "Draft_Snap_Parallel",
- "Draft_Snap_Special",
- "Draft_Snap_Near",
- "Draft_Snap_Ortho",
- "Draft_Snap_Grid",
- "Draft_Snap_WorkingPlane",
- "Draft_Snap_Dimensions",
- # "Separator", # Removed: if the Python generated BIM snap toolbar
- # is displayed in the Draft WB the separator appears
- # after the last button. Can be reinstated when the
- # BIM WB has a `normal` snap toolbar as well.
- "Draft_ToggleGrid"]
+ return [
+ "Draft_Snap_Lock",
+ "Draft_Snap_Endpoint",
+ "Draft_Snap_Midpoint",
+ "Draft_Snap_Center",
+ "Draft_Snap_Angle",
+ "Draft_Snap_Intersection",
+ "Draft_Snap_Perpendicular",
+ "Draft_Snap_Extension",
+ "Draft_Snap_Parallel",
+ "Draft_Snap_Special",
+ "Draft_Snap_Near",
+ "Draft_Snap_Ortho",
+ "Draft_Snap_Grid",
+ "Draft_Snap_WorkingPlane",
+ "Draft_Snap_Dimensions",
+ # "Separator", # Removed: if the Python generated BIM snap toolbar
+ # is displayed in the Draft WB the separator appears
+ # after the last button. Can be reinstated when the
+ # BIM WB has a `normal` snap toolbar as well.
+ "Draft_ToggleGrid",
+ ]
def get_draft_context_commands():
"""Return the context menu commands list."""
- return ["Draft_SetStyle",
- "Draft_ApplyStyle",
- "Separator",
- "Draft_Layer",
- "Draft_LayerManager",
- "Draft_AddNamedGroup",
- "Draft_SelectGroup",
- "Draft_ToggleConstructionMode",
- "Separator",
- "Draft_AddToLayer",
- "Draft_AddToGroup",
- "Draft_AddConstruction",
- "Separator",
- "Draft_ToggleDisplayMode",
- "Draft_ToggleGrid",
- "Draft_SelectPlane",
- "Draft_WorkingPlaneProxy"]
+ return [
+ "Draft_SetStyle",
+ "Draft_ApplyStyle",
+ "Separator",
+ "Draft_Layer",
+ "Draft_LayerManager",
+ "Draft_AddNamedGroup",
+ "Draft_SelectGroup",
+ "Draft_ToggleConstructionMode",
+ "Separator",
+ "Draft_AddToLayer",
+ "Draft_AddToGroup",
+ "Draft_AddConstruction",
+ "Separator",
+ "Draft_ToggleDisplayMode",
+ "Draft_ToggleGrid",
+ "Draft_SelectPlane",
+ "Draft_WorkingPlaneProxy",
+ ]
def init_toolbar(workbench, toolbar, cmd_list):
@@ -231,4 +245,5 @@ def init_menu(workbench, menu_list, cmd_list):
else:
workbench.appendMenu(menu_list, [cmd])
+
## @}
diff --git a/src/Mod/Draft/draftutils/messages.py b/src/Mod/Draft/draftutils/messages.py
index 37faa86bca..d0ce58be8c 100644
--- a/src/Mod/Draft/draftutils/messages.py
+++ b/src/Mod/Draft/draftutils/messages.py
@@ -56,10 +56,12 @@ def _log(text, end="\n"):
"""Write messages to the log file including the line ending."""
App.Console.PrintLog(text + end)
+
def _toolmsg(text, end="\n"):
"""Write messages to the console including the line ending,
only if ToolMessages pref setting is True"""
if params.get_param("ToolMessages"):
App.Console.PrintMessage(text + end)
+
## @}
diff --git a/src/Mod/Draft/draftutils/params.py b/src/Mod/Draft/draftutils/params.py
index cb5978f12f..208e895915 100644
--- a/src/Mod/Draft/draftutils/params.py
+++ b/src/Mod/Draft/draftutils/params.py
@@ -21,7 +21,7 @@
# * *
# ***************************************************************************
-""" Contains a parameter observer class and parameter related functions."""
+"""Contains a parameter observer class and parameter related functions."""
import os
import PySide.QtCore as QtCore
@@ -29,6 +29,7 @@ import xml.etree.ElementTree as ET
import FreeCAD as App
import Draft_rc
+
try:
import Arch_rc
except ModuleNotFoundError:
@@ -40,14 +41,23 @@ if App.GuiUp:
import FreeCADGui as Gui
from PySide import QtWidgets
+
class ParamObserverDraft:
def slotParamChanged(self, param_grp, typ, entry, value):
if entry == "textheight":
_param_observer_callback_tray()
return
- if entry in ("gridBorder", "gridShowHuman", "coloredGridAxes", "gridEvery",
- "gridSpacing", "gridSize", "gridTransparency", "gridColor"):
+ if entry in (
+ "gridBorder",
+ "gridShowHuman",
+ "coloredGridAxes",
+ "gridEvery",
+ "gridSpacing",
+ "gridSize",
+ "gridTransparency",
+ "gridColor",
+ ):
_param_observer_callback_grid()
return
if entry == "DefaultAnnoScaleMultiplier":
@@ -83,6 +93,7 @@ class ParamObserverView:
_param_observer_callback_snaptextsize()
return
+
def _param_observer_callback_tray():
if not hasattr(Gui, "draftToolBar"):
return
@@ -96,6 +107,7 @@ def _param_observer_callback_scalemultiplier(value):
# value is a string.
# import has to happen here to avoid circular imports
from draftutils import init_draft_statusbar
+
if not value:
return
value = float(value)
@@ -103,7 +115,7 @@ def _param_observer_callback_scalemultiplier(value):
return
mw = Gui.getMainWindow()
sb = mw.statusBar()
- scale_widget = sb.findChild(QtWidgets.QToolBar,"draft_scale_widget")
+ scale_widget = sb.findChild(QtWidgets.QToolBar, "draft_scale_widget")
if scale_widget is not None:
scale_label = init_draft_statusbar.scale_to_label(1 / value)
scale_widget.scaleLabel.setText(scale_label)
@@ -138,6 +150,7 @@ def _param_observer_callback_snapbar(value):
def _param_observer_callback_snapwidget():
# import has to happen here to avoid circular imports
from draftutils import init_draft_statusbar
+
if Gui.activeWorkbench().name() == "DraftWorkbench":
init_draft_statusbar.hide_draft_statusbar()
init_draft_statusbar.show_draft_statusbar()
@@ -146,6 +159,7 @@ def _param_observer_callback_snapwidget():
def _param_observer_callback_scalewidget():
# import has to happen here to avoid circular imports
from draftutils import init_draft_statusbar
+
if Gui.activeWorkbench().name() == "DraftWorkbench":
init_draft_statusbar.hide_draft_statusbar()
init_draft_statusbar.show_draft_statusbar()
@@ -176,6 +190,7 @@ def _param_observer_callback_svg_pattern():
# imports have to happen here to avoid circular imports
from draftutils import utils
from draftviewproviders import view_base
+
utils.load_svg_patterns()
if App.ActiveDocument is None:
return
@@ -190,22 +205,30 @@ def _param_observer_callback_svg_pattern():
for obj in doc.Objects:
if hasattr(obj, "ViewObject"):
vobj = obj.ViewObject
- if hasattr(vobj, "Pattern") \
- and hasattr(vobj, "Proxy") \
- and isinstance(vobj.Proxy, view_base.ViewProviderDraft) \
- and vobj.getEnumerationsOfProperty("Pattern") != pats:
+ if (
+ hasattr(vobj, "Pattern")
+ and hasattr(vobj, "Proxy")
+ and isinstance(vobj.Proxy, view_base.ViewProviderDraft)
+ and vobj.getEnumerationsOfProperty("Pattern") != pats
+ ):
vobjs.append(vobj)
if vobjs:
data.append([doc, vobjs])
if not data:
return
- msg = translate("draft",
-"""Do you want to update the SVG pattern options
-of existing objects in all opened documents?""")
- res = QtWidgets.QMessageBox.question(None, "Update SVG patterns", msg,
- QtWidgets.QMessageBox.Yes | QtWidgets.QMessageBox.No,
- QtWidgets.QMessageBox.No)
+ msg = translate(
+ "draft",
+ """Do you want to update the SVG pattern options
+of existing objects in all opened documents?""",
+ )
+ res = QtWidgets.QMessageBox.question(
+ None,
+ "Update SVG patterns",
+ msg,
+ QtWidgets.QMessageBox.Yes | QtWidgets.QMessageBox.No,
+ QtWidgets.QMessageBox.No,
+ )
if res == QtWidgets.QMessageBox.No:
return
@@ -229,11 +252,13 @@ def _param_observer_start():
_param_observer_start_view()
-def _param_observer_start_draft(param_grp = App.ParamGet("User parameter:BaseApp/Preferences/Mod/Draft")):
+def _param_observer_start_draft(
+ param_grp=App.ParamGet("User parameter:BaseApp/Preferences/Mod/Draft"),
+):
param_grp.AttachManager(ParamObserverDraft())
-def _param_observer_start_view(param_grp = App.ParamGet("User parameter:BaseApp/Preferences/View")):
+def _param_observer_start_view(param_grp=App.ParamGet("User parameter:BaseApp/Preferences/View")):
param_grp.AttachManager(ParamObserverView())
@@ -350,7 +375,7 @@ def _param_from_PrefLineEdit(widget):
for elem in list(widget):
if "name" in elem.keys():
att_name = elem.attrib["name"]
- if att_name == "text": # Can be missing.
+ if att_name == "text": # Can be missing.
value = elem.find("string").text # If text is missing value will be None here.
elif att_name == "prefEntry":
entry = elem.find("cstring").text
@@ -376,6 +401,7 @@ def _param_from_PrefFileChooser(widget):
def _param_from_PrefFontBox(widget):
if App.GuiUp:
from PySide import QtGui
+
font = QtGui.QFont()
font.setStyleHint(QtGui.QFont.StyleHint.SansSerif)
value = font.defaultFamily()
@@ -403,12 +429,12 @@ def _get_shape_string_font_file():
# Mac fonts: "geneva" and "helvetica"
# Linux fonts: "dejavusans" and "freesans"
favorite_names = ("arial", "geneva", "helvetica", "dejavusans", "freesans")
- font_file_sans = None # Font with name containing "sans". 1st fallback.
+ font_file_sans = None # Font with name containing "sans". 1st fallback.
font_file_alpha = None # Font with name starting with a letter. 2nd fallback.
# Reverse the order of the paths so that user related paths come last:
for path in QtCore.QStandardPaths.standardLocations(QtCore.QStandardPaths.FontsLocation)[::-1]:
# We don't use os.path.join as dir_path has forward slashes even on Windows.
- for (dir_path, dir_names, file_names) in os.walk(path):
+ for dir_path, dir_names, file_names in os.walk(path):
for file_name in file_names:
base_name, ext = [s.lower() for s in os.path.splitext(file_name)]
if not ext in (".ttc", ".ttf"):
@@ -432,8 +458,9 @@ def _get_param_dictionary():
param_dict = {}
- hatch_pattern_file = App.getResourceDir().replace("\\", "/").rstrip("/") \
- + "/Mod/TechDraw/PAT/FCPAT.pat"
+ hatch_pattern_file = (
+ App.getResourceDir().replace("\\", "/").rstrip("/") + "/Mod/TechDraw/PAT/FCPAT.pat"
+ )
# Draft parameters that are not in the preferences:
# fmt: off
@@ -633,26 +660,27 @@ def _get_param_dictionary():
}
# fmt: on
-
# Preferences ui files are stored in resource files.
# For the Draft Workbench: /Mod/Draft/Draft_rc.py
# For the Arch Workbench: /Mod/Arch/Arch_rc.py
- for fnm in (":/ui/preferences-draft.ui",
- ":/ui/preferences-draftinterface.ui",
- ":/ui/preferences-draftsnap.ui",
- ":/ui/preferences-drafttexts.ui",
- ":/ui/preferences-draftvisual.ui",
- ":/ui/preferences-dwg.ui",
- ":/ui/preferences-dxf.ui",
- ":/ui/preferences-oca.ui",
- ":/ui/preferences-svg.ui",
- ":/ui/preferences-arch.ui",
- ":/ui/preferences-archdefaults.ui",
- ":/ui/preferences-dae.ui",
- ":/ui/preferences-ifc.ui",
- ":/ui/preferences-ifc-export.ui",
- ":/ui/preferences-sh3d-import.ui",
- ":/ui/preferences-webgl.ui",):
+ for fnm in (
+ ":/ui/preferences-draft.ui",
+ ":/ui/preferences-draftinterface.ui",
+ ":/ui/preferences-draftsnap.ui",
+ ":/ui/preferences-drafttexts.ui",
+ ":/ui/preferences-draftvisual.ui",
+ ":/ui/preferences-dwg.ui",
+ ":/ui/preferences-dxf.ui",
+ ":/ui/preferences-oca.ui",
+ ":/ui/preferences-svg.ui",
+ ":/ui/preferences-arch.ui",
+ ":/ui/preferences-archdefaults.ui",
+ ":/ui/preferences-dae.ui",
+ ":/ui/preferences-ifc.ui",
+ ":/ui/preferences-ifc-export.ui",
+ ":/ui/preferences-sh3d-import.ui",
+ ":/ui/preferences-webgl.ui",
+ ):
# https://stackoverflow.com/questions/14750997/load-txt-file-from-resources-in-python
fd = QtCore.QFile(fnm)
diff --git a/src/Mod/Draft/draftutils/todo.py b/src/Mod/Draft/draftutils/todo.py
index 373860d0bb..20624fee04 100644
--- a/src/Mod/Draft/draftutils/todo.py
+++ b/src/Mod/Draft/draftutils/todo.py
@@ -122,18 +122,17 @@ class ToDo:
The lists are `itinerary`, `commitlist` and `afteritinerary`.
"""
if _DEBUG:
- _msg("Debug: doing delayed tasks.\n"
- "itinerary: {0}\n"
- "commitlist: {1}\n"
- "afteritinerary: {2}\n".format(todo.itinerary,
- todo.commitlist,
- todo.afteritinerary))
+ _msg(
+ "Debug: doing delayed tasks.\n"
+ "itinerary: {0}\n"
+ "commitlist: {1}\n"
+ "afteritinerary: {2}\n".format(todo.itinerary, todo.commitlist, todo.afteritinerary)
+ )
try:
for f, arg in ToDo.itinerary:
try:
if _DEBUG_inner:
- _msg("Debug: executing.\n"
- "function: {}\n".format(f))
+ _msg("Debug: executing.\n" "function: {}\n".format(f))
if arg or (arg is False):
f(arg)
else:
@@ -141,13 +140,14 @@ class ToDo:
except Exception:
_log(traceback.format_exc())
_err(traceback.format_exc())
- wrn = ("ToDo.doTasks, Unexpected error:\n"
- "{0}\n"
- "in {1}({2})".format(sys.exc_info()[0], f, arg))
+ wrn = (
+ "ToDo.doTasks, Unexpected error:\n"
+ "{0}\n"
+ "in {1}({2})".format(sys.exc_info()[0], f, arg)
+ )
_wrn(wrn)
except ReferenceError:
- _wrn("Debug: ToDo.doTasks: "
- "queue contains a deleted object, skipping")
+ _wrn("Debug: ToDo.doTasks: " "queue contains a deleted object, skipping")
ToDo.itinerary = []
if ToDo.commitlist:
@@ -155,8 +155,7 @@ class ToDo:
ToDo.commitlist = [] # Reset immediately to avoid race condition.
for name, func in commit_list:
if _DEBUG_inner:
- _msg("Debug: committing.\n"
- "name: {}\n".format(name))
+ _msg("Debug: committing.\n" "name: {}\n".format(name))
try:
name = str(name)
App.activeDocument().openTransaction(name)
@@ -169,20 +168,20 @@ class ToDo:
except Exception:
_log(traceback.format_exc())
_err(traceback.format_exc())
- wrn = ("ToDo.doTasks, Unexpected error:\n"
- "{0}\n"
- "in {1}".format(sys.exc_info()[0], func))
+ wrn = (
+ "ToDo.doTasks, Unexpected error:\n"
+ "{0}\n"
+ "in {1}".format(sys.exc_info()[0], func)
+ )
_wrn(wrn)
# Restack Draft screen widgets after creation
if hasattr(Gui, "Snapper"):
Gui.Snapper.restack()
-
for f, arg in ToDo.afteritinerary:
try:
if _DEBUG_inner:
- _msg("Debug: executing after.\n"
- "function: {}\n".format(f))
+ _msg("Debug: executing after.\n" "function: {}\n".format(f))
if arg:
f(arg)
else:
@@ -190,9 +189,11 @@ class ToDo:
except Exception:
_log(traceback.format_exc())
_err(traceback.format_exc())
- wrn = ("ToDo.doTasks, Unexpected error:\n"
- "{0}\n"
- "in {1}({2})".format(sys.exc_info()[0], f, arg))
+ wrn = (
+ "ToDo.doTasks, Unexpected error:\n"
+ "{0}\n"
+ "in {1}({2})".format(sys.exc_info()[0], f, arg)
+ )
_wrn(wrn)
ToDo.afteritinerary = []
@@ -224,8 +225,7 @@ class ToDo:
f(arg)
"""
if _DEBUG:
- _msg("Debug: delaying.\n"
- "function: {}\n".format(f))
+ _msg("Debug: delaying.\n" "function: {}\n".format(f))
if ToDo.itinerary == []:
QtCore.QTimer.singleShot(0, ToDo.doTasks)
ToDo.itinerary.append((f, arg))
@@ -254,8 +254,7 @@ class ToDo:
See the attributes of the `ToDo` class for more information.
"""
if _DEBUG:
- _msg("Debug: delaying commit.\n"
- "commitlist: {}\n".format(cl))
+ _msg("Debug: delaying commit.\n" "commitlist: {}\n".format(cl))
QtCore.QTimer.singleShot(0, ToDo.doTasks)
ToDo.commitlist = cl
@@ -276,8 +275,7 @@ class ToDo:
and append it to the `afteritinerary` list.
"""
if _DEBUG:
- _msg("Debug: delaying after.\n"
- "function: {}\n".format(f))
+ _msg("Debug: delaying after.\n" "function: {}\n".format(f))
if ToDo.afteritinerary == []:
QtCore.QTimer.singleShot(0, ToDo.doTasks)
ToDo.afteritinerary.append((f, arg))
diff --git a/src/Mod/Draft/draftutils/units.py b/src/Mod/Draft/draftutils/units.py
index d7ff899ebc..197e639207 100644
--- a/src/Mod/Draft/draftutils/units.py
+++ b/src/Mod/Draft/draftutils/units.py
@@ -38,10 +38,10 @@ def get_default_unit(dim):
It is based on the user preferences.
"""
- if dim == 'Length':
+ if dim == "Length":
qty = App.Units.Quantity(1.0, App.Units.Length)
uom = qty.getUserPreferred()[2]
- elif dim == 'Angle':
+ elif dim == "Angle":
qty = App.Units.Quantity(1.0, App.Units.Angle)
uom = qty.getUserPreferred()[2]
else:
@@ -52,15 +52,15 @@ def get_default_unit(dim):
getDefaultUnit = get_default_unit
-def make_format_spec(decimals=4, dim='Length'):
+def make_format_spec(decimals=4, dim="Length"):
"""Return a string format specifier with decimals for a dimension.
It is based on the user preferences.
"""
- if dim == 'Length':
- fmt_spec = "%." + str(decimals) + "f " + get_default_unit('Length')
- elif dim == 'Angle':
- fmt_spec = "%." + str(decimals) + "f " + get_default_unit('Angle')
+ if dim == "Length":
+ fmt_spec = "%." + str(decimals) + "f " + get_default_unit("Length")
+ elif dim == "Angle":
+ fmt_spec = "%." + str(decimals) + "f " + get_default_unit("Angle")
else:
fmt_spec = "%." + str(decimals) + "f " + "??"
return fmt_spec
@@ -69,8 +69,7 @@ def make_format_spec(decimals=4, dim='Length'):
makeFormatSpec = make_format_spec
-def display_external(internal_value,
- decimals=None, dim='Length', showUnit=True, unit=None):
+def display_external(internal_value, decimals=None, dim="Length", showUnit=True, unit=None):
"""Return a converted value for display, according to the unit schema.
Parameters
@@ -92,7 +91,7 @@ def display_external(internal_value,
A unit string such as `'mm'`, `'cm'`, `'m'`, `'in'`, `'ft'`,
in which to express the returned value.
"""
- if dim == 'Length':
+ if dim == "Length":
q = App.Units.Quantity(internal_value, App.Units.Length)
if not unit:
if decimals is None and showUnit:
@@ -101,7 +100,7 @@ def display_external(internal_value,
conversion = q.getUserPreferred()[1]
uom = q.getUserPreferred()[2]
elif unit.lower() == "arch":
- return App.Units.schemaTranslate(q,5)[0].replace("+"," ")
+ return App.Units.schemaTranslate(q, 5)[0].replace("+", " ")
else:
try:
uom = unit
@@ -110,7 +109,7 @@ def display_external(internal_value,
except Exception:
conversion = q.getUserPreferred()[1]
uom = q.getUserPreferred()[2]
- elif dim == 'Angle':
+ elif dim == "Angle":
q = App.Units.Quantity(internal_value, App.Units.Angle)
if decimals is None:
return q.UserString
diff --git a/src/Mod/Draft/draftutils/utils.py b/src/Mod/Draft/draftutils/utils.py
index 69a11eed53..b075800473 100644
--- a/src/Mod/Draft/draftutils/utils.py
+++ b/src/Mod/Draft/draftutils/utils.py
@@ -65,25 +65,25 @@ def get_default_annotation_style():
arrow_start_type_index = params.get_param("dimsymbolstart")
arrow_end_type_index = params.get_param("dimsymbolend")
return {
- "ArrowSizeStart": ("float", params.get_param("arrowsizestart")),
- "ArrowSizeEnd": ("float", params.get_param("arrowsizeend")),
- "ArrowTypeStart": ("index", arrow_start_type_index, ARROW_TYPES[arrow_start_type_index]),
- "ArrowTypeEnd": ("index", arrow_end_type_index, ARROW_TYPES[arrow_end_type_index]),
- "Decimals": ("int", params.get_param("dimPrecision")),
- "DimOvershoot": ("float", params.get_param("dimovershoot")),
- "ExtLines": ("float", params.get_param("extlines")),
- "ExtOvershoot": ("float", params.get_param("extovershoot")),
- "FontName": ("font", params.get_param("textfont")),
- "FontSize": ("float", params.get_param("textheight")),
- "LineColor": ("color", params.get_param("DefaultAnnoLineColor") | 0x000000FF),
- "LineSpacing": ("float", params.get_param("LineSpacing")),
- "LineWidth": ("int", params.get_param("DefaultAnnoLineWidth")),
+ "ArrowSizeStart": ("float", params.get_param("arrowsizestart")),
+ "ArrowSizeEnd": ("float", params.get_param("arrowsizeend")),
+ "ArrowTypeStart": ("index", arrow_start_type_index, ARROW_TYPES[arrow_start_type_index]),
+ "ArrowTypeEnd": ("index", arrow_end_type_index, ARROW_TYPES[arrow_end_type_index]),
+ "Decimals": ("int", params.get_param("dimPrecision")),
+ "DimOvershoot": ("float", params.get_param("dimovershoot")),
+ "ExtLines": ("float", params.get_param("extlines")),
+ "ExtOvershoot": ("float", params.get_param("extovershoot")),
+ "FontName": ("font", params.get_param("textfont")),
+ "FontSize": ("float", params.get_param("textheight")),
+ "LineColor": ("color", params.get_param("DefaultAnnoLineColor") | 0x000000FF),
+ "LineSpacing": ("float", params.get_param("LineSpacing")),
+ "LineWidth": ("int", params.get_param("DefaultAnnoLineWidth")),
"ScaleMultiplier": ("float", params.get_param("DefaultAnnoScaleMultiplier")),
- "ShowLine": ("bool", params.get_param("DimShowLine")),
- "ShowUnit": ("bool", params.get_param("showUnit")),
- "TextColor": ("color", params.get_param("DefaultTextColor") | 0x000000FF),
- "TextSpacing": ("float", params.get_param("dimspacing")),
- "UnitOverride": ("str", params.get_param("overrideUnit"))
+ "ShowLine": ("bool", params.get_param("DimShowLine")),
+ "ShowUnit": ("bool", params.get_param("showUnit")),
+ "TextColor": ("color", params.get_param("DefaultTextColor") | 0x000000FF),
+ "TextSpacing": ("float", params.get_param("dimspacing")),
+ "UnitOverride": ("str", params.get_param("overrideUnit")),
}
@@ -99,9 +99,11 @@ def repair_annotation_style(style):
ArrowType has been replaced by ArrowTypeStart and ArrowTypeEnd.
"""
for key in ("ArrowSize", "ArrowType"):
- if style.get(key) is not None \
- and style.get(key + "Start") is None \
- and style.get(key + "End") is None:
+ if (
+ style.get(key) is not None
+ and style.get(key + "Start") is None
+ and style.get(key + "End") is None
+ ):
style[key + "Start"] = style[key]
style[key + "End"] = style[key]
default = get_default_annotation_style()
@@ -123,25 +125,25 @@ def get_default_shape_style():
display_mode_index = params.get_param("DefaultDisplayMode")
draw_style_index = params.get_param("DefaultDrawStyle")
return {
- "DisplayMode": ("index", display_mode_index, DISPLAY_MODES[display_mode_index]),
- "DrawStyle": ("index", draw_style_index, DRAW_STYLES[draw_style_index]),
- "LineColor": ("color", params.get_param_view("DefaultShapeLineColor") | 0x000000FF),
- "LineWidth": ("int", params.get_param_view("DefaultShapeLineWidth")),
- "PointColor": ("color", params.get_param_view("DefaultShapeVertexColor") | 0x000000FF),
- "PointSize": ("int", params.get_param_view("DefaultShapePointSize")),
- "ShapeAppearance": ("material", (get_view_material(), ))
+ "DisplayMode": ("index", display_mode_index, DISPLAY_MODES[display_mode_index]),
+ "DrawStyle": ("index", draw_style_index, DRAW_STYLES[draw_style_index]),
+ "LineColor": ("color", params.get_param_view("DefaultShapeLineColor") | 0x000000FF),
+ "LineWidth": ("int", params.get_param_view("DefaultShapeLineWidth")),
+ "PointColor": ("color", params.get_param_view("DefaultShapeVertexColor") | 0x000000FF),
+ "PointSize": ("int", params.get_param_view("DefaultShapePointSize")),
+ "ShapeAppearance": ("material", (get_view_material(),)),
}
def get_view_material():
"""Return a ShapeAppearance material with properties based on the preferences."""
material = App.Material()
- material.AmbientColor = params.get_param_view("DefaultAmbientColor") | 0x000000FF
- material.DiffuseColor = params.get_param_view("DefaultShapeColor") | 0x000000FF
+ material.AmbientColor = params.get_param_view("DefaultAmbientColor") | 0x000000FF
+ material.DiffuseColor = params.get_param_view("DefaultShapeColor") | 0x000000FF
material.EmissiveColor = params.get_param_view("DefaultEmissiveColor") | 0x000000FF
- material.Shininess = params.get_param_view("DefaultShapeShininess") / 100
+ material.Shininess = params.get_param_view("DefaultShapeShininess") / 100
material.SpecularColor = params.get_param_view("DefaultSpecularColor") | 0x000000FF
- material.Transparency = params.get_param_view("DefaultShapeTransparency") / 100
+ material.Transparency = params.get_param_view("DefaultShapeTransparency") / 100
return material
@@ -162,13 +164,14 @@ def string_encode_coin(ustr):
"""
try:
from pivy import coin
+
coin4 = coin.COIN_MAJOR_VERSION >= 4
except (ImportError, AttributeError):
coin4 = False
if coin4:
- return ustr.encode('utf-8')
+ return ustr.encode("utf-8")
else:
- return ustr.encode('latin1')
+ return ustr.encode("latin1")
stringencodecoin = string_encode_coin
@@ -297,8 +300,8 @@ def get_real_name(name):
at least one letter.
"""
for i in range(1, len(name) + 1):
- if name[-i] not in '1234567890':
- return name[:len(name) - (i - 1)]
+ if name[-i] not in "1234567890":
+ return name[: len(name) - (i - 1)]
return name
@@ -327,15 +330,16 @@ def get_type(obj):
or `None` if `obj` is `None`.
"""
import Part
+
if not obj:
return None
if isinstance(obj, Part.Shape):
return "Shape"
if hasattr(obj, "Class") and "Ifc" in str(obj.Class):
return obj.Class
- if hasattr(obj, 'Proxy') and hasattr(obj.Proxy, "Type"):
+ if hasattr(obj, "Proxy") and hasattr(obj.Proxy, "Type"):
return obj.Proxy.Type
- if hasattr(obj, 'TypeId'):
+ if hasattr(obj, "TypeId"):
return obj.TypeId
return "Unknown"
@@ -536,6 +540,7 @@ def shapify(obj, delete=True):
name = "Wire"
elif len(shape.Edges) == 1:
import DraftGeomUtils
+
if DraftGeomUtils.geomType(shape.Edges[0]) == "Line":
name = "Line"
else:
@@ -602,13 +607,19 @@ def compare_objects(obj1, obj2):
Any type of scripted object.
"""
if obj1.TypeId != obj2.TypeId:
- _msg("'{0}' ({1}), '{2}' ({3}): ".format(obj1.Name, obj1.TypeId,
- obj2.Name, obj2.TypeId)
- + translate("draft", "different types") + " (TypeId)")
+ _msg(
+ "'{0}' ({1}), '{2}' ({3}): ".format(obj1.Name, obj1.TypeId, obj2.Name, obj2.TypeId)
+ + translate("draft", "different types")
+ + " (TypeId)"
+ )
elif getType(obj1) != getType(obj2):
- _msg("'{0}' ({1}), '{2}' ({3}): ".format(obj1.Name, get_type(obj1),
- obj2.Name, get_type(obj2))
- + translate("draft", "different types") + " (Proxy.Type)")
+ _msg(
+ "'{0}' ({1}), '{2}' ({3}): ".format(
+ obj1.Name, get_type(obj1), obj2.Name, get_type(obj2)
+ )
+ + translate("draft", "different types")
+ + " (Proxy.Type)"
+ )
else:
for p in obj1.PropertiesList:
if p in obj2.PropertiesList:
@@ -616,15 +627,17 @@ def compare_objects(obj1, obj2):
pass
elif p == "Placement":
delta = obj1.Placement.Base.sub(obj2.Placement.Base)
- text = translate("draft", "Objects have different placements. "
- "Distance between the two base points:")
+ text = translate(
+ "draft",
+ "Objects have different placements. "
+ "Distance between the two base points:",
+ )
_msg(text + " " + str(delta.Length))
else:
if getattr(obj1, p) != getattr(obj2, p):
_msg("'{}' ".format(p) + translate("draft", "has a different value"))
else:
- _msg("{} ".format(p)
- + translate("draft", "doesn't exist in one of the objects"))
+ _msg("{} ".format(p) + translate("draft", "doesn't exist in one of the objects"))
compareObjects = compare_objects
@@ -637,6 +650,7 @@ def load_svg_patterns():
attribute.
"""
import importSVG
+
App.svgpatterns = {}
# Get default patterns in the resource file
@@ -645,7 +659,7 @@ def load_svg_patterns():
file = ":/patterns/" + str(fn)
f = QtCore.QFile(file)
f.open(QtCore.QIODevice.ReadOnly)
- p = importSVG.getContents(str(f.readAll()), 'pattern', True)
+ p = importSVG.getContents(str(f.readAll()), "pattern", True)
if p:
for k in p:
p[k] = [p[k], file]
@@ -657,25 +671,25 @@ def load_svg_patterns():
for f in os.listdir(altpat):
if f[-4:].upper() == ".SVG":
file = os.path.join(altpat, f)
- p = importSVG.getContents(file, 'pattern')
+ p = importSVG.getContents(file, "pattern")
if p:
for k in p:
p[k] = [p[k], file]
App.svgpatterns.update(p)
# Get TechDraw patterns
- altpat = os.path.join(App.getResourceDir(),"Mod","TechDraw","Patterns")
+ altpat = os.path.join(App.getResourceDir(), "Mod", "TechDraw", "Patterns")
if os.path.isdir(altpat):
for f in os.listdir(altpat):
if f[-4:].upper() == ".SVG":
file = os.path.join(altpat, f)
- p = importSVG.getContents(file, 'pattern')
+ p = importSVG.getContents(file, "pattern")
if p:
for k in p:
p[k] = [p[k], file]
else:
# some TD pattern files have no definition but can still be used by Draft
- p = {f[:-4]:["",file]}
+ p = {f[:-4]: ["", file]}
App.svgpatterns.update(p)
@@ -714,10 +728,10 @@ def get_rgb(color, testbw=True):
testwb : bool (default = True)
Pure white will be converted into pure black.
"""
- r = str(hex(int(color[0]*255)))[2:].zfill(2)
- g = str(hex(int(color[1]*255)))[2:].zfill(2)
- b = str(hex(int(color[2]*255)))[2:].zfill(2)
- col = "#"+r+g+b
+ r = str(hex(int(color[0] * 255)))[2:].zfill(2)
+ g = str(hex(int(color[1] * 255)))[2:].zfill(2)
+ b = str(hex(int(color[2] * 255)))[2:].zfill(2)
+ col = "#" + r + g + b
if testbw:
if col == "#ffffff":
# print(params.get_param("SvgLinesBlack"))
@@ -757,8 +771,7 @@ def argb_to_rgba(color):
def rgba_to_argb(color):
- """Change byte order of a 4 byte color int from RGBA (FreeCAD) to ARGB (Qt).
- """
+ """Change byte order of a 4 byte color int from RGBA (FreeCAD) to ARGB (Qt)."""
return ((color & 0xFFFFFF00) >> 8) + ((color & 0xFF) << 24)
@@ -773,10 +786,7 @@ def get_rgba_tuple(color, typ=1.0):
If float the values in the returned tuple are in the 0.0-1.0 range.
Else the values are in the 0-255 range.
"""
- color = ((color >> 24) & 0xFF,
- (color >> 16) & 0xFF,
- (color >> 8) & 0xFF,
- color & 0xFF)
+ color = ((color >> 24) & 0xFF, (color >> 16) & 0xFF, (color >> 8) & 0xFF, color & 0xFF)
if type(typ) == float:
return tuple([x / 255.0 for x in color])
else:
@@ -837,6 +847,7 @@ def _modifiers_process_selection(sels, copy, scale=False, add_movable_children=F
def _modifiers_get_group_contents(obj):
from draftutils import groups
+
return groups.get_group_contents(obj, addgroups=True, spaces=True, noarchchild=True)
@@ -871,14 +882,20 @@ def _modifiers_filter_objects(objs, copy, scale=False):
if parent.isDerivedFrom("Part::Feature"):
parents.append(parent.Name)
if len(parents) > 1:
- message = translate("draft", "%s shares a base with %d other objects. Please check if you want to modify this.") % (obj.Name,len(parents) - 1)
+ message = translate(
+ "draft",
+ "%s shares a base with %d other objects. Please check if you want to modify this.",
+ ) % (obj.Name, len(parents) - 1)
_err(message)
if not scale or utils.get_type(obj.Base) == "Wire":
result.append(obj.Base)
- elif not copy \
- and hasattr(obj, "Placement") \
- and "ReadOnly" in obj.getEditorMode("Placement"):
- _err(translate("draft", "%s cannot be modified because its placement is readonly") % obj.Name)
+ elif (
+ not copy and hasattr(obj, "Placement") and "ReadOnly" in obj.getEditorMode("Placement")
+ ):
+ _err(
+ translate("draft", "%s cannot be modified because its placement is readonly")
+ % obj.Name
+ )
elif not scale or is_scalable(obj):
result.append(obj)
return result
@@ -1091,16 +1108,34 @@ def use_instead(function, version=""):
then we should not give a version.
"""
if version:
- _wrn(translate("draft", "This function will be deprecated in {}. Please use '{}'.") .format(version, function))
+ _wrn(
+ translate("draft", "This function will be deprecated in {}. Please use '{}'.").format(
+ version, function
+ )
+ )
else:
- _wrn(translate("draft", "This function will be deprecated. Please use '{}'.") .format(function))
+ _wrn(
+ translate("draft", "This function will be deprecated. Please use '{}'.").format(
+ function
+ )
+ )
-def pyopen(file, mode='r', buffering=-1, encoding=None, errors=None, newline=None, closefd=True, opener=None):
+def pyopen(
+ file,
+ mode="r",
+ buffering=-1,
+ encoding=None,
+ errors=None,
+ newline=None,
+ closefd=True,
+ opener=None,
+):
if encoding is None:
- encoding = 'utf-8'
+ encoding = "utf-8"
return open(file, mode, buffering, encoding, errors, newline, closefd, opener)
+
def toggle_working_plane(obj, action=None, restore=False, dialog=None):
"""Toggle the active state of a working plane object.
@@ -1136,8 +1171,8 @@ def toggle_working_plane(obj, action=None, restore=False, dialog=None):
context = "NativeIFC"
# Check if the object is already active in its context
- is_active_arch = (FreeCADGui.ActiveDocument.ActiveView.getActiveObject("Arch") == obj)
- is_active_ifc = (FreeCADGui.ActiveDocument.ActiveView.getActiveObject("NativeIFC") == obj)
+ is_active_arch = FreeCADGui.ActiveDocument.ActiveView.getActiveObject("Arch") == obj
+ is_active_ifc = FreeCADGui.ActiveDocument.ActiveView.getActiveObject("NativeIFC") == obj
is_active = is_active_arch or is_active_ifc
if is_active:
# Deactivate the object
@@ -1146,8 +1181,11 @@ def toggle_working_plane(obj, action=None, restore=False, dialog=None):
if is_active_ifc:
FreeCADGui.ActiveDocument.ActiveView.setActiveObject("NativeIFC", None)
- if hasattr(obj, "ViewObject") and hasattr(obj.ViewObject, "Proxy") and \
- hasattr(obj.ViewObject.Proxy, "setWorkingPlane"):
+ if (
+ hasattr(obj, "ViewObject")
+ and hasattr(obj.ViewObject, "Proxy")
+ and hasattr(obj.ViewObject.Proxy, "setWorkingPlane")
+ ):
obj.ViewObject.Proxy.setWorkingPlane(restore=True)
if action:
action.setChecked(False)
@@ -1157,8 +1195,11 @@ def toggle_working_plane(obj, action=None, restore=False, dialog=None):
else:
# Activate the object
FreeCADGui.ActiveDocument.ActiveView.setActiveObject(context, obj)
- if hasattr(obj, "ViewObject") and hasattr(obj.ViewObject, "Proxy") and \
- hasattr(obj.ViewObject.Proxy, "setWorkingPlane"):
+ if (
+ hasattr(obj, "ViewObject")
+ and hasattr(obj.ViewObject, "Proxy")
+ and hasattr(obj.ViewObject.Proxy, "setWorkingPlane")
+ ):
obj.ViewObject.Proxy.setWorkingPlane()
if action:
action.setChecked(True)
@@ -1166,4 +1207,5 @@ def toggle_working_plane(obj, action=None, restore=False, dialog=None):
dialog.buttonActive.setChecked(True)
return True
+
## @}
diff --git a/src/Mod/Draft/draftviewproviders/view_array.py b/src/Mod/Draft/draftviewproviders/view_array.py
index 0a3a1810d8..94b83b0d07 100644
--- a/src/Mod/Draft/draftviewproviders/view_array.py
+++ b/src/Mod/Draft/draftviewproviders/view_array.py
@@ -34,16 +34,16 @@ from draftutils import gui_utils
class ViewProviderDraftArray(ViewProviderDraft):
"""a view provider that displays a Array icon instead of a Draft icon"""
- def __init__(self,vobj):
+ def __init__(self, vobj):
super(ViewProviderDraftArray, self).__init__(vobj)
def getIcon(self):
if hasattr(self.Object, "ArrayType"):
- if self.Object.ArrayType == 'ortho':
+ if self.Object.ArrayType == "ortho":
return ":/icons/Draft_Array.svg"
- elif self.Object.ArrayType == 'polar':
+ elif self.Object.ArrayType == "polar":
return ":/icons/Draft_PolarArray.svg"
- elif self.Object.ArrayType == 'circular':
+ elif self.Object.ArrayType == "circular":
return ":/icons/Draft_CircularArray.svg"
elif hasattr(self.Object, "PointObject"):
return ":/icons/Draft_PointArray.svg"
@@ -65,7 +65,7 @@ class ViewProviderDraftArray(ViewProviderDraft):
n = obj.NumberX * obj.NumberY * obj.NumberZ
elif obj.ArrayType == "polar":
n = obj.NumberPolar
- else: # "circular"
+ else: # "circular"
n = obj.Count
elif hasattr(obj, "Count"):
n = obj.Count
diff --git a/src/Mod/Draft/draftviewproviders/view_base.py b/src/Mod/Draft/draftviewproviders/view_base.py
index 1a832cf3dd..249e2081c4 100644
--- a/src/Mod/Draft/draftviewproviders/view_base.py
+++ b/src/Mod/Draft/draftviewproviders/view_base.py
@@ -44,6 +44,7 @@ if App.GuiUp:
from pivy import coin
import FreeCADGui as Gui
import Draft_rc
+
# The module is used to prevent complaints from code checkers (flake8)
bool(Draft_rc.__name__)
@@ -102,23 +103,25 @@ class ViewProviderDraft(object):
def _set_properties(self, vobj):
"""Set the properties of objects if they don't exist."""
if not hasattr(vobj, "Pattern"):
- vobj.addProperty("App::PropertyEnumeration",
- "Pattern",
- "Draft",
- QT_TRANSLATE_NOOP("App::Property",
- "Defines an SVG pattern."),
- locked=True)
+ vobj.addProperty(
+ "App::PropertyEnumeration",
+ "Pattern",
+ "Draft",
+ QT_TRANSLATE_NOOP("App::Property", "Defines an SVG pattern."),
+ locked=True,
+ )
patterns = list(utils.svg_patterns())
patterns.sort()
vobj.Pattern = ["None"] + patterns
if not hasattr(vobj, "PatternSize"):
- vobj.addProperty("App::PropertyFloat",
- "PatternSize",
- "Draft",
- QT_TRANSLATE_NOOP("App::Property",
- "Defines the size of the SVG pattern."),
- locked=True)
+ vobj.addProperty(
+ "App::PropertyFloat",
+ "PatternSize",
+ "Draft",
+ QT_TRANSLATE_NOOP("App::Property", "Defines the size of the SVG pattern."),
+ locked=True,
+ )
vobj.PatternSize = params.get_param("HatchPatternSize")
def dumps(self):
@@ -295,8 +298,8 @@ class ViewProviderDraft(object):
if switch is not None:
if switch.getChildren().getLength() > 0:
innodes = switch.getChild(0).getChildren().getLength()
- if innodes > 2:
- r = switch.getChild(0).getChild(innodes-1)
+ if innodes > 2:
+ r = switch.getChild(0).getChild(innodes - 1)
i = QtCore.QFileInfo(path)
if self.texture:
r.removeChild(self.texture)
@@ -401,8 +404,15 @@ class ViewProviderDraft(object):
# Facebinder, ShapeString, PanelSheet and Profile objects have their own
# setEdit and unsetEdit.
- if utils.get_type(vobj.Object) in ("Wire", "Circle", "Ellipse", "Rectangle", "Polygon",
- "BSpline", "BezCurve"):
+ if utils.get_type(vobj.Object) in (
+ "Wire",
+ "Circle",
+ "Ellipse",
+ "Rectangle",
+ "Polygon",
+ "BSpline",
+ "BezCurve",
+ ):
if not "Draft_Edit" in Gui.listCommands():
self.wb_before_edit = Gui.activeWorkbench()
Gui.activateWorkbench("DraftWorkbench")
@@ -419,8 +429,15 @@ class ViewProviderDraft(object):
if mode == 1 or mode == 2:
return None
- if utils.get_type(vobj.Object) in ("Wire", "Circle", "Ellipse", "Rectangle", "Polygon",
- "BSpline", "BezCurve"):
+ if utils.get_type(vobj.Object) in (
+ "Wire",
+ "Circle",
+ "Ellipse",
+ "Rectangle",
+ "Polygon",
+ "BSpline",
+ "BezCurve",
+ ):
if hasattr(App, "activeDraftCommand") and App.activeDraftCommand:
App.activeDraftCommand.finish()
Gui.Control.closeDialog()
@@ -434,22 +451,28 @@ class ViewProviderDraft(object):
def setupContextMenu(self, vobj, menu):
tp = utils.get_type(self.Object)
- if tp in ("Wire", "Circle", "Ellipse", "Rectangle", "Polygon",
- "BSpline", "BezCurve", "Facebinder", "ShapeString",
- "PanelSheet", "Profile"):
- action_edit = QtGui.QAction(translate("draft", "Edit"),
- menu)
- QtCore.QObject.connect(action_edit,
- QtCore.SIGNAL("triggered()"),
- self.edit)
+ if tp in (
+ "Wire",
+ "Circle",
+ "Ellipse",
+ "Rectangle",
+ "Polygon",
+ "BSpline",
+ "BezCurve",
+ "Facebinder",
+ "ShapeString",
+ "PanelSheet",
+ "Profile",
+ ):
+ action_edit = QtGui.QAction(translate("draft", "Edit"), menu)
+ QtCore.QObject.connect(action_edit, QtCore.SIGNAL("triggered()"), self.edit)
menu.addAction(action_edit)
if tp == "Wire":
- action_flatten = QtGui.QAction(translate("draft", "Flatten"),
- menu)
- QtCore.QObject.connect(action_flatten,
- QtCore.SIGNAL("triggered()"),
- self.flatten) # The flatten function is defined in view_wire.py.
+ action_flatten = QtGui.QAction(translate("draft", "Flatten"), menu)
+ QtCore.QObject.connect(
+ action_flatten, QtCore.SIGNAL("triggered()"), self.flatten
+ ) # The flatten function is defined in view_wire.py.
menu.addAction(action_flatten)
# The default Part::FeaturePython context menu contains a `Set colors`
@@ -457,15 +480,27 @@ class ViewProviderDraft(object):
# can only have a single face. In those cases we override this menu and
# have to add our own `Transform` item.
# To override the default menu this function must return `True`.
- if tp in ("Wire", "Circle", "Ellipse", "Rectangle", "Polygon",
- "BSpline","BezCurve", "Fillet", "Point", "Shape2DView",
- "PanelCut", "PanelSheet", "Profile"):
- action_transform = QtGui.QAction(Gui.getIcon("Std_TransformManip.svg"),
- translate("Command", "Transform"), # Context `Command` instead of `draft`.
- menu)
- QtCore.QObject.connect(action_transform,
- QtCore.SIGNAL("triggered()"),
- self.transform)
+ if tp in (
+ "Wire",
+ "Circle",
+ "Ellipse",
+ "Rectangle",
+ "Polygon",
+ "BSpline",
+ "BezCurve",
+ "Fillet",
+ "Point",
+ "Shape2DView",
+ "PanelCut",
+ "PanelSheet",
+ "Profile",
+ ):
+ action_transform = QtGui.QAction(
+ Gui.getIcon("Std_TransformManip.svg"),
+ translate("Command", "Transform"), # Context `Command` instead of `draft`.
+ menu,
+ )
+ QtCore.QObject.connect(action_transform, QtCore.SIGNAL("triggered()"), self.transform)
menu.addAction(action_transform)
return True
@@ -501,8 +536,9 @@ class ViewProviderDraft(object):
return ":/icons/Draft_N-Curve.svg"
if tp in ("ShapeString"):
return ":/icons/Draft_ShapeString_tree.svg"
- if hasattr(self.Object,"AutoUpdate") and not self.Object.AutoUpdate:
+ if hasattr(self.Object, "AutoUpdate") and not self.Object.AutoUpdate:
import TechDrawGui
+
return ":/icons/TechDraw_TreePageUnsync.svg"
return ":/icons/Draft_Draft.svg"
diff --git a/src/Mod/Draft/draftviewproviders/view_circulararray.py b/src/Mod/Draft/draftviewproviders/view_circulararray.py
index a513bdfc6a..923716b64b 100644
--- a/src/Mod/Draft/draftviewproviders/view_circulararray.py
+++ b/src/Mod/Draft/draftviewproviders/view_circulararray.py
@@ -48,4 +48,5 @@ class ViewProviderCircularArray(ViewProviderDraftArray):
"""Set the icon in the tree view."""
return ":/icons/Draft_CircularArray"
+
## @}
diff --git a/src/Mod/Draft/draftviewproviders/view_clone.py b/src/Mod/Draft/draftviewproviders/view_clone.py
index 5c1151c538..740d9ba7e3 100644
--- a/src/Mod/Draft/draftviewproviders/view_clone.py
+++ b/src/Mod/Draft/draftviewproviders/view_clone.py
@@ -35,10 +35,11 @@ import FreeCADGui as Gui
from drafttaskpanels import task_scale
from draftutils.translate import translate
+
class ViewProviderClone:
"""a view provider that displays a Clone icon instead of a Draft icon"""
- def __init__(self,vobj):
+ def __init__(self, vobj):
vobj.Proxy = self
def attach(self, vobj):
@@ -65,9 +66,7 @@ class ViewProviderClone:
def setupContextMenu(self, vobj, menu):
action_edit = QtGui.QAction(translate("draft", "Edit"), menu)
- QtCore.QObject.connect(action_edit,
- QtCore.SIGNAL("triggered()"),
- self.edit)
+ QtCore.QObject.connect(action_edit, QtCore.SIGNAL("triggered()"), self.edit)
menu.addAction(action_edit)
def edit(self):
diff --git a/src/Mod/Draft/draftviewproviders/view_dimension.py b/src/Mod/Draft/draftviewproviders/view_dimension.py
index ea062c4843..21e91107e4 100644
--- a/src/Mod/Draft/draftviewproviders/view_dimension.py
+++ b/src/Mod/Draft/draftviewproviders/view_dimension.py
@@ -119,82 +119,56 @@ class ViewProviderDimensionBase(ViewProviderDraftAnnotation):
super().set_text_properties(vobj, properties)
if "TextSpacing" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Spacing between text and dimension line")
- vobj.addProperty("App::PropertyLength",
- "TextSpacing",
- "Text",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Spacing between text and dimension line")
+ vobj.addProperty("App::PropertyLength", "TextSpacing", "Text", _tip, locked=True)
vobj.TextSpacing = params.get_param("dimspacing")
if "FlipText" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Rotate the dimension text 180 degrees")
- vobj.addProperty("App::PropertyBool",
- "FlipText",
- "Text",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Rotate the dimension text 180 degrees")
+ vobj.addProperty("App::PropertyBool", "FlipText", "Text", _tip, locked=True)
vobj.FlipText = False
if "TextPosition" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Text Position.\n"
- "Leave '(0,0,0)' for automatic position")
- vobj.addProperty("App::PropertyVectorDistance",
- "TextPosition",
- "Text",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Text Position.\n" "Leave '(0,0,0)' for automatic position"
+ )
+ vobj.addProperty(
+ "App::PropertyVectorDistance", "TextPosition", "Text", _tip, locked=True
+ )
vobj.TextPosition = App.Vector(0, 0, 0)
if "Override" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Text override.\n"
- "Write '$dim' so that it is replaced by "
- "the dimension length.")
- vobj.addProperty("App::PropertyString",
- "Override",
- "Text",
- _tip,
- locked=True)
- vobj.Override = ''
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Text override.\n"
+ "Write '$dim' so that it is replaced by "
+ "the dimension length.",
+ )
+ vobj.addProperty("App::PropertyString", "Override", "Text", _tip, locked=True)
+ vobj.Override = ""
def set_units_properties(self, vobj, properties):
"""Set unit properties only if they don't already exist."""
super().set_units_properties(vobj, properties)
if "Decimals" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The number of decimals to show")
- vobj.addProperty("App::PropertyInteger",
- "Decimals",
- "Units",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "The number of decimals to show")
+ vobj.addProperty("App::PropertyInteger", "Decimals", "Units", _tip, locked=True)
vobj.Decimals = params.get_param("dimPrecision")
if "ShowUnit" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Show the unit suffix")
- vobj.addProperty("App::PropertyBool",
- "ShowUnit",
- "Units",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Show the unit suffix")
+ vobj.addProperty("App::PropertyBool", "ShowUnit", "Units", _tip, locked=True)
vobj.ShowUnit = params.get_param("showUnit")
if "UnitOverride" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "A unit to express the measurement.\n"
- "Leave blank for system default.\n"
- "Use 'arch' to force US arch notation")
- vobj.addProperty("App::PropertyString",
- "UnitOverride",
- "Units",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "A unit to express the measurement.\n"
+ "Leave blank for system default.\n"
+ "Use 'arch' to force US arch notation",
+ )
+ vobj.addProperty("App::PropertyString", "UnitOverride", "Units", _tip, locked=True)
vobj.UnitOverride = params.get_param("overrideUnit")
def set_graphics_properties(self, vobj, properties):
@@ -202,56 +176,33 @@ class ViewProviderDimensionBase(ViewProviderDraftAnnotation):
super().set_graphics_properties(vobj, properties)
if "FlipArrows" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Rotate the dimension arrows 180 degrees")
- vobj.addProperty("App::PropertyBool",
- "FlipArrows",
- "Graphics",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Rotate the dimension arrows 180 degrees")
+ vobj.addProperty("App::PropertyBool", "FlipArrows", "Graphics", _tip, locked=True)
vobj.FlipArrows = False
if "DimOvershoot" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The distance the dimension line "
- "is extended\n"
- "past the extension lines")
- vobj.addProperty("App::PropertyDistance",
- "DimOvershoot",
- "Graphics",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The distance the dimension line " "is extended\n" "past the extension lines",
+ )
+ vobj.addProperty("App::PropertyDistance", "DimOvershoot", "Graphics", _tip, locked=True)
vobj.DimOvershoot = params.get_param("dimovershoot")
if "ExtLines" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Length of the extension lines")
- vobj.addProperty("App::PropertyDistance",
- "ExtLines",
- "Graphics",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Length of the extension lines")
+ vobj.addProperty("App::PropertyDistance", "ExtLines", "Graphics", _tip, locked=True)
vobj.ExtLines = params.get_param("extlines")
if "ExtOvershoot" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Length of the extension line\n"
- "beyond the dimension line")
- vobj.addProperty("App::PropertyDistance",
- "ExtOvershoot",
- "Graphics",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Length of the extension line\n" "beyond the dimension line"
+ )
+ vobj.addProperty("App::PropertyDistance", "ExtOvershoot", "Graphics", _tip, locked=True)
vobj.ExtOvershoot = params.get_param("extovershoot")
if "ShowLine" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Shows the dimension line and arrows")
- vobj.addProperty("App::PropertyBool",
- "ShowLine",
- "Graphics",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Shows the dimension line and arrows")
+ vobj.addProperty("App::PropertyBool", "ShowLine", "Graphics", _tip, locked=True)
vobj.ShowLine = params.get_param("DimShowLine")
def getIcon(self):
@@ -284,8 +235,8 @@ class ViewProviderLinearDimension(ViewProviderDimensionBase):
self.textpos = coin.SoTransform()
self.textcolor = coin.SoBaseColor()
self.font = coin.SoFont()
- self.text_wld = coin.SoAsciiText() # World orientation. Can be oriented in 3D space.
- self.text_scr = coin.SoText2() # Screen orientation. Always faces the camera.
+ self.text_wld = coin.SoAsciiText() # World orientation. Can be oriented in 3D space.
+ self.text_scr = coin.SoText2() # Screen orientation. Always faces the camera.
# The text string needs to be initialized to something,
# otherwise it may cause a crash of the system
@@ -318,7 +269,8 @@ class ViewProviderLinearDimension(ViewProviderDimensionBase):
self.linecolor = coin.SoBaseColor()
self.drawstyle = coin.SoDrawStyle()
self.coords = coin.SoCoordinate3()
- import PartGui # Required for "SoBrepEdgeSet" (because a dimension is not a Part::FeaturePython object).
+ import PartGui # Required for "SoBrepEdgeSet" (because a dimension is not a Part::FeaturePython object).
+
self.line = coin.SoType.fromName("SoBrepEdgeSet").createInstance()
self.marks = coin.SoSeparator()
self.marksDimOvershoot = coin.SoSeparator()
@@ -411,8 +363,7 @@ class ViewProviderLinearDimension(ViewProviderDimensionBase):
self.p4 = obj.End
base = None
- if (hasattr(obj, "Direction")
- and not DraftVecUtils.isNull(obj.Direction)):
+ if hasattr(obj, "Direction") and not DraftVecUtils.isNull(obj.Direction):
v2 = self.p1 - obj.Dimline
v3 = self.p4 - obj.Dimline
v2 = DraftVecUtils.project(v2, obj.Direction)
@@ -501,10 +452,8 @@ class ViewProviderLinearDimension(ViewProviderDimensionBase):
_plane_rot = DraftVecUtils.getPlaneRotation(u, v1, norm)
if _plane_rot is not None:
rot1 = App.Placement(_plane_rot).Rotation.Q
- self.transDimOvershoot1.rotation.setValue((rot1[0], rot1[1],
- rot1[2], rot1[3]))
- self.transDimOvershoot2.rotation.setValue((rot1[0], rot1[1],
- rot1[2], rot1[3]))
+ self.transDimOvershoot1.rotation.setValue((rot1[0], rot1[1], rot1[2], rot1[3]))
+ self.transDimOvershoot2.rotation.setValue((rot1[0], rot1[1], rot1[2], rot1[3]))
self.trot = rot1
else:
self.trot = (0, 0, 0, 1)
@@ -516,10 +465,8 @@ class ViewProviderLinearDimension(ViewProviderDimensionBase):
_plane_rot = DraftVecUtils.getPlaneRotation(u, v2)
if _plane_rot is not None:
rot2 = App.Placement(_plane_rot).Rotation.Q
- self.trans1.rotation.setValue((rot2[0], rot2[1],
- rot2[2], rot2[3]))
- self.trans2.rotation.setValue((rot2[0], rot2[1],
- rot2[2], rot2[3]))
+ self.trans1.rotation.setValue((rot2[0], rot2[1], rot2[2], rot2[3]))
+ self.trans2.rotation.setValue((rot2[0], rot2[1], rot2[2], rot2[3]))
if self.p1 != self.p2:
u3 = self.p1 - self.p2
@@ -528,10 +475,8 @@ class ViewProviderLinearDimension(ViewProviderDimensionBase):
_plane_rot = DraftVecUtils.getPlaneRotation(u3, v3)
if _plane_rot is not None:
rot3 = App.Placement(_plane_rot).Rotation.Q
- self.transExtOvershoot1.rotation.setValue((rot3[0], rot3[1],
- rot3[2], rot3[3]))
- self.transExtOvershoot2.rotation.setValue((rot3[0], rot3[1],
- rot3[2], rot3[3]))
+ self.transExtOvershoot1.rotation.setValue((rot3[0], rot3[1], rot3[2], rot3[3]))
+ self.transExtOvershoot2.rotation.setValue((rot3[0], rot3[1], rot3[2], rot3[3]))
# Offset is the distance from the dimension line to the textual
# element that displays the value of the measurement
@@ -560,8 +505,7 @@ class ViewProviderLinearDimension(ViewProviderDimensionBase):
# The position of the text element in the dimension is provided
# in absolute coordinates by the value of `TextPosition`,
# if it is different from the default `(0,0,0)`
- if (hasattr(vobj, "TextPosition")
- and not DraftVecUtils.isNull(vobj.TextPosition)):
+ if hasattr(vobj, "TextPosition") and not DraftVecUtils.isNull(vobj.TextPosition):
self.tbase = vobj.TextPosition
else:
# Otherwise the position is calculated from the end points
@@ -570,11 +514,10 @@ class ViewProviderLinearDimension(ViewProviderDimensionBase):
center = self.p2 + (self.p3 - self.p2).multiply(0.5)
self.tbase = center + offset
- self.textpos.translation.setValue([self.tbase.x,
- self.tbase.y,
- self.tbase.z])
- self.textpos.rotation = coin.SbRotation(self.trot[0], self.trot[1],
- self.trot[2], self.trot[3])
+ self.textpos.translation.setValue([self.tbase.x, self.tbase.y, self.tbase.z])
+ self.textpos.rotation = coin.SbRotation(
+ self.trot[0], self.trot[1], self.trot[2], self.trot[3]
+ )
show_unit = True
if hasattr(vobj, "ShowUnit"):
@@ -589,12 +532,13 @@ class ViewProviderLinearDimension(ViewProviderDimensionBase):
# Special representation if we use 'Building US' scheme
doc = obj.Document
- if (not unit and doc.UnitSystem == doc.getEnumerationsOfProperty("UnitSystem")[5]) \
- or (unit == "arch"):
+ if (not unit and doc.UnitSystem == doc.getEnumerationsOfProperty("UnitSystem")[5]) or (
+ unit == "arch"
+ ):
self.string = App.Units.Quantity(length, App.Units.Length).UserString
if self.string.count('"') > 1:
# multiple inch tokens
- self.string = self.string.replace('"', "", self.string.count('"')-1)
+ self.string = self.string.replace('"', "", self.string.count('"') - 1)
sep = params.get_param("FeetSeparator")
# use a custom separator
self.string = self.string.replace("' ", "'" + sep)
@@ -602,13 +546,9 @@ class ViewProviderLinearDimension(ViewProviderDimensionBase):
self.string = self.string.replace(" ", " ")
self.string = self.string.replace(" ", " ")
elif hasattr(vobj, "Decimals"):
- self.string = units.display_external(length,
- vobj.Decimals,
- 'Length', show_unit, unit)
+ self.string = units.display_external(length, vobj.Decimals, "Length", show_unit, unit)
else:
- self.string = units.display_external(length,
- None,
- 'Length', show_unit, unit)
+ self.string = units.display_external(length, None, "Length", show_unit, unit)
if getattr(vobj, "Override", False):
self.string = vobj.Override.replace("$dim", self.string)
@@ -620,12 +560,10 @@ class ViewProviderLinearDimension(ViewProviderDimensionBase):
if m == "Screen":
# Calculate the spacing of the text
textsize = len(self.string) * vobj.FontSize.Value / 4.0
- spacing = (self.p3 - self.p2).Length/2.0 - textsize
+ spacing = (self.p3 - self.p2).Length / 2.0 - textsize
- self.p2a = self.p2 + DraftVecUtils.scaleTo(self.p3 - self.p2,
- spacing)
- self.p2b = self.p3 + DraftVecUtils.scaleTo(self.p2 - self.p3,
- spacing)
+ self.p2a = self.p2 + DraftVecUtils.scaleTo(self.p3 - self.p2, spacing)
+ self.p2b = self.p3 + DraftVecUtils.scaleTo(self.p2 - self.p3, spacing)
# fmt: off
self.coords.point.setValues([[self.p1.x, self.p1.y, self.p1.z],
[self.p2.x, self.p2.y, self.p2.z],
@@ -657,9 +595,12 @@ class ViewProviderLinearDimension(ViewProviderDimensionBase):
# Update all dimension values
if hasattr(self, "font"):
self.font.size = vobj.FontSize.Value * vobj.ScaleMultiplier
- if (hasattr(self, "node_wld") and hasattr(self, "p2")
- and "ArrowSizeStart" in properties
- and "ArrowSizeEnd" in properties):
+ if (
+ hasattr(self, "node_wld")
+ and hasattr(self, "p2")
+ and "ArrowSizeStart" in properties
+ and "ArrowSizeEnd" in properties
+ ):
self.remove_dim_arrows()
self.draw_dim_arrows(vobj)
if "DimOvershoot" in properties:
@@ -671,46 +612,48 @@ class ViewProviderLinearDimension(ViewProviderDimensionBase):
self.updateData(obj, "Start")
- elif (prop == "FontSize" and "FontSize" in properties
- and "ScaleMultiplier" in properties):
+ elif prop == "FontSize" and "FontSize" in properties and "ScaleMultiplier" in properties:
if hasattr(self, "font"):
self.font.size = vobj.FontSize.Value * vobj.ScaleMultiplier
- elif (prop == "FontName" and "FontName" in properties
- and hasattr(self, "font")):
+ elif prop == "FontName" and "FontName" in properties and hasattr(self, "font"):
self.font.name = str(vobj.FontName)
- elif (prop == "TextColor" and "TextColor" in properties
- and hasattr(self, "textcolor")):
+ elif prop == "TextColor" and "TextColor" in properties and hasattr(self, "textcolor"):
col = vobj.TextColor
self.textcolor.rgb.setValue(col[0], col[1], col[2])
- elif (prop == "LineColor" and "LineColor" in properties
- and hasattr(self, "linecolor")):
+ elif prop == "LineColor" and "LineColor" in properties and hasattr(self, "linecolor"):
col = vobj.LineColor
self.linecolor.rgb.setValue(col[0], col[1], col[2])
- elif (prop == "LineWidth" and "LineWidth" in properties
- and hasattr(self, "drawstyle")):
+ elif prop == "LineWidth" and "LineWidth" in properties and hasattr(self, "drawstyle"):
self.drawstyle.lineWidth = vobj.LineWidth
- elif (prop in ("ArrowSizeStart", "ArrowSizeEnd", "ArrowTypeStart", "ArrowTypeEnd")
- and "ArrowSizeStart" in properties
- and "ArrowSizeEnd" in properties
- and "ScaleMultiplier" in properties
- and hasattr(self, "node_wld") and hasattr(self, "p2")):
+ elif (
+ prop in ("ArrowSizeStart", "ArrowSizeEnd", "ArrowTypeStart", "ArrowTypeEnd")
+ and "ArrowSizeStart" in properties
+ and "ArrowSizeEnd" in properties
+ and "ScaleMultiplier" in properties
+ and hasattr(self, "node_wld")
+ and hasattr(self, "p2")
+ ):
self.remove_dim_arrows()
self.draw_dim_arrows(vobj)
- elif (prop == "DimOvershoot"
- and "DimOvershoot" in properties
- and "ScaleMultiplier" in properties):
+ elif (
+ prop == "DimOvershoot"
+ and "DimOvershoot" in properties
+ and "ScaleMultiplier" in properties
+ ):
self.remove_dim_overshoot()
self.draw_dim_overshoot(vobj)
- elif (prop == "ExtOvershoot"
- and "ExtOvershoot" in properties
- and "ScaleMultiplier" in properties):
+ elif (
+ prop == "ExtOvershoot"
+ and "ExtOvershoot" in properties
+ and "ScaleMultiplier" in properties
+ ):
self.remove_ext_overshoot()
self.draw_ext_overshoot(vobj)
@@ -734,8 +677,12 @@ class ViewProviderLinearDimension(ViewProviderDimensionBase):
def draw_dim_arrows(self, vobj):
"""Draw dimension arrows."""
- if not (hasattr(vobj, "ArrowTypeStart") and hasattr(vobj, "ArrowTypeEnd") and
- hasattr(vobj, "ArrowSizeStart") and hasattr(vobj, "ArrowSizeEnd")):
+ if not (
+ hasattr(vobj, "ArrowTypeStart")
+ and hasattr(vobj, "ArrowTypeEnd")
+ and hasattr(vobj, "ArrowSizeStart")
+ and hasattr(vobj, "ArrowSizeEnd")
+ ):
return
# Set scale
@@ -872,8 +819,8 @@ class ViewProviderAngularDimension(ViewProviderDimensionBase):
self.textpos = coin.SoTransform()
self.textcolor = coin.SoBaseColor()
self.font = coin.SoFont()
- self.text_wld = coin.SoAsciiText() # World orientation. Can be oriented in 3D space.
- self.text_scr = coin.SoText2() # Screen orientation. Always faces the camera.
+ self.text_wld = coin.SoAsciiText() # World orientation. Can be oriented in 3D space.
+ self.text_scr = coin.SoText2() # Screen orientation. Always faces the camera.
# The text string needs to be initialized to something,
# otherwise it may cause a crash of the system
@@ -902,7 +849,8 @@ class ViewProviderAngularDimension(ViewProviderDimensionBase):
self.linecolor = coin.SoBaseColor()
self.drawstyle = coin.SoDrawStyle()
self.coords = coin.SoCoordinate3()
- import PartGui # Required for "SoBrepEdgeSet" (because a dimension is not a Part::FeaturePython object).
+ import PartGui # Required for "SoBrepEdgeSet" (because a dimension is not a Part::FeaturePython object).
+
self.arc = coin.SoType.fromName("SoBrepEdgeSet").createInstance()
self.marks = coin.SoSeparator()
@@ -949,9 +897,9 @@ class ViewProviderAngularDimension(ViewProviderDimensionBase):
norm = obj.Normal
radius = (obj.Dimline - obj.Center).Length
- self.circle = Part.makeCircle(radius, obj.Center, norm,
- obj.FirstAngle.Value,
- obj.LastAngle.Value)
+ self.circle = Part.makeCircle(
+ radius, obj.Center, norm, obj.FirstAngle.Value, obj.LastAngle.Value
+ )
self.p2 = self.circle.Vertexes[0].Point
self.p3 = self.circle.Vertexes[-1].Point
midp = DraftGeomUtils.findMidpoint(self.circle)
@@ -968,13 +916,9 @@ class ViewProviderAngularDimension(ViewProviderDimensionBase):
show_unit = vobj.ShowUnit
if hasattr(vobj, "Decimals"):
- self.string = units.display_external(angle,
- vobj.Decimals,
- 'Angle', show_unit)
+ self.string = units.display_external(angle, vobj.Decimals, "Angle", show_unit)
else:
- self.string = units.display_external(angle,
- None,
- 'Angle', show_unit)
+ self.string = units.display_external(angle, None, "Angle", show_unit)
if vobj.Override:
self.string = vobj.Override.replace("$dim", self.string)
@@ -1019,31 +963,21 @@ class ViewProviderAngularDimension(ViewProviderDimensionBase):
i1 = pts1_num
i2 = i1 + pts2_num
- self.arc.coordIndex.setValues(0,
- pts1_num + pts2_num + 1,
- list(range(pts1_num))
- + [-1]
- + list(range(i1, i2)))
+ self.arc.coordIndex.setValues(
+ 0, pts1_num + pts2_num + 1, list(range(pts1_num)) + [-1] + list(range(i1, i2))
+ )
if pts1_num >= 3 and pts2_num >= 3:
- self.circle1 = Part.Arc(App.Vector(pts1[0][0],
- pts1[0][1],
- pts1[0][2]),
- App.Vector(pts1[1][0],
- pts1[1][1],
- pts1[1][2]),
- App.Vector(pts1[-1][0],
- pts1[-1][1],
- pts1[-1][2])).toShape()
- self.circle2 = Part.Arc(App.Vector(pts2[0][0],
- pts2[0][1],
- pts2[0][2]),
- App.Vector(pts2[1][0],
- pts2[1][1],
- pts2[1][2]),
- App.Vector(pts2[-1][0],
- pts2[-1][1],
- pts2[-1][2])).toShape()
+ self.circle1 = Part.Arc(
+ App.Vector(pts1[0][0], pts1[0][1], pts1[0][2]),
+ App.Vector(pts1[1][0], pts1[1][1], pts1[1][2]),
+ App.Vector(pts1[-1][0], pts1[-1][1], pts1[-1][2]),
+ ).toShape()
+ self.circle2 = Part.Arc(
+ App.Vector(pts2[0][0], pts2[0][1], pts2[0][2]),
+ App.Vector(pts2[1][0], pts2[1][1], pts2[1][2]),
+ App.Vector(pts2[-1][0], pts2[-1][1], pts2[-1][2]),
+ ).toShape()
else:
pts = []
for i in range(arcsegs + 1):
@@ -1051,9 +985,7 @@ class ViewProviderAngularDimension(ViewProviderDimensionBase):
pts.append([p.x, p.y, p.z])
self.coords.point.setValues(pts)
- self.arc.coordIndex.setValues(0,
- arcsegs + 1,
- list(range(arcsegs + 1)))
+ self.arc.coordIndex.setValues(0, arcsegs + 1, list(range(arcsegs + 1)))
# Set the arrow coords and rotation
p2 = (self.p2.x, self.p2.y, self.p2.z)
@@ -1065,13 +997,15 @@ class ViewProviderAngularDimension(ViewProviderDimensionBase):
self.coord2.point.setValue(p3)
# Calculate small chords to make arrows look better
- if hasattr(vobj, "ArrowSizeStart") \
- and hasattr(vobj, "ArrowSizeEnd") \
- and hasattr(vobj, "ScaleMultiplier") \
- and hasattr(vobj, "FlipArrows") \
- and vobj.ArrowSizeStart.Value !=0 \
- and vobj.ArrowSizeEnd.Value !=0 \
- and vobj.ScaleMultiplier != 0:
+ if (
+ hasattr(vobj, "ArrowSizeStart")
+ and hasattr(vobj, "ArrowSizeEnd")
+ and hasattr(vobj, "ScaleMultiplier")
+ and hasattr(vobj, "FlipArrows")
+ and vobj.ArrowSizeStart.Value != 0
+ and vobj.ArrowSizeEnd.Value != 0
+ and vobj.ScaleMultiplier != 0
+ ):
half_arrow_length_sta = 2 * vobj.ArrowSizeStart.Value * vobj.ScaleMultiplier
arrow_angle_sta = 2 * math.asin(min(1, half_arrow_length_sta / radius))
half_arrow_length_end = 2 * vobj.ArrowSizeEnd.Value * vobj.ScaleMultiplier
@@ -1080,10 +1014,12 @@ class ViewProviderAngularDimension(ViewProviderDimensionBase):
arrow_angle_sta = -arrow_angle_sta
arrow_angle_end = -arrow_angle_end
- u1 = (self.circle.valueAt(first + arrow_angle_sta)
- - self.circle.valueAt(first)).normalize()
- u2 = (self.circle.valueAt(last)
- - self.circle.valueAt(last - arrow_angle_end)).normalize()
+ u1 = (
+ self.circle.valueAt(first + arrow_angle_sta) - self.circle.valueAt(first)
+ ).normalize()
+ u2 = (
+ self.circle.valueAt(last) - self.circle.valueAt(last - arrow_angle_end)
+ ).normalize()
w2 = self.circle.Curve.Axis
w1 = w2.negative()
@@ -1100,8 +1036,7 @@ class ViewProviderAngularDimension(ViewProviderDimensionBase):
# Set text position and rotation
self.tbase = midp
- if (hasattr(vobj, "TextPosition")
- and not DraftVecUtils.isNull(vobj.TextPosition)):
+ if hasattr(vobj, "TextPosition") and not DraftVecUtils.isNull(vobj.TextPosition):
self.tbase = vobj.TextPosition
u3 = ray.cross(norm).normalize()
@@ -1125,9 +1060,7 @@ class ViewProviderAngularDimension(ViewProviderDimensionBase):
self.tbase = self.tbase.add(offset)
q = r.Q
- self.textpos.translation.setValue([self.tbase.x,
- self.tbase.y,
- self.tbase.z])
+ self.textpos.translation.setValue([self.tbase.x, self.tbase.y, self.tbase.z])
self.textpos.rotation = coin.SbRotation(q[0], q[1], q[2], q[3])
# Set the angle property
@@ -1149,9 +1082,12 @@ class ViewProviderAngularDimension(ViewProviderDimensionBase):
if prop == "ScaleMultiplier" and "ScaleMultiplier" in properties:
if hasattr(self, "font"):
self.font.size = vobj.FontSize.Value * vobj.ScaleMultiplier
- if (hasattr(self, "node_wld") and hasattr(self, "p2")
- and "ArrowSizeStart" in properties
- and "ArrowSizeEnd" in properties):
+ if (
+ hasattr(self, "node_wld")
+ and hasattr(self, "p2")
+ and "ArrowSizeStart" in properties
+ and "ArrowSizeEnd" in properties
+ ):
self.remove_dim_arrows()
self.draw_dim_arrows(vobj)
@@ -1161,25 +1097,26 @@ class ViewProviderAngularDimension(ViewProviderDimensionBase):
if hasattr(self, "font"):
self.font.size = vobj.FontSize.Value * vobj.ScaleMultiplier
- elif (prop == "FontName" and hasattr(self, "font")):
+ elif prop == "FontName" and hasattr(self, "font"):
self.font.name = str(vobj.FontName)
- elif (prop == "TextColor" and "TextColor" in properties
- and hasattr(self, "textcolor")):
+ elif prop == "TextColor" and "TextColor" in properties and hasattr(self, "textcolor"):
col = vobj.TextColor
self.textcolor.rgb.setValue(col[0], col[1], col[2])
- elif (prop == "LineColor" and "LineColor" in properties
- and hasattr(self, "linecolor")):
+ elif prop == "LineColor" and "LineColor" in properties and hasattr(self, "linecolor"):
col = vobj.LineColor
self.linecolor.rgb.setValue(col[0], col[1], col[2])
elif prop == "LineWidth" and hasattr(self, "drawstyle"):
self.drawstyle.lineWidth = vobj.LineWidth
- elif (prop in ("ArrowSizeStart", "ArrowTypeStart", "ArrowSizeEnd", "ArrowTypeEnd")
- and "ScaleMultiplier" in properties
- and hasattr(self, "node_wld") and hasattr(self, "p2")):
+ elif (
+ prop in ("ArrowSizeStart", "ArrowTypeStart", "ArrowSizeEnd", "ArrowTypeEnd")
+ and "ScaleMultiplier" in properties
+ and hasattr(self, "node_wld")
+ and hasattr(self, "p2")
+ ):
self.updateData(obj, None)
self.remove_dim_arrows()
self.draw_dim_arrows(vobj)
@@ -1197,8 +1134,12 @@ class ViewProviderAngularDimension(ViewProviderDimensionBase):
def draw_dim_arrows(self, vobj):
"""Draw dimension arrows."""
- if not (hasattr(vobj, "ArrowTypeStart") and hasattr(vobj, "ArrowTypeEnd") and
- hasattr(vobj, "ArrowSizeStart") and hasattr(vobj, "ArrowSizeEnd")):
+ if not (
+ hasattr(vobj, "ArrowTypeStart")
+ and hasattr(vobj, "ArrowTypeEnd")
+ and hasattr(vobj, "ArrowSizeStart")
+ and hasattr(vobj, "ArrowSizeEnd")
+ ):
return
# Set scale
diff --git a/src/Mod/Draft/draftviewproviders/view_draft_annotation.py b/src/Mod/Draft/draftviewproviders/view_draft_annotation.py
index 2ae971188a..591308b22d 100644
--- a/src/Mod/Draft/draftviewproviders/view_draft_annotation.py
+++ b/src/Mod/Draft/draftviewproviders/view_draft_annotation.py
@@ -76,34 +76,34 @@ class ViewProviderDraftAnnotation(object):
def set_annotation_properties(self, vobj, properties):
"""Set annotation properties only if they don't already exist."""
if "ScaleMultiplier" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "General scaling factor that affects "
- "the annotation consistently\n"
- "because it scales the text, "
- "and the line decorations, if any,\n"
- "in the same proportion.")
- vobj.addProperty("App::PropertyFloat",
- "ScaleMultiplier",
- "Annotation",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "General scaling factor that affects "
+ "the annotation consistently\n"
+ "because it scales the text, "
+ "and the line decorations, if any,\n"
+ "in the same proportion.",
+ )
+ vobj.addProperty(
+ "App::PropertyFloat", "ScaleMultiplier", "Annotation", _tip, locked=True
+ )
vobj.ScaleMultiplier = params.get_param("DefaultAnnoScaleMultiplier")
if "AnnotationStyle" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Annotation style to apply "
- "to this object.\n"
- "When using a saved style "
- "some of the view properties "
- "will become read-only;\n"
- "they will only be editable by changing "
- "the style through "
- "the 'Annotation style editor' tool.")
- vobj.addProperty("App::PropertyEnumeration",
- "AnnotationStyle",
- "Annotation",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "Annotation style to apply "
+ "to this object.\n"
+ "When using a saved style "
+ "some of the view properties "
+ "will become read-only;\n"
+ "they will only be editable by changing "
+ "the style through "
+ "the 'Annotation style editor' tool.",
+ )
+ vobj.addProperty(
+ "App::PropertyEnumeration", "AnnotationStyle", "Annotation", _tip, locked=True
+ )
styles = []
for key in vobj.Object.Document.Meta.keys():
if key.startswith("Draft_Style_"):
@@ -114,33 +114,18 @@ class ViewProviderDraftAnnotation(object):
def set_text_properties(self, vobj, properties):
"""Set text properties only if they don't already exist."""
if "FontName" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Font name")
- vobj.addProperty("App::PropertyFont",
- "FontName",
- "Text",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Font name")
+ vobj.addProperty("App::PropertyFont", "FontName", "Text", _tip, locked=True)
vobj.FontName = params.get_param("textfont")
if "FontSize" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Font size")
- vobj.addProperty("App::PropertyLength",
- "FontSize",
- "Text",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Font size")
+ vobj.addProperty("App::PropertyLength", "FontSize", "Text", _tip, locked=True)
vobj.FontSize = params.get_param("textheight")
if "TextColor" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Text color")
- vobj.addProperty("App::PropertyColor",
- "TextColor",
- "Text",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Text color")
+ vobj.addProperty("App::PropertyColor", "TextColor", "Text", _tip, locked=True)
vobj.TextColor = params.get_param("DefaultTextColor") | 0x000000FF
def set_units_properties(self, vobj, properties):
@@ -152,65 +137,43 @@ class ViewProviderDraftAnnotation(object):
return
if "ArrowSizeStart" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Arrow size")
- vobj.addProperty("App::PropertyLength",
- "ArrowSizeStart",
- "Graphics",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Arrow size")
+ vobj.addProperty("App::PropertyLength", "ArrowSizeStart", "Graphics", _tip, locked=True)
vobj.ArrowSizeStart = params.get_param("arrowsizestart")
if "ArrowTypeStart" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Arrow type")
- vobj.addProperty("App::PropertyEnumeration",
- "ArrowTypeStart",
- "Graphics",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Arrow type")
+ vobj.addProperty(
+ "App::PropertyEnumeration", "ArrowTypeStart", "Graphics", _tip, locked=True
+ )
vobj.ArrowTypeStart = utils.ARROW_TYPES
vobj.ArrowTypeStart = "None"
if vobj.Object.Proxy.Type != "Label":
if "ArrowSizeEnd" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Arrow size")
- vobj.addProperty("App::PropertyLength",
- "ArrowSizeEnd",
- "Graphics",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Arrow size")
+ vobj.addProperty(
+ "App::PropertyLength", "ArrowSizeEnd", "Graphics", _tip, locked=True
+ )
vobj.ArrowSizeEnd = params.get_param("arrowsizeend")
if "ArrowTypeEnd" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Arrow type")
- vobj.addProperty("App::PropertyEnumeration",
- "ArrowTypeEnd",
- "Graphics",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Arrow type")
+ vobj.addProperty(
+ "App::PropertyEnumeration", "ArrowTypeEnd", "Graphics", _tip, locked=True
+ )
vobj.ArrowTypeEnd = utils.ARROW_TYPES
vobj.ArrowTypeEnd = "None"
if "LineWidth" not in properties:
_tip = QT_TRANSLATE_NOOP("App::Property", "Line width")
- vobj.addProperty("App::PropertyFloat",
- "LineWidth",
- "Graphics",
- _tip,
- locked=True)
+ vobj.addProperty("App::PropertyFloat", "LineWidth", "Graphics", _tip, locked=True)
vobj.LineWidth = params.get_param("DefaultAnnoLineWidth")
if "LineColor" not in properties:
_tip = QT_TRANSLATE_NOOP("App::Property", "Line color")
- vobj.addProperty("App::PropertyColor",
- "LineColor",
- "Graphics",
- _tip,
- locked=True)
+ vobj.addProperty("App::PropertyColor", "LineColor", "Graphics", _tip, locked=True)
vobj.LineColor = params.get_param("DefaultAnnoLineColor") | 0x000000FF
def dumps(self):
@@ -252,7 +215,7 @@ class ViewProviderDraftAnnotation(object):
for visprop in utils.get_default_annotation_style().keys():
if visprop in properties:
# make property writable
- vobj.setPropertyStatus(visprop, '-ReadOnly')
+ vobj.setPropertyStatus(visprop, "-ReadOnly")
else:
# set style
for key, value in meta.items():
@@ -284,7 +247,7 @@ class ViewProviderDraftAnnotation(object):
return None
if utils.get_type(vobj.Object) == "AngularDimension":
- return False # Required, else edit mode is entered.
+ return False # Required, else edit mode is entered.
if not "Draft_Edit" in Gui.listCommands():
self.wb_before_edit = Gui.activeWorkbench()
@@ -315,11 +278,8 @@ class ViewProviderDraftAnnotation(object):
if utils.get_type(self.Object) in ("AngularDimension", "Label"):
return
- action_edit = QtGui.QAction(translate("draft", "Edit"),
- menu)
- QtCore.QObject.connect(action_edit,
- QtCore.SIGNAL("triggered()"),
- self.edit)
+ action_edit = QtGui.QAction(translate("draft", "Edit"), menu)
+ QtCore.QObject.connect(action_edit, QtCore.SIGNAL("triggered()"), self.edit)
menu.addAction(action_edit)
def edit(self):
@@ -329,4 +289,5 @@ class ViewProviderDraftAnnotation(object):
"""Return the path to the icon used by the view provider."""
return ":/icons/Draft_Text.svg"
+
## @}
diff --git a/src/Mod/Draft/draftviewproviders/view_draftlink.py b/src/Mod/Draft/draftviewproviders/view_draftlink.py
index 60b54a7b65..b0a625bab3 100644
--- a/src/Mod/Draft/draftviewproviders/view_draftlink.py
+++ b/src/Mod/Draft/draftviewproviders/view_draftlink.py
@@ -30,32 +30,32 @@
# @{
from draftviewproviders.view_base import ViewProviderDraft
-class ViewProviderDraftLink(ViewProviderDraft):
- """ A view provider for link type object.
- """
- def __init__(self,vobj):
+class ViewProviderDraftLink(ViewProviderDraft):
+ """A view provider for link type object."""
+
+ def __init__(self, vobj):
super(ViewProviderDraftLink, self).__init__(vobj)
def getIcon(self):
tp = self.Object.Proxy.Type
- if tp == 'Array':
- if self.Object.ArrayType == 'ortho':
+ if tp == "Array":
+ if self.Object.ArrayType == "ortho":
return ":/icons/Draft_LinkArray.svg"
- elif self.Object.ArrayType == 'polar':
+ elif self.Object.ArrayType == "polar":
return ":/icons/Draft_PolarLinkArray.svg"
- elif self.Object.ArrayType == 'circular':
+ elif self.Object.ArrayType == "circular":
return ":/icons/Draft_CircularLinkArray.svg"
- elif tp == 'PathArray':
+ elif tp == "PathArray":
return ":/icons/Draft_PathLinkArray.svg"
- elif tp == 'PathTwistedArray':
+ elif tp == "PathTwistedArray":
return ":/icons/Draft_PathTwistedLinkArray.svg"
- elif tp == 'PointArray':
+ elif tp == "PointArray":
return ":/icons/Draft_PointLinkArray.svg"
def claimChildren(self):
obj = self.Object
- if hasattr(obj,'ExpandArray'):
+ if hasattr(obj, "ExpandArray"):
expand = obj.ExpandArray
else:
expand = obj.ShowElement
diff --git a/src/Mod/Draft/draftviewproviders/view_facebinder.py b/src/Mod/Draft/draftviewproviders/view_facebinder.py
index 2190493823..241e27ed77 100644
--- a/src/Mod/Draft/draftviewproviders/view_facebinder.py
+++ b/src/Mod/Draft/draftviewproviders/view_facebinder.py
@@ -31,6 +31,7 @@ import FreeCADGui as Gui
from draftviewproviders.view_base import ViewProviderDraft
+
class ViewProviderFacebinder(ViewProviderDraft):
def __init__(self, vobj):
@@ -43,7 +44,8 @@ class ViewProviderFacebinder(ViewProviderDraft):
if mode != 0:
return None
- import DraftGui # Moving this to the top of the file results in a circular import.
+ import DraftGui # Moving this to the top of the file results in a circular import.
+
taskd = DraftGui.FacebinderTaskPanel()
taskd.obj = vobj.Object
taskd.update()
diff --git a/src/Mod/Draft/draftviewproviders/view_fillet.py b/src/Mod/Draft/draftviewproviders/view_fillet.py
index 89e568f722..425a6f302a 100644
--- a/src/Mod/Draft/draftviewproviders/view_fillet.py
+++ b/src/Mod/Draft/draftviewproviders/view_fillet.py
@@ -42,6 +42,7 @@ class ViewProviderFillet(ViewProviderWire):
def doubleClicked(self, vobj):
# See setEdit in ViewProviderDraft.
import FreeCADGui as Gui
+
Gui.runCommand("Std_TransformManip")
return True
diff --git a/src/Mod/Draft/draftviewproviders/view_hatch.py b/src/Mod/Draft/draftviewproviders/view_hatch.py
index f66f0c20bf..994b7ad0b7 100644
--- a/src/Mod/Draft/draftviewproviders/view_hatch.py
+++ b/src/Mod/Draft/draftviewproviders/view_hatch.py
@@ -1,24 +1,24 @@
-#***************************************************************************
-#* *
-#* Copyright (c) 2021 Yorik van Havre *
-#* *
-#* This program is free software; you can redistribute it and/or modify *
-#* it under the terms of the GNU Lesser General Public License (LGPL) *
-#* as published by the Free Software Foundation; either version 2 of *
-#* the License, or (at your option) any later version. *
-#* for detail see the LICENCE text file. *
-#* *
-#* This program is distributed in the hope that it will be useful, *
-#* but WITHOUT ANY WARRANTY; without even the implied warranty of *
-#* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
-#* GNU Library General Public License for more details. *
-#* *
-#* You should have received a copy of the GNU Library General Public *
-#* License along with this program; if not, write to the Free Software *
-#* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 *
-#* USA *
-#* *
-#***************************************************************************
+# ***************************************************************************
+# * *
+# * Copyright (c) 2021 Yorik van Havre *
+# * *
+# * This program is free software; you can redistribute it and/or modify *
+# * it under the terms of the GNU Lesser General Public License (LGPL) *
+# * as published by the Free Software Foundation; either version 2 of *
+# * the License, or (at your option) any later version. *
+# * for detail see the LICENCE text file. *
+# * *
+# * This program is distributed in the hope that it will be useful, *
+# * but WITHOUT ANY WARRANTY; without even the implied warranty of *
+# * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
+# * GNU Library General Public License for more details. *
+# * *
+# * You should have received a copy of the GNU Library General Public *
+# * License along with this program; if not, write to the Free Software *
+# * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 *
+# * USA *
+# * *
+# ***************************************************************************
"""Provides the viewprovider code for the Hatch object."""
@@ -31,6 +31,7 @@ import FreeCADGui as Gui
from draftguitools.gui_hatch import Draft_Hatch_TaskPanel
from draftutils.translate import translate
+
class ViewProviderDraftHatch:
def __init__(self, vobj):
@@ -80,23 +81,20 @@ class ViewProviderDraftHatch:
return True
def setupContextMenu(self, vobj, menu):
- action_edit = QtGui.QAction(translate("draft", "Edit"),
- menu)
- QtCore.QObject.connect(action_edit,
- QtCore.SIGNAL("triggered()"),
- self.edit)
+ action_edit = QtGui.QAction(translate("draft", "Edit"), menu)
+ QtCore.QObject.connect(action_edit, QtCore.SIGNAL("triggered()"), self.edit)
menu.addAction(action_edit)
- action_transform = QtGui.QAction(Gui.getIcon("Std_TransformManip.svg"),
- translate("Command", "Transform"), # Context `Command` instead of `draft`.
- menu)
- QtCore.QObject.connect(action_transform,
- QtCore.SIGNAL("triggered()"),
- self.transform)
+ action_transform = QtGui.QAction(
+ Gui.getIcon("Std_TransformManip.svg"),
+ translate("Command", "Transform"), # Context `Command` instead of `draft`.
+ menu,
+ )
+ QtCore.QObject.connect(action_transform, QtCore.SIGNAL("triggered()"), self.transform)
menu.addAction(action_transform)
- return True # Removes `Transform` and `Set colors` from the default
- # Part::FeaturePython context menu. See view_base.py.
+ return True # Removes `Transform` and `Set colors` from the default
+ # Part::FeaturePython context menu. See view_base.py.
def edit(self):
Gui.ActiveDocument.setEdit(self.Object, 0)
diff --git a/src/Mod/Draft/draftviewproviders/view_label.py b/src/Mod/Draft/draftviewproviders/view_label.py
index 0a6e70418d..2b7855aada 100644
--- a/src/Mod/Draft/draftviewproviders/view_label.py
+++ b/src/Mod/Draft/draftviewproviders/view_label.py
@@ -53,44 +53,25 @@ class ViewProviderLabel(ViewProviderDraftAnnotation):
super().set_text_properties(vobj, properties)
if "TextAlignment" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Vertical alignment")
- vobj.addProperty("App::PropertyEnumeration",
- "TextAlignment",
- "Text",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Vertical alignment")
+ vobj.addProperty("App::PropertyEnumeration", "TextAlignment", "Text", _tip, locked=True)
vobj.TextAlignment = ["Top", "Middle", "Bottom"]
vobj.TextAlignment = "Bottom"
if "MaxChars" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Maximum number of characters "
- "on each line of the text box")
- vobj.addProperty("App::PropertyInteger",
- "MaxChars",
- "Text",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Maximum number of characters " "on each line of the text box"
+ )
+ vobj.addProperty("App::PropertyInteger", "MaxChars", "Text", _tip, locked=True)
if "Justification" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Horizontal alignment")
- vobj.addProperty("App::PropertyEnumeration",
- "Justification",
- "Text",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Horizontal alignment")
+ vobj.addProperty("App::PropertyEnumeration", "Justification", "Text", _tip, locked=True)
vobj.Justification = ["Left", "Center", "Right"]
if "LineSpacing" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Line spacing (relative to font size)")
- vobj.addProperty("App::PropertyFloat",
- "LineSpacing",
- "Text",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Line spacing (relative to font size)")
+ vobj.addProperty("App::PropertyFloat", "LineSpacing", "Text", _tip, locked=True)
vobj.LineSpacing = params.get_param("LineSpacing")
def set_graphics_properties(self, vobj, properties):
@@ -100,24 +81,15 @@ class ViewProviderLabel(ViewProviderDraftAnnotation):
vobj.ArrowTypeStart = params.get_param("dimsymbolstart")
if "Frame" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The type of frame around the text "
- "of this object")
- vobj.addProperty("App::PropertyEnumeration",
- "Frame",
- "Graphics",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "The type of frame around the text " "of this object"
+ )
+ vobj.addProperty("App::PropertyEnumeration", "Frame", "Graphics", _tip, locked=True)
vobj.Frame = ["None", "Rectangle"]
if "Line" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Display a leader line or not")
- vobj.addProperty("App::PropertyBool",
- "Line",
- "Graphics",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Display a leader line or not")
+ vobj.addProperty("App::PropertyBool", "Line", "Graphics", _tip, locked=True)
vobj.Line = True
def getIcon(self):
@@ -137,7 +109,7 @@ class ViewProviderLabel(ViewProviderDraftAnnotation):
self.drawstyle = coin.SoDrawStyle()
self.drawstyle.style = coin.SoDrawStyle.LINES
- import PartGui # Required for "SoBrepEdgeSet" (because a label is not a Part::FeaturePython object).
+ import PartGui # Required for "SoBrepEdgeSet" (because a label is not a Part::FeaturePython object).
self.lcoords = coin.SoCoordinate3()
self.line = coin.SoType.fromName("SoBrepEdgeSet").createInstance()
@@ -145,8 +117,8 @@ class ViewProviderLabel(ViewProviderDraftAnnotation):
self.mattext = coin.SoMaterial()
self.textpos = coin.SoTransform()
self.font = coin.SoFont()
- self.text_wld = coin.SoAsciiText() # World orientation. Can be oriented in 3D space.
- self.text_scr = coin.SoText2() # Screen orientation. Always faces the camera.
+ self.text_wld = coin.SoAsciiText() # World orientation. Can be oriented in 3D space.
+ self.text_scr = coin.SoText2() # Screen orientation. Always faces the camera.
self.fcoords = coin.SoCoordinate3()
self.frame = coin.SoType.fromName("SoBrepEdgeSet").createInstance()
@@ -223,14 +195,16 @@ class ViewProviderLabel(ViewProviderDraftAnnotation):
if n_points >= 2:
self.line.coordIndex.deleteValues(0)
self.lcoords.point.setValues(obj.Points)
- self.line.coordIndex.setValues(0,
- n_points,
- range(n_points))
+ self.line.coordIndex.setValues(0, n_points, range(n_points))
self.onChanged(obj.ViewObject, "ArrowTypeStart")
# When initially called (on doc open) properties of vobj are not yet available.
# This function is however triggered again from update_label.
- if getattr(vobj, "Justification", "") == "Center" and obj.StraightDistance != 0.0 and obj.StraightDirection != "Custom":
+ if (
+ getattr(vobj, "Justification", "") == "Center"
+ and obj.StraightDistance != 0.0
+ and obj.StraightDirection != "Custom"
+ ):
if obj.StraightDirection != "Vertical":
obj.StraightDirection = "Vertical"
if not hasattr(vobj, "TextAlignment"):
@@ -246,8 +220,10 @@ class ViewProviderLabel(ViewProviderDraftAnnotation):
if vobj.Justification == "Right":
vobj.Justification = "Left"
- self.onChanged(obj.ViewObject, "DisplayMode") # Property to trigger update_label and update_frame.
- # We could have used a different property.
+ self.onChanged(
+ obj.ViewObject, "DisplayMode"
+ ) # Property to trigger update_label and update_frame.
+ # We could have used a different property.
elif prop == "Text" and obj.Text:
self.text_wld.string.setValue("")
@@ -266,17 +242,26 @@ class ViewProviderLabel(ViewProviderDraftAnnotation):
obj = vobj.Object
properties = vobj.PropertiesList
- can_update_label = ("DisplayMode" in properties
- and "FontName" in properties
- and "FontSize" in properties
- and "Justification" in properties
- and "LineSpacing" in properties
- and "ScaleMultiplier" in properties
- and "TextAlignment" in properties) # Top, Middle or Bottom.
- can_update_frame = (can_update_label
- and "Frame" in properties)
+ can_update_label = (
+ "DisplayMode" in properties
+ and "FontName" in properties
+ and "FontSize" in properties
+ and "Justification" in properties
+ and "LineSpacing" in properties
+ and "ScaleMultiplier" in properties
+ and "TextAlignment" in properties
+ ) # Top, Middle or Bottom.
+ can_update_frame = can_update_label and "Frame" in properties
- if prop in ["DisplayMode", "FontName", "FontSize", "Justification", "LineSpacing", "TextAlignment", "Frame"]:
+ if prop in [
+ "DisplayMode",
+ "FontName",
+ "FontSize",
+ "Justification",
+ "LineSpacing",
+ "TextAlignment",
+ "Frame",
+ ]:
if can_update_label:
self.update_label(obj, vobj)
if can_update_frame:
@@ -292,9 +277,11 @@ class ViewProviderLabel(ViewProviderDraftAnnotation):
if can_update_frame:
self.update_frame(obj, vobj)
- elif (prop == "ArrowSizeStart"
- and "ArrowSizeStart" in properties
- and "ScaleMultiplier" in properties):
+ elif (
+ prop == "ArrowSizeStart"
+ and "ArrowSizeStart" in properties
+ and "ScaleMultiplier" in properties
+ ):
s = vobj.ArrowSizeStart.Value * vobj.ScaleMultiplier
if s:
self.arrowpos.scaleFactor.setValue((s, s, s))
@@ -362,8 +349,9 @@ class ViewProviderLabel(ViewProviderDraftAnnotation):
if obj.StraightDistance != 0.0 and obj.StraightDirection != "Custom":
if obj.StraightDirection != "Vertical":
obj.StraightDirection = "Vertical"
- if (obj.StraightDistance < 0.0 and vobj.TextAlignment == "Top") \
- or (obj.StraightDistance > 0.0 and vobj.TextAlignment == "Bottom"):
+ if (obj.StraightDistance < 0.0 and vobj.TextAlignment == "Top") or (
+ obj.StraightDistance > 0.0 and vobj.TextAlignment == "Bottom"
+ ):
obj.StraightDistance = -obj.StraightDistance
obj.recompute()
obj.purgeTouched()
@@ -417,23 +405,23 @@ class ViewProviderLabel(ViewProviderDraftAnnotation):
self.startSymbol = gui_utils.dim_symbol(startS)
self.arrow.addChild(self.startSymbol)
- prec = 10**(-utils.precision())
- x_axis = App.Vector(1,0,0)
+ prec = 10 ** (-utils.precision())
+ x_axis = App.Vector(1, 0, 0)
target_dir = None
# search in Points to get first point != to TargetPoint and use it
# to get the target line direction
for pnt in obj.Points[-2::-1]:
- if not pnt.isEqual(obj.Points[-1],prec):
+ if not pnt.isEqual(obj.Points[-1], prec):
target_dir = pnt.sub(obj.Points[-1])
break
if target_dir is None:
target_dir = x_axis
- target_dir_xy = obj.Placement.Rotation.inverted()*target_dir
- angle = target_dir_xy.getAngle(x_axis)*App.Units.Radian
+ target_dir_xy = obj.Placement.Rotation.inverted() * target_dir
+ angle = target_dir_xy.getAngle(x_axis) * App.Units.Radian
axis = x_axis.cross(target_dir_xy)
rot = App.Rotation(axis, angle)
- self.arrowpos.rotation.setValue((obj.Placement.Rotation*rot).Q)
+ self.arrowpos.rotation.setValue((obj.Placement.Rotation * rot).Q)
self.arrowpos.translation.setValue(obj.Points[-1])
def update_frame(self, obj, vobj):
@@ -478,9 +466,7 @@ class ViewProviderLabel(ViewProviderDraftAnnotation):
pts.append(first_frame_point)
self.fcoords.point.setValues(pts)
- self.frame.coordIndex.setValues(0,
- len(pts),
- range(len(pts)))
+ self.frame.coordIndex.setValues(0, len(pts), range(len(pts)))
# Alias for compatibility with v0.18 and earlier
diff --git a/src/Mod/Draft/draftviewproviders/view_layer.py b/src/Mod/Draft/draftviewproviders/view_layer.py
index 70eedc9ed6..29bbfcdac7 100644
--- a/src/Mod/Draft/draftviewproviders/view_layer.py
+++ b/src/Mod/Draft/draftviewproviders/view_layer.py
@@ -60,122 +60,98 @@ class ViewProviderLayer:
def set_override_options(self, vobj, properties):
"""Set property options only if they don't already exist."""
if "OverrideLineColorChildren" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "If it is true, the objects contained "
- "within this layer will adopt "
- "the line color of the layer")
- vobj.addProperty("App::PropertyBool",
- "OverrideLineColorChildren",
- "Layer",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "If it is true, the objects contained "
+ "within this layer will adopt "
+ "the line color of the layer",
+ )
+ vobj.addProperty(
+ "App::PropertyBool", "OverrideLineColorChildren", "Layer", _tip, locked=True
+ )
vobj.OverrideLineColorChildren = True
if "OverrideShapeAppearanceChildren" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "If it is true, the objects contained "
- "within this layer will adopt "
- "the shape appearance of the layer")
- vobj.addProperty("App::PropertyBool",
- "OverrideShapeAppearanceChildren",
- "Layer",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "If it is true, the objects contained "
+ "within this layer will adopt "
+ "the shape appearance of the layer",
+ )
+ vobj.addProperty(
+ "App::PropertyBool", "OverrideShapeAppearanceChildren", "Layer", _tip, locked=True
+ )
vobj.OverrideShapeAppearanceChildren = True
if "UsePrintColor" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "If it is true, the print color "
- "will be used when objects in this "
- "layer are placed on a TechDraw page")
- vobj.addProperty("App::PropertyBool",
- "UsePrintColor",
- "Print",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "If it is true, the print color "
+ "will be used when objects in this "
+ "layer are placed on a TechDraw page",
+ )
+ vobj.addProperty("App::PropertyBool", "UsePrintColor", "Print", _tip, locked=True)
def set_visual_properties(self, vobj, properties):
"""Set visual properties only if they don't already exist."""
if "LineColor" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The line color of the objects "
- "contained within this layer")
- vobj.addProperty("App::PropertyColor",
- "LineColor",
- "Layer",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "The line color of the objects " "contained within this layer"
+ )
+ vobj.addProperty("App::PropertyColor", "LineColor", "Layer", _tip, locked=True)
vobj.LineColor = params.get_param_view("DefaultShapeLineColor") | 0x000000FF
if "ShapeColor" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The shape color of the objects "
- "contained within this layer")
- vobj.addProperty("App::PropertyColor",
- "ShapeColor",
- "Layer",
- _tip,
- 4,
- locked=True) # Hidden
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "The shape color of the objects " "contained within this layer"
+ )
+ vobj.addProperty(
+ "App::PropertyColor", "ShapeColor", "Layer", _tip, 4, locked=True
+ ) # Hidden
vobj.ShapeColor = params.get_param_view("DefaultShapeColor") | 0x000000FF
if "ShapeAppearance" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The shape appearance of the objects "
- "contained within this layer")
- vobj.addProperty("App::PropertyMaterialList",
- "ShapeAppearance",
- "Layer",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The shape appearance of the objects " "contained within this layer",
+ )
+ vobj.addProperty(
+ "App::PropertyMaterialList", "ShapeAppearance", "Layer", _tip, locked=True
+ )
material = App.Material()
material.DiffuseColor = params.get_param_view("DefaultShapeColor") | 0x000000FF
- vobj.ShapeAppearance = (material, )
+ vobj.ShapeAppearance = (material,)
if "LineWidth" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The line width of the objects contained "
- "within this layer")
- vobj.addProperty("App::PropertyFloat",
- "LineWidth",
- "Layer",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "The line width of the objects contained " "within this layer"
+ )
+ vobj.addProperty("App::PropertyFloat", "LineWidth", "Layer", _tip, locked=True)
vobj.LineWidth = params.get_param_view("DefaultShapeLineWidth")
if "DrawStyle" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The draw style of the objects contained "
- "within this layer")
- vobj.addProperty("App::PropertyEnumeration",
- "DrawStyle",
- "Layer",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "The draw style of the objects contained " "within this layer"
+ )
+ vobj.addProperty("App::PropertyEnumeration", "DrawStyle", "Layer", _tip, locked=True)
vobj.DrawStyle = utils.DRAW_STYLES
vobj.DrawStyle = params.get_param("DefaultDrawStyle")
if "Transparency" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The transparency of the objects "
- "contained within this layer")
- vobj.addProperty("App::PropertyPercent",
- "Transparency",
- "Layer",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "The transparency of the objects " "contained within this layer"
+ )
+ vobj.addProperty("App::PropertyPercent", "Transparency", "Layer", _tip, locked=True)
vobj.Transparency = params.get_param_view("DefaultShapeTransparency")
if "LinePrintColor" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "The line color of the objects "
- "contained within this layer, "
- "when used on a TechDraw page")
- vobj.addProperty("App::PropertyColor",
- "LinePrintColor",
- "Print",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property",
+ "The line color of the objects "
+ "contained within this layer, "
+ "when used on a TechDraw page",
+ )
+ vobj.addProperty("App::PropertyColor", "LinePrintColor", "Print", _tip, locked=True)
vobj.LinePrintColor = params.get_param("DefaultPrintColor")
def getIcon(self):
@@ -277,18 +253,18 @@ class ViewProviderLayer:
target_vobj = target_obj.ViewObject
if hasattr(target_vobj, prop):
- if old_prop is None \
- or _prop_is_same(getattr(target_vobj, prop), old_prop):
+ if old_prop is None or _prop_is_same(getattr(target_vobj, prop), old_prop):
setattr(target_vobj, prop, getattr(vobj, prop))
# Use the line color for the point color and text color,
# and the line width for the point size
- dic = {"LineColor": ("PointColor", "TextColor"), "LineWidth": ("PointSize", )}
+ dic = {"LineColor": ("PointColor", "TextColor"), "LineWidth": ("PointSize",)}
if prop in dic:
for target_prop in dic[prop]:
if hasattr(target_vobj, target_prop):
- if old_prop is None \
- or _prop_is_same(getattr(target_vobj, target_prop), old_prop):
+ if old_prop is None or _prop_is_same(
+ getattr(target_vobj, target_prop), old_prop
+ ):
setattr(target_vobj, target_prop, getattr(vobj, prop))
def onBeforeChange(self, vobj, prop):
@@ -306,7 +282,7 @@ class ViewProviderLayer:
material = vobj.ShapeAppearance[0]
if material.DiffuseColor != vobj.ShapeColor:
material.DiffuseColor = vobj.ShapeColor
- vobj.ShapeAppearance = (material, )
+ vobj.ShapeAppearance = (material,)
# The changed ShapeAppearance will do the rest:
return
@@ -315,23 +291,26 @@ class ViewProviderLayer:
material = vobj.ShapeAppearance[0]
if material.Transparency != vobj.Transparency / 100:
material.Transparency = vobj.Transparency / 100
- vobj.ShapeAppearance = (material, )
+ vobj.ShapeAppearance = (material,)
# The changed ShapeAppearance will do the rest:
return
- if (prop == "ShapeAppearance"
- and hasattr(vobj, "ShapeColor")
- and hasattr(vobj, "Transparency")):
+ if (
+ prop == "ShapeAppearance"
+ and hasattr(vobj, "ShapeColor")
+ and hasattr(vobj, "Transparency")
+ ):
material = vobj.ShapeAppearance[0]
if material.DiffuseColor != vobj.ShapeColor:
vobj.ShapeColor = material.DiffuseColor
if material.Transparency != vobj.Transparency / 100:
vobj.Transparency = int(material.Transparency * 100)
- if (prop in ("LineColor", "ShapeAppearance", "LineWidth",
- "DrawStyle", "Visibility")
- and hasattr(vobj, "OverrideLineColorChildren")
- and hasattr(vobj, "OverrideShapeAppearanceChildren")):
+ if (
+ prop in ("LineColor", "ShapeAppearance", "LineWidth", "DrawStyle", "Visibility")
+ and hasattr(vobj, "OverrideLineColorChildren")
+ and hasattr(vobj, "OverrideShapeAppearanceChildren")
+ ):
old_prop = getattr(self, "old" + prop, None)
self.change_view_properties(vobj, prop, old_prop)
if hasattr(self, "old" + prop):
@@ -349,12 +328,8 @@ class ViewProviderLayer:
l_color = vobj.LineColor
s_color = vobj.ShapeAppearance[0].DiffuseColor
- l_color = QtGui.QColor(int(l_color[0] * 255),
- int(l_color[1] * 255),
- int(l_color[2] * 255))
- s_color = QtGui.QColor(int(s_color[0] * 255),
- int(s_color[1] * 255),
- int(s_color[2] * 255))
+ l_color = QtGui.QColor(int(l_color[0] * 255), int(l_color[1] * 255), int(l_color[2] * 255))
+ s_color = QtGui.QColor(int(s_color[0] * 255), int(s_color[1] * 255), int(s_color[2] * 255))
p1 = QtCore.QPointF(2, 17)
p2 = QtCore.QPointF(13, 8)
p3 = QtCore.QPointF(30, 15)
@@ -366,8 +341,7 @@ class ViewProviderLayer:
pt = QtGui.QPainter(image)
pt.setBrush(QtGui.QBrush(s_color, QtCore.Qt.SolidPattern))
pt.drawPolygon([p1, p2, p3, p4])
- pt.setPen(QtGui.QPen(l_color, 2,
- QtCore.Qt.SolidLine, QtCore.Qt.FlatCap))
+ pt.setPen(QtGui.QPen(l_color, 2, QtCore.Qt.SolidLine, QtCore.Qt.FlatCap))
pt.drawPolygon([p1, p2, p3, p4])
pt.end()
@@ -479,8 +453,9 @@ class ViewProviderLayer:
# the document node, in that case we do nothing.
old_parents = [sub[0] for sub in old_data]
for new_parent in child.InList:
- if (hasattr(new_parent, "Group")
- and new_parent not in old_parents): # New group check.
+ if (
+ hasattr(new_parent, "Group") and new_parent not in old_parents
+ ): # New group check.
for old_parent, old_parent_group in old_data:
if old_parent == old_layer:
parents_to_update.append([old_parent, old_parent_group])
@@ -508,21 +483,25 @@ class ViewProviderLayer:
def setupContextMenu(self, vobj, menu):
"""Set up actions to perform in the context menu."""
- action_activate = QtGui.QAction(QtGui.QIcon(":/icons/button_right.svg"),
- translate("draft", "Activate Layer"),
- menu)
+ action_activate = QtGui.QAction(
+ QtGui.QIcon(":/icons/button_right.svg"), translate("draft", "Activate Layer"), menu
+ )
action_activate.triggered.connect(self.activate)
menu.addAction(action_activate)
- action_reassign = QtGui.QAction(QtGui.QIcon(":/icons/Draft_Apply.svg"),
- translate("draft", "Reassign Properties of Layer"),
- menu)
+ action_reassign = QtGui.QAction(
+ QtGui.QIcon(":/icons/Draft_Apply.svg"),
+ translate("draft", "Reassign Properties of Layer"),
+ menu,
+ )
action_reassign.triggered.connect(self.reassign_props)
menu.addAction(action_reassign)
- action_select = QtGui.QAction(QtGui.QIcon(":/icons/Draft_SelectGroup.svg"),
- translate("draft", "Select Layer Contents"),
- menu)
+ action_select = QtGui.QAction(
+ QtGui.QIcon(":/icons/Draft_SelectGroup.svg"),
+ translate("draft", "Select Layer Contents"),
+ menu,
+ )
action_select.triggered.connect(self.select_contents)
menu.addAction(action_select)
@@ -562,21 +541,25 @@ class ViewProviderLayerContainer:
def setupContextMenu(self, vobj, menu):
"""Set up actions to perform in the context menu."""
- action_add = QtGui.QAction(QtGui.QIcon(":/icons/Draft_NewLayer.svg"),
- translate("draft", "Add New Layer"),
- menu)
+ action_add = QtGui.QAction(
+ QtGui.QIcon(":/icons/Draft_NewLayer.svg"), translate("draft", "Add New Layer"), menu
+ )
action_add.triggered.connect(self.add_layer)
menu.addAction(action_add)
- action_reassign = QtGui.QAction(QtGui.QIcon(":/icons/Draft_Apply.svg"),
- translate("draft", "Reassign Properties of All Layers"),
- menu)
+ action_reassign = QtGui.QAction(
+ QtGui.QIcon(":/icons/Draft_Apply.svg"),
+ translate("draft", "Reassign Properties of All Layers"),
+ menu,
+ )
action_reassign.triggered.connect(self.reassign_props)
menu.addAction(action_reassign)
- action_merge = QtGui.QAction(QtGui.QIcon(":/icons/Draft_Layers.svg"),
- translate("draft", "Merge Layer Duplicates"),
- menu)
+ action_merge = QtGui.QAction(
+ QtGui.QIcon(":/icons/Draft_Layers.svg"),
+ translate("draft", "Merge Layer Duplicates"),
+ menu,
+ )
action_merge.triggered.connect(self.merge_by_name)
menu.addAction(action_merge)
@@ -587,8 +570,14 @@ class ViewProviderLayerContainer:
doc = App.ActiveDocument
doc.openTransaction(translate("draft", "Add New Layer"))
- Draft.make_layer(name=None, line_color=None, shape_color=None,
- line_width=None, draw_style=None, transparency=None)
+ Draft.make_layer(
+ name=None,
+ line_color=None,
+ shape_color=None,
+ line_width=None,
+ draw_style=None,
+ transparency=None,
+ )
doc.recompute()
doc.commitTransaction()
@@ -618,9 +607,11 @@ class ViewProviderLayerContainer:
# Try to find the `'base'` layer:
base = None
for other_layer in layers:
- if ((not other_layer in to_delete) # Required if there are duplicate labels.
- and other_layer != layer
- and other_layer.Label.upper() == base_label.upper()):
+ if (
+ (not other_layer in to_delete) # Required if there are duplicate labels.
+ and other_layer != layer
+ and other_layer.Label.upper() == base_label.upper()
+ ):
base = other_layer
break
diff --git a/src/Mod/Draft/draftviewproviders/view_orthoarray.py b/src/Mod/Draft/draftviewproviders/view_orthoarray.py
index e978e1ba97..5b9eec40bf 100644
--- a/src/Mod/Draft/draftviewproviders/view_orthoarray.py
+++ b/src/Mod/Draft/draftviewproviders/view_orthoarray.py
@@ -48,4 +48,5 @@ class ViewProviderOrthoArray(ViewProviderDraftArray):
"""Set the icon in the tree view."""
return ":/icons/Draft_Array"
+
## @}
diff --git a/src/Mod/Draft/draftviewproviders/view_point.py b/src/Mod/Draft/draftviewproviders/view_point.py
index 6c803c4581..9ad7bb90e1 100644
--- a/src/Mod/Draft/draftviewproviders/view_point.py
+++ b/src/Mod/Draft/draftviewproviders/view_point.py
@@ -32,23 +32,24 @@ from draftviewproviders.view_base import ViewProviderDraft
class ViewProviderPoint(ViewProviderDraft):
"""A viewprovider for the Draft Point object"""
+
def __init__(self, obj):
super(ViewProviderPoint, self).__init__(obj)
def onChanged(self, vobj, prop):
mode = 2
- vobj.setEditorMode('AngularDeflection', mode)
- vobj.setEditorMode('BoundingBox', mode)
- vobj.setEditorMode('Deviation', mode)
- vobj.setEditorMode('DisplayMode', mode)
- vobj.setEditorMode('DrawStyle', mode)
- vobj.setEditorMode('Lighting', mode)
- vobj.setEditorMode('LineColor', mode)
- vobj.setEditorMode('LineWidth', mode)
- vobj.setEditorMode('Pattern', mode)
- vobj.setEditorMode('PatternSize', mode)
- vobj.setEditorMode('ShapeAppearance', mode)
- vobj.setEditorMode('Transparency', mode)
+ vobj.setEditorMode("AngularDeflection", mode)
+ vobj.setEditorMode("BoundingBox", mode)
+ vobj.setEditorMode("Deviation", mode)
+ vobj.setEditorMode("DisplayMode", mode)
+ vobj.setEditorMode("DrawStyle", mode)
+ vobj.setEditorMode("Lighting", mode)
+ vobj.setEditorMode("LineColor", mode)
+ vobj.setEditorMode("LineWidth", mode)
+ vobj.setEditorMode("Pattern", mode)
+ vobj.setEditorMode("PatternSize", mode)
+ vobj.setEditorMode("ShapeAppearance", mode)
+ vobj.setEditorMode("Transparency", mode)
def getIcon(self):
return ":/icons/Draft_Dot.svg"
@@ -56,6 +57,7 @@ class ViewProviderPoint(ViewProviderDraft):
def doubleClicked(self, vobj):
# See setEdit in ViewProviderDraft.
import FreeCADGui as Gui
+
Gui.runCommand("Std_TransformManip")
return True
diff --git a/src/Mod/Draft/draftviewproviders/view_polararray.py b/src/Mod/Draft/draftviewproviders/view_polararray.py
index bcd67e155f..bc6593f7d5 100644
--- a/src/Mod/Draft/draftviewproviders/view_polararray.py
+++ b/src/Mod/Draft/draftviewproviders/view_polararray.py
@@ -48,4 +48,5 @@ class ViewProviderPolarArray(ViewProviderDraftArray):
"""Set the icon in the tree view."""
return ":/icons/Draft_PolarArray"
+
## @}
diff --git a/src/Mod/Draft/draftviewproviders/view_rectangle.py b/src/Mod/Draft/draftviewproviders/view_rectangle.py
index 12ccd73169..a9efa43aaf 100644
--- a/src/Mod/Draft/draftviewproviders/view_rectangle.py
+++ b/src/Mod/Draft/draftviewproviders/view_rectangle.py
@@ -34,12 +34,13 @@ from draftviewproviders.view_base import ViewProviderDraft
class ViewProviderRectangle(ViewProviderDraft):
- def __init__(self,vobj):
+ def __init__(self, vobj):
super(ViewProviderRectangle, self).__init__(vobj)
- _tip = QT_TRANSLATE_NOOP("App::Property","Defines a texture image (overrides hatch patterns)")
- vobj.addProperty("App::PropertyFile","TextureImage",
- "Draft", _tip, locked=True)
+ _tip = QT_TRANSLATE_NOOP(
+ "App::Property", "Defines a texture image (overrides hatch patterns)"
+ )
+ vobj.addProperty("App::PropertyFile", "TextureImage", "Draft", _tip, locked=True)
# Alias for compatibility with v0.18 and earlier
diff --git a/src/Mod/Draft/draftviewproviders/view_shapestring.py b/src/Mod/Draft/draftviewproviders/view_shapestring.py
index 42b6f2056c..d5e07eee5f 100644
--- a/src/Mod/Draft/draftviewproviders/view_shapestring.py
+++ b/src/Mod/Draft/draftviewproviders/view_shapestring.py
@@ -1,24 +1,24 @@
-#***************************************************************************
-#* *
-#* Copyright (c) 2022 Mario Passaglia *
-#* *
-#* This program is free software; you can redistribute it and/or modify *
-#* it under the terms of the GNU Lesser General Public License (LGPL) *
-#* as published by the Free Software Foundation; either version 2 of *
-#* the License, or (at your option) any later version. *
-#* for detail see the LICENCE text file. *
-#* *
-#* This program is distributed in the hope that it will be useful, *
-#* but WITHOUT ANY WARRANTY; without even the implied warranty of *
-#* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
-#* GNU Library General Public License for more details. *
-#* *
-#* You should have received a copy of the GNU Library General Public *
-#* License along with this program; if not, write to the Free Software *
-#* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 *
-#* USA *
-#* *
-#***************************************************************************
+# ***************************************************************************
+# * *
+# * Copyright (c) 2022 Mario Passaglia *
+# * *
+# * This program is free software; you can redistribute it and/or modify *
+# * it under the terms of the GNU Lesser General Public License (LGPL) *
+# * as published by the Free Software Foundation; either version 2 of *
+# * the License, or (at your option) any later version. *
+# * for detail see the LICENCE text file. *
+# * *
+# * This program is distributed in the hope that it will be useful, *
+# * but WITHOUT ANY WARRANTY; without even the implied warranty of *
+# * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
+# * GNU Library General Public License for more details. *
+# * *
+# * You should have received a copy of the GNU Library General Public *
+# * License along with this program; if not, write to the Free Software *
+# * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 *
+# * USA *
+# * *
+# ***************************************************************************
"""Provides the viewprovider code for the Shapestring object."""
@@ -28,9 +28,10 @@ import FreeCADGui as Gui
from draftviewproviders.view_base import ViewProviderDraft
from drafttaskpanels.task_shapestring import ShapeStringTaskPanelEdit
+
class ViewProviderShapeString(ViewProviderDraft):
- def __init__(self,vobj):
+ def __init__(self, vobj):
vobj.Proxy = self
@@ -42,7 +43,9 @@ class ViewProviderShapeString(ViewProviderDraft):
if mode != 0:
return None
- if not "Draft_Edit" in Gui.listCommands(): # Using Draft_Edit to detect if the Draft, Arch or BIM WB has been loaded.
+ if (
+ not "Draft_Edit" in Gui.listCommands()
+ ): # Using Draft_Edit to detect if the Draft, Arch or BIM WB has been loaded.
self.wb_before_edit = Gui.activeWorkbench()
Gui.activateWorkbench("DraftWorkbench")
self.task = ShapeStringTaskPanelEdit(vobj)
diff --git a/src/Mod/Draft/draftviewproviders/view_text.py b/src/Mod/Draft/draftviewproviders/view_text.py
index 60a307c6c9..47de8fbfd1 100644
--- a/src/Mod/Draft/draftviewproviders/view_text.py
+++ b/src/Mod/Draft/draftviewproviders/view_text.py
@@ -49,23 +49,13 @@ class ViewProviderText(ViewProviderDraftAnnotation):
super().set_text_properties(vobj, properties)
if "Justification" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Horizontal alignment")
- vobj.addProperty("App::PropertyEnumeration",
- "Justification",
- "Text",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Horizontal alignment")
+ vobj.addProperty("App::PropertyEnumeration", "Justification", "Text", _tip, locked=True)
vobj.Justification = ["Left", "Center", "Right"]
if "LineSpacing" not in properties:
- _tip = QT_TRANSLATE_NOOP("App::Property",
- "Line spacing (relative to font size)")
- vobj.addProperty("App::PropertyFloat",
- "LineSpacing",
- "Text",
- _tip,
- locked=True)
+ _tip = QT_TRANSLATE_NOOP("App::Property", "Line spacing (relative to font size)")
+ vobj.addProperty("App::PropertyFloat", "LineSpacing", "Text", _tip, locked=True)
vobj.LineSpacing = params.get_param("LineSpacing")
def getIcon(self):
@@ -79,8 +69,8 @@ class ViewProviderText(ViewProviderDraftAnnotation):
# Main attributes of the Coin scenegraph
self.mattext = coin.SoMaterial()
self.font = coin.SoFont()
- self.text_wld = coin.SoAsciiText() # World orientation. Can be oriented in 3D space.
- self.text_scr = coin.SoText2() # Screen orientation. Always faces the camera.
+ self.text_wld = coin.SoAsciiText() # World orientation. Can be oriented in 3D space.
+ self.text_scr = coin.SoText2() # Screen orientation. Always faces the camera.
textdrawstyle = coin.SoDrawStyle()
textdrawstyle.style = coin.SoDrawStyle.FILLED
@@ -133,8 +123,7 @@ class ViewProviderText(ViewProviderDraftAnnotation):
properties = vobj.PropertiesList
- if (prop == "ScaleMultiplier" and "ScaleMultiplier" in properties
- and vobj.ScaleMultiplier):
+ if prop == "ScaleMultiplier" and "ScaleMultiplier" in properties and vobj.ScaleMultiplier:
if "FontSize" in properties:
self.font.size = vobj.FontSize.Value * vobj.ScaleMultiplier
@@ -145,8 +134,12 @@ class ViewProviderText(ViewProviderDraftAnnotation):
elif prop == "FontName" and "FontName" in properties:
self.font.name = vobj.FontName.encode("utf8")
- elif (prop == "FontSize" and "FontSize" in properties
- and "ScaleMultiplier" in properties and vobj.ScaleMultiplier):
+ elif (
+ prop == "FontSize"
+ and "FontSize" in properties
+ and "ScaleMultiplier" in properties
+ and vobj.ScaleMultiplier
+ ):
# In v0.19 this code causes an `AttributeError` exception
# during loading of the document as `ScaleMultiplier`
# apparently isn't set immediately when the document loads.
@@ -189,7 +182,7 @@ class ViewProviderText(ViewProviderDraftAnnotation):
Gui.draftToolBar.textValue.setFocus()
def createObject(self):
- if hasattr(self,"Object"):
+ if hasattr(self, "Object"):
txt = self.text
if not txt:
self.finish()
@@ -199,7 +192,7 @@ class ViewProviderText(ViewProviderDraftAnnotation):
txt.pop()
t_list = ['"' + l + '"' for l in txt]
list_as_text = ", ".join(t_list)
- string = '[' + list_as_text + ']'
+ string = "[" + list_as_text + "]"
Gui.doCommand("FreeCAD.ActiveDocument." + self.Object.Name + ".Text = " + string)
App.ActiveDocument.recompute()
self.finish()
diff --git a/src/Mod/Draft/draftviewproviders/view_wire.py b/src/Mod/Draft/draftviewproviders/view_wire.py
index 685f83dfdd..ad4bcb666e 100644
--- a/src/Mod/Draft/draftviewproviders/view_wire.py
+++ b/src/Mod/Draft/draftviewproviders/view_wire.py
@@ -61,39 +61,25 @@ class ViewProviderWire(ViewProviderDraft):
if not hasattr(vobj, "ArrowSizeStart"):
_tip = QT_TRANSLATE_NOOP("App::Property", "Arrow size")
- vobj.addProperty("App::PropertyLength",
- "ArrowSizeStart",
- "Draft",
- _tip,
- locked=True)
+ vobj.addProperty("App::PropertyLength", "ArrowSizeStart", "Draft", _tip, locked=True)
vobj.ArrowSizeStart = params.get_param("arrowsizestart")
if not hasattr(vobj, "ArrowTypeStart"):
_tip = QT_TRANSLATE_NOOP("App::Property", "Arrow type")
- vobj.addProperty("App::PropertyEnumeration",
- "ArrowTypeStart",
- "Draft",
- _tip,
- locked=True)
+ vobj.addProperty(
+ "App::PropertyEnumeration", "ArrowTypeStart", "Draft", _tip, locked=True
+ )
vobj.ArrowTypeStart = utils.ARROW_TYPES
vobj.ArrowTypeStart = "None"
if not hasattr(vobj, "ArrowSizeEnd"):
_tip = QT_TRANSLATE_NOOP("App::Property", "Arrow size")
- vobj.addProperty("App::PropertyLength",
- "ArrowSizeEnd",
- "Draft",
- _tip,
- locked=True)
+ vobj.addProperty("App::PropertyLength", "ArrowSizeEnd", "Draft", _tip, locked=True)
vobj.ArrowSizeEnd = params.get_param("arrowsizeend")
if not hasattr(vobj, "ArrowTypeEnd"):
_tip = QT_TRANSLATE_NOOP("App::Property", "Arrow type")
- vobj.addProperty("App::PropertyEnumeration",
- "ArrowTypeEnd",
- "Draft",
- _tip,
- locked=True)
+ vobj.addProperty("App::PropertyEnumeration", "ArrowTypeEnd", "Draft", _tip, locked=True)
vobj.ArrowTypeEnd = utils.ARROW_TYPES
vobj.ArrowTypeEnd = "None"
@@ -121,11 +107,13 @@ class ViewProviderWire(ViewProviderDraft):
self.onChanged(vobj, "ArrowSizeStart")
def updateData(self, obj, prop):
- if prop == "Points" \
- and hasattr(obj, "Points") \
- and len(obj.Points) >= 2 \
- and hasattr(self, "coords1") \
- and hasattr(self, "coords2"):
+ if (
+ prop == "Points"
+ and hasattr(obj, "Points")
+ and len(obj.Points) >= 2
+ and hasattr(self, "coords1")
+ and hasattr(self, "coords2")
+ ):
self.coords1.translation.setValue(*obj.Points[0])
v1 = obj.Points[1].sub(obj.Points[0])
if not DraftVecUtils.isNull(v1):
@@ -142,24 +130,25 @@ class ViewProviderWire(ViewProviderDraft):
self.coords2.rotation.setValue(rot2)
def onChanged(self, vobj, prop):
- if prop in ["ArrowSizeStart",
- "ArrowSizeEnd",
- "ArrowTypeStart",
- "ArrowTypeEnd",
- "Visibility"] \
- and hasattr(vobj, "ArrowSizeStart") \
- and hasattr(vobj, "ArrowSizeEnd") \
- and hasattr(vobj, "ArrowTypeStart") \
- and hasattr(vobj, "ArrowTypeEnd") \
- and hasattr(vobj, "Visibility") \
- and hasattr(self, "pt1") \
- and hasattr(self, "pt2"):
+ if (
+ prop
+ in ["ArrowSizeStart", "ArrowSizeEnd", "ArrowTypeStart", "ArrowTypeEnd", "Visibility"]
+ and hasattr(vobj, "ArrowSizeStart")
+ and hasattr(vobj, "ArrowSizeEnd")
+ and hasattr(vobj, "ArrowTypeStart")
+ and hasattr(vobj, "ArrowTypeEnd")
+ and hasattr(vobj, "Visibility")
+ and hasattr(self, "pt1")
+ and hasattr(self, "pt2")
+ ):
rn = vobj.RootNode
rn.removeChild(self.pt1)
rn.removeChild(self.pt2)
if vobj.Visibility:
self.pt1.removeChild(self.startSymbol)
- self.startSymbol = gui_utils.dim_symbol(utils.ARROW_TYPES.index(vobj.ArrowTypeStart))
+ self.startSymbol = gui_utils.dim_symbol(
+ utils.ARROW_TYPES.index(vobj.ArrowTypeStart)
+ )
self.pt1.addChild(self.startSymbol)
self.coords1.scaleFactor.setValue([vobj.ArrowSizeStart] * 3)
@@ -172,28 +161,30 @@ class ViewProviderWire(ViewProviderDraft):
rn.addChild(self.pt1)
rn.addChild(self.pt2)
- if prop == "LineColor" \
- and hasattr(vobj, "LineColor") \
- and hasattr(self, "pt1") \
- and hasattr(self, "pt2"):
+ if (
+ prop == "LineColor"
+ and hasattr(vobj, "LineColor")
+ and hasattr(self, "pt1")
+ and hasattr(self, "pt2")
+ ):
self.color.rgb.setValue(*vobj.LineColor[:3])
super().onChanged(vobj, prop)
return
def claimChildren(self):
- if hasattr(self.Object,"Base"):
- return [self.Object.Base,self.Object.Tool]
+ if hasattr(self.Object, "Base"):
+ return [self.Object.Base, self.Object.Tool]
return []
- def flatten(self): # Only to be used for Draft_Wires.
+ def flatten(self): # Only to be used for Draft_Wires.
if not hasattr(self, "Object"):
return
wp = WorkingPlane.get_working_plane()
- flat_wire = wires.flattenWire(self.Object.Shape.Wires[0],
- origin=wp.position,
- normal=wp.axis)
+ flat_wire = wires.flattenWire(
+ self.Object.Shape.Wires[0], origin=wp.position, normal=wp.axis
+ )
doc = App.ActiveDocument
doc.openTransaction(translate("draft", "Flatten"))
diff --git a/src/Mod/Draft/draftviewproviders/view_wpproxy.py b/src/Mod/Draft/draftviewproviders/view_wpproxy.py
index 579e747bd6..76e4aca7f1 100644
--- a/src/Mod/Draft/draftviewproviders/view_wpproxy.py
+++ b/src/Mod/Draft/draftviewproviders/view_wpproxy.py
@@ -40,33 +40,29 @@ from draftutils import params
class ViewProviderWorkingPlaneProxy:
"""A View Provider for working plane proxies"""
- def __init__(self,vobj):
+ def __init__(self, vobj):
# ViewData: 0,1,2: position; 3,4,5,6: rotation; 7: near dist; 8: far dist, 9:aspect ratio;
# 10: focal dist; 11: height (ortho) or height angle (persp); 12: ortho (0) or persp (1)
_tip = QT_TRANSLATE_NOOP("App::Property", "The display length of this section plane")
- vobj.addProperty("App::PropertyLength", "DisplaySize",
- "Draft", _tip,
- locked=True)
+ vobj.addProperty("App::PropertyLength", "DisplaySize", "Draft", _tip, locked=True)
_tip = QT_TRANSLATE_NOOP("App::Property", "The size of the arrows of this section plane")
- vobj.addProperty("App::PropertyLength", "ArrowSize",
- "Draft", _tip,
- locked=True)
+ vobj.addProperty("App::PropertyLength", "ArrowSize", "Draft", _tip, locked=True)
- vobj.addProperty("App::PropertyPercent","Transparency","Base","",locked=True)
+ vobj.addProperty("App::PropertyPercent", "Transparency", "Base", "", locked=True)
- vobj.addProperty("App::PropertyFloat","LineWidth","Base","",locked=True)
+ vobj.addProperty("App::PropertyFloat", "LineWidth", "Base", "", locked=True)
- vobj.addProperty("App::PropertyColor","LineColor","Base","",locked=True)
+ vobj.addProperty("App::PropertyColor", "LineColor", "Base", "", locked=True)
- vobj.addProperty("App::PropertyFloatList","ViewData","Base","",locked=True)
+ vobj.addProperty("App::PropertyFloatList", "ViewData", "Base", "", locked=True)
- vobj.addProperty("App::PropertyBool","RestoreView","Base","",locked=True)
+ vobj.addProperty("App::PropertyBool", "RestoreView", "Base", "", locked=True)
- vobj.addProperty("App::PropertyMap","VisibilityMap","Base","",locked=True)
+ vobj.addProperty("App::PropertyMap", "VisibilityMap", "Base", "", locked=True)
- vobj.addProperty("App::PropertyBool","RestoreState","Base","",locked=True)
+ vobj.addProperty("App::PropertyBool", "RestoreState", "Base", "", locked=True)
vobj.DisplaySize = 100
vobj.ArrowSize = 5
@@ -84,56 +80,63 @@ class ViewProviderWorkingPlaneProxy:
def claimChildren(self):
return []
- def doubleClicked(self,vobj):
+ def doubleClicked(self, vobj):
Gui.runCommand("Draft_SelectPlane")
return True
- def setupContextMenu(self,vobj,menu):
- action1 = QtGui.QAction(QtGui.QIcon(":/icons/Draft_SelectPlane.svg"),"Save Camera Position",menu)
- QtCore.QObject.connect(action1,QtCore.SIGNAL("triggered()"),self.writeCamera)
+ def setupContextMenu(self, vobj, menu):
+ action1 = QtGui.QAction(
+ QtGui.QIcon(":/icons/Draft_SelectPlane.svg"), "Save Camera Position", menu
+ )
+ QtCore.QObject.connect(action1, QtCore.SIGNAL("triggered()"), self.writeCamera)
menu.addAction(action1)
- action2 = QtGui.QAction(QtGui.QIcon(":/icons/Draft_SelectPlane.svg"),"Save Visibility of Objects",menu)
- QtCore.QObject.connect(action2,QtCore.SIGNAL("triggered()"),self.writeState)
+ action2 = QtGui.QAction(
+ QtGui.QIcon(":/icons/Draft_SelectPlane.svg"), "Save Visibility of Objects", menu
+ )
+ QtCore.QObject.connect(action2, QtCore.SIGNAL("triggered()"), self.writeState)
menu.addAction(action2)
def writeCamera(self):
- if hasattr(self,"Object"):
+ if hasattr(self, "Object"):
n = Gui.ActiveDocument.ActiveView.getCameraNode()
- App.Console.PrintMessage(QT_TRANSLATE_NOOP("Draft","Writing camera position")+"\n")
+ App.Console.PrintMessage(QT_TRANSLATE_NOOP("Draft", "Writing camera position") + "\n")
cdata = list(n.position.getValue().getValue())
cdata.extend(list(n.orientation.getValue().getValue()))
cdata.append(n.nearDistance.getValue())
cdata.append(n.farDistance.getValue())
cdata.append(n.aspectRatio.getValue())
cdata.append(n.focalDistance.getValue())
- if isinstance(n,coin.SoOrthographicCamera):
+ if isinstance(n, coin.SoOrthographicCamera):
cdata.append(n.height.getValue())
- cdata.append(0.0) # orthograhic camera
- elif isinstance(n,coin.SoPerspectiveCamera):
+ cdata.append(0.0) # orthograhic camera
+ elif isinstance(n, coin.SoPerspectiveCamera):
cdata.append(n.heightAngle.getValue())
- cdata.append(1.0) # perspective camera
+ cdata.append(1.0) # perspective camera
self.Object.ViewObject.ViewData = cdata
def writeState(self):
- if hasattr(self,"Object"):
- App.Console.PrintMessage(QT_TRANSLATE_NOOP("Draft","Writing objects shown/hidden state")+"\n")
+ if hasattr(self, "Object"):
+ App.Console.PrintMessage(
+ QT_TRANSLATE_NOOP("Draft", "Writing objects shown/hidden state") + "\n"
+ )
vis = {}
for o in App.ActiveDocument.Objects:
if o.ViewObject:
vis[o.Name] = str(o.ViewObject.Visibility)
self.Object.ViewObject.VisibilityMap = vis
- def attach(self,vobj):
+ def attach(self, vobj):
self.clip = None
self.mat1 = coin.SoMaterial()
self.mat2 = coin.SoMaterial()
self.fcoords = coin.SoCoordinate3()
fs = coin.SoIndexedFaceSet()
- fs.coordIndex.setValues(0,7,[0,1,2,-1,0,2,3])
+ fs.coordIndex.setValues(0, 7, [0, 1, 2, -1, 0, 2, 3])
self.drawstyle = coin.SoDrawStyle()
self.drawstyle.style = coin.SoDrawStyle.LINES
self.lcoords = coin.SoCoordinate3()
- import PartGui # Required for "SoBrepEdgeSet" (because a WorkingPlaneProxy is not a Part::FeaturePython object).
+ import PartGui # Required for "SoBrepEdgeSet" (because a WorkingPlaneProxy is not a Part::FeaturePython object).
+
ls = coin.SoType.fromName("SoBrepEdgeSet").createInstance()
# fmt: off
ls.coordIndex.setValues(
@@ -162,77 +165,77 @@ class ViewProviderWorkingPlaneProxy:
psep.addChild(ls)
sep.addChild(fsep)
sep.addChild(psep)
- vobj.addDisplayMode(sep,"Default")
- self.onChanged(vobj,"DisplaySize")
- self.onChanged(vobj,"LineColor")
- self.onChanged(vobj,"Transparency")
+ vobj.addDisplayMode(sep, "Default")
+ self.onChanged(vobj, "DisplaySize")
+ self.onChanged(vobj, "LineColor")
+ self.onChanged(vobj, "Transparency")
self.Object = vobj.Object
- def getDisplayModes(self,vobj):
+ def getDisplayModes(self, vobj):
return ["Default"]
def getDefaultDisplayMode(self):
return "Default"
- def setDisplayMode(self,mode):
+ def setDisplayMode(self, mode):
return mode
- def updateData(self,obj,prop):
+ def updateData(self, obj, prop):
if prop in ["Placement"]:
- self.onChanged(obj.ViewObject,"DisplaySize")
+ self.onChanged(obj.ViewObject, "DisplaySize")
return
- def onChanged(self,vobj,prop):
+ def onChanged(self, vobj, prop):
if prop == "LineColor":
l = vobj.LineColor
- self.mat1.diffuseColor.setValue([l[0],l[1],l[2]])
- self.mat2.diffuseColor.setValue([l[0],l[1],l[2]])
+ self.mat1.diffuseColor.setValue([l[0], l[1], l[2]])
+ self.mat2.diffuseColor.setValue([l[0], l[1], l[2]])
elif prop == "Transparency":
- if hasattr(vobj,"Transparency"):
- self.mat2.transparency.setValue(vobj.Transparency/100.0)
+ if hasattr(vobj, "Transparency"):
+ self.mat2.transparency.setValue(vobj.Transparency / 100.0)
- elif prop in ["DisplaySize","ArrowSize"]:
- if hasattr(vobj,"DisplaySize"):
- l = vobj.DisplaySize.Value/2
+ elif prop in ["DisplaySize", "ArrowSize"]:
+ if hasattr(vobj, "DisplaySize"):
+ l = vobj.DisplaySize.Value / 2
else:
l = 1
verts = []
fverts = []
l1 = 0.1
- if hasattr(vobj,"ArrowSize"):
+ if hasattr(vobj, "ArrowSize"):
l1 = vobj.ArrowSize.Value if vobj.ArrowSize.Value > 0 else 0.1
- l2 = l1/3
+ l2 = l1 / 3
pl = App.Placement(vobj.Object.Placement)
- fverts.append(pl.multVec(App.Vector(-l,-l,0)))
- fverts.append(pl.multVec(App.Vector(l,-l,0)))
- fverts.append(pl.multVec(App.Vector(l,l,0)))
- fverts.append(pl.multVec(App.Vector(-l,l,0)))
+ fverts.append(pl.multVec(App.Vector(-l, -l, 0)))
+ fverts.append(pl.multVec(App.Vector(l, -l, 0)))
+ fverts.append(pl.multVec(App.Vector(l, l, 0)))
+ fverts.append(pl.multVec(App.Vector(-l, l, 0)))
- verts.append(pl.multVec(App.Vector(0,0,0)))
- verts.append(pl.multVec(App.Vector(l-l1,0,0)))
- verts.append(pl.multVec(App.Vector(l-l1,l2,0)))
- verts.append(pl.multVec(App.Vector(l,0,0)))
- verts.append(pl.multVec(App.Vector(l-l1,-l2,0)))
- verts.append(pl.multVec(App.Vector(l-l1,l2,0)))
+ verts.append(pl.multVec(App.Vector(0, 0, 0)))
+ verts.append(pl.multVec(App.Vector(l - l1, 0, 0)))
+ verts.append(pl.multVec(App.Vector(l - l1, l2, 0)))
+ verts.append(pl.multVec(App.Vector(l, 0, 0)))
+ verts.append(pl.multVec(App.Vector(l - l1, -l2, 0)))
+ verts.append(pl.multVec(App.Vector(l - l1, l2, 0)))
- verts.append(pl.multVec(App.Vector(0,0,0)))
- verts.append(pl.multVec(App.Vector(0,l-l1,0)))
- verts.append(pl.multVec(App.Vector(-l2,l-l1,0)))
- verts.append(pl.multVec(App.Vector(0,l,0)))
- verts.append(pl.multVec(App.Vector(l2,l-l1,0)))
- verts.append(pl.multVec(App.Vector(-l2,l-l1,0)))
+ verts.append(pl.multVec(App.Vector(0, 0, 0)))
+ verts.append(pl.multVec(App.Vector(0, l - l1, 0)))
+ verts.append(pl.multVec(App.Vector(-l2, l - l1, 0)))
+ verts.append(pl.multVec(App.Vector(0, l, 0)))
+ verts.append(pl.multVec(App.Vector(l2, l - l1, 0)))
+ verts.append(pl.multVec(App.Vector(-l2, l - l1, 0)))
- verts.append(pl.multVec(App.Vector(0,0,0)))
- verts.append(pl.multVec(App.Vector(0,0,l-l1)))
- verts.append(pl.multVec(App.Vector(-l2,0,l-l1)))
- verts.append(pl.multVec(App.Vector(0,0,l)))
- verts.append(pl.multVec(App.Vector(l2,0,l-l1)))
- verts.append(pl.multVec(App.Vector(-l2,0,l-l1)))
- verts.append(pl.multVec(App.Vector(0,-l2,l-l1)))
- verts.append(pl.multVec(App.Vector(0,0,l)))
- verts.append(pl.multVec(App.Vector(0,l2,l-l1)))
- verts.append(pl.multVec(App.Vector(0,-l2,l-l1)))
+ verts.append(pl.multVec(App.Vector(0, 0, 0)))
+ verts.append(pl.multVec(App.Vector(0, 0, l - l1)))
+ verts.append(pl.multVec(App.Vector(-l2, 0, l - l1)))
+ verts.append(pl.multVec(App.Vector(0, 0, l)))
+ verts.append(pl.multVec(App.Vector(l2, 0, l - l1)))
+ verts.append(pl.multVec(App.Vector(-l2, 0, l - l1)))
+ verts.append(pl.multVec(App.Vector(0, -l2, l - l1)))
+ verts.append(pl.multVec(App.Vector(0, 0, l)))
+ verts.append(pl.multVec(App.Vector(0, l2, l - l1)))
+ verts.append(pl.multVec(App.Vector(0, -l2, l - l1)))
self.lcoords.point.setValues(verts)
self.fcoords.point.setValues(fverts)
@@ -244,7 +247,8 @@ class ViewProviderWorkingPlaneProxy:
def dumps(self):
return None
- def loads(self,state):
+ def loads(self, state):
return None
+
## @}
diff --git a/src/Mod/Draft/importAirfoilDAT.py b/src/Mod/Draft/importAirfoilDAT.py
index e9af498e59..45ff0afad0 100644
--- a/src/Mod/Draft/importAirfoilDAT.py
+++ b/src/Mod/Draft/importAirfoilDAT.py
@@ -3,11 +3,11 @@
# \brief Airfoil (.dat) file importer
#
# This module provides support for importing airfoil .dat files
-'''@package importAirfoilDAT
+"""@package importAirfoilDAT
Airfoil (.dat) file importer
This module provides support for importing airfoil .dat files.
-'''
+"""
# Check code with
# flake8 --ignore=E226,E266,E401,W503
@@ -48,11 +48,11 @@ from draftutils.utils import pyopen
if FreeCAD.GuiUp:
from draftutils.translate import translate
else:
+
def translate(context, txt):
return txt
-
useDraftWire = True
@@ -125,12 +125,12 @@ def process(filename):
than 3 points.
"""
# Regex to identify data rows and throw away unused metadata
- xval = r'(?P\-?\s*\d*\.*\d*([Ee]\-?\d+)?)'
- yval = r'(?P\-?\s*\d*\.*\d*([Ee]\-?\d+)?)'
- _regex = r'^\s*' + xval + r'\,?\s*' + yval + r'\s*$'
+ xval = r"(?P\-?\s*\d*\.*\d*([Ee]\-?\d+)?)"
+ yval = r"(?P\-?\s*\d*\.*\d*([Ee]\-?\d+)?)"
+ _regex = r"^\s*" + xval + r"\,?\s*" + yval + r"\s*$"
regex = re.compile(_regex)
- afile = pyopen(filename, 'r')
+ afile = pyopen(filename, "r")
# read the airfoil name which is always in the first line
airfoilname = afile.readline().strip()
@@ -141,9 +141,7 @@ def process(filename):
# Collect the data
for lin in afile:
curdat = regex.match(lin)
- if (curdat is not None
- and curdat.group("xval")
- and curdat.group("yval")):
+ if curdat is not None and curdat.group("xval") and curdat.group("yval"):
x = float(curdat.group("xval"))
y = float(curdat.group("yval"))
@@ -167,7 +165,7 @@ def process(filename):
if coords[0:-1].count(coords[0]) > 1:
flippoint = coords.index(coords[0], 1)
upper = coords[0:flippoint]
- lower = coords[flippoint+1:]
+ lower = coords[flippoint + 1 :]
lower.reverse()
for i in lower:
upper.append(i)
@@ -199,7 +197,7 @@ def process(filename):
wire = Part.Wire(lines)
face = Part.Face(wire)
- obj = FreeCAD.ActiveDocument.addObject('Part::Feature', airfoilname)
+ obj = FreeCAD.ActiveDocument.addObject("Part::Feature", airfoilname)
obj.Shape = face
return obj
diff --git a/src/Mod/Draft/importDWG.py b/src/Mod/Draft/importDWG.py
index c482639d89..6b1f1126d6 100644
--- a/src/Mod/Draft/importDWG.py
+++ b/src/Mod/Draft/importDWG.py
@@ -2,7 +2,7 @@
## @package importDWG
# \ingroup DRAFT
# \brief DWG file importer & exporter
-'''
+"""
@package importDWG
ingroup DRAFT
\brief DWG file importer & exporter
@@ -15,7 +15,7 @@ importDXF
Test files
https://knowledge.autodesk.com/support/autocad/downloads/
caas/downloads/content/autocad-sample-files.html
-'''
+"""
# Check code quality with
# flake8 --ignore=E226,E266,E401,W503
@@ -47,12 +47,11 @@ from draftutils import params
if FreeCAD.GuiUp:
from draftutils.translate import translate
else:
+
def translate(context, txt):
return txt
-
-
def open(filename):
"""Open filename and parse using importDXF.open().
@@ -69,6 +68,7 @@ def open(filename):
dxf = convertToDxf(filename)
if dxf:
import importDXF
+
doc = importDXF.open(dxf)
return doc
return
@@ -96,6 +96,7 @@ def insert(filename, docname):
dxf = convertToDxf(filename)
if dxf:
import importDXF
+
# Warning: function doesn't return?
doc = importDXF.insert(dxf, docname)
return doc
@@ -123,6 +124,7 @@ def export(objectslist, filename):
import importDXF
import os
import tempfile
+
outdir = tempfile.mkdtemp()
_basename = os.path.splitext(os.path.basename(filename))[0]
dxf = outdir + os.sep + _basename + ".dxf"
@@ -154,7 +156,7 @@ def get_libredwg_converter(typ):
path = params.get_param("TeighaFileConverter")
- if "dwg2dxf" in path or "dxf2dwg" in path: # path set manually
+ if "dwg2dxf" in path or "dxf2dwg" in path: # path set manually
if typ not in path:
path = os.path.dirname(path) + "/" + typ + os.path.splitext(path)[1]
if os.path.exists(path) and os.path.isfile(path):
@@ -164,7 +166,7 @@ def get_libredwg_converter(typ):
path = sub.replace("\\", "/") + "/" + typ + ".exe"
if os.path.exists(path) and os.path.isfile(path):
return path
- else: # for Linux and macOS
+ else: # for Linux and macOS
for sub in os.getenv("PATH").split(os.pathsep):
path = sub + "/" + typ
if os.path.exists(path) and os.path.isfile(path):
@@ -192,7 +194,7 @@ def get_oda_converter():
path = params.get_param("TeighaFileConverter")
- if "ODAFileConverter" in path: # path set manually
+ if "ODAFileConverter" in path: # path set manually
if os.path.exists(path) and os.path.isfile(path):
return path
elif platform.system() == "Windows":
@@ -206,7 +208,7 @@ def get_oda_converter():
path = "/usr/bin/ODAFileConverter"
if os.path.exists(path) and os.path.isfile(path):
return path
- else: # for macOS
+ else: # for macOS
path = "/Applications/ODAFileConverter.app/Contents/MacOS/ODAFileConverter"
if os.path.exists(path) and os.path.isfile(path):
return path
@@ -233,7 +235,7 @@ def get_qcad_converter():
path = params.get_param("TeighaFileConverter")
- if "dwg2dwg" in path: # path set manually
+ if "dwg2dwg" in path: # path set manually
pass
elif platform.system() == "Windows":
path = os.path.expandvars("%ProgramFiles%\\QCAD\\dwg2dwg.bat").replace("\\", "/")
@@ -245,7 +247,7 @@ def get_qcad_converter():
if "qcad" in sub:
path = path + "/" + sub + "/" + "dwg2dwg"
break
- else: # for macOS
+ else: # for macOS
path = "/Applications/QCAD.app/Contents/Resources/dwg2dwg"
if os.path.exists(path) and os.path.isfile(path):
@@ -274,11 +276,17 @@ def convertToDxf(dwgfilename):
dwgfilename = dwgfilename.replace("\\", "/")
conv = params.get_param("DWGConversion")
- error_msg = translate("draft", """Error during DWG conversion.
+ error_msg = (
+ translate(
+ "draft",
+ """Error during DWG conversion.
Try moving the DWG file to a directory path without spaces and non-english characters,
-or try saving to a lower DWG version.""") + "\n"
+or try saving to a lower DWG version.""",
+ )
+ + "\n"
+ )
- if conv in [0, 1]: # LibreDWG
+ if conv in [0, 1]: # LibreDWG
libredwg = get_libredwg_converter("dwg2dxf")
if libredwg is not None:
outdir = tempfile.mkdtemp().replace("\\", "/")
@@ -296,7 +304,7 @@ or try saving to a lower DWG version.""") + "\n"
elif conv != 0:
FCC.PrintError(translate("draft", "LibreDWG converter not found") + "\n")
- if conv in [0, 2]: # ODA
+ if conv in [0, 2]: # ODA
oda = get_oda_converter()
if oda is not None:
indir = os.path.dirname(dwgfilename)
@@ -315,7 +323,7 @@ or try saving to a lower DWG version.""") + "\n"
elif conv != 0:
FCC.PrintError(translate("draft", "ODA converter not found") + "\n")
- if conv in [0, 3]: # QCAD
+ if conv in [0, 3]: # QCAD
qcad = get_qcad_converter()
if qcad is not None:
outdir = tempfile.mkdtemp().replace("\\", "/")
@@ -323,7 +331,7 @@ or try saving to a lower DWG version.""") + "\n"
result = outdir + "/" + os.path.splitext(basename)[0] + ".dxf"
cmdline = [qcad, "-f", "-o", result, dwgfilename]
FCC.PrintMessage(translate("draft", "Converting:") + " " + str(cmdline) + "\n")
- proc = subprocess.Popen(cmdline, cwd=os.path.dirname(qcad)) # cwd required for Windows
+ proc = subprocess.Popen(cmdline, cwd=os.path.dirname(qcad)) # cwd required for Windows
proc.communicate()
if os.path.exists(result):
FCC.PrintMessage(translate("draft", "Conversion successful") + "\n")
@@ -333,10 +341,16 @@ or try saving to a lower DWG version.""") + "\n"
elif conv != 0:
FCC.PrintError(translate("draft", "QCAD converter not found") + "\n")
- FCC.PrintError(translate("draft", """No suitable external DWG converter has been found.
+ FCC.PrintError(
+ translate(
+ "draft",
+ """No suitable external DWG converter has been found.
Please set one manually under menu Edit → Preferences → Import/Export → DWG
For more information see:
-https://wiki.freecad.org/Import_Export_Preferences""") + "\n")
+https://wiki.freecad.org/Import_Export_Preferences""",
+ )
+ + "\n"
+ )
return None
@@ -364,7 +378,7 @@ def convertToDwg(dxffilename, dwgfilename):
dwgfilename = dwgfilename.replace("\\", "/")
conv = params.get_param("DWGConversion")
- if conv in [0, 1]: # LibreDWG
+ if conv in [0, 1]: # LibreDWG
libredwg = get_libredwg_converter("dxf2dwg")
if libredwg is not None:
cmdline = [libredwg, dxffilename, "-y", "-o", dwgfilename]
@@ -375,7 +389,7 @@ def convertToDwg(dxffilename, dwgfilename):
elif conv != 0:
FCC.PrintError(translate("draft", "LibreDWG converter not found") + "\n")
- if conv in [0, 2]: # ODA
+ if conv in [0, 2]: # ODA
oda = get_oda_converter()
if oda is not None:
indir = os.path.dirname(dxffilename)
@@ -389,19 +403,25 @@ def convertToDwg(dxffilename, dwgfilename):
elif conv != 0:
FCC.PrintError(translate("draft", "ODA converter not found") + "\n")
- if conv in [0, 3]: # QCAD
+ if conv in [0, 3]: # QCAD
qcad = get_qcad_converter()
if qcad is not None:
cmdline = [qcad, "-f", "-o", dwgfilename, dxffilename]
FCC.PrintMessage(translate("draft", "Converting:") + " " + str(cmdline) + "\n")
- proc = subprocess.Popen(cmdline, cwd=os.path.dirname(qcad)) # cwd required for Windows
+ proc = subprocess.Popen(cmdline, cwd=os.path.dirname(qcad)) # cwd required for Windows
proc.communicate()
return dwgfilename
elif conv != 0:
FCC.PrintError(translate("draft", "QCAD converter not found") + "\n")
- FCC.PrintError(translate("draft", """No suitable external DWG converter has been found.
+ FCC.PrintError(
+ translate(
+ "draft",
+ """No suitable external DWG converter has been found.
Please set one manually under menu Edit → Preferences → Import/Export → DWG
For more information see:
-https://wiki.freecad.org/Import_Export_Preferences""") + "\n")
+https://wiki.freecad.org/Import_Export_Preferences""",
+ )
+ + "\n"
+ )
return None
diff --git a/src/Mod/Draft/importDXF.py b/src/Mod/Draft/importDXF.py
index 5f1660edc7..27a39c117b 100644
--- a/src/Mod/Draft/importDXF.py
+++ b/src/Mod/Draft/importDXF.py
@@ -75,6 +75,7 @@ gui = FreeCAD.GuiUp
draftui = None
if gui:
import FreeCADGui
+
try:
draftui = FreeCADGui.draftToolBar
except (AttributeError, NameError):
@@ -89,9 +90,11 @@ if gui:
from draftutils.translate import translate
from PySide import QtWidgets
else:
+
def translate(context, txt):
return txt
+
dxfReader = None
dxfColorMap = None
dxfLibrary = None
@@ -115,13 +118,13 @@ def errorDXFLib(gui):
"""
dxfAllowDownload = params.get_param("dxfAllowDownload")
if dxfAllowDownload:
- files = ['dxfColorMap.py', 'dxfImportObjects.py',
- 'dxfLibrary.py', 'dxfReader.py']
+ files = ["dxfColorMap.py", "dxfImportObjects.py", "dxfLibrary.py", "dxfReader.py"]
- baseurl = 'https://raw.githubusercontent.com/yorikvanhavre/'
- baseurl += 'Draft-dxf-importer/master/'
+ baseurl = "https://raw.githubusercontent.com/yorikvanhavre/"
+ baseurl += "Draft-dxf-importer/master/"
import ArchCommands
from FreeCAD import Base
+
progressbar = Base.ProgressIndicator()
progressbar.start("Downloading files...", 4)
for f in files:
@@ -130,43 +133,63 @@ def errorDXFLib(gui):
p = ArchCommands.download(baseurl + f, force=True)
if not p:
if gui:
- message = translate("Draft", """Download of DXF libraries failed.
+ message = translate(
+ "Draft",
+ """Download of DXF libraries failed.
Please install the DXF Library addon manually
-from menu Tools → Addon Manager""")
+from menu Tools → Addon Manager""",
+ )
QtWidgets.QMessageBox.information(None, "", message)
else:
- FCC.PrintWarning("The DXF import/export libraries needed by FreeCAD to handle the DXF format are not installed.\n")
- FCC.PrintWarning("Please install the DXF Library addon from Tools → Addon Manager\n")
+ FCC.PrintWarning(
+ "The DXF import/export libraries needed by FreeCAD to handle the DXF format are not installed.\n"
+ )
+ FCC.PrintWarning(
+ "Please install the DXF Library addon from Tools → Addon Manager\n"
+ )
break
progressbar.stop()
sys.path.append(FreeCAD.ConfigGet("UserAppData"))
else:
if gui:
- message = translate('draft', """The DXF import/export libraries needed by FreeCAD to handle
+ message = translate(
+ "draft",
+ """The DXF import/export libraries needed by FreeCAD to handle
the DXF format were not found on this system.
Please either allow FreeCAD to download these libraries:
1 - Load Draft workbench
2 - Menu Edit → Preferences → Import-Export → DXF → Enable downloads
Or download these libraries manually, as explained on
https://github.com/yorikvanhavre/Draft-dxf-importer
-To enabled FreeCAD to download these libraries, answer Yes.""")
- reply = QtWidgets.QMessageBox.question(None, "", message,
- QtWidgets.QMessageBox.Yes | QtWidgets.QMessageBox.No,
- QtWidgets.QMessageBox.No)
+To enabled FreeCAD to download these libraries, answer Yes.""",
+ )
+ reply = QtWidgets.QMessageBox.question(
+ None,
+ "",
+ message,
+ QtWidgets.QMessageBox.Yes | QtWidgets.QMessageBox.No,
+ QtWidgets.QMessageBox.No,
+ )
if reply == QtWidgets.QMessageBox.Yes:
params.set_param("dxfAllowDownload", True)
errorDXFLib(gui)
if reply == QtWidgets.QMessageBox.No:
pass
else:
- FCC.PrintWarning("The DXF import/export libraries needed by FreeCAD to handle the DXF format are not installed.\n")
+ FCC.PrintWarning(
+ "The DXF import/export libraries needed by FreeCAD to handle the DXF format are not installed.\n"
+ )
_ver = FreeCAD.Version()
_maj = _ver[0]
_min = _ver[1]
if float(_maj + "." + _min) >= 0.17:
- FCC.PrintWarning("Please install the DXF Library addon from Tools → Addon Manager\n")
+ FCC.PrintWarning(
+ "Please install the DXF Library addon from Tools → Addon Manager\n"
+ )
else:
- FCC.PrintWarning("Please check https://github.com/yorikvanhavre/Draft-dxf-importer\n")
+ FCC.PrintWarning(
+ "Please check https://github.com/yorikvanhavre/Draft-dxf-importer\n"
+ )
def getDXFlibs():
@@ -186,6 +209,7 @@ def getDXFlibs():
global dxfLibrary, dxfColorMap, dxfReader
import dxfLibrary
import dxfColorMap
+
try:
import dxfReader
except Exception:
@@ -197,14 +221,14 @@ def getDXFlibs():
if float(dxfLibrary.__version__[1:5]) >= CURRENTDXFLIB:
libsok = True
else:
- FCC.PrintWarning("DXF libraries need to be updated. "
- "Trying to download…\n")
+ FCC.PrintWarning("DXF libraries need to be updated. " "Trying to download…\n")
libsok = False
if not libsok:
errorDXFLib(gui)
try:
import dxfColorMap, dxfLibrary, dxfReader
import importlib
+
importlib.reload(dxfColorMap)
importlib.reload(dxfLibrary)
importlib.reload(dxfReader)
@@ -236,12 +260,12 @@ def deformat(text):
t = re.sub(r"\\\\.*?;", "", t)
# replace UTF codes by utf chars
sts = re.split("\\\\(U\\+....)", t)
- t = u"".join(sts)
+ t = "".join(sts)
# replace degrees, diameters chars
- t = re.sub(r'%%d', u'°', t)
- t = re.sub(r'%%c', u'Ø', t)
- t = re.sub(r'%%D', u'°', t)
- t = re.sub(r'%%C', u'Ø', t)
+ t = re.sub(r"%%d", "°", t)
+ t = re.sub(r"%%c", "Ø", t)
+ t = re.sub(r"%%D", "°", t)
+ t = re.sub(r"%%C", "Ø", t)
# print("output text: ", t)
return t
@@ -299,14 +323,16 @@ def locateLayer(wantedLayer, color=None, drawstyle=None, visibility=True):
# layers is a global variable.
# It should probably be passed as an argument.
if wantedLayer is None:
- wantedLayer = '0'
+ wantedLayer = "0"
for layer in layers:
if layer.Label == wantedLayer:
return layer
if dxfUseDraftVisGroups:
- newLayer = Draft.make_layer(name=wantedLayer,
- line_color=(0.0,0.0,0.0) if not color else color,
- draw_style="Solid" if not drawstyle else drawstyle)
+ newLayer = Draft.make_layer(
+ name=wantedLayer,
+ line_color=(0.0, 0.0, 0.0) if not color else color,
+ draw_style="Solid" if not drawstyle else drawstyle,
+ )
newLayer.Visibility = visibility
else:
newLayer = doc.addObject("App::DocumentObjectGroup", wantedLayer)
@@ -339,7 +365,7 @@ def getdimheight(style):
Use local variables, not global variables.
"""
for t in drawing.tables.data:
- if t.name == 'dimstyle':
+ if t.name == "dimstyle":
for a in t.data:
if hasattr(a, "type"):
if a.type == "dimstyle":
@@ -380,7 +406,7 @@ def calcBulge(v1, bulge, v2):
The new point between `v1` and `v2`.
"""
chord = v2.sub(v1)
- sagitta = (bulge * chord.Length)/2
+ sagitta = (bulge * chord.Length) / 2
perp = chord.cross(Vector(0, 0, 1))
startpoint = v1.add(chord.multiply(0.5))
if not DraftVecUtils.isNull(perp):
@@ -459,7 +485,9 @@ def getACI(ob, text=False):
for parent in ob.InList:
if Draft.getType(parent) == "Layer":
if ob in parent.Group:
- if hasattr(parent, "ViewObject") and hasattr(parent.ViewObject, "OverrideChildren"):
+ if hasattr(parent, "ViewObject") and hasattr(
+ parent.ViewObject, "OverrideChildren"
+ ):
if parent.ViewObject.OverrideChildren:
return 256 # BYLAYER
if text:
@@ -469,9 +497,7 @@ def getACI(ob, text=False):
aci = [0, 442]
for i in range(255, -1, -1):
ref = dxfColorMap.color_map[i]
- dist = ((ref[0]-col[0])**2
- + (ref[1]-col[1])**2
- + (ref[2]-col[2])**2)
+ dist = (ref[0] - col[0]) ** 2 + (ref[1] - col[1]) ** 2 + (ref[2] - col[2]) ** 2
if dist <= aci[1]:
aci = [i, dist]
return aci[0]
@@ -556,7 +582,7 @@ def isBrightBackground():
else:
r1, g1, b1, _ = utils.get_rgba_tuple(params.get_param_view("BackgroundColor"))
cv = Vector(r1, g1, b1)
- value = cv.x*.3 + cv.y*.59 + cv.z*.11
+ value = cv.x * 0.3 + cv.y * 0.59 + cv.z * 0.11
if value < 128:
return False
else:
@@ -716,9 +742,7 @@ def vec(pt):
if resolvedScale != 1:
v = v * resolvedScale
else:
- v = Vector(round(pt[0], pre),
- round(pt[1], pre),
- round(pt[2], pre))
+ v = Vector(round(pt[0], pre), round(pt[1], pre), round(pt[2], pre))
if resolvedScale != 1:
v.multiply(resolvedScale)
return v
@@ -757,8 +781,7 @@ def placementFromDXFOCS(ent):
WorkingPlane.align_to_point_and_axis, WorkingPlane.get_global_coords
"""
draftWPlane = WorkingPlane.PlaneBase()
- draftWPlane.align_to_point_and_axis(Vector(0.0, 0.0, 0.0),
- vec(ent.extrusion), 0.0)
+ draftWPlane.align_to_point_and_axis(Vector(0.0, 0.0, 0.0), vec(ent.extrusion), 0.0)
# Object Coordinate Systems (OCS)
# http://docs.autodesk.com/ACD/2011/ENU/filesDXF/WS1a9193826455f5ff18cb41610ec0a2e719-7941.htm
# Arbitrary Axis Algorithm
@@ -766,14 +789,14 @@ def placementFromDXFOCS(ent):
# Riferimenti dell'algoritmo dell'asse arbitrario in italiano
# http://docs.autodesk.com/ACD/2011/ITA/filesDXF/WS1a9193826455f5ff18cb41610ec0a2e719-7941.htm
# http://docs.autodesk.com/ACD/2011/ITA/filesDXF/WS1a9193826455f5ff18cb41610ec0a2e719-793d.htm#WSc30cd3d5faa8f6d81cb25f1ffb755717d-7ff5
- if (draftWPlane.axis == FreeCAD.Vector(1.0, 0.0, 0.0)):
+ if draftWPlane.axis == FreeCAD.Vector(1.0, 0.0, 0.0):
draftWPlane.u = FreeCAD.Vector(0.0, 1.0, 0.0)
draftWPlane.v = FreeCAD.Vector(0.0, 0.0, 1.0)
- elif (draftWPlane.axis == FreeCAD.Vector(-1.0, 0.0, 0.0)):
+ elif draftWPlane.axis == FreeCAD.Vector(-1.0, 0.0, 0.0):
draftWPlane.u = FreeCAD.Vector(0.0, -1.0, 0.0)
draftWPlane.v = FreeCAD.Vector(0.0, 0.0, 1.0)
else:
- if ((abs(ent.extrusion[0]) < (1.0 / 64.0)) and (abs(ent.extrusion[1]) < (1.0 / 64.0))):
+ if (abs(ent.extrusion[0]) < (1.0 / 64.0)) and (abs(ent.extrusion[1]) < (1.0 / 64.0)):
draftWPlane.u = FreeCAD.Vector(0.0, 1.0, 0.0).cross(draftWPlane.axis)
else:
draftWPlane.u = FreeCAD.Vector(0.0, 0.0, 1.0).cross(draftWPlane.axis)
@@ -783,7 +806,7 @@ def placementFromDXFOCS(ent):
draftWPlane.position = Vector(0.0, 0.0, 0.0)
pl = draftWPlane.get_placement()
- if ((ent.type == "lwpolyline") or (ent.type == "polyline")):
+ if (ent.type == "lwpolyline") or (ent.type == "polyline"):
pl.Base = draftWPlane.get_global_coords(vec([0.0, 0.0, ent.elevation]))
else:
pl.Base = draftWPlane.get_global_coords(vec(ent.loc))
@@ -884,9 +907,9 @@ def drawPolyline(polyline, forceShape=False, num=None):
edges = []
curves = False
verts = []
- for p in range(len(polyline.points)-1):
+ for p in range(len(polyline.points) - 1):
p1 = polyline.points[p]
- p2 = polyline.points[p+1]
+ p2 = polyline.points[p + 1]
v1 = vec(p1)
v2 = vec(p2)
verts.append(v1)
@@ -911,7 +934,7 @@ def drawPolyline(polyline, forceShape=False, num=None):
warn(polyline, num)
verts.append(v2)
if polyline.closed:
- p1 = polyline.points[len(polyline.points)-1]
+ p1 = polyline.points[len(polyline.points) - 1]
p2 = polyline.points[0]
v1 = vec(p1)
v2 = vec(p2)
@@ -932,9 +955,9 @@ def drawPolyline(polyline, forceShape=False, num=None):
width = rawValue(polyline, 43)
if width and dxfRenderPolylineWidth:
w = Part.Wire(edges)
- w1 = w.makeOffset(width/2)
+ w1 = w.makeOffset(width / 2)
if polyline.closed:
- w2 = w.makeOffset(-width/2)
+ w2 = w.makeOffset(-width / 2)
w1 = Part.Face(w1)
w2 = Part.Face(w2)
if w1.BoundBox.DiagonalLength > w2.BoundBox.DiagonalLength:
@@ -996,18 +1019,15 @@ def drawArc(arc, forceShape=False):
pre = Draft.precision()
pl = placementFromDXFOCS(arc)
rad = vec(arc.radius)
- firstangle = round(arc.start_angle%360, pre)
- lastangle = round(arc.end_angle%360, pre)
+ firstangle = round(arc.start_angle % 360, pre)
+ lastangle = round(arc.end_angle % 360, pre)
try:
if (dxfCreateDraft or dxfCreateSketch) and (not forceShape):
- return Draft.make_circle(rad, pl, face=False,
- startangle=firstangle,
- endangle=lastangle)
+ return Draft.make_circle(rad, pl, face=False, startangle=firstangle, endangle=lastangle)
else:
circle = Part.Circle()
circle.Radius = rad
- shape = circle.toShape(math.radians(firstangle),
- math.radians(lastangle))
+ shape = circle.toShape(math.radians(firstangle), math.radians(lastangle))
shape.Placement = pl
return shape
except Part.OCCError:
@@ -1100,7 +1120,7 @@ def drawEllipse(ellipse, forceShape=False):
end = round(ellipse.end_angle, pre)
majv = vec(ellipse.major)
majr = majv.Length
- minr = majr*ellipse.ratio
+ minr = majr * ellipse.ratio
el = Part.Ellipse(vec((0, 0, 0)), majr, minr)
x = majv.normalize()
z = vec(ellipse.extrusion).normalize()
@@ -1109,7 +1129,7 @@ def drawEllipse(ellipse, forceShape=False):
pl = FreeCAD.Placement(m)
pl.move(c)
if (dxfCreateDraft or dxfCreateSketch) and (not forceShape):
- if (start != 0.0) or ((end != 0.0) or (end != round(math.pi/2, pre))):
+ if (start != 0.0) or ((end != 0.0) or (end != round(math.pi / 2, pre))):
shape = el.toShape(start, end)
shape.Placement = pl
return shape
@@ -1182,13 +1202,13 @@ def drawMesh(mesh, forceShape=False):
pts = mesh.points
udim = rawValue(mesh, 71)
vdim = rawValue(mesh, 72)
- for u in range(udim-1):
- for v in range(vdim-1):
- b = u+v*udim
+ for u in range(udim - 1):
+ for v in range(vdim - 1):
+ b = u + v * udim
p1 = pts[b]
- p2 = pts[b+1]
- p3 = pts[b+udim]
- p4 = pts[b+udim+1]
+ p2 = pts[b + 1]
+ p3 = pts[b + udim]
+ p4 = pts[b + udim + 1]
md.append([p1, p2, p4])
md.append([p1, p4, p3])
elif mesh.flags == 64:
@@ -1276,8 +1296,7 @@ def drawSolid(solid):
return None
-def drawSplineIterpolation(verts, closed=False, forceShape=False,
- alwaysDiscretize=False):
+def drawSplineIterpolation(verts, closed=False, forceShape=False, alwaysDiscretize=False):
"""Return a wire or spline, opened or closed.
Parameters
@@ -1327,7 +1346,7 @@ def drawSplineIterpolation(verts, closed=False, forceShape=False,
return ob
else:
if dxfDiscretizeCurves or alwaysDiscretize:
- sh = Part.makePolygon(verts+[verts[0]])
+ sh = Part.makePolygon(verts + [verts[0]])
else:
sp = Part.BSplineCurve()
# print(knots)
@@ -1507,17 +1526,17 @@ def drawSpline(spline, forceShape=False):
# print(groupnumber)
if nbknots != len(knots):
- raise ValueError('Wrong number of knots')
+ raise ValueError("Wrong number of knots")
if nbcontrolp != len(controlpoints):
- raise ValueError('Wrong number of control points')
+ raise ValueError("Wrong number of control points")
if nbfitp != len(fitpoints):
- raise ValueError('Wrong number of fit points')
+ raise ValueError("Wrong number of fit points")
if rational == all((w == 1.0 or w is None) for w in weights):
- raise ValueError('inconsistant rational flag')
+ raise ValueError("inconsistant rational flag")
if len(weights) == 0:
weights = None
elif len(weights) != len(controlpoints):
- raise ValueError('Wrong number of weights')
+ raise ValueError("Wrong number of weights")
# build knotvector and multvector
# this means to remove duplicate knots
@@ -1538,41 +1557,42 @@ def drawSpline(spline, forceShape=False):
# check if the multiplicities are valid
innermults = multvector[:] if periodic else multvector[1:-1]
if any(m > degree for m in innermults): # invalid
- if all(m == degree+1 for m in multvector):
+ if all(m == degree + 1 for m in multvector):
if not forceShape and weights is None:
points = controlpoints[:]
- del points[degree+1::degree+1]
+ del points[degree + 1 :: degree + 1]
return Draft.make_bezcurve(points, degree=degree)
else:
poles = controlpoints[:]
edges = []
- while len(poles) >= degree+1:
+ while len(poles) >= degree + 1:
# bezier segments
bzseg = Part.BezierCurve()
bzseg.increase(degree)
- bzseg.setPoles(poles[0:degree+1])
- poles = poles[degree+1:]
+ bzseg.setPoles(poles[0 : degree + 1])
+ poles = poles[degree + 1 :]
if weights is not None:
- bzseg.setWeights(weights[0:degree+1])
- weights = weights[degree+1:]
+ bzseg.setWeights(weights[0 : degree + 1])
+ weights = weights[degree + 1 :]
edges.append(bzseg.toShape())
return Part.Wire(edges)
else:
- warn('polygon fallback on %s' % spline)
- return drawSplineIterpolation(controlpoints, closed=closed,
- forceShape=forceShape,
- alwaysDiscretize=True)
+ warn("polygon fallback on %s" % spline)
+ return drawSplineIterpolation(
+ controlpoints, closed=closed, forceShape=forceShape, alwaysDiscretize=True
+ )
if fitpoints and not controlpoints:
- return drawSplineIterpolation(fitpoints, closed=closed,
- forceShape=forceShape)
+ return drawSplineIterpolation(fitpoints, closed=closed, forceShape=forceShape)
try:
bspline = Part.BSplineCurve()
- bspline.buildFromPolesMultsKnots(poles=controlpoints,
- mults=multvector,
- knots=knotvector,
- degree=degree,
- periodic=periodic,
- weights=weights)
+ bspline.buildFromPolesMultsKnots(
+ poles=controlpoints,
+ mults=multvector,
+ knots=knotvector,
+ degree=degree,
+ periodic=periodic,
+ weights=weights,
+ )
return bspline.toShape()
except Part.OCCError:
warn(spline)
@@ -1640,7 +1660,7 @@ def drawBlock(blockref, num=None, createObject=False):
Use local variables, not global variables.
"""
if not dxfStarBlocks:
- if blockref.name[0] == '*':
+ if blockref.name[0] == "*":
return None
if len(blockref.entities.data) == 0:
print("skipping empty block ", blockref.name)
@@ -1648,48 +1668,48 @@ def drawBlock(blockref, num=None, createObject=False):
# print("creating block ", blockref.name,
# " containing ", len(blockref.entities.data), " entities")
shapes = []
- for line in blockref.entities.get_type('line'):
+ for line in blockref.entities.get_type("line"):
s = drawLine(line, forceShape=True)
if s:
shapes.append(s)
- for polyline in blockref.entities.get_type('polyline'):
+ for polyline in blockref.entities.get_type("polyline"):
if hasattr(polyline, "flags") and polyline.flags in [16, 64]:
s = drawMesh(polyline, forceShape=True)
else:
s = drawPolyline(polyline, forceShape=True)
if s:
shapes.append(s)
- for polyline in blockref.entities.get_type('lwpolyline'):
+ for polyline in blockref.entities.get_type("lwpolyline"):
s = drawPolyline(polyline, forceShape=True)
if s:
shapes.append(s)
- for arc in blockref.entities.get_type('arc'):
+ for arc in blockref.entities.get_type("arc"):
s = drawArc(arc, forceShape=True)
if s:
shapes.append(s)
- for circle in blockref.entities.get_type('circle'):
+ for circle in blockref.entities.get_type("circle"):
s = drawCircle(circle, forceShape=True)
if s:
shapes.append(s)
- for insert in blockref.entities.get_type('insert'):
+ for insert in blockref.entities.get_type("insert"):
# print("insert ",insert," in block ",insert.block[0])
- if dxfStarBlocks or insert.block[0] != '*':
+ if dxfStarBlocks or insert.block[0] != "*":
s = drawInsert(insert)
if s:
shapes.append(s)
- for solid in blockref.entities.get_type('solid'):
+ for solid in blockref.entities.get_type("solid"):
s = drawSolid(solid)
if s:
shapes.append(s)
- for spline in blockref.entities.get_type('spline'):
+ for spline in blockref.entities.get_type("spline"):
s = drawSpline(spline, forceShape=True)
if s:
shapes.append(s)
- for text in blockref.entities.get_type('text'):
+ for text in blockref.entities.get_type("text"):
if dxfImportTexts:
if dxfImportLayouts or (not rawValue(text, 67)):
addText(text)
- for text in blockref.entities.get_type('mtext'):
+ for text in blockref.entities.get_type("mtext"):
if dxfImportTexts:
if dxfImportLayouts or (not rawValue(text, 67)):
print("adding block text", text.value, " from ", blockref)
@@ -1887,12 +1907,12 @@ def attribs(insert):
break
if index is None:
return []
- j = index+1
+ j = index + 1
while True:
ent = drawing.entities.data[j]
- if str(ent) == 'seqend':
+ if str(ent) == "seqend":
return atts
- elif str(ent) == 'attrib':
+ elif str(ent) == "attrib":
atts.append(ent)
j += 1
@@ -1992,9 +2012,7 @@ def addText(text, attrib=False):
if attrib:
lay = locateLayer(rawValue(text, 8))
val = rawValue(text, 1)
- pos = vec([rawValue(text, 10),
- rawValue(text, 20),
- rawValue(text, 30)])
+ pos = vec([rawValue(text, 10), rawValue(text, 20), rawValue(text, 30)])
hgt = vec(rawValue(text, 40))
else:
lay = locateLayer(text.layer)
@@ -2023,8 +2041,7 @@ def addText(text, attrib=False):
ax = (xv.cross(Vector(1, 0, 0))).negative()
if DraftVecUtils.isNull(ax):
ax = Vector(0, 0, 1)
- ang = -math.degrees(DraftVecUtils.angle(xv,
- Vector(1, 0, 0), ax))
+ ang = -math.degrees(DraftVecUtils.angle(xv, Vector(1, 0, 0), ax))
Draft.rotate(newob, ang, axis=ax)
if ax == Vector(0, 0, -1):
ax = Vector(0, 0, 1)
@@ -2042,11 +2059,11 @@ def addText(text, attrib=False):
if hasattr(text, "alignment"):
yv = ax.cross(xv)
if text.alignment in [1, 2, 3]:
- sup = DraftVecUtils.scaleTo(yv, fsize/TEXTSCALING).negative()
+ sup = DraftVecUtils.scaleTo(yv, fsize / TEXTSCALING).negative()
# print(ax, sup)
pos = pos.add(sup)
elif text.alignment in [4, 5, 6]:
- sup = DraftVecUtils.scaleTo(yv, fsize/(2*TEXTSCALING)).negative()
+ sup = DraftVecUtils.scaleTo(yv, fsize / (2 * TEXTSCALING)).negative()
pos = pos.add(sup)
newob.Placement.Base = pos
if gui:
@@ -2263,11 +2280,11 @@ def processdxf(document, filename, getShapes=False, reComputeFlag=True):
drawstyle = "Dotted"
if ("DASHDOT" in lt.upper()) or ("CENTER" in lt.upper()):
drawstyle = "Dashdot"
- locateLayer(name, color, drawstyle, layer.color>0)
+ locateLayer(name, color, drawstyle, layer.color > 0)
else:
locateLayer("0", (0.0, 0.0, 0.0), "Solid")
- # Draw lines
+ # Draw lines
lines = drawing.entities.get_type("line")
if lines:
FCC.PrintMessage("drawing " + str(len(lines)) + " lines...\n")
@@ -2279,16 +2296,12 @@ def processdxf(document, filename, getShapes=False, reComputeFlag=True):
FreeCAD.ActiveDocument.recompute()
if dxfMakeBlocks or dxfJoin:
if sketch:
- shape = Draft.make_sketch(shape,
- autoconstraints=True,
- addTo=sketch)
+ shape = Draft.make_sketch(shape, autoconstraints=True, addTo=sketch)
else:
- shape = Draft.make_sketch(shape,
- autoconstraints=True)
+ shape = Draft.make_sketch(shape, autoconstraints=True)
sketch = shape
else:
- shape = Draft.make_sketch(shape,
- autoconstraints=True)
+ shape = Draft.make_sketch(shape, autoconstraints=True)
elif dxfJoin or getShapes:
if isinstance(shape, Part.Shape):
shapes.append(shape)
@@ -2323,23 +2336,18 @@ def processdxf(document, filename, getShapes=False, reComputeFlag=True):
if shape:
if dxfCreateSketch:
if isinstance(shape, Part.Shape):
- t = FreeCAD.ActiveDocument.addObject("Part::Feature",
- "Shape")
+ t = FreeCAD.ActiveDocument.addObject("Part::Feature", "Shape")
t.Shape = shape
shape = t
FreeCAD.ActiveDocument.recompute()
if dxfMakeBlocks or dxfJoin:
if sketch:
- shape = Draft.make_sketch(shape,
- autoconstraints=True,
- addTo=sketch)
+ shape = Draft.make_sketch(shape, autoconstraints=True, addTo=sketch)
else:
- shape = Draft.make_sketch(shape,
- autoconstraints=True)
+ shape = Draft.make_sketch(shape, autoconstraints=True)
sketch = shape
else:
- shape = Draft.make_sketch(shape,
- autoconstraints=True)
+ shape = Draft.make_sketch(shape, autoconstraints=True)
elif dxfJoin or getShapes:
if isinstance(shape, Part.Shape):
shapes.append(shape)
@@ -2365,16 +2373,12 @@ def processdxf(document, filename, getShapes=False, reComputeFlag=True):
FreeCAD.ActiveDocument.recompute()
if dxfMakeBlocks or dxfJoin:
if sketch:
- shape = Draft.make_sketch(shape,
- autoconstraints=True,
- addTo=sketch)
+ shape = Draft.make_sketch(shape, autoconstraints=True, addTo=sketch)
else:
- shape = Draft.make_sketch(shape,
- autoconstraints=True)
+ shape = Draft.make_sketch(shape, autoconstraints=True)
sketch = shape
else:
- shape = Draft.make_sketch(shape,
- autoconstraints=True)
+ shape = Draft.make_sketch(shape, autoconstraints=True)
elif dxfJoin or getShapes:
if isinstance(shape, Part.Shape):
shapes.append(shape)
@@ -2398,13 +2402,14 @@ def processdxf(document, filename, getShapes=False, reComputeFlag=True):
if gui:
d = QtWidgets.QMessageBox()
d.setText("Warning: High number of entities to join (>100)")
- d.setInformativeText("This might take a long time "
- "or even freeze your computer. "
- "Are you sure? You can also disable "
- "the 'join geometry' setting in DXF "
- "import preferences")
- d.setStandardButtons(QtWidgets.QMessageBox.Ok
- | QtWidgets.QMessageBox.Cancel)
+ d.setInformativeText(
+ "This might take a long time "
+ "or even freeze your computer. "
+ "Are you sure? You can also disable "
+ "the 'join geometry' setting in DXF "
+ "import preferences"
+ )
+ d.setStandardButtons(QtWidgets.QMessageBox.Ok | QtWidgets.QMessageBox.Cancel)
d.setDefaultButton(QtWidgets.QMessageBox.Cancel)
res = d.exec_()
if res == QtWidgets.QMessageBox.Cancel:
@@ -2417,7 +2422,7 @@ def processdxf(document, filename, getShapes=False, reComputeFlag=True):
# Draw circles
circles = drawing.entities.get_type("circle")
if circles:
- FCC.PrintMessage("drawing " + str(len(circles))+" circles...\n")
+ FCC.PrintMessage("drawing " + str(len(circles)) + " circles...\n")
for circle in circles:
if dxfImportLayouts or (not rawValue(circle, 67)):
shape = drawCircle(circle)
@@ -2426,16 +2431,12 @@ def processdxf(document, filename, getShapes=False, reComputeFlag=True):
FreeCAD.ActiveDocument.recompute()
if dxfMakeBlocks or dxfJoin:
if sketch:
- shape = Draft.make_sketch(shape,
- autoconstraints=True,
- addTo=sketch)
+ shape = Draft.make_sketch(shape, autoconstraints=True, addTo=sketch)
else:
- shape = Draft.make_sketch(shape,
- autoconstraints=True)
+ shape = Draft.make_sketch(shape, autoconstraints=True)
sketch = shape
else:
- shape = Draft.make_sketch(shape,
- autoconstraints=True)
+ shape = Draft.make_sketch(shape, autoconstraints=True)
elif dxfMakeBlocks:
addToBlock(shape, circle.layer)
elif getShapes:
@@ -2623,6 +2624,7 @@ def processdxf(document, filename, getShapes=False, reComputeFlag=True):
_Dimension(newob)
if gui:
from Draft import _ViewProviderDimension
+
_ViewProviderDimension(newob.ViewObject)
newob.Start = p1
newob.End = p2
@@ -2636,7 +2638,7 @@ def processdxf(document, filename, getShapes=False, reComputeFlag=True):
else:
st = rawValue(dim, 3)
size = getdimheight(st) or 1
- newob.ViewObject.FontSize = float(size)*TEXTSCALING
+ newob.ViewObject.FontSize = float(size) * TEXTSCALING
else:
FCC.PrintMessage("skipping dimensions...\n")
@@ -2716,7 +2718,7 @@ def processdxf(document, filename, getShapes=False, reComputeFlag=True):
newinserts = []
for i in inserts:
if dxfImportLayouts or (not rawValue(i, 67)):
- if i.block[0] != '*':
+ if i.block[0] != "*":
newinserts.append(i)
inserts = newinserts
if inserts:
@@ -2737,8 +2739,7 @@ def processdxf(document, filename, getShapes=False, reComputeFlag=True):
if dxfMakeBlocks:
addToBlock(shape, insert.layer)
else:
- newob = addObject(shape, "Block." + insert.block,
- insert.layer)
+ newob = addObject(shape, "Block." + insert.block, insert.layer)
if gui:
formatObject(newob, insert)
num += 1
@@ -2759,7 +2760,7 @@ def processdxf(document, filename, getShapes=False, reComputeFlag=True):
del blockobjects
# Move layer contents to layers
- for (l, contents) in layerObjects.items():
+ for l, contents in layerObjects.items():
l.Group += contents
# Finishing
@@ -2813,11 +2814,13 @@ def _import_dxf_file(filename, doc_name=None):
if gui and not use_legacy and hGrp.GetBool("dxfShowDialog", True):
try:
import ImportGui
+
entity_counts = ImportGui.preScanDxf(filename)
except Exception:
entity_counts = {}
from DxfImportDialog import DxfImportDialog
+
dlg = DxfImportDialog(entity_counts)
if dlg.exec_():
@@ -2833,7 +2836,7 @@ def _import_dxf_file(filename, doc_name=None):
params.set_param("dxfImportAsFused", mode == 3)
hGrp.SetBool("dxfShowDialog", dlg.get_show_dialog_again())
else:
- return None, None, None, None # Return None to indicate cancellation
+ return None, None, None, None # Return None to indicate cancellation
finally:
if gui:
FreeCADGui.resumeWaitCursor()
@@ -2841,13 +2844,13 @@ def _import_dxf_file(filename, doc_name=None):
import_mode = hGrp.GetInt("DxfImportMode", 2)
# --- Document Handling ---
- if doc_name: # INSERT operation
+ if doc_name: # INSERT operation
try:
doc = FreeCAD.getDocument(doc_name)
except NameError:
doc = FreeCAD.newDocument(doc_name)
FreeCAD.setActiveDocument(doc_name)
- else: # OPEN operation
+ else: # OPEN operation
docname = os.path.splitext(os.path.basename(filename))[0]
doc = FreeCAD.newDocument(docname)
doc.Label = docname
@@ -2859,7 +2862,7 @@ def _import_dxf_file(filename, doc_name=None):
# Take snapshot of objects before import
objects_before = set(doc.Objects)
- stats = None # For C++ importer stats
+ stats = None # For C++ importer stats
if use_legacy:
getDXFlibs()
if dxfReader:
@@ -2867,12 +2870,14 @@ def _import_dxf_file(filename, doc_name=None):
else:
errorDXFLib(gui)
return None, None
- else: # Modern C++ Importer
+ else: # Modern C++ Importer
if gui:
import ImportGui
+
stats = ImportGui.readDXF(filename)
else:
import Import
+
stats = Import.readDXF(filename)
# Find the newly created objects
@@ -2884,7 +2889,7 @@ def _import_dxf_file(filename, doc_name=None):
draft_postprocessor = DxfDraftPostProcessor(doc, newly_created_objects, import_mode)
draft_postprocessor.run()
- Draft.convert_draft_texts() # This is a general utility that should run for both importers
+ Draft.convert_draft_texts() # This is a general utility that should run for both importers
doc.recompute()
processing_end_time = time.perf_counter()
@@ -2920,6 +2925,7 @@ def open(filename):
return doc
+
def insert(filename, docname):
"""Import a file into the specified document.
@@ -2969,6 +2975,7 @@ def getShapes(filename):
# EXPORT ######################################################################
+
def projectShape(shape, direction, tess=None):
"""Project shape in a given direction.
@@ -3006,6 +3013,7 @@ def projectShape(shape, direction, tess=None):
TechDraw.projectEx, DraftGeomUtils.cleanProjection
"""
import TechDraw
+
edges = []
try:
groups = TechDraw.projectEx(shape, direction)
@@ -3018,8 +3026,7 @@ def projectShape(shape, direction, tess=None):
edges.append(g)
# return DraftGeomUtils.cleanProjection(Part.makeCompound(edges))
if tess:
- return DraftGeomUtils.cleanProjection(Part.makeCompound(edges),
- tess[0], tess[1])
+ return DraftGeomUtils.cleanProjection(Part.makeCompound(edges), tess[0], tess[1])
else:
return Part.makeCompound(edges)
# return DraftGeomUtils.cleanProjection(Part.makeCompound(edges))
@@ -3085,8 +3092,7 @@ def getArcData(edge):
# ang1 -= DraftVecUtils.angle(edge.Curve.XAxis)
# ang2 -= DraftVecUtils.angle(edge.Curve.XAxis)
- return (DraftVecUtils.tup(ce), radius,
- math.degrees(ang1), math.degrees(ang2))
+ return (DraftVecUtils.tup(ce), radius, math.degrees(ang1), math.degrees(ang2))
def getSplineSegs(edge):
@@ -3115,11 +3121,11 @@ def getSplineSegs(edge):
else:
points.append(edge.valueAt(edge.FirstParameter))
if edge.Length > seglength:
- nbsegs = int(math.ceil(edge.Length/seglength))
- step = (edge.LastParameter-edge.FirstParameter)/nbsegs
+ nbsegs = int(math.ceil(edge.Length / seglength))
+ step = (edge.LastParameter - edge.FirstParameter) / nbsegs
for nv in range(1, nbsegs):
# print("value at", nv*step, "=", edge.valueAt(nv*step))
- v = edge.valueAt(edge.FirstParameter+(nv*step))
+ v = edge.valueAt(edge.FirstParameter + (nv * step))
points.append(v)
points.append(edge.valueAt(edge.LastParameter))
return points
@@ -3184,6 +3190,7 @@ def getWire(wire, nospline=False, lw=True, asis=False):
--------
calcBulge
"""
+
def fmt(v, b=0.0):
if lw:
# LWpolyline format
@@ -3191,6 +3198,7 @@ def getWire(wire, nospline=False, lw=True, asis=False):
else:
# Polyline format
return ((v.x, v.y, v.z), None, [None, None], b)
+
points = []
if asis:
points = [fmt(v.Point) for v in wire.OrderedVertexes]
@@ -3201,17 +3209,17 @@ def getWire(wire, nospline=False, lw=True, asis=False):
v1 = edge.Vertexes[0].Point
if DraftGeomUtils.geomType(edge) == "Circle":
# polyline bulge -> negative makes the arc go clockwise
- angle = edge.LastParameter-edge.FirstParameter
- bul = math.tan(angle/4)
+ angle = edge.LastParameter - edge.FirstParameter
+ bul = math.tan(angle / 4)
# if cross1[2] < 0:
# # polyline bulge -> negative makes the arc go clockwise
# bul = -bul
if edge.Curve.Axis.dot(Vector(0, 0, 1)) < 0:
bul = -bul
points.append(fmt(v1, bul))
- elif (DraftGeomUtils.geomType(edge) in ["BSplineCurve",
- "BezierCurve",
- "Ellipse"]) and (not nospline):
+ elif (DraftGeomUtils.geomType(edge) in ["BSplineCurve", "BezierCurve", "Ellipse"]) and (
+ not nospline
+ ):
spline = getSplineSegs(edge)
spline.pop()
for p in spline:
@@ -3255,8 +3263,7 @@ def getBlock(sh, obj, lwPoly=False):
return block
-def writeShape(sh, ob, dxfobject, nospline=False, lwPoly=False,
- layer=None, color=None, asis=False):
+def writeShape(sh, ob, dxfobject, nospline=False, lwPoly=False, layer=None, color=None, asis=False):
"""Write the object's shape contents in the given DXF object.
Iterates over the wires (polylines) and lone edges of `sh`.
@@ -3343,32 +3350,40 @@ def writeShape(sh, ob, dxfobject, nospline=False, lwPoly=False,
center, radius, ang1, ang2 = getArcData(wire.Edges[0])
if center is not None:
if len(wire.Edges[0].Vertexes) == 1: # circle
- dxfobject.append(dxfLibrary.Circle(center, radius,
- color=color,
- layer=layer))
+ dxfobject.append(dxfLibrary.Circle(center, radius, color=color, layer=layer))
else: # arc
- dxfobject.append(dxfLibrary.Arc(center, radius,
- ang1, ang2, color=color,
- layer=layer))
+ dxfobject.append(
+ dxfLibrary.Arc(center, radius, ang1, ang2, color=color, layer=layer)
+ )
else:
if lwPoly:
if hasattr(dxfLibrary, "LwPolyLine"):
- dxfobject.append(dxfLibrary.LwPolyLine(getWire(wire, nospline, asis=asis),
- [0.0, 0.0],
- int(DraftGeomUtils.isReallyClosed(wire)),
- color=color,
- layer=layer))
+ dxfobject.append(
+ dxfLibrary.LwPolyLine(
+ getWire(wire, nospline, asis=asis),
+ [0.0, 0.0],
+ int(DraftGeomUtils.isReallyClosed(wire)),
+ color=color,
+ layer=layer,
+ )
+ )
else:
- FCC.PrintWarning("LwPolyLine support not found. "
- "Please delete dxfLibrary.py "
- "from your FreeCAD user directory "
- "to force auto-update\n")
+ FCC.PrintWarning(
+ "LwPolyLine support not found. "
+ "Please delete dxfLibrary.py "
+ "from your FreeCAD user directory "
+ "to force auto-update\n"
+ )
else:
- dxfobject.append(dxfLibrary.PolyLine(getWire(wire, nospline, lw=False, asis=asis),
- [0.0, 0.0, 0.0],
- int(DraftGeomUtils.isReallyClosed(wire)),
- color=color,
- layer=layer))
+ dxfobject.append(
+ dxfLibrary.PolyLine(
+ getWire(wire, nospline, lw=False, asis=asis),
+ [0.0, 0.0, 0.0],
+ int(DraftGeomUtils.isReallyClosed(wire)),
+ color=color,
+ layer=layer,
+ )
+ )
if len(processededges) < len(sh.Edges): # lone edges
loneedges = []
for e in sh.Edges:
@@ -3377,51 +3392,51 @@ def writeShape(sh, ob, dxfobject, nospline=False, lwPoly=False,
# print("lone edges ", loneedges)
for edge in loneedges:
# splines
- if (DraftGeomUtils.geomType(edge) in ["BSplineCurve",
- "BezierCurve"]):
+ if DraftGeomUtils.geomType(edge) in ["BSplineCurve", "BezierCurve"]:
if (len(edge.Vertexes) == 1) and (edge.Curve.isClosed()) and (edge.Area > 0):
# special case: 1-vert closed spline, approximate as a circle
c = DraftGeomUtils.getCircleFromSpline(edge)
if c:
- dxfobject.append(dxfLibrary.Circle(DraftVecUtils.tup(c.Curve.Center),
- c.Curve.Radius,
- color=color,
- layer=layer))
+ dxfobject.append(
+ dxfLibrary.Circle(
+ DraftVecUtils.tup(c.Curve.Center),
+ c.Curve.Radius,
+ color=color,
+ layer=layer,
+ )
+ )
else:
points = []
spline = getSplineSegs(edge)
for p in spline:
points.append(((p.x, p.y, p.z), None, [None, None], 0.0))
- dxfobject.append(dxfLibrary.PolyLine(points,
- [0.0, 0.0, 0.0],
- 0, color=color,
- layer=layer))
+ dxfobject.append(
+ dxfLibrary.PolyLine(points, [0.0, 0.0, 0.0], 0, color=color, layer=layer)
+ )
elif DraftGeomUtils.geomType(edge) == "Circle": # curves
center, radius, ang1, ang2 = getArcData(edge)
if center is not None:
if not isinstance(center, tuple):
center = DraftVecUtils.tup(center)
if len(edge.Vertexes) == 1: # circles
- dxfobject.append(dxfLibrary.Circle(center,
- radius,
- color=color,
- layer=layer))
+ dxfobject.append(
+ dxfLibrary.Circle(center, radius, color=color, layer=layer)
+ )
else: # arcs
- dxfobject.append(dxfLibrary.Arc(center,
- radius,
- ang1, ang2,
- color=getACI(ob),
- layer=layer))
+ dxfobject.append(
+ dxfLibrary.Arc(
+ center, radius, ang1, ang2, color=getACI(ob), layer=layer
+ )
+ )
elif DraftGeomUtils.geomType(edge) == "Ellipse": # ellipses:
if params.get_param("DiscretizeEllipses"):
points = []
spline = getSplineSegs(edge)
for p in spline:
points.append(((p.x, p.y, p.z), None, [None, None], 0.0))
- dxfobject.append(dxfLibrary.PolyLine(points,
- [0.0, 0.0, 0.0],
- 0, color=color,
- layer=layer))
+ dxfobject.append(
+ dxfLibrary.PolyLine(points, [0.0, 0.0, 0.0], 0, color=color, layer=layer)
+ )
else:
if hasattr(dxfLibrary, "Ellipse"):
center = DraftVecUtils.tup(edge.Curve.Center)
@@ -3430,30 +3445,39 @@ def writeShape(sh, ob, dxfobject, nospline=False, lwPoly=False,
end = edge.LastParameter
ax = edge.Curve.Focus1.sub(edge.Curve.Center)
major = DraftVecUtils.tup(DraftVecUtils.scaleTo(ax, edge.Curve.MajorRadius))
- minor = edge.Curve.MinorRadius/edge.Curve.MajorRadius
+ minor = edge.Curve.MinorRadius / edge.Curve.MajorRadius
# print("exporting ellipse: ", center, norm,
# start, end, major, minor)
- dxfobject.append(dxfLibrary.Ellipse(center=center,
- majorAxis=major,
- normalAxis=norm,
- minorAxisRatio=minor,
- startParameter=start,
- endParameter=end,
- color=color,
- layer=layer))
+ dxfobject.append(
+ dxfLibrary.Ellipse(
+ center=center,
+ majorAxis=major,
+ normalAxis=norm,
+ minorAxisRatio=minor,
+ startParameter=start,
+ endParameter=end,
+ color=color,
+ layer=layer,
+ )
+ )
else:
- FCC.PrintWarning("Ellipses support not found. "
- "Please delete dxfLibrary.py "
- "from your FreeCAD user directory "
- "to force auto-update\n")
+ FCC.PrintWarning(
+ "Ellipses support not found. "
+ "Please delete dxfLibrary.py "
+ "from your FreeCAD user directory "
+ "to force auto-update\n"
+ )
else: # anything else is treated as lines
if len(edge.Vertexes) > 1:
ve1 = edge.Vertexes[0].Point
ve2 = edge.Vertexes[1].Point
- dxfobject.append(dxfLibrary.Line([DraftVecUtils.tup(ve1),
- DraftVecUtils.tup(ve2)],
- color=color,
- layer=layer))
+ dxfobject.append(
+ dxfLibrary.Line(
+ [DraftVecUtils.tup(ve1), DraftVecUtils.tup(ve2)],
+ color=color,
+ layer=layer,
+ )
+ )
def writeMesh(ob, dxf):
@@ -3489,10 +3513,11 @@ def writeMesh(ob, dxf):
for f in meshdata[1]:
faces.append([f[0] + 1, f[1] + 1, f[2] + 1])
# print(len(points),len(faces))
- dxf.append(dxfLibrary.PolyLine([points, faces],
- [0.0, 0.0, 0.0],
- 64, color=getACI(ob),
- layer=getGroup(ob)))
+ dxf.append(
+ dxfLibrary.PolyLine(
+ [points, faces], [0.0, 0.0, 0.0], 64, color=getACI(ob), layer=getGroup(ob)
+ )
+ )
def writePanelCut(ob, dxf, nospline, lwPoly, parent=None):
@@ -3576,14 +3601,11 @@ def writePanelCut(ob, dxf, nospline, lwPoly, parent=None):
inl = None
outl = outl.Wires[0]
- writeShape(outl, parent, dxf, nospline, lwPoly,
- layer="Outlines", color=5)
+ writeShape(outl, parent, dxf, nospline, lwPoly, layer="Outlines", color=5)
if inl:
- writeShape(inl, parent, dxf, nospline, lwPoly,
- layer="Cuts", color=4)
+ writeShape(inl, parent, dxf, nospline, lwPoly, layer="Cuts", color=4)
if tag:
- writeShape(tag, parent, dxf, nospline, lwPoly,
- layer="Tags", color=2, asis=True)
+ writeShape(tag, parent, dxf, nospline, lwPoly, layer="Tags", color=2, asis=True)
# sticky fonts can render very odd wires...
# for w in tag.Edges:
# pts = [(v.X, v.Y, v.Z) for v in w.Vertexes]
@@ -3674,6 +3696,7 @@ def export(objectslist, filename, nospline=False, lwPoly=False):
readPreferences()
if not dxfUseLegacyExporter:
import Import
+
version = 14
if nospline:
version = 12
@@ -3716,24 +3739,26 @@ def export(objectslist, filename, nospline=False, lwPoly=False):
# other cases, treat objects one by one
dxf = dxfLibrary.Drawing()
# add global variables
- if hasattr(dxf,"header"):
- dxf.header.append(" 9\n$DIMTXT\n 40\n" + str(params.get_param("textheight")) + "\n")
+ if hasattr(dxf, "header"):
+ dxf.header.append(
+ " 9\n$DIMTXT\n 40\n" + str(params.get_param("textheight")) + "\n"
+ )
dxf.header.append(" 9\n$INSUNITS\n 70\n4\n")
for ob in exportLayers:
if ob.Label != "0": # dxflibrary already creates it
- ltype = 'continuous'
+ ltype = "continuous"
if ob.ViewObject:
if ob.ViewObject.DrawStyle == "Dashed":
- ltype = 'DASHED'
+ ltype = "DASHED"
elif ob.ViewObject.DrawStyle == "Dotted":
- ltype = 'HIDDEN'
+ ltype = "HIDDEN"
elif ob.ViewObject.DrawStyle == "Dashdot":
- ltype = 'DASHDOT'
+ ltype = "DASHDOT"
# print("exporting layer:", ob.Label,
# getACI(ob), ltype)
- dxf.layers.append(dxfLibrary.Layer(name=ob.Label,
- color=getACI(ob),
- lineType=ltype))
+ dxf.layers.append(
+ dxfLibrary.Layer(name=ob.Label, color=getACI(ob), lineType=ltype)
+ )
base_sketch_pla = None # Placement of the 1st sketch.
for ob in exportList:
obtype = Draft.getType(ob)
@@ -3744,22 +3769,18 @@ def export(objectslist, filename, nospline=False, lwPoly=False):
sb = ob.Proxy.sheetborder
if sb:
sb.Placement = ob.Placement
- writeShape(sb, ob, dxf, nospline, lwPoly,
- layer="Sheets", color=1)
+ writeShape(sb, ob, dxf, nospline, lwPoly, layer="Sheets", color=1)
ss = ob.Proxy.sheettag
if ss:
ss.Placement = ob.Placement.multiply(ss.Placement)
- writeShape(ss, ob, dxf, nospline, lwPoly,
- layer="SheetTags", color=1)
+ writeShape(ss, ob, dxf, nospline, lwPoly, layer="SheetTags", color=1)
for subob in ob.Group:
if Draft.getType(subob) == "PanelCut":
- writePanelCut(subob, dxf, nospline, lwPoly,
- parent=ob)
+ writePanelCut(subob, dxf, nospline, lwPoly, parent=ob)
elif subob.isDerivedFrom("Part::Feature"):
shp = subob.Shape.copy()
shp.Placement = ob.Placement.multiply(shp.Placement)
- writeShape(shp, ob, dxf, nospline, lwPoly,
- layer="Outlines", color=5)
+ writeShape(shp, ob, dxf, nospline, lwPoly, layer="Outlines", color=5)
elif obtype == "PanelCut":
writePanelCut(ob, dxf, nospline, lwPoly)
@@ -3777,74 +3798,103 @@ def export(objectslist, filename, nospline=False, lwPoly=False):
lspc = FreeCAD.Vector(_h)
p1 = ob.Placement.multVec(p2 + lspc)
justifyhor = ("Left", "Center", "Right").index(vobj.TextAlign)
- dxf.append(dxfLibrary.Text(t1,
- p1,
- alignment=p1 if justifyhor else None,
- height=h1 * 0.8,
- justifyhor=justifyhor,
- rotation=rotation,
- color=getACI(ob, text=True),
- style='STANDARD',
- layer=getStrGroup(ob)))
+ dxf.append(
+ dxfLibrary.Text(
+ t1,
+ p1,
+ alignment=p1 if justifyhor else None,
+ height=h1 * 0.8,
+ justifyhor=justifyhor,
+ rotation=rotation,
+ color=getACI(ob, text=True),
+ style="STANDARD",
+ layer=getStrGroup(ob),
+ )
+ )
if t2:
ofs = FreeCAD.Vector(0, -lspc.Length, 0)
if rotation:
Z = FreeCAD.Vector(0, 0, 1)
ofs = FreeCAD.Rotation(Z, rotation).multVec(ofs)
- dxf.append(dxfLibrary.Text(t2,
- p1.add(ofs),
- alignment=p1.add(ofs) if justifyhor else None,
- height=h2 * 0.8,
- justifyhor=justifyhor,
- rotation=rotation,
- color=getACI(ob, text=True),
- style='STANDARD',
- layer=getStrGroup(ob)))
+ dxf.append(
+ dxfLibrary.Text(
+ t2,
+ p1.add(ofs),
+ alignment=p1.add(ofs) if justifyhor else None,
+ height=h2 * 0.8,
+ justifyhor=justifyhor,
+ rotation=rotation,
+ color=getACI(ob, text=True),
+ style="STANDARD",
+ layer=getStrGroup(ob),
+ )
+ )
elif obtype == "Axis":
axes = ob.Proxy.getAxisData(ob)
if not axes:
continue
for ax in axes:
- dxf.append(dxfLibrary.Line([ax[0],
- ax[1]],
- color=getACI(ob),
- layer=getStrGroup(ob)))
+ dxf.append(
+ dxfLibrary.Line([ax[0], ax[1]], color=getACI(ob), layer=getStrGroup(ob))
+ )
h = 1
if gui:
vobj = ob.ViewObject
h = float(vobj.FontSize)
for text in vobj.Proxy.getTextData():
- pos = text[1].add(FreeCAD.Vector(0,-h/2,0))
- dxf.append(dxfLibrary.Text(text[0],
- pos,
- alignment=pos,
- height=h,
- justifyhor=1,
- color=getACI(ob),
- style='STANDARD',
- layer=getStrGroup(ob)))
+ pos = text[1].add(FreeCAD.Vector(0, -h / 2, 0))
+ dxf.append(
+ dxfLibrary.Text(
+ text[0],
+ pos,
+ alignment=pos,
+ height=h,
+ justifyhor=1,
+ color=getACI(ob),
+ style="STANDARD",
+ layer=getStrGroup(ob),
+ )
+ )
for shape in vobj.Proxy.getShapeData():
- if hasattr(shape,"Curve") and isinstance(shape.Curve,Part.Circle):
- dxf.append(dxfLibrary.Circle(shape.Curve.Center,
- shape.Curve.Radius,
- color=getACI(ob),
- layer=getStrGroup(ob)))
+ if hasattr(shape, "Curve") and isinstance(shape.Curve, Part.Circle):
+ dxf.append(
+ dxfLibrary.Circle(
+ shape.Curve.Center,
+ shape.Curve.Radius,
+ color=getACI(ob),
+ layer=getStrGroup(ob),
+ )
+ )
else:
if lwPoly:
- points = [(v.Point.x, v.Point.y, v.Point.z, None, None, 0.0) for v in shape.Vertexes]
- dxf.append(dxfLibrary.LwPolyLine(points,
- [0.0, 0.0],
- 1,
- color=getACI(ob),
- layer=getGroup(ob)))
+ points = [
+ (v.Point.x, v.Point.y, v.Point.z, None, None, 0.0)
+ for v in shape.Vertexes
+ ]
+ dxf.append(
+ dxfLibrary.LwPolyLine(
+ points,
+ [0.0, 0.0],
+ 1,
+ color=getACI(ob),
+ layer=getGroup(ob),
+ )
+ )
else:
- points = [((v.Point.x, v.Point.y, v.Point.z), None, [None, None], 0.0) for v in shape.Vertexes]
- dxf.append(dxfLibrary.PolyLine(points,
- [0.0, 0.0, 0.0],
- 1,
- color=getACI(ob),
- layer=getGroup(ob)))
+ points = [
+ ((v.Point.x, v.Point.y, v.Point.z), None, [None, None], 0.0)
+ for v in shape.Vertexes
+ ]
+ dxf.append(
+ dxfLibrary.PolyLine(
+ points,
+ [0.0, 0.0, 0.0],
+ 1,
+ color=getACI(ob),
+ layer=getGroup(ob),
+ )
+ )
elif ob.isDerivedFrom("Part::Feature"):
tess = None
@@ -3871,27 +3921,34 @@ def export(objectslist, filename, nospline=False, lwPoly=False):
sh = ob.Shape
if sh:
if not sh.isNull():
- if sh.ShapeType == 'Compound':
+ if sh.ShapeType == "Compound":
if len(sh.Wires) == 1:
# only one wire in this compound,
# no lone edge -> polyline
if len(sh.Wires[0].Edges) == len(sh.Edges):
- writeShape(sh, ob, dxf,
- nospline, lwPoly)
+ writeShape(sh, ob, dxf, nospline, lwPoly)
else:
# 1 wire + lone edges -> block
block = getBlock(sh, ob, lwPoly)
dxf.blocks.append(block)
- dxf.append(dxfLibrary.Insert(name=ob.Name.upper(),
- color=getACI(ob),
- layer=getStrGroup(ob)))
+ dxf.append(
+ dxfLibrary.Insert(
+ name=ob.Name.upper(),
+ color=getACI(ob),
+ layer=getStrGroup(ob),
+ )
+ )
else:
# all other cases: block
block = getBlock(sh, ob, lwPoly)
dxf.blocks.append(block)
- dxf.append(dxfLibrary.Insert(name=ob.Name.upper(),
- color=getACI(ob),
- layer=getStrGroup(ob)))
+ dxf.append(
+ dxfLibrary.Insert(
+ name=ob.Name.upper(),
+ color=getACI(ob),
+ layer=getStrGroup(ob),
+ )
+ )
else:
writeShape(sh, ob, dxf, nospline, lwPoly)
@@ -3902,25 +3959,35 @@ def export(objectslist, filename, nospline=False, lwPoly=False):
# well, anyway, at the moment, Draft only writes
# single-line texts, so...
for text in ob.LabelText:
- point = DraftVecUtils.tup(Vector(ob.Position.x,
- ob.Position.y - ob.LabelText.index(text),
- ob.Position.z))
+ point = DraftVecUtils.tup(
+ Vector(
+ ob.Position.x,
+ ob.Position.y - ob.LabelText.index(text),
+ ob.Position.z,
+ )
+ )
if gui:
height = float(ob.ViewObject.FontSize)
- justifyhor = ("Left", "Center", "Right").index(ob.ViewObject.Justification)
+ justifyhor = ("Left", "Center", "Right").index(
+ ob.ViewObject.Justification
+ )
else:
height = 1
justifyhor = 0
- dxf.append(dxfLibrary.Text(text,
- point,
- alignment=point if justifyhor else None,
- height=height,
- justifyhor=justifyhor,
- color=getACI(ob, text=True),
- style='STANDARD',
- layer=getStrGroup(ob)))
+ dxf.append(
+ dxfLibrary.Text(
+ text,
+ point,
+ alignment=point if justifyhor else None,
+ height=height,
+ justifyhor=justifyhor,
+ color=getACI(ob, text=True),
+ style="STANDARD",
+ layer=getStrGroup(ob),
+ )
+ )
- elif obtype in ("DraftText","Text"):
+ elif obtype in ("DraftText", "Text"):
# texts
if gui:
height = float(ob.ViewObject.FontSize)
@@ -3929,21 +3996,29 @@ def export(objectslist, filename, nospline=False, lwPoly=False):
height = 1
justifyhor = 0
for idx, text in enumerate(ob.Text):
- point = DraftVecUtils.tup(Vector(ob.Placement.Base.x,
- ob.Placement.Base.y - (height * 1.2 * idx),
- ob.Placement.Base.z))
+ point = DraftVecUtils.tup(
+ Vector(
+ ob.Placement.Base.x,
+ ob.Placement.Base.y - (height * 1.2 * idx),
+ ob.Placement.Base.z,
+ )
+ )
rotation = math.degrees(ob.Placement.Rotation.Angle)
- dxf.append(dxfLibrary.Text(text,
- point,
- alignment=point if justifyhor else None,
- height=height * 0.8,
- justifyhor=justifyhor,
- rotation=rotation,
- color=getACI(ob, text=True),
- style='STANDARD',
- layer=getStrGroup(ob)))
+ dxf.append(
+ dxfLibrary.Text(
+ text,
+ point,
+ alignment=point if justifyhor else None,
+ height=height * 0.8,
+ justifyhor=justifyhor,
+ rotation=rotation,
+ color=getACI(ob, text=True),
+ style="STANDARD",
+ layer=getStrGroup(ob),
+ )
+ )
- elif obtype in ["Dimension","LinearDimension"]:
+ elif obtype in ["Dimension", "LinearDimension"]:
p1 = DraftVecUtils.tup(ob.Start)
p2 = DraftVecUtils.tup(ob.End)
base = Part.LineSegment(ob.Start, ob.End).toShape()
@@ -3952,10 +4027,9 @@ def export(objectslist, filename, nospline=False, lwPoly=False):
pbase = DraftVecUtils.tup(ob.End)
else:
pbase = DraftVecUtils.tup(ob.End.add(proj.negative()))
- dxf.append(dxfLibrary.Dimension(pbase,
- p1, p2,
- color=getACI(ob),
- layer=getStrGroup(ob)))
+ dxf.append(
+ dxfLibrary.Dimension(pbase, p1, p2, color=getACI(ob), layer=getStrGroup(ob))
+ )
dxf.saveas(filename)
@@ -3966,8 +4040,8 @@ def export(objectslist, filename, nospline=False, lwPoly=False):
class dxfcounter:
- """DXF counter class to count the number of entities.
- """
+ """DXF counter class to count the number of entities."""
+
def __init__(self):
# this leaves 10000 entities for the template
self.count = 10000
@@ -3975,7 +4049,7 @@ class dxfcounter:
def incr(self, matchobj):
self.count += 1
# print(format(self.count, '02x'))
- return format(self.count, '02x')
+ return format(self.count, "02x")
def exportPage(page, filename):
@@ -4025,8 +4099,7 @@ def exportPage(page, filename):
template = template.replace(editables[i], values[i])
else:
# dummy default template
- print("DXF version of the template not found. "
- "Creating a default empty template.")
+ print("DXF version of the template not found. " "Creating a default empty template.")
_v = FreeCAD.Version()
_version = _v[0] + "." + _v[1] + "-" + _v[2]
template = "999\nFreeCAD DXF exporter v" + _version + "\n"
@@ -4041,8 +4114,7 @@ def exportPage(page, filename):
if ver:
# at the moment this is not used.
# TODO: if r12, do not print ellipses or splines
- if ver[0].upper() in ["AC1009", "AC1010", "AC1011",
- "AC1012", "AC1013"]:
+ if ver[0].upper() in ["AC1009", "AC1010", "AC1011", "AC1012", "AC1013"]:
r12 = True
for view in views:
b, e = getViewDXF(view)
@@ -4106,8 +4178,7 @@ def getViewBlock(geom, view, blockcount):
for g in geom: # getDXF returns a list of entities
if dxfExportBlocks:
# change layer and set color and ltype to BYBLOCK (0)
- g = g.replace("sheet_layer\n",
- "0\n6\nBYBLOCK\n62\n0\n5\n_handle_\n")
+ g = g.replace("sheet_layer\n", "0\n6\nBYBLOCK\n62\n0\n5\n_handle_\n")
block += "0\nBLOCK\n5\n_handle_\n100\nAcDbEntity\n8\n0\n100\nAcDbBlockBegin\n2\n"
block += view.Name + str(blockcount)
block += "\n70\n0\n10\n0\n20\n0\n3\n"
@@ -4117,7 +4188,14 @@ def getViewBlock(geom, view, blockcount):
insert += "0\nINSERT\n5\n_handle_\n8\n0\n6\nBYLAYER\n62\n256\n2\n"
insert += view.Name + str(blockcount)
insert += "\n10\n" + str(view.X) + "\n20\n" + str(view.Y)
- insert += "\n30\n0\n41\n" + str(view.Scale) + "\n42\n" + str(view.Scale) + "\n43\n" + str(view.Scale)
+ insert += (
+ "\n30\n0\n41\n"
+ + str(view.Scale)
+ + "\n42\n"
+ + str(view.Scale)
+ + "\n43\n"
+ + str(view.Scale)
+ )
insert += "\n50\n" + str(r) + "\n"
blockcount += 1
else:
@@ -4170,17 +4248,18 @@ def getViewDXF(view):
elif view.isDerivedFrom("TechDraw::DrawViewArch"):
import ArchSectionPlane
+
geom = ArchSectionPlane.getDXF(view)
block, insert, blockcount = getViewBlock(geom, view, blockcount)
elif view.isDerivedFrom("TechDraw::DrawViewPart"):
import TechDraw
+
for obj in view.Source:
proj = TechDraw.projectToDXF(obj.Shape, view.Direction)
if dxfExportBlocks:
# change layer and set color and ltype to BYBLOCK (0)
- proj = proj.replace("sheet_layer\n",
- "0\n6\nBYBLOCK\n62\n0\n5\n_handle_\n")
+ proj = proj.replace("sheet_layer\n", "0\n6\nBYBLOCK\n62\n0\n5\n_handle_\n")
block += "0\nBLOCK\n5\n_handle_\n100\nAcDbEntity\n8\n0\n100\nAcDbBlockBegin\n2\n"
block += view.Name + str(blockcount)
block += "\n70\n0\n10\n0\n20\n0\n3\n" + view.Name + str(blockcount)
@@ -4196,12 +4275,12 @@ def getViewDXF(view):
blockcount += 1
else:
proj = proj.replace("sheet_layer\n", "0\n5\n_handle_\n")
- insert += proj # view.Rotation is ignored
+ insert += proj # view.Rotation is ignored
elif view.isDerivedFrom("TechDraw::DrawViewAnnotation"):
insert = "0\nTEXT\n5\n_handle_\n8\n0\n100\nAcDbEntity\n100\nAcDbText\n5\n_handle_"
insert += "\n10\n" + str(view.X) + "\n20\n" + str(view.Y)
- insert += "\n30\n0\n40\n" + str(view.Scale/2)
+ insert += "\n30\n0\n40\n" + str(view.Scale / 2)
insert += "\n50\n" + str(view.Rotation)
insert += "\n1\n" + view.Text[0] + "\n"
@@ -4250,7 +4329,7 @@ def readPreferences():
import_mode = 1
elif hGrp.GetBool("dxfImportAsFused", False):
import_mode = 3
- else: # Default to "Individual part shapes"
+ else: # Default to "Individual part shapes"
import_mode = 2
hGrp.SetInt("DxfImportMode", import_mode)
@@ -4260,7 +4339,7 @@ def readPreferences():
# Legacy override for sketch creation takes highest priority
dxfCreateSketch = hGrp.GetBool("dxfCreateSketch", False)
- if dxfCreateSketch: # dxfCreateSketch overrides the import mode for the legacy importer
+ if dxfCreateSketch: # dxfCreateSketch overrides the import mode for the legacy importer
dxfCreatePart = False
dxfCreateDraft = False
dxfMakeBlocks = False
@@ -4300,8 +4379,10 @@ def readPreferences():
dxfBrightBackground = isBrightBackground()
dxfDefaultColor = getColor()
+
class DxfImportReporter:
"""Formats and reports statistics from a DXF import process."""
+
def __init__(self, filename, stats_dict, total_time=0.0):
self.filename = filename
self.stats = stats_dict
@@ -4322,30 +4403,30 @@ class DxfImportReporter:
lines.append(f"File encoding: {self.stats.get('dxfEncoding', 'Unknown')}")
# Scaling info
- file_units = self.stats.get('fileUnits', 'Not specified')
- source = self.stats.get('scalingSource', '')
+ file_units = self.stats.get("fileUnits", "Not specified")
+ source = self.stats.get("scalingSource", "")
if source:
lines.append(f"File units: {file_units} (from {source})")
else:
lines.append(f"File units: {file_units}")
- manual_scaling = self.stats.get('importSettings', {}).get('Manual scaling factor', '1.0')
+ manual_scaling = self.stats.get("importSettings", {}).get("Manual scaling factor", "1.0")
lines.append(f"Manual scaling factor: {manual_scaling}")
- final_scaling = self.stats.get('finalScalingFactor', 1.0)
+ final_scaling = self.stats.get("finalScalingFactor", 1.0)
lines.append(f"Final scaling: 1 DXF unit = {final_scaling:.4f} mm")
lines.append("")
# Timing
lines.append("Performance:")
- cpp_time = self.stats.get('importTimeSeconds', 0.0)
+ cpp_time = self.stats.get("importTimeSeconds", 0.0)
lines.append(f" - C++ import time: {cpp_time:.4f} seconds")
lines.append(f" - Total import time: {self.total_time:.4f} seconds")
lines.append("")
# Settings
lines.append("Import settings:")
- settings = self.stats.get('importSettings', {})
+ settings = self.stats.get("importSettings", {})
if settings:
for key, value in sorted(settings.items()):
lines.append(f" - {key}: {value}")
@@ -4356,7 +4437,7 @@ class DxfImportReporter:
# Counts
lines.append("Entity counts:")
total_read = 0
- unsupported_keys = self.stats.get('unsupportedFeatures', {}).keys()
+ unsupported_keys = self.stats.get("unsupportedFeatures", {}).keys()
unsupported_entity_names = set()
for key in unsupported_keys:
# Extract the entity name from the key string, e.g., 'HATCH' from "Entity type 'HATCH'"
@@ -4365,7 +4446,7 @@ class DxfImportReporter:
unsupported_entity_names.add(entity_name_match.group(1))
has_unsupported_indicator = False
- entities = self.stats.get('entityCounts', {})
+ entities = self.stats.get("entityCounts", {})
if entities:
for key, value in sorted(entities.items()):
indicator = ""
@@ -4384,7 +4465,7 @@ class DxfImportReporter:
# System Blocks
lines.append("System Blocks:")
- system_blocks = self.stats.get('systemBlockCounts', {})
+ system_blocks = self.stats.get("systemBlockCounts", {})
if system_blocks:
for key, value in sorted(system_blocks.items()):
lines.append(f" - {key}: {value}")
@@ -4397,7 +4478,7 @@ class DxfImportReporter:
lines.append("")
lines.append("Unsupported features:")
- unsupported = self.stats.get('unsupportedFeatures', {})
+ unsupported = self.stats.get("unsupportedFeatures", {})
if unsupported:
for key, occurrences in sorted(unsupported.items()):
count = len(occurrences)
@@ -4437,6 +4518,7 @@ class DxfDraftPostProcessor:
converting them into fully parametric Draft objects while preserving
the block and layer hierarchy.
"""
+
def __init__(self, doc, new_objects, import_mode):
self.doc = doc
self.all_imported_objects = new_objects
@@ -4455,8 +4537,7 @@ class DxfDraftPostProcessor:
for block_def_obj in block_group.Group:
if block_def_obj.isValid() and block_def_obj.isDerivedFrom("Part::Compound"):
block_definitions[block_def_obj] = [
- child for child in block_def_obj.Links
- if child.isValid()
+ child for child in block_def_obj.Links if child.isValid()
]
all_block_internal_objects_set = set()
@@ -4489,12 +4570,13 @@ class DxfDraftPostProcessor:
# Skip invalid objects or objects that are block definitions themselves (their
# links/children will be converted)
- if not part_obj.isValid() or \
- (part_obj.isDerivedFrom("Part::Compound") and hasattr(part_obj, "Links")):
+ if not part_obj.isValid() or (
+ part_obj.isDerivedFrom("Part::Compound") and hasattr(part_obj, "Links")
+ ):
return None, None
new_obj = None
- obj_type_str = None # Will be set based on converted type
+ obj_type_str = None # Will be set based on converted type
# Handle specific Part primitives (created directly by C++ importer as Part::Line,
# Part::Circle, Part::Vertex) These C++ primitives (Part::Line, Part::Circle) inherently
@@ -4503,12 +4585,13 @@ class DxfDraftPostProcessor:
# Input `part_obj` is Part::Line. Create a Part::Part2DObjectPython as the
# Python-extensible base for Draft Line. Part::Part2DObjectPython (via Part::Feature)
# inherently has Shape and Placement, and supports .Proxy.
- new_obj = self.doc.addObject("Part::Part2DObjectPython",
- self.doc.getUniqueObjectName("Line"))
+ new_obj = self.doc.addObject(
+ "Part::Part2DObjectPython", self.doc.getUniqueObjectName("Line")
+ )
# Transfer the TopoDS_Shape from the original Part::Line to the new object's Shape
# property.
new_obj.Shape = part_obj.Shape
- Draft.Wire(new_obj) # Attach the Python proxy. It will find Shape, Placement.
+ Draft.Wire(new_obj) # Attach the Python proxy. It will find Shape, Placement.
# Manually transfer the parametric data from the Part::Line primitive
# to the new Draft.Wire's 'Points' property.
@@ -4520,8 +4603,9 @@ class DxfDraftPostProcessor:
elif part_obj.isDerivedFrom("Part::Circle"):
# Input `part_obj` is Part::Circle. Create a Part::Part2DObjectPython.
- new_obj = self.doc.addObject("Part::Part2DObjectPython",
- self.doc.getUniqueObjectName("Circle"))
+ new_obj = self.doc.addObject(
+ "Part::Part2DObjectPython", self.doc.getUniqueObjectName("Circle")
+ )
# Transfer the TopoDS_Shape from the original Part::Circle. This needs to happen
# *before* proxy attach.
new_obj.Shape = part_obj.Shape
@@ -4535,37 +4619,42 @@ class DxfDraftPostProcessor:
# to them.
# Part::Circle has Radius, Angle1, Angle2 properties.
# Draft.Circle proxy uses FirstAngle and LastAngle instead of Angle1 and Angle2.
- if hasattr(part_obj, 'Radius'):
+ if hasattr(part_obj, "Radius"):
new_obj.Radius = FreeCAD.Units.Quantity(part_obj.Radius.Value, "mm")
# Calculate and transfer angles
- if hasattr(part_obj, 'Angle1') and hasattr(part_obj, 'Angle2'):
+ if hasattr(part_obj, "Angle1") and hasattr(part_obj, "Angle2"):
start_angle, end_angle = self._get_canonical_angles(
- part_obj.Angle1.Value,
- part_obj.Angle2.Value,
- part_obj.Radius.Value
+ part_obj.Angle1.Value, part_obj.Angle2.Value, part_obj.Radius.Value
)
new_obj.FirstAngle = FreeCAD.Units.Quantity(start_angle, "deg")
new_obj.LastAngle = FreeCAD.Units.Quantity(end_angle, "deg")
# Determine the final object type string based on the canonical angles
- is_full_circle = (abs(new_obj.FirstAngle.Value - 0.0) < 1e-7 and
- abs(new_obj.LastAngle.Value - 360.0) < 1e-7)
+ is_full_circle = (
+ abs(new_obj.FirstAngle.Value - 0.0) < 1e-7
+ and abs(new_obj.LastAngle.Value - 360.0) < 1e-7
+ )
obj_type_str = "Circle" if is_full_circle else "Arc"
-
- elif part_obj.isDerivedFrom("Part::Vertex"): # Input `part_obj` is Part::Vertex (C++ primitive for a point location).
+ elif part_obj.isDerivedFrom(
+ "Part::Vertex"
+ ): # Input `part_obj` is Part::Vertex (C++ primitive for a point location).
# For Draft.Point, the proxy expects an App::FeaturePython base.
- new_obj = self.doc.addObject("App::FeaturePython", self.doc.getUniqueObjectName("Point"))
- new_obj.addExtension("Part::AttachExtensionPython") # Needed to provide Placement for App::FeaturePython.
+ new_obj = self.doc.addObject(
+ "App::FeaturePython", self.doc.getUniqueObjectName("Point")
+ )
+ new_obj.addExtension(
+ "Part::AttachExtensionPython"
+ ) # Needed to provide Placement for App::FeaturePython.
# Transfer Placement explicitly from the original Part::Vertex.
- if hasattr(part_obj, 'Placement'):
+ if hasattr(part_obj, "Placement"):
new_obj.Placement = part_obj.Placement
else:
new_obj.Placement = FreeCAD.Placement()
- Draft.Point(new_obj) # Attach the Python proxy.
+ Draft.Point(new_obj) # Attach the Python proxy.
obj_type_str = "Point"
elif part_obj.isDerivedFrom("Part::Ellipse"):
@@ -4576,7 +4665,9 @@ class DxfDraftPostProcessor:
if is_full_ellipse:
# Create the C++ base object that has .Shape and .Placement.
- new_obj = self.doc.addObject("Part::Part2DObjectPython", self.doc.getUniqueObjectName("Ellipse"))
+ new_obj = self.doc.addObject(
+ "Part::Part2DObjectPython", self.doc.getUniqueObjectName("Ellipse")
+ )
# Attach the parametric Draft.Ellipse Python proxy.
Draft.Ellipse(new_obj)
@@ -4591,15 +4682,20 @@ class DxfDraftPostProcessor:
else:
# Fallback for elliptical arcs.
- new_obj = self.doc.addObject("Part::Part2DObjectPython", self.doc.getUniqueObjectName("EllipticalArc"))
- Draft.Wire(new_obj) # Attach proxy.
+ new_obj = self.doc.addObject(
+ "Part::Part2DObjectPython", self.doc.getUniqueObjectName("EllipticalArc")
+ )
+ Draft.Wire(new_obj) # Attach proxy.
# Re-create geometry at the origin using parametric properties.
# Convert degrees back to radians for the geometry kernel.
center_at_origin = FreeCAD.Vector(0, 0, 0)
- geom = Part.Ellipse(center_at_origin, part_obj.MajorRadius.Value, part_obj.MinorRadius.Value)
- shape_at_origin = geom.toShape(math.radians(part_obj.Angle1.Value),
- math.radians(part_obj.Angle2.Value))
+ geom = Part.Ellipse(
+ center_at_origin, part_obj.MajorRadius.Value, part_obj.MinorRadius.Value
+ )
+ shape_at_origin = geom.toShape(
+ math.radians(part_obj.Angle1.Value), math.radians(part_obj.Angle2.Value)
+ )
# Assign the un-transformed shape and the separate placement.
new_obj.Shape = shape_at_origin
@@ -4607,17 +4703,23 @@ class DxfDraftPostProcessor:
obj_type_str = "Shape"
# --- Handle generic Part::Feature objects (from C++ importer, wrapping TopoDS_Shapes like Wires, Splines, Ellipses) ---
- elif part_obj.isDerivedFrom("Part::Feature"): # Input `part_obj` is a generic Part::Feature (from C++ importer).
- shape = part_obj.Shape # This is the underlying TopoDS_Shape (Wire, Edge, Compound, Face etc.).
+ elif part_obj.isDerivedFrom(
+ "Part::Feature"
+ ): # Input `part_obj` is a generic Part::Feature (from C++ importer).
+ shape = (
+ part_obj.Shape
+ ) # This is the underlying TopoDS_Shape (Wire, Edge, Compound, Face etc.).
if not shape.isValid():
return None, None
# Determine specific Draft object type based on the ShapeType of the TopoDS_Shape.
- if shape.ShapeType == "Wire": # If the TopoDS_Shape is a Wire (from DXF POLYLINE).
+ if shape.ShapeType == "Wire": # If the TopoDS_Shape is a Wire (from DXF POLYLINE).
# Create a Part::Part2DObjectPython as the Python-extensible base for Draft Wire.
- new_obj = self.doc.addObject("Part::Part2DObjectPython", self.doc.getUniqueObjectName("Wire"))
- new_obj.Shape = shape # Transfer the TopoDS_Wire from the original Part::Feature.
- Draft.Wire(new_obj) # Attach Python proxy. It will find Shape, Placement.
+ new_obj = self.doc.addObject(
+ "Part::Part2DObjectPython", self.doc.getUniqueObjectName("Wire")
+ )
+ new_obj.Shape = shape # Transfer the TopoDS_Wire from the original Part::Feature.
+ Draft.Wire(new_obj) # Attach Python proxy. It will find Shape, Placement.
# Check if all segments of the wire are straight lines.
# If so, we can safely populate the .Points property to make it parametric.
@@ -4626,27 +4728,33 @@ class DxfDraftPostProcessor:
for edge in shape.Edges:
if edge.Curve.TypeId == "Part::GeomLine":
- continue # This is a straight segment
+ continue # This is a straight segment
else:
is_all_lines = False
- break # Found a curve, no need to check further
+ break # Found a curve, no need to check further
if is_all_lines and shape.OrderedVertexes:
# All segments are straight, so we can make it an editable wire
points = [v.Point for v in shape.OrderedVertexes]
new_obj.Points = points
- new_obj.Closed = shape.isClosed() # Transfer specific properties expected by Draft.Wire.
+ new_obj.Closed = (
+ shape.isClosed()
+ ) # Transfer specific properties expected by Draft.Wire.
obj_type_str = "Wire"
# Fallback for other Part::Feature shapes (e.g., 3DFACE, SOLID, or unsupported Edge types).
- else: # If the TopoDS_Shape is not a recognized primitive (e.g., Compound, Face, Solid).
+ else: # If the TopoDS_Shape is not a recognized primitive (e.g., Compound, Face, Solid).
# Wrap it in a Part::FeaturePython to allow Python property customization if needed.
- new_obj = self.doc.addObject("Part::FeaturePython", self.doc.getUniqueObjectName("Shape"))
- new_obj.addExtension("Part::AttachExtensionPython") # Add extension for Placement for App::FeaturePython.
- new_obj.Shape = shape # Assign the TopoDS_Shape from the original Part::Feature.
+ new_obj = self.doc.addObject(
+ "Part::FeaturePython", self.doc.getUniqueObjectName("Shape")
+ )
+ new_obj.addExtension(
+ "Part::AttachExtensionPython"
+ ) # Add extension for Placement for App::FeaturePython.
+ new_obj.Shape = shape # Assign the TopoDS_Shape from the original Part::Feature.
# Explicitly set Placement for App::FeaturePython.
- if hasattr(part_obj, 'Placement'):
+ if hasattr(part_obj, "Placement"):
new_obj.Placement = part_obj.Placement
else:
new_obj.Placement = FreeCAD.Placement()
@@ -4654,21 +4762,23 @@ class DxfDraftPostProcessor:
obj_type_str = "Shape"
# --- Handle App::Link objects (block instances from C++ importer) ---
- elif part_obj.isDerivedFrom("App::Link"): # Input `part_obj` is an App::Link.
+ elif part_obj.isDerivedFrom("App::Link"): # Input `part_obj` is an App::Link.
# App::Link objects are already suitable as a base for Draft.Clone/Array links.
# They natively have Placement and Link properties, and support .Proxy.
- new_obj = part_obj # Reuse the object directly.
+ new_obj = part_obj # Reuse the object directly.
obj_type_str = "Link"
# --- Handle App::FeaturePython placeholder objects (Text, Dimension from C++ importer) ---
- elif part_obj.isDerivedFrom("App::FeaturePython"): # Input `part_obj` is an App::FeaturePython placeholder.
+ elif part_obj.isDerivedFrom(
+ "App::FeaturePython"
+ ): # Input `part_obj` is an App::FeaturePython placeholder.
# These are specific placeholders the C++ importer created (`DxfEntityType` property).
# They are processed later in `_create_from_placeholders` to become proper Draft.Text/Dimension objects.
- return None, None # Don't process them here; let the dedicated function handle them.
+ return None, None # Don't process them here; let the dedicated function handle them.
# --- Final Common Steps for Newly Created Draft Objects ---
if new_obj:
- new_obj.Label = part_obj.Label # Always transfer label.
+ new_obj.Label = part_obj.Label # Always transfer label.
# If `new_obj` was freshly created (not `part_obj` reused), and `part_obj` had a Placement,
# ensure `new_obj`'s Placement is correctly set from `part_obj`.
@@ -4679,7 +4789,9 @@ class DxfDraftPostProcessor:
new_obj.Placement = part_obj.Placement
elif not hasattr(new_obj, "Placement"):
# This should ideally not happen with the corrected logic above.
- FCC.PrintWarning(f"Created object '{new_obj.Label}' of type '{obj_type_str}' does not have a 'Placement' property even after intended setup. This is unexpected.\n")
+ FCC.PrintWarning(
+ f"Created object '{new_obj.Label}' of type '{obj_type_str}' does not have a 'Placement' property even after intended setup. This is unexpected.\n"
+ )
# Add the original object (from C++ importer) to the list for deletion.
if new_obj is not part_obj:
@@ -4690,7 +4802,9 @@ class DxfDraftPostProcessor:
# If no conversion could be made (e.g., unsupported DXF entity not falling into a handled case),
# mark original for deletion and return None.
self.all_originals_to_delete.add(part_obj)
- FCC.PrintWarning(f"DXF Post-Processor: Failed to convert object '{part_obj.Label}'. Discarding.\n")
+ FCC.PrintWarning(
+ f"DXF Post-Processor: Failed to convert object '{part_obj.Label}'. Discarding.\n"
+ )
return None, None
def _parent_object_to_layer(self, new_obj, original_obj):
@@ -4703,14 +4817,16 @@ class DxfDraftPostProcessor:
layer_obj = None
if found_layers:
for l_obj in found_layers:
- if Draft.get_type(l_obj) == 'Layer':
+ if Draft.get_type(l_obj) == "Layer":
layer_obj = l_obj
break
if layer_obj:
layer_obj.Proxy.addObject(layer_obj, new_obj)
else:
- FCC.PrintWarning(f"DXF Post-Processor: Could not find a valid Draft Layer with label '{layer_name}' for object '{new_obj.Label}'.\n")
+ FCC.PrintWarning(
+ f"DXF Post-Processor: Could not find a valid Draft Layer with label '{layer_name}' for object '{new_obj.Label}'.\n"
+ )
def _create_and_parent_geometry(self, intermediate_obj):
"""High-level helper to convert, name, and parent a single geometric object."""
@@ -4723,7 +4839,9 @@ class DxfDraftPostProcessor:
self._parent_object_to_layer(new_draft_obj, intermediate_obj)
self.newly_created_draft_objects.append(new_draft_obj)
else:
- FCC.PrintWarning(f"DXF Post-Processor: Failed to convert object '{intermediate_obj.Label}'. Discarding.\n")
+ FCC.PrintWarning(
+ f"DXF Post-Processor: Failed to convert object '{intermediate_obj.Label}'. Discarding.\n"
+ )
return new_draft_obj
def _create_from_placeholders(self, placeholders):
@@ -4774,7 +4892,7 @@ class DxfDraftPostProcessor:
# A type of 0 indicates that the dimension is projected. The
# projection direction is given by its rotation angle.
if dim_type == 0 and hasattr(placeholder, "DxfRotation"):
- angle = placeholder.DxfRotation.Value # Angle is in radians
+ angle = placeholder.DxfRotation.Value # Angle is in radians
# The Direction property on a Draft.Dimension controls its
# projection. Setting it here ensures the ViewProvider
@@ -4795,7 +4913,9 @@ class DxfDraftPostProcessor:
self._parent_object_to_layer(new_obj, placeholder)
self.newly_created_draft_objects.append(new_obj)
except Exception as e:
- FCC.PrintWarning(f"Could not create Draft object from placeholder '{placeholder.Label}': {e}\n")
+ FCC.PrintWarning(
+ f"Could not create Draft object from placeholder '{placeholder.Label}': {e}\n"
+ )
self.all_originals_to_delete.update(placeholders)
@@ -4813,9 +4933,11 @@ class DxfDraftPostProcessor:
try:
proxy_name = obj.Proxy.__class__.__name__
if proxy_name in ("Wire", "Line"):
- if ViewProviderWire: ViewProviderWire(obj.ViewObject)
+ if ViewProviderWire:
+ ViewProviderWire(obj.ViewObject)
elif proxy_name == "Circle":
- if ViewProviderDraft: ViewProviderDraft(obj.ViewObject)
+ if ViewProviderDraft:
+ ViewProviderDraft(obj.ViewObject)
elif proxy_name == "Text":
if hasattr(obj, "DxfTextHeight"):
obj.ViewObject.FontSize = obj.DxfTextHeight * TEXTSCALING
@@ -4829,10 +4951,14 @@ class DxfDraftPostProcessor:
for obj in self.all_originals_to_delete:
if obj.isValid() and self.doc.getObject(obj.Name) is not None:
try:
- if not obj.isDerivedFrom("App::DocumentObjectGroup") and not obj.isDerivedFrom("App::Link"):
+ if not obj.isDerivedFrom("App::DocumentObjectGroup") and not obj.isDerivedFrom(
+ "App::Link"
+ ):
self.doc.removeObject(obj.Name)
except Exception as e:
- FCC.PrintWarning(f"Failed to delete object '{getattr(obj, 'Label', obj.Name)}': {e}\n")
+ FCC.PrintWarning(
+ f"Failed to delete object '{getattr(obj, 'Label', obj.Name)}': {e}\n"
+ )
def _cleanup_organizational_groups(self):
"""Removes empty organizational groups after processing."""
@@ -4909,9 +5035,13 @@ class DxfDraftPostProcessor:
# Process geometry inside block definitions
for block_def_obj, original_children in block_defs.items():
- new_draft_children = [self._create_and_parent_geometry(child) for child in original_children]
+ new_draft_children = [
+ self._create_and_parent_geometry(child) for child in original_children
+ ]
block_def_obj.Links = [obj for obj in new_draft_children if obj]
- self.all_originals_to_delete.update(set(original_children) - set(new_draft_children))
+ self.all_originals_to_delete.update(
+ set(original_children) - set(new_draft_children)
+ )
# Process top-level geometry
converted_top_geo = []
@@ -4931,6 +5061,7 @@ class DxfDraftPostProcessor:
self.doc.abortTransaction()
FCC.PrintError(f"Aborting DXF post-processing due to an error: {e}\n")
import traceback
+
traceback.print_exc()
return
finally:
diff --git a/src/Mod/Draft/importOCA.py b/src/Mod/Draft/importOCA.py
index 810cd25d8e..ce8578be25 100644
--- a/src/Mod/Draft/importOCA.py
+++ b/src/Mod/Draft/importOCA.py
@@ -2,7 +2,7 @@
## @package importOCA
# \ingroup DRAFT
# \brief OCA (Open CAD Format) file importer & exporter
-'''@package importOCA
+"""@package importOCA
OCA (Open CAD Format) file importer & exporter
This module provides support for importing from and exporting to
@@ -11,7 +11,7 @@ See: https://groups.google.com/forum/#!forum/open_cad_format
As of 2019 this file format is practically obsolete, and this module is not
maintained.
-'''
+"""
# Check code with
# flake8 --ignore=E226,E266,E401,W503
@@ -49,12 +49,11 @@ from draftutils.utils import pyopen
if FreeCAD.GuiUp:
from draftutils.translate import translate
else:
+
def translate(context, txt):
return txt
-
-
def getpoint(data):
"""Turn an OCA point definition into a FreeCAD.Vector.
@@ -82,8 +81,7 @@ def getpoint(data):
elif data[1][0] == "C":
# Error: DraftGeomUtils.findProjection()
# doesn't exist
- return DraftGeomUtils.findProjection(objects[data[0]],
- objects[data[1]])
+ return DraftGeomUtils.findProjection(objects[data[0]], objects[data[1]])
elif data[0][0] == "C":
if objects[data[0]]:
p1 = objects[data[0]].Curve.Position
@@ -141,7 +139,7 @@ def getarc(data):
verts = []
for p in range(len(pts)):
if pts[p] == "P":
- verts.append(getpoint(pts[p:p+3]))
+ verts.append(getpoint(pts[p : p + 3]))
elif pts[p][0] == "P":
verts.append(getpoint([pts[p]]))
if verts[0] and verts[1] and verts[2]:
@@ -153,11 +151,11 @@ def getarc(data):
lines = []
for p in range(len(data)):
if data[p] == "P":
- verts.append(getpoint(data[p:p+4]))
+ verts.append(getpoint(data[p : p + 4]))
elif data[p][0] == "P":
verts.append(getpoint([data[p]]))
elif data[p] == "VAL":
- rad = float(data[p+1])
+ rad = float(data[p + 1])
elif data[p][0] == "L":
lines.append(objects[data[p]])
c = Part.Circle()
@@ -174,12 +172,10 @@ def getarc(data):
rad = None
for p in range(len(data)):
if data[p] == "VAL":
- rad = float(data[p+1])
+ rad = float(data[p + 1])
elif data[p][0] == "L":
lines.append(objects[data[p]])
- circles = DraftGeomUtils.circleFrom2LinesRadius(lines[0],
- lines[1],
- rad)
+ circles = DraftGeomUtils.circleFrom2LinesRadius(lines[0], lines[1], rad)
if circles:
c = circles[0]
if c:
@@ -203,7 +199,7 @@ def getline(data):
verts = []
for p in range(len(data)):
if data[p] == "P":
- verts.append(getpoint(data[p:p+4]))
+ verts.append(getpoint(data[p : p + 4]))
elif data[p][0] == "P":
verts.append(getpoint([data[p]]))
L = Part.LineSegment(verts[0], verts[1])
@@ -246,7 +242,7 @@ def writepoint(vector):
str
A string "P(X Y Z)" with the information from `vector`.
"""
- return "P("+str(vector.x)+" "+str(vector.y)+" "+str(vector.z)+")"
+ return "P(" + str(vector.x) + " " + str(vector.y) + " " + str(vector.z) + ")"
def createobject(oid, doc):
@@ -303,7 +299,7 @@ def parse(filename, doc):
if _id[0] == "P":
# point
objects[_id] = getpoint(data)
- elif ((_id[0] == "A") and params.get_param("ocaareas")):
+ elif (_id[0] == "A") and params.get_param("ocaareas"):
# area
objects[_id] = getarea(data)
createobject(_id, doc)
@@ -325,9 +321,7 @@ def parse(filename, doc):
elif readline[0:6] == "DEFCOL":
# color
c = readline.split()
- color = (float(c[1])/255,
- float(c[2])/255,
- float(c[3])/255)
+ color = (float(c[1]) / 255, float(c[2]) / 255, float(c[3]) / 255)
def open(filename):
@@ -408,33 +402,31 @@ def export(exportList, filename):
for e in ob.Shape.Edges:
edges.append(e)
if not (edges or faces):
- FCC.PrintMessage(translate("importOCA",
- "OCA: found no data to export")
- + "\n")
+ FCC.PrintMessage(translate("importOCA", "OCA: found no data to export") + "\n")
return
# writing file
- oca = pyopen(filename, 'w')
+ oca = pyopen(filename, "w")
oca.write("#oca file generated from FreeCAD\r\n")
oca.write("# edges\r\n")
count = 1
for e in edges:
if DraftGeomUtils.geomType(e) == "Line":
- oca.write("L"+str(count)+"=")
+ oca.write("L" + str(count) + "=")
oca.write(writepoint(e.Vertexes[0].Point))
oca.write(" ")
oca.write(writepoint(e.Vertexes[-1].Point))
oca.write("\r\n")
elif DraftGeomUtils.geomType(e) == "Circle":
if len(e.Vertexes) > 1:
- oca.write("C"+str(count)+"=ARC ")
+ oca.write("C" + str(count) + "=ARC ")
oca.write(writepoint(e.Vertexes[0].Point))
oca.write(" ")
oca.write(writepoint(DraftGeomUtils.findMidpoint(e)))
oca.write(" ")
oca.write(writepoint(e.Vertexes[-1].Point))
else:
- oca.write("C"+str(count)+"= ")
+ oca.write("C" + str(count) + "= ")
oca.write(writepoint(e.Curve.Center))
oca.write(" ")
oca.write(str(e.Curve.Radius))
@@ -442,7 +434,7 @@ def export(exportList, filename):
count += 1
oca.write("# faces\r\n")
for f in faces:
- oca.write("A"+str(count)+"=S(POL")
+ oca.write("A" + str(count) + "=S(POL")
for v in f.Vertexes:
oca.write(" ")
oca.write(writepoint(v.Point))
@@ -453,6 +445,4 @@ def export(exportList, filename):
# closing
oca.close()
- FCC.PrintMessage(translate("importOCA",
- "successfully exported")
- + " " + filename + "\n")
+ FCC.PrintMessage(translate("importOCA", "successfully exported") + " " + filename + "\n")
diff --git a/src/Mod/Draft/importSVG.py b/src/Mod/Draft/importSVG.py
index f8a1ac2904..247d71b8cd 100644
--- a/src/Mod/Draft/importSVG.py
+++ b/src/Mod/Draft/importSVG.py
@@ -71,6 +71,7 @@ from copy import deepcopy
if FreeCAD.GuiUp:
from PySide import QtWidgets
import FreeCADGui
+
gui = True
try:
draftui = FreeCADGui.draftToolBar
@@ -82,157 +83,156 @@ else:
svgcolors = {
- 'Pink': (255, 192, 203),
- 'Blue': (0, 0, 255),
- 'Honeydew': (240, 255, 240),
- 'Purple': (128, 0, 128),
- 'Fuchsia': (255, 0, 255),
- 'LawnGreen': (124, 252, 0),
- 'Amethyst': (153, 102, 204),
- 'Crimson': (220, 20, 60),
- 'White': (255, 255, 255),
- 'NavajoWhite': (255, 222, 173),
- 'Cornsilk': (255, 248, 220),
- 'Bisque': (255, 228, 196),
- 'PaleGreen': (152, 251, 152),
- 'Brown': (165, 42, 42),
- 'DarkTurquoise': (0, 206, 209),
- 'DarkGreen': (0, 100, 0),
- 'MediumOrchid': (186, 85, 211),
- 'Chocolate': (210, 105, 30),
- 'PapayaWhip': (255, 239, 213),
- 'Olive': (128, 128, 0),
- 'Silver': (192, 192, 192),
- 'PeachPuff': (255, 218, 185),
- 'Plum': (221, 160, 221),
- 'DarkGoldenrod': (184, 134, 11),
- 'SlateGrey': (112, 128, 144),
- 'MintCream': (245, 255, 250),
- 'CornflowerBlue': (100, 149, 237),
- 'Gold': (255, 215, 0),
- 'HotPink': (255, 105, 180),
- 'DarkBlue': (0, 0, 139),
- 'LimeGreen': (50, 205, 50),
- 'DeepSkyBlue': (0, 191, 255),
- 'DarkKhaki': (189, 183, 107),
- 'LightGrey': (211, 211, 211),
- 'Yellow': (255, 255, 0),
- 'Gainsboro': (220, 220, 220),
- 'MistyRose': (255, 228, 225),
- 'SandyBrown': (244, 164, 96),
- 'DeepPink': (255, 20, 147),
- 'Magenta': (255, 0, 255),
- 'AliceBlue': (240, 248, 255),
- 'DarkCyan': (0, 139, 139),
- 'DarkSlateGrey': (47, 79, 79),
- 'GreenYellow': (173, 255, 47),
- 'DarkOrchid': (153, 50, 204),
- 'OliveDrab': (107, 142, 35),
- 'Chartreuse': (127, 255, 0),
- 'Peru': (205, 133, 63),
- 'Orange': (255, 165, 0),
- 'Red': (255, 0, 0),
- 'Wheat': (245, 222, 179),
- 'LightCyan': (224, 255, 255),
- 'LightSeaGreen': (32, 178, 170),
- 'BlueViolet': (138, 43, 226),
- 'LightSlateGrey': (119, 136, 153),
- 'Cyan': (0, 255, 255),
- 'MediumPurple': (147, 112, 219),
- 'MidnightBlue': (25, 25, 112),
- 'FireBrick': (178, 34, 34),
- 'PaleTurquoise': (175, 238, 238),
- 'PaleGoldenrod': (238, 232, 170),
- 'Gray': (128, 128, 128),
- 'MediumSeaGreen': (60, 179, 113),
- 'Moccasin': (255, 228, 181),
- 'Ivory': (255, 255, 240),
- 'DarkSlateBlue': (72, 61, 139),
- 'Beige': (245, 245, 220),
- 'Green': (0, 128, 0),
- 'SlateBlue': (106, 90, 205),
- 'Teal': (0, 128, 128),
- 'Azure': (240, 255, 255),
- 'LightSteelBlue': (176, 196, 222),
- 'DimGrey': (105, 105, 105),
- 'Tan': (210, 180, 140),
- 'AntiqueWhite': (250, 235, 215),
- 'SkyBlue': (135, 206, 235),
- 'GhostWhite': (248, 248, 255),
- 'MediumTurquoise': (72, 209, 204),
- 'FloralWhite': (255, 250, 240),
- 'LavenderBlush': (255, 240, 245),
- 'SeaGreen': (46, 139, 87),
- 'Lavender': (230, 230, 250),
- 'BlanchedAlmond': (255, 235, 205),
- 'DarkOliveGreen': (85, 107, 47),
- 'DarkSeaGreen': (143, 188, 143),
- 'SpringGreen': (0, 255, 127),
- 'Navy': (0, 0, 128),
- 'Orchid': (218, 112, 214),
- 'SaddleBrown': (139, 69, 19),
- 'IndianRed': (205, 92, 92),
- 'Snow': (255, 250, 250),
- 'SteelBlue': (70, 130, 180),
- 'MediumSlateBlue': (123, 104, 238),
- 'Black': (0, 0, 0),
- 'LightBlue': (173, 216, 230),
- 'Turquoise': (64, 224, 208),
- 'MediumVioletRed': (199, 21, 133),
- 'DarkViolet': (148, 0, 211),
- 'DarkGray': (169, 169, 169),
- 'Salmon': (250, 128, 114),
- 'DarkMagenta': (139, 0, 139),
- 'Tomato': (255, 99, 71),
- 'WhiteSmoke': (245, 245, 245),
- 'Goldenrod': (218, 165, 32),
- 'MediumSpringGreen': (0, 250, 154),
- 'DodgerBlue': (30, 144, 255),
- 'Aqua': (0, 255, 255),
- 'ForestGreen': (34, 139, 34),
- 'LemonChiffon': (255, 250, 205),
- 'LightSlateGray': (119, 136, 153),
- 'SlateGray': (112, 128, 144),
- 'LightGray': (211, 211, 211),
- 'Indigo': (75, 0, 130),
- 'CadetBlue': (95, 158, 160),
- 'LightYellow': (255, 255, 224),
- 'DarkOrange': (255, 140, 0),
- 'PowderBlue': (176, 224, 230),
- 'RoyalBlue': (65, 105, 225),
- 'Sienna': (160, 82, 45),
- 'Thistle': (216, 191, 216),
- 'Lime': (0, 255, 0),
- 'Seashell': (255, 245, 238),
- 'DarkRed': (139, 0, 0),
- 'LightSkyBlue': (135, 206, 250),
- 'YellowGreen': (154, 205, 50),
- 'Aquamarine': (127, 255, 212),
- 'LightCoral': (240, 128, 128),
- 'DarkSlateGray': (47, 79, 79),
- 'Khaki': (240, 230, 140),
- 'DarkGrey': (169, 169, 169),
- 'BurlyWood': (222, 184, 135),
- 'LightGoldenrodYellow': (250, 250, 210),
- 'MediumBlue': (0, 0, 205),
- 'DarkSalmon': (233, 150, 122),
- 'RosyBrown': (188, 143, 143),
- 'LightSalmon': (255, 160, 122),
- 'PaleVioletRed': (219, 112, 147),
- 'Coral': (255, 127, 80),
- 'Violet': (238, 130, 238),
- 'Grey': (128, 128, 128),
- 'LightGreen': (144, 238, 144),
- 'Linen': (250, 240, 230),
- 'OrangeRed': (255, 69, 0),
- 'DimGray': (105, 105, 105),
- 'Maroon': (128, 0, 0),
- 'LightPink': (255, 182, 193),
- 'MediumAquamarine': (102, 205, 170),
- 'OldLace': (253, 245, 230)
+ "Pink": (255, 192, 203),
+ "Blue": (0, 0, 255),
+ "Honeydew": (240, 255, 240),
+ "Purple": (128, 0, 128),
+ "Fuchsia": (255, 0, 255),
+ "LawnGreen": (124, 252, 0),
+ "Amethyst": (153, 102, 204),
+ "Crimson": (220, 20, 60),
+ "White": (255, 255, 255),
+ "NavajoWhite": (255, 222, 173),
+ "Cornsilk": (255, 248, 220),
+ "Bisque": (255, 228, 196),
+ "PaleGreen": (152, 251, 152),
+ "Brown": (165, 42, 42),
+ "DarkTurquoise": (0, 206, 209),
+ "DarkGreen": (0, 100, 0),
+ "MediumOrchid": (186, 85, 211),
+ "Chocolate": (210, 105, 30),
+ "PapayaWhip": (255, 239, 213),
+ "Olive": (128, 128, 0),
+ "Silver": (192, 192, 192),
+ "PeachPuff": (255, 218, 185),
+ "Plum": (221, 160, 221),
+ "DarkGoldenrod": (184, 134, 11),
+ "SlateGrey": (112, 128, 144),
+ "MintCream": (245, 255, 250),
+ "CornflowerBlue": (100, 149, 237),
+ "Gold": (255, 215, 0),
+ "HotPink": (255, 105, 180),
+ "DarkBlue": (0, 0, 139),
+ "LimeGreen": (50, 205, 50),
+ "DeepSkyBlue": (0, 191, 255),
+ "DarkKhaki": (189, 183, 107),
+ "LightGrey": (211, 211, 211),
+ "Yellow": (255, 255, 0),
+ "Gainsboro": (220, 220, 220),
+ "MistyRose": (255, 228, 225),
+ "SandyBrown": (244, 164, 96),
+ "DeepPink": (255, 20, 147),
+ "Magenta": (255, 0, 255),
+ "AliceBlue": (240, 248, 255),
+ "DarkCyan": (0, 139, 139),
+ "DarkSlateGrey": (47, 79, 79),
+ "GreenYellow": (173, 255, 47),
+ "DarkOrchid": (153, 50, 204),
+ "OliveDrab": (107, 142, 35),
+ "Chartreuse": (127, 255, 0),
+ "Peru": (205, 133, 63),
+ "Orange": (255, 165, 0),
+ "Red": (255, 0, 0),
+ "Wheat": (245, 222, 179),
+ "LightCyan": (224, 255, 255),
+ "LightSeaGreen": (32, 178, 170),
+ "BlueViolet": (138, 43, 226),
+ "LightSlateGrey": (119, 136, 153),
+ "Cyan": (0, 255, 255),
+ "MediumPurple": (147, 112, 219),
+ "MidnightBlue": (25, 25, 112),
+ "FireBrick": (178, 34, 34),
+ "PaleTurquoise": (175, 238, 238),
+ "PaleGoldenrod": (238, 232, 170),
+ "Gray": (128, 128, 128),
+ "MediumSeaGreen": (60, 179, 113),
+ "Moccasin": (255, 228, 181),
+ "Ivory": (255, 255, 240),
+ "DarkSlateBlue": (72, 61, 139),
+ "Beige": (245, 245, 220),
+ "Green": (0, 128, 0),
+ "SlateBlue": (106, 90, 205),
+ "Teal": (0, 128, 128),
+ "Azure": (240, 255, 255),
+ "LightSteelBlue": (176, 196, 222),
+ "DimGrey": (105, 105, 105),
+ "Tan": (210, 180, 140),
+ "AntiqueWhite": (250, 235, 215),
+ "SkyBlue": (135, 206, 235),
+ "GhostWhite": (248, 248, 255),
+ "MediumTurquoise": (72, 209, 204),
+ "FloralWhite": (255, 250, 240),
+ "LavenderBlush": (255, 240, 245),
+ "SeaGreen": (46, 139, 87),
+ "Lavender": (230, 230, 250),
+ "BlanchedAlmond": (255, 235, 205),
+ "DarkOliveGreen": (85, 107, 47),
+ "DarkSeaGreen": (143, 188, 143),
+ "SpringGreen": (0, 255, 127),
+ "Navy": (0, 0, 128),
+ "Orchid": (218, 112, 214),
+ "SaddleBrown": (139, 69, 19),
+ "IndianRed": (205, 92, 92),
+ "Snow": (255, 250, 250),
+ "SteelBlue": (70, 130, 180),
+ "MediumSlateBlue": (123, 104, 238),
+ "Black": (0, 0, 0),
+ "LightBlue": (173, 216, 230),
+ "Turquoise": (64, 224, 208),
+ "MediumVioletRed": (199, 21, 133),
+ "DarkViolet": (148, 0, 211),
+ "DarkGray": (169, 169, 169),
+ "Salmon": (250, 128, 114),
+ "DarkMagenta": (139, 0, 139),
+ "Tomato": (255, 99, 71),
+ "WhiteSmoke": (245, 245, 245),
+ "Goldenrod": (218, 165, 32),
+ "MediumSpringGreen": (0, 250, 154),
+ "DodgerBlue": (30, 144, 255),
+ "Aqua": (0, 255, 255),
+ "ForestGreen": (34, 139, 34),
+ "LemonChiffon": (255, 250, 205),
+ "LightSlateGray": (119, 136, 153),
+ "SlateGray": (112, 128, 144),
+ "LightGray": (211, 211, 211),
+ "Indigo": (75, 0, 130),
+ "CadetBlue": (95, 158, 160),
+ "LightYellow": (255, 255, 224),
+ "DarkOrange": (255, 140, 0),
+ "PowderBlue": (176, 224, 230),
+ "RoyalBlue": (65, 105, 225),
+ "Sienna": (160, 82, 45),
+ "Thistle": (216, 191, 216),
+ "Lime": (0, 255, 0),
+ "Seashell": (255, 245, 238),
+ "DarkRed": (139, 0, 0),
+ "LightSkyBlue": (135, 206, 250),
+ "YellowGreen": (154, 205, 50),
+ "Aquamarine": (127, 255, 212),
+ "LightCoral": (240, 128, 128),
+ "DarkSlateGray": (47, 79, 79),
+ "Khaki": (240, 230, 140),
+ "DarkGrey": (169, 169, 169),
+ "BurlyWood": (222, 184, 135),
+ "LightGoldenrodYellow": (250, 250, 210),
+ "MediumBlue": (0, 0, 205),
+ "DarkSalmon": (233, 150, 122),
+ "RosyBrown": (188, 143, 143),
+ "LightSalmon": (255, 160, 122),
+ "PaleVioletRed": (219, 112, 147),
+ "Coral": (255, 127, 80),
+ "Violet": (238, 130, 238),
+ "Grey": (128, 128, 128),
+ "LightGreen": (144, 238, 144),
+ "Linen": (250, 240, 230),
+ "OrangeRed": (255, 69, 0),
+ "DimGray": (105, 105, 105),
+ "Maroon": (128, 0, 0),
+ "LightPink": (255, 182, 193),
+ "MediumAquamarine": (102, 205, 170),
+ "OldLace": (253, 245, 230),
}
-svgcolorslower = \
- dict((key.lower(), value) for (key, value) in list(svgcolors.items()))
+svgcolorslower = dict((key.lower(), value) for (key, value) in list(svgcolors.items()))
def getcolor(color):
@@ -253,7 +253,7 @@ def getcolor(color):
FreeCAD.Console.PrintMessage("Color defined as 'none', defaulting to black\n")
return (0.0, 0.0, 0.0, 0.0)
if color[0] == "#":
- if len(color) == 7 or len(color) == 9: # Color string '#RRGGBB' or '#RRGGBBAA'
+ if len(color) == 7 or len(color) == 9: # Color string '#RRGGBB' or '#RRGGBBAA'
r = float(int(color[1:3], 16) / 255.0)
g = float(int(color[3:5], 16) / 255.0)
b = float(int(color[5:7], 16) / 255.0)
@@ -261,27 +261,29 @@ def getcolor(color):
if len(color) == 9:
a = float(int(color[7:9], 16) / 255.0)
FreeCAD.Console.PrintMessage(f"Non standard color format #RRGGBBAA : {color}\n")
- return (r, g, b, 1-a)
- if len(color) == 4: # Color string '#RGB'
+ return (r, g, b, 1 - a)
+ if len(color) == 4: # Color string '#RGB'
# Expand the hex digits
r = float(int(color[1], 16) * 17 / 255.0)
g = float(int(color[2], 16) * 17 / 255.0)
b = float(int(color[3], 16) * 17 / 255.0)
return (r, g, b, 0.0)
- if color.lower().startswith('rgb(') or color.lower().startswith('rgba('): # Color string 'rgb[a](0.12,0.23,0.3,0.0)'
- cvalues = color.lstrip('rgba(').rstrip(')').replace('%', '').split(',')
+ if color.lower().startswith("rgb(") or color.lower().startswith(
+ "rgba("
+ ): # Color string 'rgb[a](0.12,0.23,0.3,0.0)'
+ cvalues = color.lstrip("rgba(").rstrip(")").replace("%", "").split(",")
if len(cvalues) == 3:
a = 1.0
- if '%' in color:
+ if "%" in color:
r, g, b = [int(float(cv)) / 100.0 for cv in cvalues]
else:
r, g, b = [int(float(cv)) / 255.0 for cv in cvalues]
if len(cvalues) == 4:
- if '%' in color:
+ if "%" in color:
r, g, b, a = [int(float(cv)) / 100.0 for cv in cvalues]
else:
r, g, b, a = [int(float(cv)) / 255.0 for cv in cvalues]
- return (r, g, b, 1-a)
+ return (r, g, b, 1 - a)
# Trying named color like 'MediumAquamarine'
v = svgcolorslower.get(color.lower())
if v:
@@ -322,7 +324,7 @@ def transformCopyShape(shape, m):
return shape.transformGeometry(m)
-def getsize(length, mode='discard', base=1):
+def getsize(length, mode="discard", base=1):
"""Parse the length string containing number and unit.
Parameters
@@ -358,74 +360,74 @@ def getsize(length, mode='discard', base=1):
#
# The percentage factor is arbitrarily chosen, as it should depend
# on the viewport size or for filling patterns on the bounding box.
- if mode == 'mm90.0':
+ if mode == "mm90.0":
tomm = {
- '': 25.4/90, # default
- 'px': 25.4/90,
- 'pt': 4.0/3 * 25.4/90,
- 'pc': 15 * 25.4/90,
- 'mm': 1.0,
- 'cm': 10.0,
- 'in': 25.4,
- 'em': 15 * 2.54/90,
- 'ex': 10 * 2.54/90,
- '%': 100
+ "": 25.4 / 90, # default
+ "px": 25.4 / 90,
+ "pt": 4.0 / 3 * 25.4 / 90,
+ "pc": 15 * 25.4 / 90,
+ "mm": 1.0,
+ "cm": 10.0,
+ "in": 25.4,
+ "em": 15 * 2.54 / 90,
+ "ex": 10 * 2.54 / 90,
+ "%": 100,
}
- elif mode == 'mm96.0':
+ elif mode == "mm96.0":
tomm = {
- '': 25.4/96, # default
- 'px': 25.4/96,
- 'pt': 4.0/3 * 25.4/96,
- 'pc': 15 * 25.4/96,
- 'mm': 1.0,
- 'cm': 10.0,
- 'in': 25.4,
- 'em': 15 * 2.54/96,
- 'ex': 10 * 2.54/96,
- '%': 100
+ "": 25.4 / 96, # default
+ "px": 25.4 / 96,
+ "pt": 4.0 / 3 * 25.4 / 96,
+ "pc": 15 * 25.4 / 96,
+ "mm": 1.0,
+ "cm": 10.0,
+ "in": 25.4,
+ "em": 15 * 2.54 / 96,
+ "ex": 10 * 2.54 / 96,
+ "%": 100,
}
- elif mode == 'css90.0':
+ elif mode == "css90.0":
topx = {
- '': 1.0, # default
- 'px': 1.0,
- 'pt': 4.0/3,
- 'pc': 15,
- 'mm': 90.0/25.4,
- 'cm': 90.0/254.0,
- 'in': 90,
- 'em': 15,
- 'ex': 10,
- '%': 100
+ "": 1.0, # default
+ "px": 1.0,
+ "pt": 4.0 / 3,
+ "pc": 15,
+ "mm": 90.0 / 25.4,
+ "cm": 90.0 / 254.0,
+ "in": 90,
+ "em": 15,
+ "ex": 10,
+ "%": 100,
}
- elif mode == 'css96.0':
+ elif mode == "css96.0":
topx = {
- '': 1.0, # default
- 'px': 1.0,
- 'pt': 4.0/3,
- 'pc': 15,
- 'mm': 96.0/25.4,
- 'cm': 96.0/254.0,
- 'in': 96,
- 'em': 15,
- 'ex': 10,
- '%': 100
+ "": 1.0, # default
+ "px": 1.0,
+ "pt": 4.0 / 3,
+ "pc": 15,
+ "mm": 96.0 / 25.4,
+ "cm": 96.0 / 254.0,
+ "in": 96,
+ "em": 15,
+ "ex": 10,
+ "%": 100,
}
# Extract a number from a string like '+56215.14565E+6mm'
- _num = '([-+]?[0-9]*\\.?[0-9]+([eE][-+]?[0-9]+)?)'
- _unit = '(px|pt|pc|mm|cm|in|em|ex|%)?'
+ _num = "([-+]?[0-9]*\\.?[0-9]+([eE][-+]?[0-9]+)?)"
+ _unit = "(px|pt|pc|mm|cm|in|em|ex|%)?"
_full_num = _num + _unit
number, exponent, unit = re.findall(_full_num, length)[0]
- if mode == 'discard':
+ if mode == "discard":
return float(number)
- elif mode == 'tuple':
+ elif mode == "tuple":
return float(number), unit
- elif mode == 'isabsolute':
- return unit in ('mm', 'cm', 'in', 'px', 'pt')
- elif mode == 'mm96.0' or mode == 'mm90.0':
+ elif mode == "isabsolute":
+ return unit in ("mm", "cm", "in", "px", "pt")
+ elif mode == "mm96.0" or mode == "mm90.0":
return float(number) * tomm[unit]
- elif mode == 'css96.0' or mode == 'css90.0':
- if unit != '%':
+ elif mode == "css96.0" or mode == "css90.0":
+ if unit != "%":
return float(number) * topx[unit]
else:
return float(number) * base
@@ -450,8 +452,6 @@ def getrgb(color):
return "#" + r + g + b
-
-
class svgHandler(xml.sax.ContentHandler):
"""Parse SVG files and create FreeCAD objects."""
@@ -498,7 +498,6 @@ class svgHandler(xml.sax.ContentHandler):
if self.fill:
v.ShapeColor = self.fill
-
def __addFaceToDoc(self, named_face):
"""Create a named document object from a name/face tuple
@@ -530,15 +529,15 @@ class svgHandler(xml.sax.ContentHandler):
self.count += 1
precision = svg_precision()
- _msg('processing element {0}: {1}'.format(self.count, name))
- _msg('existing group transform: {}'.format(self.grouptransform))
- _msg('existing group style: {}'.format(self.groupstyles))
+ _msg("processing element {0}: {1}".format(self.count, name))
+ _msg("existing group transform: {}".format(self.grouptransform))
+ _msg("existing group style: {}".format(self.groupstyles))
data = {}
- for (keyword, content) in list(attrs.items()):
+ for keyword, content in list(attrs.items()):
# print(keyword, content)
if keyword != "style":
- content = content.replace(',', ' ')
+ content = content.replace(",", " ")
content = content.split()
# print(keyword, content)
data[keyword] = content
@@ -546,10 +545,10 @@ class svgHandler(xml.sax.ContentHandler):
# If it's the first element, which is ")
svg.close()
if hidden_doc is not None:
try:
@@ -1390,14 +1374,15 @@ def export(exportList, filename):
except:
pass
+
# function to replace use tag to it's referenced object
def replace_use_with_reference(file_path):
- #function that replace use tag to freecad:used
+ # function that replace use tag to freecad:used
def register_svg_namespaces(svg_content):
# register namespaces
xmlns_attrs = re.findall(r'\s+xmlns(?::([a-zA-Z0-9_]+))?="([^"]+)"', svg_content)
for prefix, uri in xmlns_attrs:
- ns_prefix = '' if prefix is None or prefix == 'svg' else prefix
+ ns_prefix = "" if prefix is None or prefix == "svg" else prefix
ET.register_namespace(ns_prefix, uri)
def replace_use(element, tree):
@@ -1424,12 +1409,15 @@ def replace_use_with_reference(file_path):
new_element = ET.Element("freecad:used")
for attr in use.attrib:
# copy attribute to new one except href attribute
- if attr not in {"href", "{http://www.w3.org/1999/xlink}href"} and attr not in new_element.attrib:
+ if (
+ attr not in {"href", "{http://www.w3.org/1999/xlink}href"}
+ and attr not in new_element.attrib
+ ):
new_element.set(attr, use.attrib[attr])
- ref_element=deepcopy(ref_element)
+ ref_element = deepcopy(ref_element)
# change referenced symbol tag to g tag, because symbol tag will be ignored when importing.
if ref_element.tag.endswith("symbol"):
- ref_element.tag="g"
+ ref_element.tag = "g"
# remove id from referenced element.(without this multiple same id problem)
if "id" in ref_element.attrib:
del ref_element.attrib["id"]
@@ -1440,10 +1428,10 @@ def replace_use_with_reference(file_path):
new_element.append(ref_element)
# replace use tag by freecad:used tag.
parent.append(new_element)
- #remove use when referenced element is not found.
+ # remove use when referenced element is not found.
parent.remove(use)
- #now all use tag processd
- #remove symbol and defs tag from tree.
+ # now all use tag processd
+ # remove symbol and defs tag from tree.
parent_map = {child: parent for parent in tree.iter() for child in parent}
symbols = element.findall(".//{http://www.w3.org/2000/svg}symbol")
for symbol in symbols:
@@ -1456,7 +1444,7 @@ def replace_use_with_reference(file_path):
# open file and read
svg_content = pyopen(file_path).read()
- #register namespace before parsing
+ # register namespace before parsing
register_svg_namespaces(svg_content)
# parse as xml.
tree = ET.ElementTree(ET.fromstring(svg_content))
@@ -1470,4 +1458,4 @@ def replace_use_with_reference(file_path):
replace_use(root, tree)
# return tree as xml string with namespace declaration.
- return ET.tostring(root, encoding='unicode',xml_declaration=True)
+ return ET.tostring(root, encoding="unicode", xml_declaration=True)