mirror of
https://github.com/IfcOpenShell/IfcOpenShell.git
synced 2026-09-16 13:46:54 +00:00
ifcviewer: include settings for deflection tolerances
This commit is contained in:
@@ -22,6 +22,7 @@
|
|||||||
|
|
||||||
#include <QCheckBox>
|
#include <QCheckBox>
|
||||||
#include <QDialogButtonBox>
|
#include <QDialogButtonBox>
|
||||||
|
#include <QDoubleSpinBox>
|
||||||
#include <QFormLayout>
|
#include <QFormLayout>
|
||||||
#include <QLineEdit>
|
#include <QLineEdit>
|
||||||
#include <QShowEvent>
|
#include <QShowEvent>
|
||||||
@@ -66,6 +67,25 @@ void SettingsWindow::setupUi() {
|
|||||||
"time; dropping them keeps load times sane.");
|
"time; dropping them keeps load times sane.");
|
||||||
form->addRow("Void Limit", void_limit_spin_);
|
form->addRow("Void Limit", void_limit_spin_);
|
||||||
|
|
||||||
|
deflection_tolerance_spin_ = new QDoubleSpinBox(this);
|
||||||
|
deflection_tolerance_spin_->setRange(0.000001, 1000.0);
|
||||||
|
deflection_tolerance_spin_->setDecimals(6);
|
||||||
|
deflection_tolerance_spin_->setSingleStep(0.001);
|
||||||
|
deflection_tolerance_spin_->setToolTip(
|
||||||
|
"Linear chord error between curved geometry and its triangulation, "
|
||||||
|
"in model length units. Smaller = smoother curves but more "
|
||||||
|
"triangles and slower load.");
|
||||||
|
form->addRow("Deflection Tolerance", deflection_tolerance_spin_);
|
||||||
|
|
||||||
|
angular_tolerance_spin_ = new QDoubleSpinBox(this);
|
||||||
|
angular_tolerance_spin_->setRange(0.000001, 3.141592);
|
||||||
|
angular_tolerance_spin_->setDecimals(6);
|
||||||
|
angular_tolerance_spin_->setSingleStep(0.05);
|
||||||
|
angular_tolerance_spin_->setToolTip(
|
||||||
|
"Maximum angle (radians) between adjacent facet normals on a "
|
||||||
|
"curved surface. Smaller = smoother shading but more triangles.");
|
||||||
|
form->addRow("Angular Tolerance", angular_tolerance_spin_);
|
||||||
|
|
||||||
auto* button_box = new QDialogButtonBox(
|
auto* button_box = new QDialogButtonBox(
|
||||||
QDialogButtonBox::Ok | QDialogButtonBox::Cancel, this);
|
QDialogButtonBox::Ok | QDialogButtonBox::Cancel, this);
|
||||||
|
|
||||||
@@ -90,6 +110,8 @@ void SettingsWindow::syncFromSettings() {
|
|||||||
backface_culling_check_->setChecked(AppSettings::instance().backfaceCulling());
|
backface_culling_check_->setChecked(AppSettings::instance().backfaceCulling());
|
||||||
load_data_source_check_->setChecked(AppSettings::instance().loadDataSource());
|
load_data_source_check_->setChecked(AppSettings::instance().loadDataSource());
|
||||||
void_limit_spin_->setValue(AppSettings::instance().voidLimit());
|
void_limit_spin_->setValue(AppSettings::instance().voidLimit());
|
||||||
|
deflection_tolerance_spin_->setValue(AppSettings::instance().deflectionTolerance());
|
||||||
|
angular_tolerance_spin_->setValue(AppSettings::instance().angularTolerance());
|
||||||
}
|
}
|
||||||
|
|
||||||
void SettingsWindow::onAccepted() {
|
void SettingsWindow::onAccepted() {
|
||||||
@@ -98,5 +120,7 @@ void SettingsWindow::onAccepted() {
|
|||||||
AppSettings::instance().setBackfaceCulling(backface_culling_check_->isChecked());
|
AppSettings::instance().setBackfaceCulling(backface_culling_check_->isChecked());
|
||||||
AppSettings::instance().setLoadDataSource(load_data_source_check_->isChecked());
|
AppSettings::instance().setLoadDataSource(load_data_source_check_->isChecked());
|
||||||
AppSettings::instance().setVoidLimit(void_limit_spin_->value());
|
AppSettings::instance().setVoidLimit(void_limit_spin_->value());
|
||||||
|
AppSettings::instance().setDeflectionTolerance(deflection_tolerance_spin_->value());
|
||||||
|
AppSettings::instance().setAngularTolerance(angular_tolerance_spin_->value());
|
||||||
accept();
|
accept();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -23,6 +23,7 @@
|
|||||||
#include <QDialog>
|
#include <QDialog>
|
||||||
|
|
||||||
class QCheckBox;
|
class QCheckBox;
|
||||||
|
class QDoubleSpinBox;
|
||||||
class QLineEdit;
|
class QLineEdit;
|
||||||
class QShowEvent;
|
class QShowEvent;
|
||||||
class QSpinBox;
|
class QSpinBox;
|
||||||
@@ -47,6 +48,8 @@ private:
|
|||||||
QCheckBox* backface_culling_check_ = nullptr;
|
QCheckBox* backface_culling_check_ = nullptr;
|
||||||
QCheckBox* load_data_source_check_ = nullptr;
|
QCheckBox* load_data_source_check_ = nullptr;
|
||||||
QSpinBox* void_limit_spin_ = nullptr;
|
QSpinBox* void_limit_spin_ = nullptr;
|
||||||
|
QDoubleSpinBox* deflection_tolerance_spin_ = nullptr;
|
||||||
|
QDoubleSpinBox* angular_tolerance_spin_ = nullptr;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -29,6 +29,10 @@ constexpr const char* kBackfaceCullingKey = "viewport/backface_culling";
|
|||||||
constexpr const char* kLoadDataSourceKey = "loading/load_data_source";
|
constexpr const char* kLoadDataSourceKey = "loading/load_data_source";
|
||||||
constexpr const char* kVoidLimitKey = "loading/void_limit";
|
constexpr const char* kVoidLimitKey = "loading/void_limit";
|
||||||
constexpr int kVoidLimitDefault = 30;
|
constexpr int kVoidLimitDefault = 30;
|
||||||
|
constexpr const char* kDeflectionToleranceKey = "loading/deflection_tolerance";
|
||||||
|
constexpr double kDeflectionToleranceDefault = 0.001;
|
||||||
|
constexpr const char* kAngularToleranceKey = "loading/angular_tolerance";
|
||||||
|
constexpr double kAngularToleranceDefault = 0.5;
|
||||||
}
|
}
|
||||||
|
|
||||||
AppSettings& AppSettings::instance() {
|
AppSettings& AppSettings::instance() {
|
||||||
@@ -96,6 +100,30 @@ void AppSettings::setVoidLimit(int value) {
|
|||||||
emit voidLimitChanged(value);
|
emit voidLimitChanged(value);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
double AppSettings::deflectionTolerance() const {
|
||||||
|
return deflection_tolerance_;
|
||||||
|
}
|
||||||
|
|
||||||
|
void AppSettings::setDeflectionTolerance(double value) {
|
||||||
|
if (value <= 0.0) value = kDeflectionToleranceDefault;
|
||||||
|
if (deflection_tolerance_ == value) return;
|
||||||
|
deflection_tolerance_ = value;
|
||||||
|
persist();
|
||||||
|
emit deflectionToleranceChanged(value);
|
||||||
|
}
|
||||||
|
|
||||||
|
double AppSettings::angularTolerance() const {
|
||||||
|
return angular_tolerance_;
|
||||||
|
}
|
||||||
|
|
||||||
|
void AppSettings::setAngularTolerance(double value) {
|
||||||
|
if (value <= 0.0) value = kAngularToleranceDefault;
|
||||||
|
if (angular_tolerance_ == value) return;
|
||||||
|
angular_tolerance_ = value;
|
||||||
|
persist();
|
||||||
|
emit angularToleranceChanged(value);
|
||||||
|
}
|
||||||
|
|
||||||
void AppSettings::load() {
|
void AppSettings::load() {
|
||||||
QSettings settings;
|
QSettings settings;
|
||||||
geometry_library_ = settings.value(kGeometryLibraryKey, kGeometryLibraryDefault).toString();
|
geometry_library_ = settings.value(kGeometryLibraryKey, kGeometryLibraryDefault).toString();
|
||||||
@@ -104,6 +132,10 @@ void AppSettings::load() {
|
|||||||
load_data_source_ = settings.value(kLoadDataSourceKey, true).toBool();
|
load_data_source_ = settings.value(kLoadDataSourceKey, true).toBool();
|
||||||
void_limit_ = settings.value(kVoidLimitKey, kVoidLimitDefault).toInt();
|
void_limit_ = settings.value(kVoidLimitKey, kVoidLimitDefault).toInt();
|
||||||
if (void_limit_ < 0) void_limit_ = 0;
|
if (void_limit_ < 0) void_limit_ = 0;
|
||||||
|
deflection_tolerance_ = settings.value(kDeflectionToleranceKey, kDeflectionToleranceDefault).toDouble();
|
||||||
|
if (deflection_tolerance_ <= 0.0) deflection_tolerance_ = kDeflectionToleranceDefault;
|
||||||
|
angular_tolerance_ = settings.value(kAngularToleranceKey, kAngularToleranceDefault).toDouble();
|
||||||
|
if (angular_tolerance_ <= 0.0) angular_tolerance_ = kAngularToleranceDefault;
|
||||||
}
|
}
|
||||||
|
|
||||||
void AppSettings::persist() {
|
void AppSettings::persist() {
|
||||||
@@ -113,4 +145,6 @@ void AppSettings::persist() {
|
|||||||
settings.setValue(kBackfaceCullingKey, backface_culling_);
|
settings.setValue(kBackfaceCullingKey, backface_culling_);
|
||||||
settings.setValue(kLoadDataSourceKey, load_data_source_);
|
settings.setValue(kLoadDataSourceKey, load_data_source_);
|
||||||
settings.setValue(kVoidLimitKey, void_limit_);
|
settings.setValue(kVoidLimitKey, void_limit_);
|
||||||
|
settings.setValue(kDeflectionToleranceKey, deflection_tolerance_);
|
||||||
|
settings.setValue(kAngularToleranceKey, angular_tolerance_);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -53,12 +53,25 @@ public:
|
|||||||
int voidLimit() const;
|
int voidLimit() const;
|
||||||
void setVoidLimit(int value);
|
void setVoidLimit(int value);
|
||||||
|
|
||||||
|
// Mesher tolerances passed straight to the IfcOpenShell iterator.
|
||||||
|
// Linear deflection bounds the chord error between a curve and its
|
||||||
|
// triangulation, in model length units; angular deflection bounds the
|
||||||
|
// angle (radians) between adjacent facet normals on a curved surface.
|
||||||
|
// Smaller values mean smoother geometry at the cost of more triangles
|
||||||
|
// and slower iteration.
|
||||||
|
double deflectionTolerance() const;
|
||||||
|
void setDeflectionTolerance(double value);
|
||||||
|
double angularTolerance() const;
|
||||||
|
void setAngularTolerance(double value);
|
||||||
|
|
||||||
signals:
|
signals:
|
||||||
void geometryLibraryChanged(const QString& value);
|
void geometryLibraryChanged(const QString& value);
|
||||||
void showStatsChanged(bool value);
|
void showStatsChanged(bool value);
|
||||||
void backfaceCullingChanged(bool value);
|
void backfaceCullingChanged(bool value);
|
||||||
void loadDataSourceChanged(bool value);
|
void loadDataSourceChanged(bool value);
|
||||||
void voidLimitChanged(int value);
|
void voidLimitChanged(int value);
|
||||||
|
void deflectionToleranceChanged(double value);
|
||||||
|
void angularToleranceChanged(double value);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
AppSettings();
|
AppSettings();
|
||||||
@@ -70,6 +83,8 @@ private:
|
|||||||
bool backface_culling_ = true;
|
bool backface_culling_ = true;
|
||||||
bool load_data_source_ = true;
|
bool load_data_source_ = true;
|
||||||
int void_limit_ = 30;
|
int void_limit_ = 30;
|
||||||
|
double deflection_tolerance_ = 0.001;
|
||||||
|
double angular_tolerance_ = 0.5;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // APPSETTINGS_H
|
#endif // APPSETTINGS_H
|
||||||
|
|||||||
@@ -284,12 +284,17 @@ void GeometryStreamer::run(const std::string& path, int num_threads) {
|
|||||||
// applied on the GPU per instance.
|
// applied on the GPU per instance.
|
||||||
settings.set("use-world-coords", false);
|
settings.set("use-world-coords", false);
|
||||||
settings.set("weld-vertices", false);
|
settings.set("weld-vertices", false);
|
||||||
settings.set("apply-default-materials", true);
|
settings.set("apply-default-materials", false);
|
||||||
// Off by default in IfcOpenShell — makes face winding consistent within
|
// Off by default in IfcOpenShell — makes face winding consistent within
|
||||||
// each shell, which we need for GL_CULL_FACE and for per-vertex normals
|
// each shell, which we need for GL_CULL_FACE and for per-vertex normals
|
||||||
// to shade a solid without dark inside-out patches. Costs some iterator
|
// to shade a solid without dark inside-out patches. Costs some iterator
|
||||||
// time, but results are cached in the sidecar so it's a one-shot hit.
|
// time, but results are cached in the sidecar so it's a one-shot hit.
|
||||||
settings.set("reorient-shells", true);
|
settings.set("reorient-shells", true);
|
||||||
|
settings.set("layerset-first", true);
|
||||||
|
settings.set("mesher-linear-deflection", AppSettings::instance().deflectionTolerance());
|
||||||
|
settings.set("mesher-angular-deflection", AppSettings::instance().angularTolerance());
|
||||||
|
// Wire intersection checks is prohibitively slow on advanced breps. See bug #5999.
|
||||||
|
settings.set("no-wire-intersection-check", true);
|
||||||
|
|
||||||
// @todo parallel mapping on RocksDB-backed files still races somewhere
|
// @todo parallel mapping on RocksDB-backed files still races somewhere
|
||||||
// outside the instance cache, producing inconsistent shape counts. Force
|
// outside the instance cache, producing inconsistent shape counts. Force
|
||||||
|
|||||||
Reference in New Issue
Block a user