diff --git a/src/App/Material.cpp b/src/App/Material.cpp
index af399dcc32..89c55430d1 100644
--- a/src/App/Material.cpp
+++ b/src/App/Material.cpp
@@ -31,19 +31,7 @@
#include "Application.h"
#include "Material.h"
-// Helper functions to consistently convert between float and long
-namespace
-{
-float fromPercent(long value)
-{
- return std::roundf(value) / 100.0F;
-}
-
-long toPercent(float value)
-{
- return std::lround(100.0 * value);
-}
-} // namespace
+#include
using namespace App;
@@ -351,9 +339,9 @@ App::Material Material::getDefaultAppearance()
};
App::Material mat(App::Material::DEFAULT);
- mat.transparency = fromPercent(hGrp->GetInt("DefaultShapeTransparency", 0));
- long shininess = toPercent(mat.shininess);
- mat.shininess = fromPercent(hGrp->GetInt("DefaultShapeShininess", shininess));
+ mat.transparency = Base::fromPercent(hGrp->GetInt("DefaultShapeTransparency", 0));
+ long shininess = Base::toPercent(mat.shininess);
+ mat.shininess = Base::fromPercent(hGrp->GetInt("DefaultShapeShininess", shininess));
// This is handled in the material code when using the object appearance
bool randomColor = hGrp->GetBool("RandomColor", false);
diff --git a/src/Base/Builder3D.cpp b/src/Base/Builder3D.cpp
index 806ef38f89..e356faf093 100644
--- a/src/Base/Builder3D.cpp
+++ b/src/Base/Builder3D.cpp
@@ -1253,7 +1253,7 @@ bool InventorLoader::isValid() const
namespace Base
{
-BaseExport Vector3f to_vector(std::string str)
+BaseExport Vector3f stringToVector(std::string str)
{
std::string_view view = str;
if (!boost::starts_with(view, "(") || !boost::ends_with(str, ")")) {
@@ -1282,4 +1282,9 @@ BaseExport Vector3f to_vector(std::string str)
return vec;
}
+BaseExport std::string vectorToString(Vector3f vec)
+{
+ return fmt::format("({},{},{})", vec.x, vec.y, vec.z);
+}
+
} // namespace Base
diff --git a/src/Base/Builder3D.h b/src/Base/Builder3D.h
index d3375f5ad3..32616d2e6a 100644
--- a/src/Base/Builder3D.h
+++ b/src/Base/Builder3D.h
@@ -845,7 +845,14 @@ private:
* If it fails then a std::exception is thrown.
* Supported type names are float or double
*/
-BaseExport Base::Vector3f to_vector(std::string);
+BaseExport Base::Vector3f stringToVector(std::string);
+
+/*!
+ * Expects a string of the form "(x,y,z)" and creates a vector from it.
+ * If it fails then a std::exception is thrown.
+ * Supported type names are float or double
+ */
+BaseExport std::string vectorToString(Vector3f);
} // namespace Base
diff --git a/src/Base/Tools.h b/src/Base/Tools.h
index 6c0e0657ec..107be7617d 100644
--- a/src/Base/Tools.h
+++ b/src/Base/Tools.h
@@ -143,6 +143,16 @@ inline T toDegrees(T r)
return static_cast((r / M_PI) * 180.0);
}
+inline float fromPercent(const long value)
+{
+ return std::roundf(value) / 100.0F;
+}
+
+inline long toPercent(float value)
+{
+ return std::lround(100.0 * value);
+}
+
template
inline T fmod(T numerator, T denominator)
{
diff --git a/src/Gui/Dialogs/DlgMaterialPropertiesImp.cpp b/src/Gui/Dialogs/DlgMaterialPropertiesImp.cpp
index a121928968..2b59d320d6 100644
--- a/src/Gui/Dialogs/DlgMaterialPropertiesImp.cpp
+++ b/src/Gui/Dialogs/DlgMaterialPropertiesImp.cpp
@@ -28,6 +28,8 @@
#include "ui_DlgMaterialProperties.h"
#include "ViewProvider.h"
+#include
+
using namespace Gui::Dialog;
@@ -129,7 +131,7 @@ void DlgMaterialPropertiesImp::onSpecularColorChanged()
*/
void DlgMaterialPropertiesImp::onShininessValueChanged(int sh)
{
- customMaterial.shininess = (float)sh / 100.0F;
+ customMaterial.shininess = Base::fromPercent(sh);
}
/**
@@ -137,7 +139,7 @@ void DlgMaterialPropertiesImp::onShininessValueChanged(int sh)
*/
void DlgMaterialPropertiesImp::onTransparencyValueChanged(int sh)
{
- customMaterial.transparency = (float)sh / 100.0F;
+ customMaterial.transparency = Base::fromPercent(sh);
}
/**
diff --git a/src/Gui/PreferencePages/DlgSettings3DView.ui b/src/Gui/PreferencePages/DlgSettings3DView.ui
index 4bbdc75615..23151a012d 100644
--- a/src/Gui/PreferencePages/DlgSettings3DView.ui
+++ b/src/Gui/PreferencePages/DlgSettings3DView.ui
@@ -7,7 +7,7 @@
0
0
499
- 520
+ 600
@@ -48,11 +48,12 @@ lower right corner within opened files
-
- Qt::Horizontal
+ Qt::Orientation::Horizontal
40
+ 0
@@ -63,7 +64,7 @@ lower right corner within opened files
Relative size:
- Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter
+ Qt::AlignmentFlag::AlignRight|Qt::AlignmentFlag::AlignTrailing|Qt::AlignmentFlag::AlignVCenter
@@ -73,6 +74,9 @@ lower right corner within opened files
Size of main coordinate system representation
in the corner -- in % of height/width of viewport
+
+ %
+
2
@@ -82,9 +86,6 @@ in the corner -- in % of height/width of viewport
10
-
- %
-
CornerCoordSystemSize
@@ -105,7 +106,7 @@ in the corner -- in % of height/width of viewport
Axis letter and FPS counter color
-
+
0
0
@@ -324,14 +325,76 @@ report this setting as enabled when seeking support on the FreeCAD forums
-
-
-
-
-
- Render cache
+
-
+
+
+
+ 120
+ 0
+
+
+
+ What kind of multisample anti-aliasing is used
- -
+
-
+
+
+
+
+
+ Marker size:
+
+
+
+ -
+
+
+ Anti-Aliasing
+
+
+
+ -
+
+
+
+
+
+ Transparent objects:
+
+
+
+ -
+
+
+
+ 120
+ 0
+
+
+
+ Render types of transparent objects
+
+
+ TransparentObjectRenderType
+
+
+ View
+
+
-
+
+ One pass
+
+
+ -
+
+ Backface pass
+
+
+
+
+ -
@@ -368,76 +431,21 @@ but slower response to any scene changes.
- -
-
+
-
+
- Anti-Aliasing
+ Render cache
- -
-
-
-
- 120
- 0
-
-
-
- What kind of multisample anti-aliasing is used
-
-
-
- -
-
-
-
-
+
-
+
- Transparent objects:
+ Eye to eye distance for stereo modes
- -
-
-
-
- 120
- 0
-
-
-
- Render types of transparent objects
-
-
- TransparentObjectRenderType
-
-
- View
-
-
-
-
- One pass
-
-
- -
-
- Backface pass
-
-
-
-
- -
-
-
-
-
-
- Marker size:
-
-
-
- -
+
-
@@ -450,14 +458,7 @@ but slower response to any scene changes.
- -
-
-
- Eye to eye distance for stereo modes
-
-
-
- -
+
-
@@ -493,120 +494,6 @@ bounding box size of the 3D object that is currently displayed.
- -
-
-
- Backlight is enabled with the defined color
-
-
- Backlight color
-
-
- EnableBacklight
-
-
- View
-
-
-
- -
-
-
- false
-
-
- Backlight color
-
-
-
- 255
- 255
- 255
-
-
-
- BacklightColor
-
-
- View
-
-
-
- -
-
-
- Qt::Horizontal
-
-
-
- 40
- 20
-
-
-
-
- -
-
-
- false
-
-
-
-
-
- Intensity
-
-
- Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter
-
-
-
- -
-
-
- false
-
-
-
- 0
- 0
-
-
-
-
- 120
- 0
-
-
-
- Intensity of the backlight
-
-
- 100
-
-
- 1
-
-
- 100
-
-
- Qt::Horizontal
-
-
- QSlider::TicksBelow
-
-
- 10
-
-
- BacklightIntensity
-
-
- View
-
-
-
@@ -674,7 +561,7 @@ bounding box size of the 3D object that is currently displayed.
-
- Qt::Vertical
+ Qt::Orientation::Vertical
@@ -694,18 +581,8 @@ bounding box size of the 3D object that is currently displayed.
- Gui::PrefCheckBox
- QCheckBox
-
-
-
- Gui::PrefRadioButton
- QRadioButton
-
-
-
- Gui::PrefComboBox
- QComboBox
+ Gui::PrefSpinBox
+ QSpinBox
@@ -714,8 +591,18 @@ bounding box size of the 3D object that is currently displayed.
- Gui::PrefSlider
- QSlider
+ Gui::PrefRadioButton
+ QRadioButton
+
+
+
+ Gui::PrefCheckBox
+ QCheckBox
+
+
+
+ Gui::PrefComboBox
+ QComboBox
@@ -723,73 +610,40 @@ bounding box size of the 3D object that is currently displayed.
QDoubleSpinBox
-
- Gui::PrefSpinBox
- QSpinBox
-
-
-
- checkBoxBacklight
- toggled(bool)
- backlightColor
- setEnabled(bool)
-
-
- 161
- 227
-
-
- 290
- 224
-
-
-
-
- checkBoxBacklight
- toggled(bool)
- sliderIntensity
- setEnabled(bool)
-
-
- 92
- 235
-
-
- 293
- 256
-
-
-
-
- checkBoxBacklight
- toggled(bool)
- backlightLabel
- setEnabled(bool)
-
-
- 82
- 507
-
-
- 316
- 507
-
-
-
CheckBox_CornerCoordSystem
toggled(bool)
SpinBox_CornerCoordSystemSize
setEnabled(bool)
+
+
+ 20
+ 20
+
+
+ 20
+ 20
+
+
CheckBox_CornerCoordSystem
toggled(bool)
axisLetterColor
setEnabled(bool)
+
+
+ 20
+ 20
+
+
+ 20
+ 20
+
+
diff --git a/src/Gui/PreferencePages/DlgSettings3DViewImp.cpp b/src/Gui/PreferencePages/DlgSettings3DViewImp.cpp
index 35112bc81c..cd4d069ef5 100644
--- a/src/Gui/PreferencePages/DlgSettings3DViewImp.cpp
+++ b/src/Gui/PreferencePages/DlgSettings3DViewImp.cpp
@@ -69,10 +69,7 @@ void DlgSettings3DViewImp::saveSettings()
ui->CheckBox_use_SW_OpenGL->onSave();
ui->CheckBox_useVBO->onSave();
ui->FloatSpinBox_EyeDistance->onSave();
- ui->checkBoxBacklight->onSave();
- ui->backlightColor->onSave();
ui->axisLetterColor->onSave();
- ui->sliderIntensity->onSave();
ui->radioPerspective->onSave();
ui->radioOrthographic->onSave();
ui->xAxisColor->onSave();
@@ -89,10 +86,7 @@ void DlgSettings3DViewImp::loadSettings()
ui->CheckBox_use_SW_OpenGL->onRestore();
ui->CheckBox_useVBO->onRestore();
ui->FloatSpinBox_EyeDistance->onRestore();
- ui->checkBoxBacklight->onRestore();
- ui->backlightColor->onRestore();
ui->axisLetterColor->onRestore();
- ui->sliderIntensity->onRestore();
ui->radioPerspective->onRestore();
ui->radioOrthographic->onRestore();
ui->comboTransparentRender->onRestore();
diff --git a/src/Gui/PreferencePages/DlgSettingsLightSources.cpp b/src/Gui/PreferencePages/DlgSettingsLightSources.cpp
index fd1701e92a..d39fe4bf50 100644
--- a/src/Gui/PreferencePages/DlgSettingsLightSources.cpp
+++ b/src/Gui/PreferencePages/DlgSettingsLightSources.cpp
@@ -24,12 +24,11 @@
#include "PreCompiled.h"
#ifndef _PreComp_
-#include
#include
#include
#include
#include
-#include
+#include
#include
#include
#include
@@ -37,7 +36,10 @@
#include "DlgSettingsLightSources.h"
#include "ui_DlgSettingsLightSources.h"
-#include
+
+#include
+#include
+#include
#include
#include
@@ -46,273 +48,305 @@ using namespace Gui::Dialog;
/* TRANSLATOR Gui::Dialog::DlgSettingsLightSources */
-DlgSettingsLightSources::DlgSettingsLightSources(QWidget* parent)
- : PreferencePage(parent)
- , ui(new Ui_DlgSettingsLightSources)
-{
- ui->setupUi(this);
-
- view = ui->viewer;
- createViewer();
-}
-
-static inline
-SbVec3f getDirectionVector(const SbRotation &rotation)
+static inline SbVec3f getDirectionVector(const SbRotation& rotation)
{
SbVec3f dir {0.0f, 0.0f, -1.0f};
rotation.multVec(dir, dir);
return dir;
}
-static inline
-void setLightDirection(const SbRotation &rotation, Gui::View3DInventorViewer *viewer)
+DlgSettingsLightSources::DlgSettingsLightSources(QWidget* parent)
+ : PreferencePage(parent)
+ , ui(new Ui_DlgSettingsLightSources)
{
- viewer->getHeadlight()->direction = getDirectionVector(rotation);
+ ui->setupUi(this);
+
+ view = ui->viewer;
+
+ configureViewer();
+
+ const auto connectLightEvents = [&](QuantitySpinBox* horizontalAngleSpinBox,
+ QuantitySpinBox* verticalAngleSpinBox,
+ QSpinBox* intensitySpinBox,
+ ColorButton* colorButton,
+ QCheckBox* enabledCheckbox,
+ auto updateLightFunction) {
+ connect(horizontalAngleSpinBox,
+ qOverload(&QuantitySpinBox::valueChanged),
+ this,
+ updateLightFunction);
+ connect(verticalAngleSpinBox,
+ qOverload(&QuantitySpinBox::valueChanged),
+ this,
+ updateLightFunction);
+ connect(intensitySpinBox,
+ qOverload(&QSpinBox::valueChanged),
+ this,
+ updateLightFunction);
+ connect(colorButton, &ColorButton::changed, this, updateLightFunction);
+ connect(enabledCheckbox, &QCheckBox::stateChanged, this, updateLightFunction);
+ };
+
+ const auto updateLight = [&](SoDirectionalLight* light,
+ QuantitySpinBox* horizontalAngleSpinBox,
+ QuantitySpinBox* verticalAngleSpinBox,
+ QSpinBox* intensitySpinBox,
+ ColorButton* colorButton,
+ QCheckBox* enabledCheckbox,
+ std::function setLightEnabled) {
+ light->color = Base::convertTo(colorButton->color());
+ light->intensity = Base::fromPercent(intensitySpinBox->value());
+ light->direction =
+ Base::convertTo(azimuthElevationToDirection(horizontalAngleSpinBox->rawValue(),
+ verticalAngleSpinBox->rawValue()));
+ setLightEnabled(enabledCheckbox->isChecked());
+ };
+
+ const auto updateHeadLight = [&] {
+ updateLight(view->getHeadlight(),
+ ui->mainLightHorizontalAngle,
+ ui->mainLightVerticalAngle,
+ ui->mainLightIntensitySpinBox,
+ ui->mainLightColor,
+ ui->mainLightEnable,
+ [&](bool enabled) {
+ view->setHeadlightEnabled(enabled);
+ });
+ };
+
+ const auto updateFillLight = [&] {
+ updateLight(view->getFillLight(),
+ ui->fillLightHorizontalAngle,
+ ui->fillLightVerticalAngle,
+ ui->fillLightIntensitySpinBox,
+ ui->fillLightColor,
+ ui->fillLightEnable,
+ [&](bool enabled) {
+ view->setFillLightEnabled(enabled);
+ });
+ };
+
+ const auto updateBackLight = [&] {
+ updateLight(view->getBacklight(),
+ ui->backLightHorizontalAngle,
+ ui->backLightVerticalAngle,
+ ui->backLightIntensitySpinBox,
+ ui->backLightColor,
+ ui->backLightEnable,
+ [&](bool enabled) {
+ view->setBacklightEnabled(enabled);
+ });
+ };
+
+ connectLightEvents(ui->mainLightHorizontalAngle,
+ ui->mainLightVerticalAngle,
+ ui->mainLightIntensitySpinBox,
+ ui->mainLightColor,
+ ui->mainLightEnable,
+ updateHeadLight);
+ connectLightEvents(ui->backLightHorizontalAngle,
+ ui->backLightVerticalAngle,
+ ui->backLightIntensitySpinBox,
+ ui->backLightColor,
+ ui->backLightEnable,
+ updateBackLight);
+ connectLightEvents(ui->fillLightHorizontalAngle,
+ ui->fillLightVerticalAngle,
+ ui->fillLightIntensitySpinBox,
+ ui->fillLightColor,
+ ui->fillLightEnable,
+ updateFillLight);
+
+ const auto updateAmbientLight = [&] {
+ view->getEnvironment()->ambientColor =
+ Base::convertTo(ui->ambientLightColor->color());
+ view->getEnvironment()->ambientIntensity =
+ Base::fromPercent(ui->ambientLightIntensitySpinBox->value());
+ };
+
+ connect(ui->ambientLightIntensitySpinBox,
+ qOverload(&QSpinBox::valueChanged),
+ this,
+ updateAmbientLight);
+ connect(ui->ambientLightColor, &ColorButton::changed, this, updateAmbientLight);
+
+ connect(ui->zoomInButton, &QToolButton::clicked, this, &DlgSettingsLightSources::zoomIn);
+ connect(ui->zoomOutButton, &QToolButton::clicked, this, &DlgSettingsLightSources::zoomOut);
+
+ DlgSettingsLightSources::loadSettings();
}
-static inline
-void setLightDraggerDirection(const SbRotation &rotation, SoDirectionalLightDragger *light_dragger)
+static inline SoMaterial* createMaterial(void)
{
- light_dragger->rotation = rotation;
-}
+ const QColor ambientColor {0xff333333}, diffuseColor {0xffd2d2ff}, emissiveColor {0xff000000},
+ specularColor {0xffcccccc};
-static inline
-void setValueSilently(QDoubleSpinBox *spn, const float val)
-{
- Q_ASSERT_X(spn, "setValueSilently", "QDoubleSpinBox has been deleted");
+ auto material = new SoMaterial();
- spn->blockSignals(true);
- spn->setValue(val);
- spn->blockSignals(false);
-}
-
-void DlgSettingsLightSources::dragMotionCallback(void *data, SoDragger *drag)
-{
- auto lightdrag = dynamic_cast (drag);
- auto self = static_cast(data);
-
- const SbRotation rotation = lightdrag->rotation.getValue();
-
- setLightDirection(rotation, self->view);
-
- setValueSilently(self->ui->q0_spnBox, rotation[0]);
- setValueSilently(self->ui->q1_spnBox, rotation[1]);
- setValueSilently(self->ui->q2_spnBox, rotation[2]);
- setValueSilently(self->ui->q3_spnBox, rotation[3]);
-
- const SbVec3f dir = getDirectionVector(rotation);
-
- setValueSilently(self->ui->x_spnBox, dir[0]);
- setValueSilently(self->ui->y_spnBox, dir[1]);
- setValueSilently(self->ui->z_spnBox, dir[2]);
-}
-
-static inline
-SoMaterial *createMaterial(void)
-{
- const QColor ambientColor {0xff333333},
- diffuseColor {0xffd2d2ff},
- emissiveColor {0xff000000},
- specularColor {0xffcccccc};
-
- auto material = new SoMaterial ();
- material->ambientColor.setValue (ambientColor.redF(), ambientColor.greenF(), ambientColor.blueF());
- material->diffuseColor.setValue (diffuseColor.redF(), diffuseColor.greenF(), diffuseColor.blueF());
- material->emissiveColor.setValue(emissiveColor.redF(), emissiveColor.greenF(), emissiveColor.blueF());
- material->specularColor.setValue(specularColor.redF(), specularColor.greenF(), specularColor.blueF());
+ material->ambientColor.setValue(Base::convertTo(ambientColor));
+ material->diffuseColor.setValue(Base::convertTo(diffuseColor));
+ material->emissiveColor.setValue(Base::convertTo(emissiveColor));
+ material->specularColor.setValue(Base::convertTo(specularColor));
material->shininess = 0.9f;
return material;
}
-static inline
-SoSphere *createSphere(void)
+static inline SoSphere* createSphere(void)
{
auto sphere = new SoSphere();
- sphere->radius = 2;
+ sphere->radius = 3;
return sphere;
}
-void DlgSettingsLightSources::createViewer()
+static inline SoComplexity* createGoodComplexity()
{
- const QColor default_bg_color {180, 180, 180};
- const SbVec3f default_view_direction {1.0f, 1.0f, -5.0f};
+ auto complexity = new SoComplexity();
+ complexity->value = 1.0;
+
+ return complexity;
+}
+
+void DlgSettingsLightSources::configureViewer()
+{
+ const SbVec3f defaultViewDirection {0.0f, 1.0f, 0.3f};
+
+ View3DSettings(hGrp, view).applySettings();
- // NOLINTBEGIN
view->setRedirectToSceneGraph(true);
view->setViewing(true);
view->setPopupMenuEnabled(false);
-
- view->setBackgroundColor(default_bg_color);
- view->setGradientBackground(Gui::View3DInventorViewer::NoGradient);
view->setEnabledNaviCube(false);
- auto root = static_cast(view->getSceneGraph());
- root->addChild(createDragger());
+ const auto root = static_cast(view->getSceneGraph());
+ root->addChild(createGoodComplexity());
root->addChild(createMaterial());
root->addChild(createSphere());
- auto callback = new SoEventCallback();
+ const auto callback = new SoEventCallback();
root->addChild(callback);
callback->addEventCallback(SoEvent::getClassTypeId(),
- [] (void* ud, SoEventCallback* cb) {
- Q_UNUSED(ud)
- cb->setHandled();
- });
+ []([[maybe_unused]] void* ud, SoEventCallback* cb) {
+ cb->setHandled();
+ });
view->setCameraType(SoOrthographicCamera::getClassTypeId());
- view->setViewDirection(default_view_direction);
+ view->setViewDirection(defaultViewDirection);
view->viewAll();
- camera = dynamic_cast (view->getCamera());
- const float camera_height = camera->height.getValue() * 2.0f;
- camera->height = camera_height;
- cam_step = camera_height / 14.0f;
- // NOLINTEND
+ camera = dynamic_cast(view->getCamera());
+ const float cameraHeight = camera->height.getValue() * 2.0f;
+ camera->height = cameraHeight;
+ zoomStep = cameraHeight / 14.0f;
}
-SoDirectionalLightDragger* DlgSettingsLightSources::createDragger()
+Base::Vector3d DlgSettingsLightSources::azimuthElevationToDirection(double azimuth,
+ double elevation)
{
- // NOLINTBEGIN
- lightDragger = new SoDirectionalLightDragger();
- if (SoDragger* translator = dynamic_cast(lightDragger->getPart("translator", false))) {
- translator->setPartAsDefault("xTranslator.translatorActive", nullptr);
- translator->setPartAsDefault("yTranslator.translatorActive", nullptr);
- translator->setPartAsDefault("zTranslator.translatorActive", nullptr);
- translator->setPartAsDefault("xTranslator.translator", nullptr);
- translator->setPartAsDefault("yTranslator.translator", nullptr);
- translator->setPartAsDefault("zTranslator.translator", nullptr);
- SoNode* node = translator->getPart("yzTranslator.translator", false);
- if (node && node->isOfType(SoGroup::getClassTypeId())) {
- auto ps = new SoPickStyle();
- ps->style = SoPickStyle::UNPICKABLE;
- static_cast(node)->insertChild(ps, 0);
- }
- }
+ azimuth = Base::toRadians(azimuth);
+ elevation = Base::toRadians(elevation);
- lightDragger->addMotionCallback(dragMotionCallback, this);
- return lightDragger;
- // NOLINTEND
+ auto direction = Base::Vector3d {std::sin(azimuth) * std::cos(elevation),
+ std::cos(azimuth) * std::cos(elevation),
+ std::sin(elevation)};
+
+ direction.Normalize();
+
+ return direction;
+}
+
+std::pair
+DlgSettingsLightSources::directionToAzimuthElevation(Base::Vector3d direction)
+{
+ const auto azimuth = std::atan2(direction[0], direction[1]);
+ const auto elevation =
+ std::atan2(direction[2],
+ std::sqrt(direction[1] * direction[1] + direction[0] * direction[0]));
+
+ return {Base::toDegrees(azimuth), Base::toDegrees(elevation)};
}
void DlgSettingsLightSources::saveSettings()
{
- ui->checkBoxLight1->onSave();
- ui->light1Color->onSave();
- ui->sliderIntensity1->onSave();
- saveDirection();
+ for (const auto& widget : findChildren()) {
+ if (const auto pref = dynamic_cast(widget)) {
+ pref->onSave();
+ }
+ }
+
+ const auto saveAngles = [&](QuantitySpinBox* horizontalAngleSpinBox,
+ QuantitySpinBox* verticalAngleSpinBox,
+ const char* parameter) {
+ try {
+ const auto direction = azimuthElevationToDirection(horizontalAngleSpinBox->rawValue(),
+ verticalAngleSpinBox->rawValue());
+
+ hGrp->SetASCII(parameter,
+ Base::vectorToString(Base::convertTo(direction)));
+ }
+ catch (...) {
+ }
+ };
+
+ saveAngles(ui->mainLightHorizontalAngle, ui->mainLightVerticalAngle, "HeadlightDirection");
+ saveAngles(ui->backLightHorizontalAngle, ui->backLightVerticalAngle, "BacklightDirection");
+ saveAngles(ui->fillLightHorizontalAngle, ui->fillLightVerticalAngle, "FillLightDirection");
}
void DlgSettingsLightSources::loadSettings()
{
- ui->checkBoxLight1->onRestore();
- ui->light1Color->onRestore();
- ui->sliderIntensity1->onRestore();
- loadDirection();
- lightColor();
+ for (const auto& widget : findChildren()) {
+ if (const auto pref = dynamic_cast(widget)) {
+ pref->onRestore();
+ }
+ }
+
+ const auto loadAngles = [&](QuantitySpinBox* horizontalAngleSpinBox,
+ QuantitySpinBox* verticalAngleSpinBox,
+ const char* parameter) {
+ try {
+ const auto direction = Base::stringToVector(hGrp->GetASCII(parameter));
+ const auto [azimuth, elevation] =
+ directionToAzimuthElevation(Base::convertTo(direction));
+
+ horizontalAngleSpinBox->setValue(azimuth);
+ verticalAngleSpinBox->setValue(elevation);
+ }
+ catch (...) {
+ }
+ };
+
+ loadAngles(ui->mainLightHorizontalAngle, ui->mainLightVerticalAngle, "HeadlightDirection");
+ loadAngles(ui->backLightHorizontalAngle, ui->backLightVerticalAngle, "BacklightDirection");
+ loadAngles(ui->fillLightHorizontalAngle, ui->fillLightVerticalAngle, "FillLightDirection");
}
void DlgSettingsLightSources::resetSettingsToDefaults()
{
- ParameterGrp::handle grp = ui->sliderIntensity1->getWindowParameter();
-
- grp->SetFloat("HeadlightRotationX", 0.0);
- grp->SetFloat("HeadlightRotationY", 0.0);
- grp->SetFloat("HeadlightRotationZ", 0.0);
- grp->SetFloat("HeadlightRotationW", 1.0);
-
- grp->SetASCII("HeadlightDirection", "(0.0,0.0,-1.0)");
-
PreferencePage::resetSettingsToDefaults();
+
+ loadSettings();
+ configureViewer();
}
-void DlgSettingsLightSources::saveDirection()
+void DlgSettingsLightSources::zoomIn() const
{
- if (lightDragger) {
- const SbRotation rotation = lightDragger->rotation.getValue();
- const SbVec3f dir = getDirectionVector(rotation);
- const QString headlightDir = QStringLiteral("(%1,%2,%3)").arg(dir[0]).arg(dir[1]).arg(dir[2]);
-
- ParameterGrp::handle grp = ui->sliderIntensity1->getWindowParameter();
-
- grp->SetFloat("HeadlightRotationX", rotation[0]);
- grp->SetFloat("HeadlightRotationY", rotation[1]);
- grp->SetFloat("HeadlightRotationZ", rotation[2]);
- grp->SetFloat("HeadlightRotationW", rotation[3]);
-
- grp->SetASCII("HeadlightDirection", qPrintable(headlightDir));
- }
-}
-
-void DlgSettingsLightSources::loadDirection()
-{
- ParameterGrp::handle grp = ui->sliderIntensity1->getWindowParameter();
- SbRotation rotation = lightDragger->rotation.getValue();
-
- auto get_q = [&grp](const char *name, const float def){return static_cast (grp->GetFloat(name, def));};
-
- const float q0 = get_q("HeadlightRotationX", rotation[0]),
- q1 = get_q("HeadlightRotationY", rotation[1]),
- q2 = get_q("HeadlightRotationZ", rotation[2]),
- q3 = get_q("HeadlightRotationW", rotation[3]);
-
- rotation.setValue(q0, q1, q2, q3);
-
- setLightDirection(rotation, ui->viewer);
- setLightDraggerDirection(rotation, lightDragger);
-
- setValueSilently(ui->q0_spnBox, rotation[0]);
- setValueSilently(ui->q1_spnBox, rotation[1]);
- setValueSilently(ui->q2_spnBox, rotation[2]);
- setValueSilently(ui->q3_spnBox, rotation[3]);
-
- const SbVec3f dir = getDirectionVector(rotation);
-
- setValueSilently(ui->x_spnBox, dir[0]);
- setValueSilently(ui->y_spnBox, dir[1]);
- setValueSilently(ui->z_spnBox, dir[2]);
-}
-
-void DlgSettingsLightSources::toggleLight(bool on)
-{
- if (view) {
- view->setHeadlightEnabled(on);
- }
-}
-
-void DlgSettingsLightSources::lightIntensity(int value)
-{
- if (view) {
- view->getHeadlight()->intensity = static_cast (value) / 100.0f;
- }
-}
-
-void DlgSettingsLightSources::lightColor()
-{
- if (view) {
- const QColor color = ui->light1Color->color();
- view->getHeadlight()->color.setValue(color.redF(),
- color.greenF(),
- color.blueF());
- }
-}
-
-void DlgSettingsLightSources::pushIn(void)
-{
- if (camera == nullptr)
+ if (camera == nullptr) {
return;
+ }
- camera->height = camera->height.getValue() - cam_step;
+ camera->height = camera->height.getValue() - zoomStep;
}
-void DlgSettingsLightSources::pullOut(void)
+void DlgSettingsLightSources::zoomOut() const
{
- if (camera == nullptr)
+ if (camera == nullptr) {
return;
+ }
- camera->height = camera->height.getValue() + cam_step;
+ camera->height = camera->height.getValue() + zoomStep;
}
void DlgSettingsLightSources::changeEvent(QEvent* event)
@@ -323,41 +357,4 @@ void DlgSettingsLightSources::changeEvent(QEvent* event)
PreferencePage::changeEvent(event);
}
-void DlgSettingsLightSources::updateDraggerQS()
-{
- const float q0 = ui->q0_spnBox->value(),
- q1 = ui->q1_spnBox->value(),
- q2 = ui->q2_spnBox->value(),
- q3 = ui->q3_spnBox->value();
-
- const SbRotation rotation {q0, q1, q2, q3};
-
- setLightDirection(rotation, view);
- setLightDraggerDirection(rotation, lightDragger);
-
- const SbVec3f dir = getDirectionVector(rotation);
-
- setValueSilently(ui->x_spnBox, dir[0]);
- setValueSilently(ui->y_spnBox, dir[1]);
- setValueSilently(ui->z_spnBox, dir[2]);
-}
-
-void DlgSettingsLightSources::updateDraggerXYZ()
-{
- const float x = ui->x_spnBox->value(),
- y = ui->y_spnBox->value(),
- z = ui->z_spnBox->value();
-
- const SbRotation rotation {SbVec3f{0.0f, 0.0f, -1.0f}, SbVec3f{x, y, z}};
-
- setLightDirection(rotation, view);
- setLightDraggerDirection(rotation, lightDragger);
-
- setValueSilently(ui->q0_spnBox, rotation[0]);
- setValueSilently(ui->q1_spnBox, rotation[1]);
- setValueSilently(ui->q2_spnBox, rotation[2]);
- setValueSilently(ui->q3_spnBox, rotation[3]);
-}
-
-
#include "moc_DlgSettingsLightSources.cpp"
diff --git a/src/Gui/PreferencePages/DlgSettingsLightSources.h b/src/Gui/PreferencePages/DlgSettingsLightSources.h
index 60145bf42b..2e1e1bd9de 100644
--- a/src/Gui/PreferencePages/DlgSettingsLightSources.h
+++ b/src/Gui/PreferencePages/DlgSettingsLightSources.h
@@ -28,8 +28,12 @@
#include
#include
#include
+#include
+#include
+#include
class SoDragger;
+class SbRotation;
class SoDirectionalLightDragger;
class SoOrthographicCamera;
@@ -56,32 +60,26 @@ public:
void resetSettingsToDefaults() override;
public Q_SLOTS:
- void updateDraggerQS ();
- void updateDraggerXYZ();
- void toggleLight(bool on);
- void lightIntensity(int value);
- void lightColor();
-
- void pushIn (void);
- void pullOut(void);
+ void zoomIn() const;
+ void zoomOut() const;
protected:
void changeEvent(QEvent* event) override;
private:
- void saveDirection();
- void loadDirection();
- void createViewer();
- SoDirectionalLightDragger* createDragger();
- static void dragMotionCallback(void *data, SoDragger *drag);
+ void configureViewer();
+
+ Base::Vector3d azimuthElevationToDirection(double azimuth, double elevation);
+ std::pair directionToAzimuthElevation(Base::Vector3d direction);
private:
std::unique_ptr ui;
QPointer view;
- SoDirectionalLightDragger* lightDragger = nullptr;
SoOrthographicCamera *camera = nullptr;
- float cam_step = 3.0f;
+ ParameterGrp::handle hGrp = App::GetApplication().GetParameterGroupByPath("User parameter:BaseApp/Preferences/View");
+
+ float zoomStep = 3.0f;
};
} // namespace Dialog
diff --git a/src/Gui/PreferencePages/DlgSettingsLightSources.ui b/src/Gui/PreferencePages/DlgSettingsLightSources.ui
index 00c3eaad27..6c09e0ec81 100644
--- a/src/Gui/PreferencePages/DlgSettingsLightSources.ui
+++ b/src/Gui/PreferencePages/DlgSettingsLightSources.ui
@@ -6,7 +6,7 @@
0
0
- 484
+ 743
515
@@ -26,141 +26,10 @@
Adjust the orientation of the directional light source by dragging the handle with the mouse or use the spin boxes for fine tuning.
- Direction
+ Preview
- -
-
-
- -100.000000000000000
-
-
- 0.100000000000000
-
-
-
- -
-
-
- -100.000000000000000
-
-
- 0.100000000000000
-
-
-
- -
-
-
- z
-
-
-
- -
-
-
- x
-
-
-
- -
-
-
- 2
-
-
- -100.000000000000000
-
-
- 0.100000000000000
-
-
-
- -
-
-
- 2
-
-
- -100.000000000000000
-
-
- 0.100000000000000
-
-
-
- -
-
-
- 2
-
-
- -100.000000000000000
-
-
- 0.100000000000000
-
-
-
- -
-
-
- y
-
-
-
- -
-
-
- q2
-
-
-
- -
-
-
- q0
-
-
-
- -
-
-
- 2
-
-
- -100.000000000000000
-
-
- 0.100000000000000
-
-
-
- -
-
-
- q1
-
-
-
- -
-
-
- q3
-
-
-
- -
-
-
- -100.000000000000000
-
-
- 0.100000000000000
-
-
-
- -
+
-
@@ -169,7 +38,7 @@
- Qt::NoFocus
+ Qt::FocusPolicy::NoFocus
@@ -183,7 +52,7 @@
-
- Qt::Vertical
+ Qt::Orientation::Vertical
@@ -194,9 +63,9 @@
-
-
+
- Qt::NoFocus
+ Qt::FocusPolicy::NoFocus
Push In
@@ -214,9 +83,9 @@
-
-
+
- Qt::NoFocus
+ Qt::FocusPolicy::NoFocus
Pull Out
@@ -238,7 +107,7 @@
-
- Qt::Horizontal
+ Qt::Orientation::Horizontal
@@ -254,16 +123,72 @@
+ -
+
+
+ Qt::Orientation::Vertical
+
+
+
+ 20
+ 40
+
+
+
+
-
Light sources
-
-
-
+
-
+
- Light source
+ Color
+
+
+
+ -
+
+
+ %
+
+
+ 100
+
+
+ 20
+
+
+ AmbientLightIntensity
+
+
+ View
+
+
+
+ -
+
+
+
+ 245
+ 245
+ 238
+
+
+
+ BacklightColor
+
+
+ View
+
+
+
+ -
+
+
+ Main Light
true
@@ -276,9 +201,226 @@
- -
-
-
+
-
+
+
+
+
+
+ -130.000000000000000
+
+
+
+ -
+
+
+
+
+
+ -10.000000000000000
+
+
+
+ -
+
+
+ Back Light
+
+
+ true
+
+
+ EnableBacklight
+
+
+ View
+
+
+
+ -
+
+
+
+
+
+ -40.000000000000000
+
+
+
+ -
+
+
+ Vertical Angle
+
+
+
+ -
+
+
+
+ 255
+ 255
+ 255
+
+
+
+ AmbientLightColor
+
+
+ View
+
+
+
+ -
+
+
+ Horizontal Angle
+
+
+
+ -
+
+
+ %
+
+
+ 100
+
+
+ 90
+
+
+ HeadlightIntensity
+
+
+ View
+
+
+
+ -
+
+
+
+
+
+ 100.000000000000000
+
+
+
+ -
+
+
+
+
+
+ 5.000000000000000
+
+
+
+ -
+
+
+ %
+
+
+ 100
+
+
+ 60
+
+
+ BacklightIntensity
+
+
+ View
+
+
+
+ -
+
+
+ Fill Light
+
+
+ true
+
+
+ EnableFillLight
+
+
+ View
+
+
+
+ -
+
+
+ %
+
+
+ 100
+
+
+ 40
+
+
+ FillLightIntensity
+
+
+ View
+
+
+
+ -
+
+
+ Intensity
+
+
+
+ -
+
+
+ Qt::Orientation::Horizontal
+
+
+
+ 40
+ 20
+
+
+
+
+ -
+
+
+
+ 230
+ 250
+ 255
+
+
+
+ FillLightColor
+
+
+ View
+
+
+
+ -
+
+
+
+
+
+ -46.000000000000000
+
+
+
+ -
+
+
255
255
@@ -293,83 +435,37 @@
- -
-
-
- Qt::Horizontal
-
-
-
- 115
- 13
-
-
-
-
- -
-
+
-
+
- Intensity
-
-
-
- -
-
-
- 100
-
-
- 100
-
-
- Qt::Horizontal
-
-
- QSlider::TicksBelow
-
-
- 10
-
-
- HeadlightIntensity
-
-
- View
+ Ambient Light
- -
-
-
- Qt::Vertical
-
-
-
- 20
- 40
-
-
-
-
+
+ Gui::QuantitySpinBox
+ QAbstractSpinBox
+
+
Gui::ColorButton
QPushButton
- Gui::PrefColorButton
- Gui::ColorButton
+ Gui::PrefSpinBox
+ QSpinBox
- Gui::PrefSlider
- QSlider
+ Gui::PrefColorButton
+ Gui::ColorButton
@@ -384,262 +480,28 @@
- checkBoxLight1
- light1Color
- sliderIntensity1
- x_spnBox
- y_spnBox
- z_spnBox
- q0_spnBox
- q1_spnBox
- q2_spnBox
- q3_spnBox
+ mainLightEnable
+ mainLightHorizontalAngle
+ mainLightVerticalAngle
+ mainLightColor
+ mainLightIntensitySpinBox
+ backLightEnable
+ backLightHorizontalAngle
+ backLightVerticalAngle
+ backLightColor
+ backLightIntensitySpinBox
+ fillLightEnable
+ fillLightHorizontalAngle
+ fillLightVerticalAngle
+ fillLightColor
+ fillLightIntensitySpinBox
+ ambientLightColor
+ ambientLightIntensitySpinBox
-
-
- checkBoxLight1
- toggled(bool)
- light1Color
- setEnabled(bool)
-
-
- 73
- 53
-
-
- 150
- 53
-
-
-
-
- checkBoxLight1
- toggled(bool)
- light1Label
- setEnabled(bool)
-
-
- 73
- 53
-
-
- 339
- 65
-
-
-
-
- checkBoxLight1
- toggled(bool)
- sliderIntensity1
- setEnabled(bool)
-
-
- 73
- 53
-
-
- 357
- 53
-
-
-
-
- q1_spnBox
- valueChanged(double)
- Gui::Dialog::DlgSettingsLightSources
- updateDraggerQS(void)
-
-
- 399
- 168
-
-
- 20
- 20
-
-
-
-
- q2_spnBox
- valueChanged(double)
- Gui::Dialog::DlgSettingsLightSources
- updateDraggerQS(void)
-
-
- 399
- 200
-
-
- 20
- 20
-
-
-
-
- q3_spnBox
- valueChanged(double)
- Gui::Dialog::DlgSettingsLightSources
- updateDraggerQS(void)
-
-
- 399
- 232
-
-
- 20
- 20
-
-
-
-
- q0_spnBox
- valueChanged(double)
- Gui::Dialog::DlgSettingsLightSources
- updateDraggerQS(void)
-
-
- 422
- 128
-
-
- 241
- 257
-
-
-
-
- checkBoxLight1
- toggled(bool)
- Gui::Dialog::DlgSettingsLightSources
- toggleLight(bool)
-
-
- 68
- 53
-
-
- 241
- 257
-
-
-
-
- sliderIntensity1
- valueChanged(int)
- Gui::Dialog::DlgSettingsLightSources
- lightIntensity(int)
-
-
- 404
- 52
-
-
- 241
- 257
-
-
-
-
- light1Color
- changed(void)
- Gui::Dialog::DlgSettingsLightSources
- lightColor(void)
-
-
- 140
- 53
-
-
- 241
- 257
-
-
-
-
- x_spnBox
- valueChanged(double)
- Gui::Dialog::DlgSettingsLightSources
- updateDraggerXYZ(void)
-
-
- 186
- 141
-
-
- 241
- 257
-
-
-
-
- y_spnBox
- valueChanged(double)
- Gui::Dialog::DlgSettingsLightSources
- updateDraggerXYZ(void)
-
-
- 186
- 173
-
-
- 241
- 257
-
-
-
-
- z_spnBox
- valueChanged(double)
- Gui::Dialog::DlgSettingsLightSources
- updateDraggerXYZ(void)
-
-
- 186
- 205
-
-
- 241
- 257
-
-
-
-
- pushInTB
- clicked()
- Gui::Dialog::DlgSettingsLightSources
- pushIn(void)
-
-
- 126
- 224
-
-
- 241
- 257
-
-
-
-
- pullOutTB
- clicked()
- Gui::Dialog::DlgSettingsLightSources
- pullOut(void)
-
-
- 126
- 255
-
-
- 241
- 257
-
-
-
-
+
updateDraggerQS(void)
updateDraggerXYZ(void)
diff --git a/src/Gui/Utilities.h b/src/Gui/Utilities.h
index 42079bf1e1..3cc2333eca 100644
--- a/src/Gui/Utilities.h
+++ b/src/Gui/Utilities.h
@@ -24,6 +24,7 @@
#define GUI_UTILITIES_H
#include
+#include
#include
#include
#include
@@ -33,7 +34,6 @@
#include
#include
-
class SbViewVolume;
class QAbstractItemView;
@@ -105,6 +105,18 @@ private:
const vec_type& v;
};
+template <>
+struct vec_traits {
+ using vec_type = QColor;
+ using float_type = float;
+ explicit vec_traits(const vec_type& v) : v(v){}
+ inline std::tuple get() const {
+ return std::make_tuple(v.redF(), v.greenF(), v.blueF());
+ }
+private:
+ const vec_type& v;
+};
+
template <>
inline SbMatrix convertTo(const Base::Matrix4D& vec2)
{
diff --git a/src/Gui/View3DInventorViewer.cpp b/src/Gui/View3DInventorViewer.cpp
index 00bc181768..10816de6e1 100644
--- a/src/Gui/View3DInventorViewer.cpp
+++ b/src/Gui/View3DInventorViewer.cpp
@@ -130,6 +130,8 @@
#include "Navigation/NavigationAnimation.h"
#include "Utilities.h"
+#include
+#include
#include
@@ -435,12 +437,25 @@ void View3DInventorViewer::init()
// setup light sources
SoDirectionalLight* hl = this->getHeadlight();
+
+ environment = new SoEnvironment();
+ environment->ref();
+ environment->setName("environment");
+
backlight = new SoDirectionalLight();
backlight->ref();
backlight->setName("backlight");
backlight->direction.setValue(-hl->direction.getValue());
backlight->on.setValue(false); // by default off
+ fillLight = new SoDirectionalLight();
+ fillLight->ref();
+ fillLight->setName("filllight");
+ fillLight->direction.setValue(-0.60, -0.35, -0.79);
+ fillLight->intensity.setValue(0.6);
+ fillLight->color.setValue(0.95, 0.95, 1.0);
+ fillLight->on.setValue(false); // by default off
+
// Set up background scenegraph with image in it.
backgroundroot = new SoSeparator;
backgroundroot->ref();
@@ -470,10 +485,20 @@ void View3DInventorViewer::init()
cam->farDistance = 10;
// NOLINTEND
+ lightRotation = new SoRotation;
+ lightRotation->ref();
+ lightRotation->rotation.connectFrom(&cam->orientation);
+
this->foregroundroot->addChild(cam);
this->foregroundroot->addChild(lm);
this->foregroundroot->addChild(bc);
+ auto threePointLightingSeparator = new SoTransformSeparator;
+ threePointLightingSeparator->addChild(lightRotation);
+ threePointLightingSeparator->addChild(this->fillLight);
+
+ this->foregroundroot->addChild(cam);
+
// NOTE: For every mouse click event the SoFCUnifiedSelection searches for the picked
// point which causes a certain slow-down because for all objects the primitives
// must be created. Using an SoSeparator avoids this drawback.
@@ -482,6 +507,8 @@ void View3DInventorViewer::init()
// set the ViewProvider root node
pcViewProviderRoot = selectionRoot;
+ pcViewProviderRoot->addChild(threePointLightingSeparator);
+ pcViewProviderRoot->addChild(environment);
// increase refcount before passing it to setScenegraph(), to avoid
// premature destruction
@@ -633,6 +660,10 @@ View3DInventorViewer::~View3DInventorViewer()
this->objectGroup = nullptr;
this->backlight->unref();
this->backlight = nullptr;
+ this->fillLight->unref();
+ this->fillLight = nullptr;
+ this->environment->unref();
+ this->environment = nullptr;
inventorSelection.reset(nullptr);
@@ -1545,6 +1576,25 @@ bool View3DInventorViewer::isBacklightEnabled() const
return this->backlight->on.getValue();
}
+SoDirectionalLight* View3DInventorViewer::getFillLight() const
+{
+ return this->fillLight;
+}
+
+void View3DInventorViewer::setFillLightEnabled(bool on)
+{
+ this->fillLight->on = on;
+}
+
+bool View3DInventorViewer::isFillLightEnabled() const
+{
+ return this->fillLight->on.getValue();
+}
+SoEnvironment* View3DInventorViewer::getEnvironment() const
+{
+ return this->environment;
+}
+
void View3DInventorViewer::setSceneGraph(SoNode* root)
{
inherited::setSceneGraph(root);
@@ -3175,18 +3225,22 @@ void View3DInventorViewer::setCameraType(SoType type)
{
inherited::setCameraType(type);
+ SoCamera* cam = this->getSoRenderManager()->getCamera();
+
+ if (!cam) {
+ return;
+ }
+
if (type.isDerivedFrom(SoPerspectiveCamera::getClassTypeId())) {
// When doing a viewAll() for an orthographic camera and switching
// to perspective the scene looks completely strange because of the
// heightAngle. Setting it to 45 deg also causes an issue with a too
// close camera but we don't have this other ugly effect.
- SoCamera* cam = this->getSoRenderManager()->getCamera();
- if (!cam) {
- return;
- }
static_cast(cam)->heightAngle = (float)(M_PI / 4.0); // NOLINT
}
+
+ lightRotation->rotation.connectFrom(&cam->orientation);
}
void View3DInventorViewer::moveCameraTo(const SbRotation& orientation, const SbVec3f& position, int duration)
diff --git a/src/Gui/View3DInventorViewer.h b/src/Gui/View3DInventorViewer.h
index e7c1e867fc..69b7bdbd46 100644
--- a/src/Gui/View3DInventorViewer.h
+++ b/src/Gui/View3DInventorViewer.h
@@ -46,6 +46,9 @@
#include "View3DInventorSelection.h"
#include "Quarter/SoQTQuarterAdaptor.h"
+#include
+#include
+
class SoTranslation;
class SoTransform;
@@ -146,6 +149,13 @@ public:
SoDirectionalLight* getBacklight() const;
void setBacklightEnabled(bool on);
bool isBacklightEnabled() const;
+
+ SoDirectionalLight* getFillLight() const;
+ void setFillLightEnabled(bool on);
+ bool isFillLightEnabled() const;
+
+ SoEnvironment* getEnvironment() const;
+
void setSceneGraph (SoNode *root) override;
bool searchNode(SoNode*) const;
@@ -496,7 +506,12 @@ private:
SoFCBackgroundGradient *pcBackGround;
SoSeparator * backgroundroot;
SoSeparator * foregroundroot;
+
SoDirectionalLight* backlight;
+ SoDirectionalLight* fillLight;
+ SoEnvironment* environment;
+
+ SoRotation* lightRotation;
// Scene graph root
SoSeparator * pcViewProviderRoot;
diff --git a/src/Gui/View3DSettings.cpp b/src/Gui/View3DSettings.cpp
index 80ae157cbd..287b4d6d77 100644
--- a/src/Gui/View3DSettings.cpp
+++ b/src/Gui/View3DSettings.cpp
@@ -38,6 +38,8 @@
#include "View3DSettings.h"
#include "View3DInventorViewer.h"
+#include
+
using namespace Gui;
View3DSettings::View3DSettings(ParameterGrp::handle hGrp,
@@ -100,6 +102,12 @@ void View3DSettings::applySettings()
OnChange(*hGrp,"BacklightColor");
OnChange(*hGrp,"BacklightDirection");
OnChange(*hGrp,"BacklightIntensity");
+ OnChange(*hGrp,"EnableFillLight");
+ OnChange(*hGrp,"FillLightColor");
+ OnChange(*hGrp,"FillLightDirection");
+ OnChange(*hGrp,"FillLightIntensity");
+ OnChange(*hGrp,"AmbientLightColor");
+ OnChange(*hGrp,"AmbientLightIntensity");
OnChange(*hGrp,"NavigationStyle");
OnChange(*hGrp,"OrbitStyle");
OnChange(*hGrp,"Sensitivity");
@@ -121,7 +129,7 @@ void View3DSettings::OnChange(ParameterGrp::SubjectType &rCaller,ParameterGrp::M
}
}
else if (strcmp(Reason,"HeadlightColor") == 0) {
- unsigned long headlight = rGrp.GetUnsigned("HeadlightColor",ULONG_MAX); // default color (white)
+ unsigned long headlight = rGrp.GetUnsigned("HeadlightColor", 0xFFFFFFFF); // default color (white)
float transparency;
SbColor headlightColor;
headlightColor.setPackedValue((uint32_t)headlight, transparency);
@@ -131,9 +139,9 @@ void View3DSettings::OnChange(ParameterGrp::SubjectType &rCaller,ParameterGrp::M
}
else if (strcmp(Reason,"HeadlightDirection") == 0) {
try {
- std::string pos = rGrp.GetASCII("HeadlightDirection");
+ std::string pos = rGrp.GetASCII("HeadlightDirection", defaultHeadLightDirection);
if (!pos.empty()) {
- Base::Vector3f dir = Base::to_vector(pos);
+ Base::Vector3f dir = Base::stringToVector(pos);
for (auto _viewer : _viewers) {
_viewer->getHeadlight()->direction.setValue(dir.x, dir.y, dir.z);
}
@@ -144,18 +152,18 @@ void View3DSettings::OnChange(ParameterGrp::SubjectType &rCaller,ParameterGrp::M
}
}
else if (strcmp(Reason,"HeadlightIntensity") == 0) {
- long value = rGrp.GetInt("HeadlightIntensity", 100);
+ long value = rGrp.GetInt("HeadlightIntensity", 90);
for (auto _viewer : _viewers) {
- _viewer->getHeadlight()->intensity.setValue((float)value/100.0f);
+ _viewer->getHeadlight()->intensity.setValue(Base::fromPercent(value));
}
}
else if (strcmp(Reason,"EnableBacklight") == 0) {
for (auto _viewer : _viewers) {
- _viewer->setBacklightEnabled(rGrp.GetBool("EnableBacklight", false));
+ _viewer->setBacklightEnabled(rGrp.GetBool("EnableBacklight", true));
}
}
else if (strcmp(Reason,"BacklightColor") == 0) {
- unsigned long backlight = rGrp.GetUnsigned("BacklightColor",ULONG_MAX); // default color (white)
+ unsigned long backlight = rGrp.GetUnsigned("BacklightColor", 0xF5F5EEFF);
float transparency;
SbColor backlightColor;
backlightColor.setPackedValue((uint32_t)backlight, transparency);
@@ -165,9 +173,9 @@ void View3DSettings::OnChange(ParameterGrp::SubjectType &rCaller,ParameterGrp::M
}
else if (strcmp(Reason,"BacklightDirection") == 0) {
try {
- std::string pos = rGrp.GetASCII("BacklightDirection");
+ std::string pos = rGrp.GetASCII("BacklightDirection", defaultBackLightDirection);
if (!pos.empty()) {
- Base::Vector3f dir = Base::to_vector(pos);
+ Base::Vector3f dir = Base::stringToVector(pos);
for (auto _viewer : _viewers) {
_viewer->getBacklight()->direction.setValue(dir.x, dir.y, dir.z);
}
@@ -178,9 +186,58 @@ void View3DSettings::OnChange(ParameterGrp::SubjectType &rCaller,ParameterGrp::M
}
}
else if (strcmp(Reason,"BacklightIntensity") == 0) {
- long value = rGrp.GetInt("BacklightIntensity", 100);
+ long value = rGrp.GetInt("BacklightIntensity", 60);
for (auto _viewer : _viewers) {
- _viewer->getBacklight()->intensity.setValue((float)value/100.0f);
+ _viewer->getBacklight()->intensity.setValue(Base::fromPercent(value));
+ }
+ }
+ else if (strcmp(Reason,"EnableFillLight") == 0) {
+ for (auto _viewer : _viewers) {
+ _viewer->setFillLightEnabled(rGrp.GetBool("EnableFillLight", true));
+ }
+ }
+ else if (strcmp(Reason,"FillLightColor") == 0) {
+ unsigned long backlight = rGrp.GetUnsigned("FillLightColor", 0xE6FAFFFF); // default color (white)
+ float transparency;
+ SbColor backlightColor;
+ backlightColor.setPackedValue((uint32_t)backlight, transparency);
+ for (auto _viewer : _viewers) {
+ _viewer->getFillLight()->color.setValue(backlightColor);
+ }
+ }
+ else if (strcmp(Reason,"FillLightDirection") == 0) {
+ try {
+ std::string pos = rGrp.GetASCII("FillLightDirection", defaultFillLightDirection);
+ if (!pos.empty()) {
+ Base::Vector3f dir = Base::stringToVector(pos);
+ for (auto _viewer : _viewers) {
+ _viewer->getFillLight()->direction.setValue(dir.x, dir.y, dir.z);
+ }
+ }
+ }
+ catch (const std::exception&) {
+ // ignore exception
+ }
+ }
+ else if (strcmp(Reason,"FillLightIntensity") == 0) {
+ long value = rGrp.GetInt("FillLightIntensity", 40);
+ for (auto _viewer : _viewers) {
+ _viewer->getFillLight()->intensity.setValue(Base::fromPercent(value));
+ }
+ }
+ else if (strcmp(Reason,"AmbientLightColor") == 0) {
+ unsigned long color = rGrp.GetUnsigned("AmbientLightColor", 0xFFFFFFFF);
+ float transparency;
+ SbColor backlightColor;
+ backlightColor.setPackedValue((uint32_t)color, transparency);
+ for (auto _viewer : _viewers) {
+ _viewer->getEnvironment()->ambientColor.setValue(backlightColor);
+ }
+ }
+ else if (strcmp(Reason,"AmbientLightIntensity") == 0) {
+ long value = rGrp.GetInt("AmbientLightIntensity", 20);
+ for (auto _viewer : _viewers) {
+ _viewer->getEnvironment()->ambientIntensity.setValue(Base::fromPercent(value));
}
}
else if (strcmp(Reason,"EnablePreselection") == 0) {
diff --git a/src/Gui/View3DSettings.h b/src/Gui/View3DSettings.h
index 4c3798f077..0bc7f3af6d 100644
--- a/src/Gui/View3DSettings.h
+++ b/src/Gui/View3DSettings.h
@@ -33,6 +33,10 @@ class View3DInventorViewer;
class GuiExport View3DSettings: public ParameterGrp::ObserverType
{
public:
+ static constexpr auto defaultHeadLightDirection = "(0.6841049,-0.12062616,-0.7193398)";
+ static constexpr auto defaultFillLightDirection = "(-0.6403416,0.7631294,0.087155744)";
+ static constexpr auto defaultBackLightDirection = "(-0.7544065,-0.63302225,-0.17364818)";
+
View3DSettings(ParameterGrp::handle hGrp, View3DInventorViewer*);
View3DSettings(ParameterGrp::handle hGrp, const std::vector&);
~View3DSettings() override;
diff --git a/src/Gui/ViewProviderGeometryObject.cpp b/src/Gui/ViewProviderGeometryObject.cpp
index e585a4ed60..73889f5e5c 100644
--- a/src/Gui/ViewProviderGeometryObject.cpp
+++ b/src/Gui/ViewProviderGeometryObject.cpp
@@ -49,21 +49,10 @@
#include "ViewProviderGeometryObject.h"
#include "ViewProviderGeometryObjectPy.h"
+#include
+
using namespace Gui;
-// Helper functions to consistently convert between float and long
-namespace {
-float fromPercent(long value)
-{
- return std::roundf(value) / 100.0F;
-}
-
-long toPercent(float value)
-{
- return std::lround(100.0 * value);
-}
-}
-
PROPERTY_SOURCE(Gui::ViewProviderGeometryObject, Gui::ViewProviderDragger)
const App::PropertyIntegerConstraint::Constraints intPercent = {0, 100, 5};
@@ -71,7 +60,8 @@ const App::PropertyIntegerConstraint::Constraints intPercent = {0, 100, 5};
ViewProviderGeometryObject::ViewProviderGeometryObject()
{
App::Material mat = App::Material::getDefaultAppearance();
- long initialTransparency = toPercent(mat.transparency);
+
+ long initialTransparency = Base::toPercent(mat.transparency);
static const char* dogroup = "Display Options";
static const char* sgroup = "Selection";
@@ -140,8 +130,8 @@ void ViewProviderGeometryObject::onChanged(const App::Property* prop)
setSelectable(Sel);
}
else if (prop == &Transparency) {
- long value = toPercent(ShapeAppearance.getTransparency());
- float trans = fromPercent(Transparency.getValue());
+ long value = Base::toPercent(ShapeAppearance.getTransparency());
+ float trans = Base::fromPercent(Transparency.getValue());
if (value != Transparency.getValue()) {
ShapeAppearance.setTransparency(trans);
}
@@ -152,7 +142,7 @@ void ViewProviderGeometryObject::onChanged(const App::Property* prop)
if (getObject() && getObject()->testStatus(App::ObjectStatus::TouchOnColorChange)) {
getObject()->touch(true);
}
- long value = toPercent(ShapeAppearance.getTransparency());
+ long value = Base::toPercent(ShapeAppearance.getTransparency());
if (value != Transparency.getValue()) {
Transparency.setValue(value);
}
diff --git a/src/Gui/propertyeditor/PropertyItem.cpp b/src/Gui/propertyeditor/PropertyItem.cpp
index c619e6e891..9769db88a8 100644
--- a/src/Gui/propertyeditor/PropertyItem.cpp
+++ b/src/Gui/propertyeditor/PropertyItem.cpp
@@ -71,17 +71,6 @@ namespace
{
constexpr const int lowPrec = 2;
constexpr const int highPrec = 16;
-
-int toPercent(float value)
-{
- return static_cast(100 * value); // NOLINT
-}
-
-float fromPercent(int value)
-{
- return static_cast(value) / 100.0F; // NOLINT
-}
-
} // namespace
PropertyItemFactory& PropertyItemFactory::instance()
@@ -3658,7 +3647,7 @@ int PropertyMaterialItem::getShininess() const
}
auto val = value.value();
- return toPercent(val.shininess);
+ return Base::toPercent(val.shininess);
}
void PropertyMaterialItem::setShininess(int s)
@@ -3669,7 +3658,7 @@ void PropertyMaterialItem::setShininess(int s)
}
auto mat = value.value();
- mat.shininess = fromPercent(s);
+ mat.shininess = Base::fromPercent(s);
setValue(QVariant::fromValue(mat));
}
@@ -3681,7 +3670,7 @@ int PropertyMaterialItem::getTransparency() const
}
auto val = value.value();
- return toPercent(val.transparency);
+ return Base::toPercent(val.transparency);
}
void PropertyMaterialItem::setTransparency(int t)
@@ -3692,7 +3681,7 @@ void PropertyMaterialItem::setTransparency(int t)
}
auto mat = value.value();
- mat.transparency = fromPercent(t);
+ mat.transparency = Base::fromPercent(t);
setValue(QVariant::fromValue(mat));
}
@@ -3747,8 +3736,8 @@ QVariant PropertyMaterialItem::toolTip(const App::Property* prop) const
.arg(ec.red())
.arg(ec.green())
.arg(ec.blue())
- .arg(toPercent(value.shininess))
- .arg(toPercent(value.transparency));
+ .arg(Base::toPercent(value.shininess))
+ .arg(Base::toPercent(value.transparency));
return {data};
}
@@ -4085,7 +4074,7 @@ int PropertyMaterialListItem::getShininess() const
}
auto mat = list[0].value();
- return toPercent(mat.shininess);
+ return Base::toPercent(mat.shininess);
}
void PropertyMaterialListItem::setShininess(int s)
@@ -4105,7 +4094,7 @@ void PropertyMaterialListItem::setShininess(int s)
}
auto mat = list[0].value();
- mat.shininess = fromPercent(s);
+ mat.shininess = Base::fromPercent(s);
list[0] = QVariant::fromValue(mat);
setValue(list);
}
@@ -4127,7 +4116,7 @@ int PropertyMaterialListItem::getTransparency() const
}
auto mat = list[0].value();
- return toPercent(mat.transparency);
+ return Base::toPercent(mat.transparency);
}
void PropertyMaterialListItem::setTransparency(int t)
@@ -4147,7 +4136,7 @@ void PropertyMaterialListItem::setTransparency(int t)
}
auto mat = list[0].value();
- mat.transparency = fromPercent(t);
+ mat.transparency = Base::fromPercent(t);
list[0] = QVariant::fromValue(mat);
setValue(list);
}
@@ -4235,8 +4224,8 @@ QVariant PropertyMaterialListItem::toolTip(const App::Property* prop) const
.arg(ec.red())
.arg(ec.green())
.arg(ec.blue())
- .arg(toPercent(value.shininess))
- .arg(toPercent(value.transparency));
+ .arg(Base::toPercent(value.shininess))
+ .arg(Base::toPercent(value.transparency));
return {data};
}
diff --git a/src/Mod/Fem/Gui/ViewProviderFemPostObject.cpp b/src/Mod/Fem/Gui/ViewProviderFemPostObject.cpp
index 7d33b08eb7..2f76154c3b 100644
--- a/src/Mod/Fem/Gui/ViewProviderFemPostObject.cpp
+++ b/src/Mod/Fem/Gui/ViewProviderFemPostObject.cpp
@@ -69,6 +69,8 @@
#include "ViewProviderAnalysis.h"
#include "ViewProviderFemPostObject.h"
+#include
+
using namespace FemGui;
namespace sp = std::placeholders;
@@ -659,7 +661,7 @@ void ViewProviderFemPostObject::WriteColorData(bool ResetColorBarRange)
if (Field.getEnumVector().empty() || Field.getValue() == 0) {
m_material->diffuseColor.setValue(SbColor(0.8, 0.8, 0.8));
- float trans = float(Transparency.getValue()) / 100.0;
+ float trans = Base::fromPercent(Transparency.getValue());
m_material->transparency.setValue(trans);
m_materialBinding->value = SoMaterialBinding::OVERALL;
m_materialBinding->touch();
@@ -696,7 +698,7 @@ void ViewProviderFemPostObject::WriteColorData(bool ResetColorBarRange)
SbColor* diffcol = m_material->diffuseColor.startEditing();
SbColor* edgeDiffcol = m_matPlainEdges->diffuseColor.startEditing();
- float overallTransp = Transparency.getValue() / 100.0f;
+ float overallTransp = Base::fromPercent(Transparency.getValue());
m_material->transparency.setNum(numPts);
m_matPlainEdges->transparency.setNum(numPts);
float* transp = m_material->transparency.startEditing();
@@ -737,7 +739,7 @@ void ViewProviderFemPostObject::WriteColorData(bool ResetColorBarRange)
void ViewProviderFemPostObject::WriteTransparency()
{
- float trans = static_cast(Transparency.getValue()) / 100.0;
+ float trans = Base::fromPercent(Transparency.getValue());
float* value = m_material->transparency.startEditing();
float* edgeValue = m_matPlainEdges->transparency.startEditing();
// m_material and m_matPlainEdges field containers have same size
diff --git a/src/Mod/Material/App/MaterialManager.cpp b/src/Mod/Material/App/MaterialManager.cpp
index 9595142219..30c6cf4cce 100644
--- a/src/Mod/Material/App/MaterialManager.cpp
+++ b/src/Mod/Material/App/MaterialManager.cpp
@@ -38,6 +38,8 @@
#include "ModelManager.h"
#include "ModelUuids.h"
+#include
+
using namespace Materials;
@@ -174,8 +176,8 @@ std::shared_ptr MaterialManager::defaultAppearance()
long initialTransparency = hGrp->GetInt("DefaultShapeTransparency", 0);
long initialShininess = hGrp->GetInt("DefaultShapeShininess", 90);
- mat.shininess = ((float)initialShininess / 100.0F);
- mat.transparency = ((float)initialTransparency / 100.0F);
+ mat.shininess = Base::fromPercent(initialShininess);
+ mat.transparency = Base::fromPercent(initialTransparency);
return std::make_shared(mat);
}
diff --git a/src/Mod/Mesh/Gui/ViewProvider.cpp b/src/Mod/Mesh/Gui/ViewProvider.cpp
index d414d6a670..033b0449de 100644
--- a/src/Mod/Mesh/Gui/ViewProvider.cpp
+++ b/src/Mod/Mesh/Gui/ViewProvider.cpp
@@ -329,7 +329,7 @@ void ViewProviderMesh::onChanged(const App::Property* prop)
pcMatBinding->value = SoMaterialBinding::OVERALL;
}
if (prop == &LineTransparency) {
- float trans = LineTransparency.getValue() / 100.0F;
+ float trans = Base::fromPercent(LineTransparency.getValue());
pLineColor->transparency = trans;
}
else if (prop == &LineWidth) {
@@ -590,7 +590,7 @@ void ViewProviderMesh::tryColorPerVertexOrFace(bool on)
pcMatBinding->value = SoMaterialBinding::OVERALL;
const App::Color& c = ShapeAppearance.getDiffuseColor();
pcShapeMaterial->diffuseColor.setValue(c.r, c.g, c.b);
- pcShapeMaterial->transparency.setValue(Transparency.getValue() / 100.0F);
+ pcShapeMaterial->transparency.setValue(Base::fromPercent(Transparency.getValue()));
}
}
diff --git a/src/Mod/Part/Gui/ViewProvider.cpp b/src/Mod/Part/Gui/ViewProvider.cpp
index ce8f98bff0..9174a2526e 100644
--- a/src/Mod/Part/Gui/ViewProvider.cpp
+++ b/src/Mod/Part/Gui/ViewProvider.cpp
@@ -33,6 +33,8 @@
#include "ViewProvider.h"
+#include
+
using namespace PartGui;
@@ -88,7 +90,7 @@ void ViewProviderPart::applyTransparency(float transparency, std::vector ViewProviderPartExt::getElementColors(const cha
if(!element || !element[0]) {
auto color = ShapeAppearance.getDiffuseColor();
- color.setTransparency(Transparency.getValue()/100.0F);
+ color.setTransparency(Base::fromPercent(Transparency.getValue()));
ret["Face"] = color;
ret["Edge"] = LineColor.getValue();
ret["Vertex"] = PointColor.getValue();
@@ -687,7 +674,7 @@ std::map ViewProviderPartExt::getElementColors(const cha
auto size = ShapeAppearance.getSize();
if(element[4]=='*') {
auto color = ShapeAppearance.getDiffuseColor();
- color.setTransparency(Transparency.getValue()/100.0F);
+ color.setTransparency(Base::fromPercent(Transparency.getValue()));
bool singleColor = true;
for(int i=0;i ViewProviderPartExt::getElementColors(const cha
}
if(size && singleColor) {
color = ShapeAppearance.getDiffuseColor(0);
- color.setTransparency(Transparency.getValue()/100.0F);
+ color.setTransparency(Base::fromPercent(100.0F));
ret.clear();
}
ret["Face"] = color;
@@ -710,7 +697,7 @@ std::map ViewProviderPartExt::getElementColors(const cha
else
ret[element] = ShapeAppearance.getDiffuseColor();
if(size==1)
- ret[element].setTransparency(Transparency.getValue()/100.0F);
+ ret[element].setTransparency(Base::fromPercent(Transparency.getValue()));
}
} else if (boost::starts_with(element,"Edge")) {
auto size = LineColorArray.getSize();
diff --git a/src/Mod/Sketcher/Gui/ViewProviderSketch.cpp b/src/Mod/Sketcher/Gui/ViewProviderSketch.cpp
index f82f075c32..0696d0d115 100644
--- a/src/Mod/Sketcher/Gui/ViewProviderSketch.cpp
+++ b/src/Mod/Sketcher/Gui/ViewProviderSketch.cpp
@@ -3303,7 +3303,7 @@ void ViewProviderSketch::unsetEdit(int ModNum)
// Resets the override draw style mode when leaving the sketch edit mode.
ParameterGrp::handle hGrp = App::GetApplication().GetParameterGroupByPath(
"User parameter:BaseApp/Preferences/Mod/Sketcher/General");
- auto disableShadedView = hGrp->GetBool("DisableShadedView", true);
+ auto disableShadedView = hGrp->GetBool("DisableShadedView", false);
if (disableShadedView) {
Gui::View3DInventorViewer* viewer =
static_cast(mdi)->getViewer();
@@ -3400,7 +3400,7 @@ void ViewProviderSketch::setEditViewer(Gui::View3DInventorViewer* viewer, int Mo
// Sets the view mode to no shading to prevent visibility issues against parallel surfaces with shininess when entering the sketch mode.
ParameterGrp::handle hGrp = App::GetApplication().GetParameterGroupByPath(
"User parameter:BaseApp/Preferences/Mod/Sketcher/General");
- auto disableShadedView = hGrp->GetBool("DisableShadedView", true);
+ auto disableShadedView = hGrp->GetBool("DisableShadedView", false);
hGrp = App::GetApplication().GetParameterGroupByPath(
"User parameter:BaseApp/Preferences/Mod/Sketcher/General");