[TD]add shape validation tool for debugging
This commit is contained in:
committed by
Yorik van Havre
parent
28752ca05b
commit
0fcd2241fb
@@ -650,6 +650,21 @@ void Preferences::setBalloonDragModifiers(Qt::KeyboardModifiers newModifiers)
|
||||
getPreferenceGroup("General")->SetUnsigned("BalloonDragModifier", (uint)newModifiers);
|
||||
}
|
||||
|
||||
//! if true, shapes are validated before use and problematic ones are skipped.
|
||||
//! validating shape takes time, but can prevent crashes/bad results in occt.
|
||||
//! this would normally be set to false and set to true to aid in debugging/support.
|
||||
bool Preferences::checkShapesBeforeUse()
|
||||
{
|
||||
return getPreferenceGroup("General")->GetBool("CheckShapesBeforeUse", false);
|
||||
}
|
||||
|
||||
|
||||
//! if true, shapes which fail validation are saved as brep files
|
||||
bool Preferences::debugBadShape()
|
||||
{
|
||||
return getPreferenceGroup("debug")->GetBool("debugBadShape", false);
|
||||
}
|
||||
|
||||
|
||||
//! if true, automatically switch to TD workbench when a Page is set in edit (double click)
|
||||
bool Preferences::switchOnClick()
|
||||
|
||||
@@ -152,6 +152,10 @@ public:
|
||||
static void setBalloonDragModifiers(Qt::KeyboardModifiers newModifiers);
|
||||
|
||||
static bool switchOnClick();
|
||||
|
||||
static bool checkShapesBeforeUse();
|
||||
static bool debugBadShape();
|
||||
|
||||
};
|
||||
|
||||
|
||||
|
||||
@@ -31,6 +31,7 @@
|
||||
# include <TopoDS_Iterator.hxx>
|
||||
# include <TopoDS_Vertex.hxx>
|
||||
# include <BRepBuilderAPI_Copy.hxx>
|
||||
#include <BRepCheck_Analyzer.hxx>
|
||||
#endif
|
||||
|
||||
#include <App/Document.h>
|
||||
@@ -51,7 +52,7 @@
|
||||
#include "ShapeExtractor.h"
|
||||
#include "DrawUtil.h"
|
||||
#include "ShapeUtils.h"
|
||||
|
||||
#include "Preferences.h"
|
||||
|
||||
using namespace TechDraw;
|
||||
using DU = DrawUtil;
|
||||
@@ -62,14 +63,13 @@ using SU = ShapeUtils;
|
||||
//! Note that point objects will not make it through the hlr/projection process.
|
||||
std::vector<TopoDS_Shape> ShapeExtractor::getShapes2d(const std::vector<App::DocumentObject*> links)
|
||||
{
|
||||
// Base::Console().Message("SE::getShapes2d() - links: %d\n", links.size());
|
||||
|
||||
std::vector<TopoDS_Shape> shapes2d;
|
||||
|
||||
for (auto& l:links) {
|
||||
if (is2dObject(l)) {
|
||||
if (l->getTypeId().isDerivedFrom(Part::Feature::getClassTypeId())) {
|
||||
TopoDS_Shape temp = getLocatedShape(l);
|
||||
// checkShape on 2d objs?
|
||||
if (!temp.IsNull()) {
|
||||
shapes2d.push_back(temp);
|
||||
}
|
||||
@@ -83,12 +83,10 @@ std::vector<TopoDS_Shape> ShapeExtractor::getShapes2d(const std::vector<App::Doc
|
||||
//! fused, include2d should be false as 2d & 3d shapes may not fuse.
|
||||
TopoDS_Shape ShapeExtractor::getShapes(const std::vector<App::DocumentObject*> links, bool include2d)
|
||||
{
|
||||
// Base::Console().Message("SE::getShapes() - links in: %d\n", links.size());
|
||||
std::vector<TopoDS_Shape> sourceShapes;
|
||||
|
||||
for (auto& l:links) {
|
||||
if (is2dObject(l) && !include2d) {
|
||||
// Base::Console().Message("SE::getShapes - skipping 2d link: %s\n", l->Label.getValue());
|
||||
continue;
|
||||
}
|
||||
|
||||
@@ -136,9 +134,11 @@ TopoDS_Shape ShapeExtractor::getShapes(const std::vector<App::DocumentObject*> l
|
||||
}
|
||||
else {
|
||||
auto shape = Part::Feature::getShape(obj);
|
||||
// if link obj has a shape, we use that shape.
|
||||
// if source obj has a shape, we use that shape.
|
||||
if(!SU::isShapeReallyNull(shape) && !isExplodedView) {
|
||||
sourceShapes.push_back(getLocatedShape(obj));
|
||||
if (checkShape(obj, shape)) {
|
||||
sourceShapes.push_back(getLocatedShape(obj));
|
||||
}
|
||||
}
|
||||
else {
|
||||
std::vector<TopoDS_Shape> shapeList = getShapesFromObject(obj);
|
||||
@@ -179,17 +179,14 @@ TopoDS_Shape ShapeExtractor::getShapes(const std::vector<App::DocumentObject*> l
|
||||
}
|
||||
//it appears that an empty compound is !IsNull(), so we need to check a different way
|
||||
if (!SU::isShapeReallyNull(comp)) {
|
||||
// BRepTools::Write(comp, "SEResult.brep"); //debug
|
||||
return comp;
|
||||
}
|
||||
|
||||
// Base::Console().Error("DEVEL: ShapeExtractor failed to get any shape.\n");
|
||||
return TopoDS_Shape();
|
||||
}
|
||||
|
||||
std::vector<TopoDS_Shape> ShapeExtractor::getXShapes(const App::Link* xLink)
|
||||
{
|
||||
// Base::Console().Message("SE::getXShapes() - %s\n", xLink->getNameInDocument());
|
||||
std::vector<TopoDS_Shape> xSourceShapes;
|
||||
if (!xLink) {
|
||||
return xSourceShapes;
|
||||
@@ -231,6 +228,9 @@ std::vector<TopoDS_Shape> ShapeExtractor::getXShapes(const App::Link* xLink)
|
||||
if (ts.isInfinite()) {
|
||||
shape = stripInfiniteShapes(shape);
|
||||
}
|
||||
if (!checkShape(l, shape)) {
|
||||
continue;
|
||||
}
|
||||
// copying the shape prevents "non-orthogonal GTrsf" errors in some versions
|
||||
// of OCC. Something to do with triangulation of shape??
|
||||
// it may be that incremental mesh would work here too.
|
||||
@@ -252,7 +252,8 @@ std::vector<TopoDS_Shape> ShapeExtractor::getXShapes(const App::Link* xLink)
|
||||
} else {
|
||||
// link points to a regular object, not another link? no sublinks?
|
||||
TopoDS_Shape xLinkShape = getShapeFromXLink(xLink);
|
||||
if (!xLinkShape.IsNull()) {
|
||||
if (!xLinkShape.IsNull() &&
|
||||
checkShape(xLink, xLinkShape)) {
|
||||
// copying the shape prevents "non-orthogonal GTrsf" errors in some versions
|
||||
// of OCC. Something to do with triangulation of shape??
|
||||
BRepBuilderAPI_Copy copier(xLinkShape);
|
||||
@@ -265,7 +266,6 @@ std::vector<TopoDS_Shape> ShapeExtractor::getXShapes(const App::Link* xLink)
|
||||
// get the located shape for a single childless App::Link
|
||||
TopoDS_Shape ShapeExtractor::getShapeFromXLink(const App::Link* xLink)
|
||||
{
|
||||
// Base::Console().Message("SE::getShapeFromXLink()\n");
|
||||
Base::Placement xLinkPlacement;
|
||||
if (xLink->hasPlacement()) {
|
||||
xLinkPlacement = xLink->getLinkPlacementProperty()->getValue();
|
||||
@@ -298,21 +298,24 @@ TopoDS_Shape ShapeExtractor::getShapeFromXLink(const App::Link* xLink)
|
||||
Base::Console().Error("ShapeExtractor failed to retrieve shape from %s\n", xLink->getNameInDocument());
|
||||
return TopoDS_Shape();
|
||||
}
|
||||
return ts.getShape();
|
||||
if (checkShape(linkedObject, ts.getShape())) {
|
||||
return ts.getShape();
|
||||
}
|
||||
}
|
||||
return TopoDS_Shape();
|
||||
}
|
||||
|
||||
std::vector<TopoDS_Shape> ShapeExtractor::getShapesFromObject(const App::DocumentObject* docObj)
|
||||
{
|
||||
// Base::Console().Message("SE::getShapesFromObject(%s)\n", docObj->getNameInDocument());
|
||||
std::vector<TopoDS_Shape> result;
|
||||
|
||||
const App::GroupExtension* gex = dynamic_cast<const App::GroupExtension*>(docObj);
|
||||
App::Property* gProp = docObj->getPropertyByName("Group");
|
||||
App::Property* sProp = docObj->getPropertyByName("Shape");
|
||||
if (docObj->isDerivedFrom<Part::Feature>()) {
|
||||
result.push_back(getLocatedShape(docObj));
|
||||
if (checkShape(docObj, getLocatedShape(docObj))) {
|
||||
result.push_back(getLocatedShape(docObj));
|
||||
}
|
||||
} else if (gex) { //is a group extension
|
||||
std::vector<App::DocumentObject*> objs = gex->Group.getValues();
|
||||
std::vector<TopoDS_Shape> shapes;
|
||||
@@ -326,18 +329,17 @@ std::vector<TopoDS_Shape> ShapeExtractor::getShapesFromObject(const App::Documen
|
||||
} else if (gProp) { //has a Group property
|
||||
App::PropertyLinkList* list = dynamic_cast<App::PropertyLinkList*>(gProp);
|
||||
if (list) {
|
||||
std::vector<App::DocumentObject*> objs = list->getValues();
|
||||
std::vector<TopoDS_Shape> shapes;
|
||||
for (auto& d: objs) {
|
||||
shapes = getShapesFromObject(d);
|
||||
if (!shapes.empty()) {
|
||||
result.insert(result.end(), shapes.begin(), shapes.end());
|
||||
}
|
||||
std::vector<App::DocumentObject*> objsAll = list->getValues();
|
||||
std::vector<TopoDS_Shape> shapesAll;
|
||||
for (auto& obj : objsAll) {
|
||||
shapesAll = getShapesFromObject(obj);
|
||||
result.insert(result.end(), shapesAll.begin(), shapesAll.end());
|
||||
}
|
||||
}
|
||||
} else if (sProp) { //has a Shape property
|
||||
Part::PropertyPartShape* shape = dynamic_cast<Part::PropertyPartShape*>(sProp);
|
||||
if (shape) {
|
||||
Part::PropertyPartShape* shapeProperty = dynamic_cast<Part::PropertyPartShape*>(sProp);
|
||||
if (shapeProperty &&
|
||||
checkShape(docObj, getLocatedShape(docObj))) {
|
||||
result.push_back(getLocatedShape(docObj));
|
||||
}
|
||||
}
|
||||
@@ -346,7 +348,6 @@ std::vector<TopoDS_Shape> ShapeExtractor::getShapesFromObject(const App::Documen
|
||||
|
||||
TopoDS_Shape ShapeExtractor::getShapesFused(const std::vector<App::DocumentObject*> links)
|
||||
{
|
||||
// Base::Console().Message("SE::getShapesFused()\n");
|
||||
// get only the 3d shapes and fuse them
|
||||
TopoDS_Shape baseShape = getShapes(links, false);
|
||||
if (!baseShape.IsNull()) {
|
||||
@@ -365,12 +366,10 @@ TopoDS_Shape ShapeExtractor::getShapesFused(const std::vector<App::DocumentObjec
|
||||
}
|
||||
baseShape = fusedShape;
|
||||
}
|
||||
BRepTools::Write(baseShape, "SEbaseShape.brep");
|
||||
|
||||
// if there are 2d shapes in the links they will not fuse with the 3d shapes,
|
||||
// so instead we return a compound of the fused 3d shapes and the 2d shapes
|
||||
std::vector<TopoDS_Shape> shapes2d = getShapes2d(links);
|
||||
BRepTools::Write(DrawUtil::shapeVectorToCompound(shapes2d, false), "SEshapes2d.brep");
|
||||
|
||||
if (!shapes2d.empty()) {
|
||||
shapes2d.push_back(baseShape);
|
||||
@@ -385,7 +384,6 @@ TopoDS_Shape ShapeExtractor::getShapesFused(const std::vector<App::DocumentObjec
|
||||
//Infinite shapes can not be projected, so they need to be removed.
|
||||
TopoDS_Shape ShapeExtractor::stripInfiniteShapes(TopoDS_Shape inShape)
|
||||
{
|
||||
// Base::Console().Message("SE::stripInfiniteShapes()\n");
|
||||
BRep_Builder builder;
|
||||
TopoDS_Compound comp;
|
||||
builder.MakeCompound(comp);
|
||||
@@ -436,7 +434,6 @@ bool ShapeExtractor::isEdgeType(const App::DocumentObject* obj)
|
||||
|
||||
bool ShapeExtractor::isPointType(const App::DocumentObject* obj)
|
||||
{
|
||||
// Base::Console().Message("SE::isPointType(%s)\n", obj->getNameInDocument());
|
||||
if (obj) {
|
||||
Base::Type t = obj->getTypeId();
|
||||
if (t.isDerivedFrom(Part::Vertex::getClassTypeId())) {
|
||||
@@ -452,12 +449,10 @@ bool ShapeExtractor::isPointType(const App::DocumentObject* obj)
|
||||
|
||||
bool ShapeExtractor::isDraftPoint(const App::DocumentObject* obj)
|
||||
{
|
||||
// Base::Console().Message("SE::isDraftPoint()\n");
|
||||
//if the docObj doesn't have a Proxy property, it definitely isn't a Draft point
|
||||
App::PropertyPythonObject* proxy = dynamic_cast<App::PropertyPythonObject*>(obj->getPropertyByName("Proxy"));
|
||||
if (proxy) {
|
||||
std::string pp = proxy->toString();
|
||||
// Base::Console().Message("SE::isDraftPoint - pp: %s\n", pp.c_str());
|
||||
if (pp.find("Point") != std::string::npos) {
|
||||
return true;
|
||||
}
|
||||
@@ -479,7 +474,6 @@ bool ShapeExtractor::isDatumPoint(const App::DocumentObject* obj)
|
||||
//! get the location of a point object
|
||||
Base::Vector3d ShapeExtractor::getLocation3dFromFeat(const App::DocumentObject* obj)
|
||||
{
|
||||
// Base::Console().Message("SE::getLocation3dFromFeat()\n");
|
||||
if (!isPointType(obj)) {
|
||||
return Base::Vector3d(0.0, 0.0, 0.0);
|
||||
}
|
||||
@@ -498,8 +492,6 @@ Base::Vector3d ShapeExtractor::getLocation3dFromFeat(const App::DocumentObject*
|
||||
}
|
||||
}
|
||||
|
||||
// Base::Console().Message("SE::getLocation3dFromFeat - returns: %s\n",
|
||||
// DrawUtil::formatVector(result).c_str());
|
||||
return Base::Vector3d(0.0, 0.0, 0.0);
|
||||
}
|
||||
|
||||
@@ -529,3 +521,29 @@ bool ShapeExtractor::isSketchObject(const App::DocumentObject* obj)
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
//! true if shape fails validity check. A fail here is not a guarantee of later
|
||||
//! problems, but invalid shapes are known to cause issues with HLR_Algo and boolean ops.
|
||||
bool ShapeExtractor::checkShape(const App::DocumentObject* shapeObj, TopoDS_Shape shape)
|
||||
{
|
||||
if (!Preferences::checkShapesBeforeUse()) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if (!BRepCheck_Analyzer(shape).IsValid()) {
|
||||
if (Preferences::debugBadShape()) {
|
||||
std::stringstream ssFileName;
|
||||
ssFileName << "BadShape" << shapeObj->Label.getValue() << ".brep";
|
||||
BRepTools::Write(shape, ssFileName.str().c_str());
|
||||
}
|
||||
// this is ok for devs, but there must be a better way to inform the user from somewhere deep in the
|
||||
// call stack. notification area from App?
|
||||
Base::Console().Warning(
|
||||
"ShapeExtractor found a problem shape in %s. Results may be incorrect.\n",
|
||||
shapeObj->getNameInDocument());
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -58,6 +58,8 @@ public:
|
||||
|
||||
static TopoDS_Shape getLocatedShape(const App::DocumentObject* docObj);
|
||||
|
||||
static bool checkShape(const App::DocumentObject* shapeObj, TopoDS_Shape shape);
|
||||
|
||||
protected:
|
||||
|
||||
private:
|
||||
|
||||
@@ -28,19 +28,163 @@
|
||||
<layout class="QVBoxLayout" name="verticalLayout">
|
||||
<item>
|
||||
<layout class="QGridLayout" name="gridLayout" columnstretch="1,0,0">
|
||||
<item row="7" column="0">
|
||||
<widget class="QLabel" name="label_3">
|
||||
<property name="font">
|
||||
<font>
|
||||
<italic>true</italic>
|
||||
</font>
|
||||
<item row="3" column="0">
|
||||
<widget class="Gui::PrefCheckBox" name="cbSwitchWB">
|
||||
<property name="toolTip">
|
||||
<string>If this box is checked, double clicking on a page in the tree will automatically switch to TechDraw and the page will be made visible.</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Overlap Edges Scrub Passes</string>
|
||||
<string>Switch Workbench on Click</string>
|
||||
</property>
|
||||
<property name="checked">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>SwitchToWB</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>Mod/TechDraw/General</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="3" column="0">
|
||||
<item row="4" column="2">
|
||||
<widget class="Gui::PrefCheckBox" name="cbDebugSection">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Preferred">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="toolTip">
|
||||
<string>Dump intermediate results during Section view processing</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Debug Section</string>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>debugSection</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>Mod/TechDraw/debug</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="8" column="0">
|
||||
<widget class="QLabel" name="label_5">
|
||||
<property name="text">
|
||||
<string>Edge Fuzz</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="0">
|
||||
<widget class="Gui::PrefCheckBox" name="cbNewFaceFinder">
|
||||
<property name="toolTip">
|
||||
<string>If checked, FreeCAD will use the new face finder algorithm. If not checked, FreeCAD will use the original face finder.</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Use New Face Finder Algorithm</string>
|
||||
</property>
|
||||
<property name="checked">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>NewFaceFinder</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>Mod/TechDraw/General</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="5" column="2">
|
||||
<widget class="Gui::PrefCheckBox" name="cbDebugDetail">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Preferred">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="toolTip">
|
||||
<string>Dump intermediate results during Detail view processing</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Debug Detail</string>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>debugDetail</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>Mod/TechDraw/debug</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="0">
|
||||
<widget class="Gui::PrefCheckBox" name="cbDetectFaces">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Preferred">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="toolTip">
|
||||
<string>If checked, TechDraw will attempt to build faces using the
|
||||
line segments returned by the hidden line removal algorithm.
|
||||
Faces must be detected in order to use hatching, but there
|
||||
can be a performance penalty in complex models.</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Detect Faces</string>
|
||||
</property>
|
||||
<property name="checked">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>HandleFaces</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>/Mod/TechDraw/General</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="2">
|
||||
<widget class="Gui::PrefCheckBox" name="cbAutoCorrectRefs">
|
||||
<property name="toolTip">
|
||||
<string>If checked, system will attempt to automatically correct dimension references when the model changes.</string>
|
||||
</property>
|
||||
<property name="statusTip">
|
||||
<string/>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Auto Correct Dimension Refs</string>
|
||||
</property>
|
||||
<property name="checked">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>AutoCorrectRefs</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>Mod/TechDraw/Dimensions</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="4" column="0">
|
||||
<widget class="Gui::PrefCheckBox" name="cbValidateShapes">
|
||||
<property name="toolTip">
|
||||
<string>If checked, input shapes will be checked for errors before use.and invalid shapes will be skipped by the shape extractor. Checking for errors is slower, but can prevent crashes from some geometry problems.
|
||||
</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Validate Shapes</string>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>CheckShapesBeforeUse</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>Mod/TechDraw/General</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="3" column="2">
|
||||
<widget class="Gui::PrefCheckBox" name="cbCrazyEdges">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Preferred">
|
||||
@@ -62,12 +206,71 @@
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="10" column="2">
|
||||
<widget class="Gui::PrefSpinBox" name="sbMaxTiles">
|
||||
<item row="0" column="2">
|
||||
<widget class="Gui::PrefCheckBox" name="cbReportProgress">
|
||||
<property name="toolTip">
|
||||
<string>Limit of 64x64 pixel SVG tiles used to hatch a single face.
|
||||
For large scalings you might get an error about too many SVG tiles.
|
||||
Then you need to increase the tile limit.</string>
|
||||
<string>Issue progress messages while building View geometry</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Report Progress</string>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>ReportProgress</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>/Mod/TechDraw/General</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="7" column="2">
|
||||
<widget class="Gui::PrefSpinBox" name="sbScrubCount">
|
||||
<property name="toolTip">
|
||||
<string>The number of times FreeCAD should try to remove overlapping edges returned by the Hidden Line Removal algorithm. A value of 0 indicates no scrubbing, 1 indicates a single pass and 2 indicates a second pass should be performed. Values above 2 are generally not productive. Each pass adds to the time required to produce the drawing.</string>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignmentFlag::AlignRight|Qt::AlignmentFlag::AlignTrailing|Qt::AlignmentFlag::AlignVCenter</set>
|
||||
</property>
|
||||
<property name="suffix">
|
||||
<string/>
|
||||
</property>
|
||||
<property name="prefix">
|
||||
<string/>
|
||||
</property>
|
||||
<property name="value">
|
||||
<number>1</number>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>ScrubCount</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>Mod/TechDraw/General</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="7" column="0">
|
||||
<widget class="QLabel" name="label_3">
|
||||
<property name="font">
|
||||
<font>
|
||||
<italic>true</italic>
|
||||
</font>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Overlap Edges Scrub Passes</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="9" column="0">
|
||||
<widget class="QLabel" name="label_4">
|
||||
<property name="text">
|
||||
<string>Mark Fuzz</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="11" column="2">
|
||||
<widget class="Gui::PrefSpinBox" name="sbMaxPat">
|
||||
<property name="toolTip">
|
||||
<string>Maximum hatch line segments to use
|
||||
when hatching a face with a PAT pattern</string>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignmentFlag::AlignRight</set>
|
||||
@@ -85,10 +288,60 @@ Then you need to increase the tile limit.</string>
|
||||
<number>10000</number>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>MaxSVGTile</cstring>
|
||||
<cstring>MaxSeg</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>Mod/TechDraw/Decorations</cstring>
|
||||
<cstring>Mod/TechDraw/PAT</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="10" column="0">
|
||||
<widget class="QLabel" name="label">
|
||||
<property name="text">
|
||||
<string>Max SVG Hatch Tiles</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="5" column="0">
|
||||
<widget class="Gui::PrefCheckBox" name="cbDebugBadShape">
|
||||
<property name="toolTip">
|
||||
<string>If checked, shapes which fail validation will be saved as brep files for later analysis.</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Debug Bad Shape</string>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>debugBadShape</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>Mod/TechDraw/debug</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="2">
|
||||
<widget class="Gui::PrefCheckBox" name="cbFuseBeforeSection">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Preferred">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="font">
|
||||
<font>
|
||||
<italic>true</italic>
|
||||
</font>
|
||||
</property>
|
||||
<property name="toolTip">
|
||||
<string>Perform a fuse operation on input shape(s) before Section view processing</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Fuse Before Section</string>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>SectionFuseFirst</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>Mod/TechDraw/General</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
@@ -127,47 +380,6 @@ Each unit is approx. 0.1 mm wide</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="4" column="0">
|
||||
<widget class="Gui::PrefCheckBox" name="cbDebugSection">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Preferred">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="toolTip">
|
||||
<string>Dump intermediate results during Section view processing</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Debug Section</string>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>debugSection</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>Mod/TechDraw/debug</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="0">
|
||||
<widget class="Gui::PrefCheckBox" name="cbNewFaceFinder">
|
||||
<property name="toolTip">
|
||||
<string>If checked, FreeCAD will use the new face finder algorithm. If not checked, FreeCAD will use the original face finder.</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Use New Face Finder Algorithm</string>
|
||||
</property>
|
||||
<property name="checked">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>NewFaceFinder</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>Mod/TechDraw/General</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="6" column="1">
|
||||
<spacer name="horizontalSpacer">
|
||||
<property name="orientation">
|
||||
@@ -181,119 +393,6 @@ Each unit is approx. 0.1 mm wide</string>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item row="10" column="0">
|
||||
<widget class="QLabel" name="label">
|
||||
<property name="text">
|
||||
<string>Max SVG Hatch Tiles</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="2">
|
||||
<widget class="Gui::PrefCheckBox" name="cbReportProgress">
|
||||
<property name="toolTip">
|
||||
<string>Issue progress messages while building View geometry</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Report Progress</string>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>ReportProgress</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>/Mod/TechDraw/General</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="8" column="0">
|
||||
<widget class="QLabel" name="label_5">
|
||||
<property name="text">
|
||||
<string>Edge Fuzz</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="9" column="0">
|
||||
<widget class="QLabel" name="label_4">
|
||||
<property name="text">
|
||||
<string>Mark Fuzz</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="0">
|
||||
<widget class="Gui::PrefCheckBox" name="cbShowSectionEdges">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Preferred">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="toolTip">
|
||||
<string>Highlights border of section cut in section views</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Show Section Edges</string>
|
||||
</property>
|
||||
<property name="checked">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>ShowSectionEdges</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>/Mod/TechDraw/General</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="11" column="2">
|
||||
<widget class="Gui::PrefSpinBox" name="sbMaxPat">
|
||||
<property name="toolTip">
|
||||
<string>Maximum hatch line segments to use
|
||||
when hatching a face with a PAT pattern</string>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignmentFlag::AlignRight</set>
|
||||
</property>
|
||||
<property name="minimum">
|
||||
<number>1</number>
|
||||
</property>
|
||||
<property name="maximum">
|
||||
<number>1000000</number>
|
||||
</property>
|
||||
<property name="singleStep">
|
||||
<number>100</number>
|
||||
</property>
|
||||
<property name="value">
|
||||
<number>10000</number>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>MaxSeg</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>Mod/TechDraw/PAT</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="2">
|
||||
<widget class="Gui::PrefCheckBox" name="cbAutoCorrectRefs">
|
||||
<property name="toolTip">
|
||||
<string>If checked, system will attempt to automatically correct dimension references when the model changes.</string>
|
||||
</property>
|
||||
<property name="statusTip">
|
||||
<string/>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Auto Correct Dimension Refs</string>
|
||||
</property>
|
||||
<property name="checked">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>AutoCorrectRefs</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>Mod/TechDraw/Dimensions</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="8" column="2">
|
||||
<widget class="Gui::PrefDoubleSpinBox" name="pdsbEdgeFuzz">
|
||||
<property name="sizePolicy">
|
||||
@@ -329,60 +428,8 @@ Each unit is approx. 0.1 mm wide</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="2">
|
||||
<widget class="Gui::PrefCheckBox" name="cbFuseBeforeSection">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Preferred">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="font">
|
||||
<font>
|
||||
<italic>true</italic>
|
||||
</font>
|
||||
</property>
|
||||
<property name="toolTip">
|
||||
<string>Perform a fuse operation on input shape(s) before Section view processing</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Fuse Before Section</string>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>SectionFuseFirst</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>Mod/TechDraw/General</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="7" column="2">
|
||||
<widget class="Gui::PrefSpinBox" name="sbScrubCount">
|
||||
<property name="toolTip">
|
||||
<string>The number of times FreeCAD should try to remove overlapping edges returned by the Hidden Line Removal algorithm. A value of 0 indicates no scrubbing, 1 indicates a single pass and 2 indicates a second pass should be performed. Values above 2 are generally not productive. Each pass adds to the time required to produce the drawing.</string>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignmentFlag::AlignRight|Qt::AlignmentFlag::AlignTrailing|Qt::AlignmentFlag::AlignVCenter</set>
|
||||
</property>
|
||||
<property name="suffix">
|
||||
<string/>
|
||||
</property>
|
||||
<property name="prefix">
|
||||
<string/>
|
||||
</property>
|
||||
<property name="value">
|
||||
<number>1</number>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>ScrubCount</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>Mod/TechDraw/General</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="0">
|
||||
<widget class="Gui::PrefCheckBox" name="cbDetectFaces">
|
||||
<item row="2" column="0">
|
||||
<widget class="Gui::PrefCheckBox" name="cbShowSectionEdges">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Preferred">
|
||||
<horstretch>0</horstretch>
|
||||
@@ -390,47 +437,22 @@ Each unit is approx. 0.1 mm wide</string>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="toolTip">
|
||||
<string>If checked, TechDraw will attempt to build faces using the
|
||||
line segments returned by the hidden line removal algorithm.
|
||||
Faces must be detected in order to use hatching, but there
|
||||
can be a performance penalty in complex models.</string>
|
||||
<string>Highlights border of section cut in section views</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Detect Faces</string>
|
||||
<string>Show Section Edges</string>
|
||||
</property>
|
||||
<property name="checked">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>HandleFaces</cstring>
|
||||
<cstring>ShowSectionEdges</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>/Mod/TechDraw/General</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="4" column="2">
|
||||
<widget class="Gui::PrefCheckBox" name="cbDebugDetail">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Preferred">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="toolTip">
|
||||
<string>Dump intermediate results during Detail view processing</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Debug Detail</string>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>debugDetail</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>Mod/TechDraw/debug</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="11" column="0">
|
||||
<widget class="QLabel" name="label_2">
|
||||
<property name="text">
|
||||
@@ -438,22 +460,33 @@ can be a performance penalty in complex models.</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="5" column="0">
|
||||
<widget class="Gui::PrefCheckBox" name="cbSwitchWB">
|
||||
<item row="10" column="2">
|
||||
<widget class="Gui::PrefSpinBox" name="sbMaxTiles">
|
||||
<property name="toolTip">
|
||||
<string>If this box is checked, double clicking on a page in the tree will automatically switch to TechDraw and the page will be made visible.</string>
|
||||
<string>Limit of 64x64 pixel SVG tiles used to hatch a single face.
|
||||
For large scalings you might get an error about too many SVG tiles.
|
||||
Then you need to increase the tile limit.</string>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Switch Workbench on Click</string>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignmentFlag::AlignRight</set>
|
||||
</property>
|
||||
<property name="checked">
|
||||
<bool>true</bool>
|
||||
<property name="minimum">
|
||||
<number>1</number>
|
||||
</property>
|
||||
<property name="maximum">
|
||||
<number>1000000</number>
|
||||
</property>
|
||||
<property name="singleStep">
|
||||
<number>100</number>
|
||||
</property>
|
||||
<property name="value">
|
||||
<number>10000</number>
|
||||
</property>
|
||||
<property name="prefEntry" stdset="0">
|
||||
<cstring>SwitchToWB</cstring>
|
||||
<cstring>MaxSVGTile</cstring>
|
||||
</property>
|
||||
<property name="prefPath" stdset="0">
|
||||
<cstring>Mod/TechDraw/General</cstring>
|
||||
<cstring>Mod/TechDraw/Decorations</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
|
||||
@@ -63,6 +63,9 @@ void DlgPrefsTechDrawAdvancedImp::saveSettings()
|
||||
ui->cbNewFaceFinder->onSave();
|
||||
ui->sbScrubCount->onSave();
|
||||
|
||||
ui->cbDebugBadShape->onSave();
|
||||
ui->cbValidateShapes->onSave();
|
||||
|
||||
saveBalloonOverride();
|
||||
|
||||
ui->cbSwitchWB->onSave();
|
||||
@@ -115,6 +118,9 @@ void DlgPrefsTechDrawAdvancedImp::loadSettings()
|
||||
ui->cbNewFaceFinder->onRestore();
|
||||
ui->sbScrubCount->onRestore();
|
||||
|
||||
ui->cbDebugBadShape->onRestore();
|
||||
ui->cbValidateShapes->onRestore();
|
||||
|
||||
loadBalloonOverride();
|
||||
|
||||
ui->cbSwitchWB->onRestore();
|
||||
|
||||
Reference in New Issue
Block a user