Merge remote-tracking branch 'upstream/master' into DraftModifiersAppPart
This commit is contained in:
@@ -6,8 +6,8 @@
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>459</width>
|
||||
<height>552</height>
|
||||
<width>291</width>
|
||||
<height>498</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="windowTitle">
|
||||
@@ -29,122 +29,6 @@
|
||||
<property name="spacing">
|
||||
<number>6</number>
|
||||
</property>
|
||||
<item row="3" column="0">
|
||||
<widget class="QGroupBox" name="buttonGroupComment">
|
||||
<property name="enabled">
|
||||
<bool>false</bool>
|
||||
</property>
|
||||
<property name="title">
|
||||
<string>Image comment</string>
|
||||
</property>
|
||||
<layout class="QGridLayout">
|
||||
<property name="leftMargin">
|
||||
<number>9</number>
|
||||
</property>
|
||||
<property name="topMargin">
|
||||
<number>9</number>
|
||||
</property>
|
||||
<property name="rightMargin">
|
||||
<number>9</number>
|
||||
</property>
|
||||
<property name="bottomMargin">
|
||||
<number>9</number>
|
||||
</property>
|
||||
<property name="spacing">
|
||||
<number>6</number>
|
||||
</property>
|
||||
<item row="0" column="0">
|
||||
<widget class="QRadioButton" name="radioButtonMiba">
|
||||
<property name="text">
|
||||
<string>Insert MIBA</string>
|
||||
</property>
|
||||
<property name="checked">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="0">
|
||||
<widget class="QTextEdit" name="textEditComment">
|
||||
<property name="enabled">
|
||||
<bool>false</bool>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="0">
|
||||
<widget class="QRadioButton" name="radioButtonComment">
|
||||
<property name="text">
|
||||
<string>Insert comment</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="3" column="0">
|
||||
<widget class="QCheckBox" name="checkWatermark">
|
||||
<property name="text">
|
||||
<string>Add watermark</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="0">
|
||||
<widget class="QGroupBox" name="groupBoxProp">
|
||||
<property name="title">
|
||||
<string>Image properties</string>
|
||||
</property>
|
||||
<layout class="QGridLayout">
|
||||
<property name="leftMargin">
|
||||
<number>9</number>
|
||||
</property>
|
||||
<property name="topMargin">
|
||||
<number>9</number>
|
||||
</property>
|
||||
<property name="rightMargin">
|
||||
<number>9</number>
|
||||
</property>
|
||||
<property name="bottomMargin">
|
||||
<number>9</number>
|
||||
</property>
|
||||
<property name="spacing">
|
||||
<number>6</number>
|
||||
</property>
|
||||
<item row="0" column="0">
|
||||
<widget class="QLabel" name="textLabelColor">
|
||||
<property name="text">
|
||||
<string>Back&ground:</string>
|
||||
</property>
|
||||
<property name="buddy">
|
||||
<cstring>comboBackground</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="2">
|
||||
<widget class="QComboBox" name="comboBackground">
|
||||
<item>
|
||||
<property name="text">
|
||||
<string>Current</string>
|
||||
</property>
|
||||
</item>
|
||||
<item>
|
||||
<property name="text">
|
||||
<string>White</string>
|
||||
</property>
|
||||
</item>
|
||||
<item>
|
||||
<property name="text">
|
||||
<string>Black</string>
|
||||
</property>
|
||||
</item>
|
||||
<item>
|
||||
<property name="text">
|
||||
<string>Transparent</string>
|
||||
</property>
|
||||
</item>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="0">
|
||||
<widget class="QGroupBox" name="groupBoxDim">
|
||||
<property name="title">
|
||||
@@ -183,57 +67,14 @@
|
||||
<property name="spacing">
|
||||
<number>6</number>
|
||||
</property>
|
||||
<item row="1" column="1">
|
||||
<spacer>
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>40</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item row="2" column="2">
|
||||
<widget class="QSpinBox" name="spinHeight">
|
||||
<property name="minimum">
|
||||
<number>1</number>
|
||||
</property>
|
||||
<property name="maximum">
|
||||
<number>32767</number>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="2">
|
||||
<widget class="QSpinBox" name="spinWidth">
|
||||
<property name="minimum">
|
||||
<number>1</number>
|
||||
</property>
|
||||
<property name="maximum">
|
||||
<number>32767</number>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="3">
|
||||
<widget class="QLabel" name="label_2">
|
||||
<item row="0" column="0">
|
||||
<widget class="QLabel" name="label">
|
||||
<property name="text">
|
||||
<string>Pixel</string>
|
||||
<string>Standard sizes:</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="0">
|
||||
<widget class="QLabel" name="textLabelWidth">
|
||||
<property name="text">
|
||||
<string>&Width:</string>
|
||||
</property>
|
||||
<property name="buddy">
|
||||
<cstring>spinWidth</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="2" colspan="2">
|
||||
<item row="0" column="1" colspan="2">
|
||||
<widget class="QComboBox" name="standardSizeBox">
|
||||
<item>
|
||||
<property name="text">
|
||||
@@ -352,46 +193,33 @@
|
||||
</item>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="0">
|
||||
<widget class="QLabel" name="label">
|
||||
<item row="1" column="0">
|
||||
<widget class="QLabel" name="textLabelWidth">
|
||||
<property name="text">
|
||||
<string>Standard sizes:</string>
|
||||
<string>&Width:</string>
|
||||
</property>
|
||||
<property name="buddy">
|
||||
<cstring>spinWidth</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="1">
|
||||
<spacer>
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
<item row="1" column="1">
|
||||
<widget class="QSpinBox" name="spinWidth">
|
||||
<property name="minimum">
|
||||
<number>1</number>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>40</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
<property name="maximum">
|
||||
<number>32767</number>
|
||||
</property>
|
||||
</spacer>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="3">
|
||||
<widget class="QLabel" name="label_3">
|
||||
<item row="1" column="2">
|
||||
<widget class="QLabel" name="label_2">
|
||||
<property name="text">
|
||||
<string>Pixel</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="1">
|
||||
<spacer>
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>40</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item row="2" column="0">
|
||||
<widget class="QLabel" name="textLabelHeight">
|
||||
<property name="text">
|
||||
@@ -402,6 +230,23 @@
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="1">
|
||||
<widget class="QSpinBox" name="spinHeight">
|
||||
<property name="minimum">
|
||||
<number>1</number>
|
||||
</property>
|
||||
<property name="maximum">
|
||||
<number>32767</number>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="2">
|
||||
<widget class="QLabel" name="label_3">
|
||||
<property name="text">
|
||||
<string>Pixel</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</item>
|
||||
<item row="1" column="0">
|
||||
@@ -429,7 +274,7 @@
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QPushButton" name="buttonRatioScreen">
|
||||
<widget class="QToolButton" name="buttonRatioScreen">
|
||||
<property name="text">
|
||||
<string>&Screen</string>
|
||||
</property>
|
||||
@@ -439,7 +284,7 @@
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QPushButton" name="buttonRatio4x3">
|
||||
<widget class="QToolButton" name="buttonRatio4x3">
|
||||
<property name="text">
|
||||
<string>&4:3</string>
|
||||
</property>
|
||||
@@ -449,7 +294,7 @@
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QPushButton" name="buttonRatio16x9">
|
||||
<widget class="QToolButton" name="buttonRatio16x9">
|
||||
<property name="text">
|
||||
<string>1&6:9</string>
|
||||
</property>
|
||||
@@ -459,7 +304,7 @@
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QPushButton" name="buttonRatio1x1">
|
||||
<widget class="QToolButton" name="buttonRatio1x1">
|
||||
<property name="text">
|
||||
<string>&1:1</string>
|
||||
</property>
|
||||
@@ -473,25 +318,144 @@
|
||||
</layout>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="0">
|
||||
<widget class="QGroupBox" name="groupBoxMethod">
|
||||
<item row="1" column="0">
|
||||
<widget class="QGroupBox" name="groupBoxProp">
|
||||
<property name="title">
|
||||
<string>Method</string>
|
||||
<string>Image properties</string>
|
||||
</property>
|
||||
<layout class="QGridLayout" name="gridLayoutMethod">
|
||||
<layout class="QGridLayout">
|
||||
<property name="leftMargin">
|
||||
<number>9</number>
|
||||
</property>
|
||||
<property name="topMargin">
|
||||
<number>9</number>
|
||||
</property>
|
||||
<property name="rightMargin">
|
||||
<number>9</number>
|
||||
</property>
|
||||
<property name="bottomMargin">
|
||||
<number>9</number>
|
||||
</property>
|
||||
<property name="spacing">
|
||||
<number>6</number>
|
||||
</property>
|
||||
<item row="0" column="0">
|
||||
<widget class="QLabel" name="textLabelColor">
|
||||
<property name="text">
|
||||
<string>Back&ground:</string>
|
||||
</property>
|
||||
<property name="buddy">
|
||||
<cstring>comboBackground</cstring>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="1">
|
||||
<widget class="QComboBox" name="comboBackground">
|
||||
<item>
|
||||
<property name="text">
|
||||
<string>Current</string>
|
||||
</property>
|
||||
</item>
|
||||
<item>
|
||||
<property name="text">
|
||||
<string>White</string>
|
||||
</property>
|
||||
</item>
|
||||
<item>
|
||||
<property name="text">
|
||||
<string>Black</string>
|
||||
</property>
|
||||
</item>
|
||||
<item>
|
||||
<property name="text">
|
||||
<string>Transparent</string>
|
||||
</property>
|
||||
</item>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="0">
|
||||
<widget class="QLabel" name="label_4">
|
||||
<property name="text">
|
||||
<string>Creation method:</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="1">
|
||||
<item row="1" column="1">
|
||||
<widget class="QComboBox" name="comboMethod"/>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="0">
|
||||
<widget class="QGroupBox" name="buttonGroupComment">
|
||||
<property name="enabled">
|
||||
<bool>false</bool>
|
||||
</property>
|
||||
<property name="title">
|
||||
<string>Image comment</string>
|
||||
</property>
|
||||
<layout class="QGridLayout">
|
||||
<property name="leftMargin">
|
||||
<number>9</number>
|
||||
</property>
|
||||
<property name="topMargin">
|
||||
<number>9</number>
|
||||
</property>
|
||||
<property name="rightMargin">
|
||||
<number>9</number>
|
||||
</property>
|
||||
<property name="bottomMargin">
|
||||
<number>9</number>
|
||||
</property>
|
||||
<property name="spacing">
|
||||
<number>6</number>
|
||||
</property>
|
||||
<item row="0" column="0">
|
||||
<widget class="QRadioButton" name="radioButtonMiba">
|
||||
<property name="text">
|
||||
<string>Insert MIBA</string>
|
||||
</property>
|
||||
<property name="checked">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="1" column="0">
|
||||
<widget class="QRadioButton" name="radioButtonComment">
|
||||
<property name="text">
|
||||
<string>Insert comment</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="2" column="0">
|
||||
<widget class="QTextEdit" name="textEditComment">
|
||||
<property name="enabled">
|
||||
<bool>false</bool>
|
||||
</property>
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Expanding" vsizetype="Ignored">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>0</width>
|
||||
<height>70</height>
|
||||
</size>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="3" column="0">
|
||||
<widget class="QCheckBox" name="checkWatermark">
|
||||
<property name="text">
|
||||
<string>Add watermark</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
<layoutdefault spacing="6" margin="11"/>
|
||||
@@ -504,6 +468,7 @@
|
||||
<tabstop>buttonRatio16x9</tabstop>
|
||||
<tabstop>buttonRatio1x1</tabstop>
|
||||
<tabstop>comboBackground</tabstop>
|
||||
<tabstop>comboMethod</tabstop>
|
||||
<tabstop>radioButtonMiba</tabstop>
|
||||
<tabstop>radioButtonComment</tabstop>
|
||||
<tabstop>textEditComment</tabstop>
|
||||
|
||||
@@ -252,10 +252,10 @@ void DlgSettingsImageImp::on_comboMethod_activated(int index)
|
||||
{
|
||||
QByteArray data = ui->comboMethod->itemData(index).toByteArray();
|
||||
if (data == QByteArray("GrabFramebuffer")) {
|
||||
ui->groupBoxProp->setEnabled(false);
|
||||
ui->comboBackground->setEnabled(false);
|
||||
}
|
||||
else {
|
||||
ui->groupBoxProp->setEnabled(true);
|
||||
ui->comboBackground->setEnabled(true);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -290,16 +290,6 @@ void Gui::QuantitySpinBox::setExpression(boost::shared_ptr<Expression> expr)
|
||||
}
|
||||
}
|
||||
|
||||
void Gui::QuantitySpinBox::setTooltipLE(const QString &name)
|
||||
{
|
||||
lineEdit()->setToolTip(name);
|
||||
}
|
||||
|
||||
void Gui::QuantitySpinBox::setTooltipIL(const QString &name)
|
||||
{
|
||||
iconLabel->setToolTip(name);
|
||||
}
|
||||
|
||||
QString QuantitySpinBox::boundToName() const
|
||||
{
|
||||
if (isBound()) {
|
||||
@@ -394,8 +384,7 @@ void Gui::QuantitySpinBox::onChange()
|
||||
p.setColor(QPalette::Text, Qt::lightGray);
|
||||
lineEdit()->setPalette(p);
|
||||
}
|
||||
iconLabel->setToolTip(QString());
|
||||
setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
iconLabel->setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
}
|
||||
else {
|
||||
setReadOnly(false);
|
||||
@@ -406,7 +395,6 @@ void Gui::QuantitySpinBox::onChange()
|
||||
lineEdit()->setPalette(p);
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
|
||||
|
||||
@@ -460,7 +448,7 @@ void QuantitySpinBox::resizeEvent(QResizeEvent * event)
|
||||
p.setColor(QPalette::Text, Qt::lightGray);
|
||||
lineEdit()->setPalette(p);
|
||||
}
|
||||
setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
iconLabel->setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
}
|
||||
else {
|
||||
setReadOnly(false);
|
||||
@@ -470,9 +458,8 @@ void QuantitySpinBox::resizeEvent(QResizeEvent * event)
|
||||
QPalette p(lineEdit()->palette());
|
||||
p.setColor(QPalette::Active, QPalette::Text, defaultPalette.color(QPalette::Text));
|
||||
lineEdit()->setPalette(p);
|
||||
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
catch (const Base::Exception & e) {
|
||||
setReadOnly(true);
|
||||
@@ -489,7 +476,7 @@ void Gui::QuantitySpinBox::keyPressEvent(QKeyEvent *event)
|
||||
if (event->text() == QString::fromUtf8("=") && isBound())
|
||||
openFormulaDialog();
|
||||
else if (!hasExpression())
|
||||
QAbstractSpinBox::keyPressEvent(event);
|
||||
QAbstractSpinBox::keyPressEvent(event);
|
||||
}
|
||||
|
||||
|
||||
@@ -853,6 +840,16 @@ void QuantitySpinBox::showEvent(QShowEvent * event)
|
||||
|
||||
bool QuantitySpinBox::event(QEvent * event)
|
||||
{
|
||||
// issue #0004059: Tooltips for Gui::QuantitySpinBox not showing
|
||||
// Here we must not try to show the tooltip of the icon label
|
||||
// because it would override a custom tooltip set to this widget.
|
||||
//
|
||||
// We could also check if the text of this tooltip is empty but
|
||||
// it will fail in cases where the widget is embedded into the
|
||||
// property editor and the corresponding item has set a tooltip.
|
||||
// Instead of showing the item's tooltip it will again show the
|
||||
// tooltip of the icon label.
|
||||
#if 0
|
||||
if (event->type() == QEvent::ToolTip) {
|
||||
if (isBound() && getExpression() && lineEdit()->isReadOnly()) {
|
||||
QHelpEvent * helpEvent = static_cast<QHelpEvent*>(event);
|
||||
@@ -862,6 +859,7 @@ bool QuantitySpinBox::event(QEvent * event)
|
||||
return true;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
return QAbstractSpinBox::event(event);
|
||||
}
|
||||
|
||||
@@ -129,10 +129,6 @@ public:
|
||||
bool event(QEvent *event);
|
||||
|
||||
void setExpression(boost::shared_ptr<App::Expression> expr);
|
||||
/// Sets a tooltip for the LineEdit
|
||||
void setTooltipLE(const QString &name);
|
||||
/// Sets a tooltip for the IconLabel
|
||||
void setTooltipIL(const QString &name);
|
||||
void bind(const App::ObjectIdentifier &_path);
|
||||
bool apply(const std::string &propName);
|
||||
|
||||
|
||||
@@ -292,7 +292,7 @@ void UIntSpinBox::onChange() {
|
||||
p.setColor(QPalette::Text, Qt::lightGray);
|
||||
lineEdit()->setPalette(p);
|
||||
}
|
||||
setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
iconLabel->setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
}
|
||||
else {
|
||||
setReadOnly(false);
|
||||
@@ -300,9 +300,8 @@ void UIntSpinBox::onChange() {
|
||||
QPalette p(lineEdit()->palette());
|
||||
p.setColor(QPalette::Active, QPalette::Text, defaultPalette.color(QPalette::Text));
|
||||
lineEdit()->setPalette(p);
|
||||
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
|
||||
|
||||
@@ -344,7 +343,7 @@ void UIntSpinBox::resizeEvent(QResizeEvent * event)
|
||||
p.setColor(QPalette::Text, Qt::lightGray);
|
||||
lineEdit()->setPalette(p);
|
||||
}
|
||||
setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
iconLabel->setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
}
|
||||
else {
|
||||
setReadOnly(false);
|
||||
@@ -354,9 +353,8 @@ void UIntSpinBox::resizeEvent(QResizeEvent * event)
|
||||
QPalette p(lineEdit()->palette());
|
||||
p.setColor(QPalette::Active, QPalette::Text, defaultPalette.color(QPalette::Text));
|
||||
lineEdit()->setPalette(p);
|
||||
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
catch (const Base::Exception & e) {
|
||||
setReadOnly(true);
|
||||
@@ -489,7 +487,7 @@ void IntSpinBox::onChange() {
|
||||
p.setColor(QPalette::Text, Qt::lightGray);
|
||||
lineEdit()->setPalette(p);
|
||||
}
|
||||
setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
iconLabel->setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
}
|
||||
else {
|
||||
setReadOnly(false);
|
||||
@@ -497,9 +495,8 @@ void IntSpinBox::onChange() {
|
||||
QPalette p(lineEdit()->palette());
|
||||
p.setColor(QPalette::Active, QPalette::Text, defaultPalette.color(QPalette::Text));
|
||||
lineEdit()->setPalette(p);
|
||||
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
|
||||
void IntSpinBox::resizeEvent(QResizeEvent * event)
|
||||
@@ -525,7 +522,7 @@ void IntSpinBox::resizeEvent(QResizeEvent * event)
|
||||
p.setColor(QPalette::Text, Qt::lightGray);
|
||||
lineEdit()->setPalette(p);
|
||||
}
|
||||
setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
iconLabel->setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
}
|
||||
else {
|
||||
setReadOnly(false);
|
||||
@@ -535,9 +532,8 @@ void IntSpinBox::resizeEvent(QResizeEvent * event)
|
||||
QPalette p(lineEdit()->palette());
|
||||
p.setColor(QPalette::Active, QPalette::Text, defaultPalette.color(QPalette::Text));
|
||||
lineEdit()->setPalette(p);
|
||||
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
catch (const Base::Exception & e) {
|
||||
setReadOnly(true);
|
||||
@@ -670,7 +666,7 @@ void DoubleSpinBox::onChange() {
|
||||
p.setColor(QPalette::Text, Qt::lightGray);
|
||||
lineEdit()->setPalette(p);
|
||||
}
|
||||
setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
iconLabel->setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
}
|
||||
else {
|
||||
setReadOnly(false);
|
||||
@@ -678,9 +674,8 @@ void DoubleSpinBox::onChange() {
|
||||
QPalette p(lineEdit()->palette());
|
||||
p.setColor(QPalette::Active, QPalette::Text, defaultPalette.color(QPalette::Text));
|
||||
lineEdit()->setPalette(p);
|
||||
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
|
||||
void DoubleSpinBox::resizeEvent(QResizeEvent * event)
|
||||
@@ -706,7 +701,7 @@ void DoubleSpinBox::resizeEvent(QResizeEvent * event)
|
||||
p.setColor(QPalette::Text, Qt::lightGray);
|
||||
lineEdit()->setPalette(p);
|
||||
}
|
||||
setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
iconLabel->setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
}
|
||||
else {
|
||||
setReadOnly(false);
|
||||
@@ -716,9 +711,8 @@ void DoubleSpinBox::resizeEvent(QResizeEvent * event)
|
||||
QPalette p(lineEdit()->palette());
|
||||
p.setColor(QPalette::Active, QPalette::Text, defaultPalette.color(QPalette::Text));
|
||||
lineEdit()->setPalette(p);
|
||||
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
catch (const Base::Exception & e) {
|
||||
setReadOnly(true);
|
||||
@@ -727,7 +721,6 @@ void DoubleSpinBox::resizeEvent(QResizeEvent * event)
|
||||
lineEdit()->setPalette(p);
|
||||
iconLabel->setToolTip(QString::fromLatin1(e.what()));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
void DoubleSpinBox::openFormulaDialog()
|
||||
|
||||
@@ -1489,7 +1489,7 @@ void ExpLineEdit::onChange() {
|
||||
QPalette p(palette());
|
||||
p.setColor(QPalette::Text, Qt::lightGray);
|
||||
setPalette(p);
|
||||
setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
iconLabel->setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
}
|
||||
else {
|
||||
setReadOnly(false);
|
||||
@@ -1497,9 +1497,8 @@ void ExpLineEdit::onChange() {
|
||||
QPalette p(palette());
|
||||
p.setColor(QPalette::Active, QPalette::Text, defaultPalette.color(QPalette::Text));
|
||||
setPalette(p);
|
||||
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
|
||||
void ExpLineEdit::resizeEvent(QResizeEvent * event)
|
||||
@@ -1520,7 +1519,7 @@ void ExpLineEdit::resizeEvent(QResizeEvent * event)
|
||||
QPalette p(palette());
|
||||
p.setColor(QPalette::Text, Qt::lightGray);
|
||||
setPalette(p);
|
||||
setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
iconLabel->setToolTip(Base::Tools::fromStdString(getExpression()->toString()));
|
||||
}
|
||||
else {
|
||||
setReadOnly(false);
|
||||
@@ -1530,9 +1529,8 @@ void ExpLineEdit::resizeEvent(QResizeEvent * event)
|
||||
QPalette p(palette());
|
||||
p.setColor(QPalette::Active, QPalette::Text, defaultPalette.color(QPalette::Text));
|
||||
setPalette(p);
|
||||
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
iconLabel->setToolTip(QString());
|
||||
}
|
||||
catch (const Base::Exception & e) {
|
||||
setReadOnly(true);
|
||||
|
||||
@@ -589,6 +589,10 @@ class CommandAddonManager:
|
||||
pref = FreeCAD.ParamGet("User parameter:BaseApp/Preferences/Addons")
|
||||
self.config.checkUpdates.setChecked(pref.GetBool("AutoCheck",False))
|
||||
self.config.customRepositories.setPlainText(pref.GetString("CustomRepositories",""))
|
||||
self.config.radioButtonNoProxy.setChecked(pref.GetBool("NoProxyCheck",True))
|
||||
self.config.radioButtonSystemProxy.setChecked(pref.GetBool("SystemProxyCheck",False))
|
||||
self.config.radioButtonUserProxy.setChecked(pref.GetBool("UserProxyCheck",False))
|
||||
self.config.userProxy.setPlainText(pref.GetString("ProxyUrl",""))
|
||||
|
||||
# center the dialog over the Addon Manager
|
||||
self.config.move(self.dialog.frameGeometry().topLeft() + self.dialog.rect().center() - self.config.rect().center())
|
||||
@@ -599,6 +603,10 @@ class CommandAddonManager:
|
||||
# OK button has been pressed
|
||||
pref.SetBool("AutoCheck",self.config.checkUpdates.isChecked())
|
||||
pref.SetString("CustomRepositories",self.config.customRepositories.toPlainText())
|
||||
pref.SetBool("NoProxyCheck",self.config.radioButtonNoProxy.isChecked())
|
||||
pref.SetBool("SystemProxyCheck",self.config.radioButtonSystemProxy.isChecked())
|
||||
pref.SetBool("UserProxyCheck",self.config.radioButtonUserProxy.isChecked())
|
||||
pref.SetString("ProxyUrl",self.config.userProxy.toPlainText())
|
||||
|
||||
def check_updates(addon_name,callback):
|
||||
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>390</width>
|
||||
<height>183</height>
|
||||
<height>247</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="windowTitle">
|
||||
@@ -24,6 +24,9 @@ installed addons will be checked for available updates
|
||||
<property name="text">
|
||||
<string>Automatically check for updates at start (requires GitPython)</string>
|
||||
</property>
|
||||
<property name="autoExclusive">
|
||||
<bool>false</bool>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
@@ -41,6 +44,47 @@ sto be scanned for available addons</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="Line" name="line">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QLabel" name="labelProxy">
|
||||
<property name="text">
|
||||
<string>Proxy </string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QRadioButton" name="radioButtonNoProxy">
|
||||
<property name="text">
|
||||
<string>No proxy</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QRadioButton" name="radioButtonSystemProxy">
|
||||
<property name="text">
|
||||
<string>User system proxy</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QRadioButton" name="radioButtonUserProxy">
|
||||
<property name="text">
|
||||
<string>User defined proxy :</string>
|
||||
</property>
|
||||
<property name="checked">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QTextEdit" name="userProxy"/>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QDialogButtonBox" name="buttonBox">
|
||||
<property name="orientation">
|
||||
@@ -62,12 +106,12 @@ sto be scanned for available addons</string>
|
||||
<slot>accept()</slot>
|
||||
<hints>
|
||||
<hint type="sourcelabel">
|
||||
<x>248</x>
|
||||
<y>254</y>
|
||||
<x>257</x>
|
||||
<y>237</y>
|
||||
</hint>
|
||||
<hint type="destinationlabel">
|
||||
<x>157</x>
|
||||
<y>274</y>
|
||||
<y>246</y>
|
||||
</hint>
|
||||
</hints>
|
||||
</connection>
|
||||
@@ -78,12 +122,12 @@ sto be scanned for available addons</string>
|
||||
<slot>reject()</slot>
|
||||
<hints>
|
||||
<hint type="sourcelabel">
|
||||
<x>316</x>
|
||||
<y>260</y>
|
||||
<x>325</x>
|
||||
<y>237</y>
|
||||
</hint>
|
||||
<hint type="destinationlabel">
|
||||
<x>286</x>
|
||||
<y>274</y>
|
||||
<y>246</y>
|
||||
</hint>
|
||||
</hints>
|
||||
</connection>
|
||||
|
||||
@@ -103,6 +103,9 @@ class Macro(object):
|
||||
except:
|
||||
print("AddonManager: Debug: unable to open URL",url)
|
||||
return
|
||||
if u is None :
|
||||
print("AddonManager: Debug: connection is lost (proxy setting changed?)",url)
|
||||
return
|
||||
p = u.read()
|
||||
if sys.version_info.major >= 3 and isinstance(p, bytes):
|
||||
p = p.decode('utf-8')
|
||||
|
||||
@@ -40,12 +40,12 @@ except ImportError:
|
||||
pass
|
||||
else:
|
||||
try:
|
||||
ssl_ctx = ssl.create_default_context(ssl.Purpose.CLIENT_AUTH)
|
||||
ssl_ctx = ssl.create_default_context(ssl.Purpose.SERVER_AUTH)
|
||||
except AttributeError:
|
||||
pass
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
def translate(context, text, disambig=None):
|
||||
|
||||
"Main translation function"
|
||||
@@ -93,18 +93,35 @@ def urlopen(url):
|
||||
import urllib2
|
||||
else:
|
||||
import urllib.request as urllib2
|
||||
|
||||
# Proxy an ssl configuration
|
||||
pref = FreeCAD.ParamGet("User parameter:BaseApp/Preferences/Addons")
|
||||
if pref.GetBool("NoProxyCheck",True):
|
||||
proxies = {}
|
||||
else:
|
||||
if pref.GetBool("SystemProxyCheck",False):
|
||||
proxy = urllib2.getproxies()
|
||||
proxies = {"http": proxy.get('http'),"https": proxy.get('http')}
|
||||
elif pref.GetBool("UserProxyCheck",False):
|
||||
proxy = pref.GetString("ProxyUrl","")
|
||||
proxies = {"http": proxy, "https": proxy}
|
||||
|
||||
if ssl_ctx:
|
||||
handler = urllib2.HTTPSHandler(context=ssl_ctx)
|
||||
else:
|
||||
handler = {}
|
||||
proxy_support = urllib2.ProxyHandler(proxies)
|
||||
opener = urllib2.build_opener(proxy_support, handler)
|
||||
urllib2.install_opener(opener)
|
||||
|
||||
# Url opening
|
||||
try:
|
||||
if ssl_ctx:
|
||||
u = urllib2.urlopen(url, context=ssl_ctx, timeout=timeout)
|
||||
else:
|
||||
u = urllib2.urlopen(url, timeout=timeout)
|
||||
u = urllib2.urlopen(url, timeout=timeout)
|
||||
except:
|
||||
return None
|
||||
else:
|
||||
return u
|
||||
|
||||
|
||||
def getserver(url):
|
||||
|
||||
"""returns the server part of an url"""
|
||||
|
||||
@@ -224,8 +224,8 @@ def export(exportList,filename,colors=None,preferences=None):
|
||||
objectslist = [obj for obj in objectslist if obj != contextCreator.project_object]
|
||||
|
||||
if Draft.getObjectsOfType(objectslist, "Site"): # we assume one site and one representation context only
|
||||
trueNorthX = math.tan(-Draft.getObjectsOfType(objectslist, "Site")[0].Declination.getValueAs(FreeCAD.Units.Radian))
|
||||
contextCreator.model_context.TrueNorth.DirectionRatios = (trueNorthX, 1.)
|
||||
decl = Draft.getObjectsOfType(objectslist, "Site")[0].Declination.getValueAs(FreeCAD.Units.Radian)
|
||||
contextCreator.model_context.TrueNorth.DirectionRatios = (math.cos(decl+math.pi/2), math.sin(decl+math.pi/2))
|
||||
|
||||
products = {} # { Name: IfcEntity, ... }
|
||||
subproducts = {} # { Name: IfcEntity, ... } for storing additions/subtractions and other types of subcomponents of a product
|
||||
|
||||
@@ -836,9 +836,10 @@ def insert(filename,docname,skip=[],only=[],root=None,preferences=None):
|
||||
obj.PostalCode = product.SiteAddress.PostalCode
|
||||
project = product.Decomposes[0].RelatingObject
|
||||
modelRC = next((rc for rc in project.RepresentationContexts if rc.ContextType == "Model"), None)
|
||||
if modelRC and modelRC.TrueNorth and modelRC.TrueNorth.DirectionRatios[1] > 0:
|
||||
obj.Declination = -math.degrees(math.atan(modelRC.TrueNorth.DirectionRatios[0] / modelRC.TrueNorth.DirectionRatios[1]))
|
||||
if(FreeCAD.GuiUp):
|
||||
if modelRC and modelRC.TrueNorth:
|
||||
(x, y) = modelRC.TrueNorth.DirectionRatios[:2]
|
||||
obj.Declination = ((math.degrees(math.atan2(y,x))-90+180)%360)-180
|
||||
if (FreeCAD.GuiUp):
|
||||
obj.ViewObject.CompassRotation.Value = obj.Declination
|
||||
|
||||
try:
|
||||
|
||||
@@ -50,6 +50,7 @@ SET(Draft_tests
|
||||
SET(Draft_utilities
|
||||
draftutils/__init__.py
|
||||
draftutils/utils.py
|
||||
draftutils/gui_utils.py
|
||||
)
|
||||
|
||||
SET(Draft_objects
|
||||
|
||||
@@ -80,6 +80,8 @@ makeLayer = DraftLayer.makeLayer
|
||||
# General functions
|
||||
#---------------------------------------------------------------------------
|
||||
import draftutils.utils
|
||||
import draftutils.gui_utils
|
||||
|
||||
arrowtypes = draftutils.utils.ARROW_TYPES
|
||||
|
||||
stringencodecoin = draftutils.utils.string_encode_coin
|
||||
@@ -110,20 +112,8 @@ get_type = draftutils.utils.get_type
|
||||
getObjectsOfType = draftutils.utils.get_objects_of_type
|
||||
get_objects_of_type = draftutils.utils.get_objects_of_type
|
||||
|
||||
|
||||
def get3DView():
|
||||
"""get3DView(): returns the current view if it is 3D, or the first 3D view found, or None"""
|
||||
if FreeCAD.GuiUp:
|
||||
import FreeCADGui
|
||||
v = FreeCADGui.ActiveDocument.ActiveView
|
||||
if "View3DInventor" in str(type(v)):
|
||||
return v
|
||||
#print("Debug: Draft: Warning, not working in active view")
|
||||
v = FreeCADGui.ActiveDocument.mdiViewsOfType("Gui::View3DInventor")
|
||||
if v:
|
||||
return v[0]
|
||||
return None
|
||||
|
||||
get3DView = draftutils.gui_utils.get_3d_view
|
||||
get_3d_view = draftutils.gui_utils.get_3d_view
|
||||
|
||||
isClone = draftutils.utils.is_clone
|
||||
is_clone = draftutils.utils.is_clone
|
||||
@@ -133,132 +123,21 @@ get_group_names = draftutils.utils.get_group_names
|
||||
|
||||
ungroup = draftutils.utils.ungroup
|
||||
|
||||
autogroup = draftutils.gui_utils.autogroup
|
||||
|
||||
def autogroup(obj):
|
||||
"""
|
||||
Adds a given object to the autogroup, if applicable.
|
||||
|
||||
If autogroup is present, object is added to autogroup.
|
||||
If an Arch container is active, add given object to it.
|
||||
If an App::Part container is active, add given object to it
|
||||
and update the object placement so it doesn't jump on other
|
||||
position in respect of it's creation.
|
||||
|
||||
Parameter
|
||||
--------
|
||||
obj : object.Name
|
||||
Name of the object to add to the group.
|
||||
|
||||
TODO
|
||||
--------
|
||||
add support for App::Part with Draft Annotations.
|
||||
|
||||
"""
|
||||
if FreeCAD.GuiUp:
|
||||
# Arch active container
|
||||
active_part = FreeCADGui.ActiveDocument.ActiveView.getActiveObject("part")
|
||||
# Arch active container
|
||||
active_arch_obj = FreeCADGui.ActiveDocument.ActiveView.getActiveObject("Arch")
|
||||
if hasattr(FreeCADGui,"draftToolBar"):
|
||||
if (hasattr(FreeCADGui.draftToolBar,"autogroup")
|
||||
and not FreeCADGui.draftToolBar.isConstructionMode()
|
||||
):
|
||||
if FreeCADGui.draftToolBar.autogroup is not None:
|
||||
active_group = FreeCAD.ActiveDocument.getObject(FreeCADGui.draftToolBar.autogroup)
|
||||
if active_group:
|
||||
found = False
|
||||
for o in active_group.Group:
|
||||
if o.Name == obj.Name:
|
||||
found = True
|
||||
if not found:
|
||||
gr = active_group.Group
|
||||
gr.append(obj)
|
||||
active_group.Group = gr
|
||||
elif active_arch_obj:
|
||||
active_arch_obj.addObject(obj)
|
||||
elif active_part:
|
||||
inverse_placement = active_part.getGlobalPlacement().inverse()
|
||||
if getType(obj) == 'Point':
|
||||
# point vector have a kind of placement, so should be
|
||||
# processed before generic object with placement
|
||||
point_vector = FreeCAD.Vector(obj.X, obj.Y, obj.Z)
|
||||
real_point = inverse_placement.multVec(point_vector)
|
||||
obj.X = real_point.x
|
||||
obj.Y = real_point.y
|
||||
obj.Z = real_point.z
|
||||
elif hasattr(obj,"Placement"):
|
||||
obj.Placement = FreeCAD.Placement(inverse_placement.multiply(obj.Placement))
|
||||
active_part.addObject(obj)
|
||||
|
||||
def dimSymbol(symbol=None,invert=False):
|
||||
"""returns the current dim symbol from the preferences as a pivy SoMarkerSet"""
|
||||
if symbol is None:
|
||||
symbol = getParam("dimsymbol",0)
|
||||
from pivy import coin
|
||||
if symbol == 0:
|
||||
return coin.SoSphere()
|
||||
elif symbol == 1:
|
||||
marker = coin.SoMarkerSet()
|
||||
marker.markerIndex = FreeCADGui.getMarkerIndex("circle", 9)
|
||||
return marker
|
||||
elif symbol == 2:
|
||||
marker = coin.SoSeparator()
|
||||
t = coin.SoTransform()
|
||||
t.translation.setValue((0,-2,0))
|
||||
t.center.setValue((0,2,0))
|
||||
if invert:
|
||||
t.rotation.setValue(coin.SbVec3f((0,0,1)),-math.pi/2)
|
||||
else:
|
||||
t.rotation.setValue(coin.SbVec3f((0,0,1)),math.pi/2)
|
||||
c = coin.SoCone()
|
||||
c.height.setValue(4)
|
||||
marker.addChild(t)
|
||||
marker.addChild(c)
|
||||
return marker
|
||||
elif symbol == 3:
|
||||
marker = coin.SoSeparator()
|
||||
c = coin.SoCoordinate3()
|
||||
c.point.setValues([(-1,-2,0),(0,2,0),(1,2,0),(0,-2,0)])
|
||||
f = coin.SoFaceSet()
|
||||
marker.addChild(c)
|
||||
marker.addChild(f)
|
||||
return marker
|
||||
elif symbol == 4:
|
||||
return dimDash((-1.5,-1.5,0),(1.5,1.5,0))
|
||||
else:
|
||||
print("Draft.dimsymbol: Not implemented")
|
||||
return coin.SoSphere()
|
||||
|
||||
def dimDash(p1, p2):
|
||||
"""dimDash(p1, p2): returns pivy SoSeparator.
|
||||
Used for making Tick-2, DimOvershoot, ExtOvershoot dashes.
|
||||
"""
|
||||
from pivy import coin
|
||||
dash = coin.SoSeparator()
|
||||
v = coin.SoVertexProperty()
|
||||
v.vertex.set1Value(0, p1)
|
||||
v.vertex.set1Value(1, p2)
|
||||
l = coin.SoLineSet()
|
||||
l.vertexProperty = v
|
||||
dash.addChild(l)
|
||||
return dash
|
||||
dimSymbol = draftutils.gui_utils.dim_symbol
|
||||
dim_symbol = draftutils.gui_utils.dim_symbol
|
||||
|
||||
dimDash = draftutils.gui_utils.dim_dash
|
||||
dim_dash = draftutils.gui_utils.dim_dash
|
||||
|
||||
shapify = draftutils.utils.shapify
|
||||
|
||||
getGroupContents = draftutils.utils.get_group_contents
|
||||
get_group_contents = draftutils.utils.get_group_contents
|
||||
|
||||
|
||||
def removeHidden(objectslist):
|
||||
"""removeHidden(objectslist): removes hidden objects from the list"""
|
||||
newlist = objectslist[:]
|
||||
for o in objectslist:
|
||||
if o.ViewObject:
|
||||
if not o.ViewObject.isVisible():
|
||||
newlist.remove(o)
|
||||
return newlist
|
||||
|
||||
removeHidden = draftutils.gui_utils.remove_hidden
|
||||
remove_hidden = draftutils.gui_utils.remove_hidden
|
||||
|
||||
printShape = draftutils.utils.print_shape
|
||||
print_shape = draftutils.utils.print_shape
|
||||
@@ -266,91 +145,16 @@ print_shape = draftutils.utils.print_shape
|
||||
compareObjects = draftutils.utils.compare_objects
|
||||
compare_objects = draftutils.utils.compare_objects
|
||||
|
||||
formatObject = draftutils.gui_utils.format_object
|
||||
format_object = draftutils.gui_utils.format_object
|
||||
|
||||
def formatObject(target,origin=None):
|
||||
"""
|
||||
formatObject(targetObject,[originObject]): This function applies
|
||||
to the given target object the current properties
|
||||
set on the toolbar (line color and line width),
|
||||
or copies the properties of another object if given as origin.
|
||||
It also places the object in construction group if needed.
|
||||
"""
|
||||
if not target:
|
||||
return
|
||||
obrep = target.ViewObject
|
||||
if not obrep:
|
||||
return
|
||||
ui = None
|
||||
if gui:
|
||||
if hasattr(FreeCADGui,"draftToolBar"):
|
||||
ui = FreeCADGui.draftToolBar
|
||||
if ui:
|
||||
doc = FreeCAD.ActiveDocument
|
||||
if ui.isConstructionMode():
|
||||
col = fcol = ui.getDefaultColor("constr")
|
||||
gname = getParam("constructiongroupname","Construction")
|
||||
grp = doc.getObject(gname)
|
||||
if not grp:
|
||||
grp = doc.addObject("App::DocumentObjectGroup",gname)
|
||||
grp.addObject(target)
|
||||
if hasattr(obrep,"Transparency"):
|
||||
obrep.Transparency = 80
|
||||
else:
|
||||
col = ui.getDefaultColor("ui")
|
||||
fcol = ui.getDefaultColor("face")
|
||||
col = (float(col[0]),float(col[1]),float(col[2]),0.0)
|
||||
fcol = (float(fcol[0]),float(fcol[1]),float(fcol[2]),0.0)
|
||||
lw = ui.linewidth
|
||||
fs = ui.fontsize
|
||||
if not origin or not hasattr(origin,'ViewObject'):
|
||||
if "FontSize" in obrep.PropertiesList: obrep.FontSize = fs
|
||||
if "TextColor" in obrep.PropertiesList: obrep.TextColor = col
|
||||
if "LineWidth" in obrep.PropertiesList: obrep.LineWidth = lw
|
||||
if "PointColor" in obrep.PropertiesList: obrep.PointColor = col
|
||||
if "LineColor" in obrep.PropertiesList: obrep.LineColor = col
|
||||
if "ShapeColor" in obrep.PropertiesList: obrep.ShapeColor = fcol
|
||||
else:
|
||||
matchrep = origin.ViewObject
|
||||
for p in matchrep.PropertiesList:
|
||||
if not p in ["DisplayMode","BoundingBox","Proxy","RootNode","Visibility"]:
|
||||
if p in obrep.PropertiesList:
|
||||
if not obrep.getEditorMode(p):
|
||||
if hasattr(getattr(matchrep,p),"Value"):
|
||||
val = getattr(matchrep,p).Value
|
||||
else:
|
||||
val = getattr(matchrep,p)
|
||||
try:
|
||||
setattr(obrep,p,val)
|
||||
except Exception:
|
||||
pass
|
||||
if matchrep.DisplayMode in obrep.listDisplayModes():
|
||||
obrep.DisplayMode = matchrep.DisplayMode
|
||||
if hasattr(matchrep,"DiffuseColor") and hasattr(obrep,"DiffuseColor"):
|
||||
obrep.DiffuseColor = matchrep.DiffuseColor
|
||||
getSelection = draftutils.gui_utils.get_selection
|
||||
get_selection = draftutils.gui_utils.get_selection
|
||||
|
||||
def getSelection():
|
||||
"""getSelection(): returns the current FreeCAD selection"""
|
||||
if gui:
|
||||
return FreeCADGui.Selection.getSelection()
|
||||
return None
|
||||
|
||||
def getSelectionEx():
|
||||
"""getSelectionEx(): returns the current FreeCAD selection (with subobjects)"""
|
||||
if gui:
|
||||
return FreeCADGui.Selection.getSelectionEx()
|
||||
return None
|
||||
|
||||
def select(objs=None):
|
||||
"""select(object): deselects everything and selects only the passed object or list"""
|
||||
if gui:
|
||||
FreeCADGui.Selection.clearSelection()
|
||||
if objs:
|
||||
if not isinstance(objs,list):
|
||||
objs = [objs]
|
||||
for obj in objs:
|
||||
if obj:
|
||||
FreeCADGui.Selection.addSelection(obj)
|
||||
getSelectionEx = draftutils.gui_utils.get_selection_ex
|
||||
get_selection_ex = draftutils.gui_utils.get_selection_ex
|
||||
|
||||
select = draftutils.gui_utils.select
|
||||
|
||||
loadSvgPatterns = draftutils.utils.load_svg_patterns
|
||||
load_svg_patterns = draftutils.utils.load_svg_patterns
|
||||
@@ -358,86 +162,8 @@ load_svg_patterns = draftutils.utils.load_svg_patterns
|
||||
svgpatterns = draftutils.utils.svg_patterns
|
||||
svg_patterns = draftutils.utils.svg_patterns
|
||||
|
||||
|
||||
def loadTexture(filename,size=None):
|
||||
"""loadTexture(filename,[size]): returns a SoSFImage from a file. If size
|
||||
is defined (an int or a tuple), and provided the input image is a png file,
|
||||
it will be scaled to match the given size."""
|
||||
if gui:
|
||||
from pivy import coin
|
||||
from PySide import QtGui,QtSvg
|
||||
try:
|
||||
p = QtGui.QImage(filename)
|
||||
# buggy - TODO: allow to use resolutions
|
||||
#if size and (".svg" in filename.lower()):
|
||||
# # this is a pattern, not a texture
|
||||
# if isinstance(size,int):
|
||||
# size = (size,size)
|
||||
# svgr = QtSvg.QSvgRenderer(filename)
|
||||
# p = QtGui.QImage(size[0],size[1],QtGui.QImage.Format_ARGB32)
|
||||
# pa = QtGui.QPainter()
|
||||
# pa.begin(p)
|
||||
# svgr.render(pa)
|
||||
# pa.end()
|
||||
#else:
|
||||
# p = QtGui.QImage(filename)
|
||||
size = coin.SbVec2s(p.width(), p.height())
|
||||
buffersize = p.byteCount()
|
||||
numcomponents = int (float(buffersize) / ( size[0] * size[1] ))
|
||||
|
||||
img = coin.SoSFImage()
|
||||
width = size[0]
|
||||
height = size[1]
|
||||
byteList = []
|
||||
isPy2 = sys.version_info.major < 3
|
||||
|
||||
for y in range(height):
|
||||
#line = width*numcomponents*(height-(y));
|
||||
for x in range(width):
|
||||
rgb = p.pixel(x,y)
|
||||
if numcomponents == 1:
|
||||
if isPy2:
|
||||
byteList.append(chr(QtGui.qGray( rgb )))
|
||||
else:
|
||||
byteList.append(chr(QtGui.qGray( rgb )).encode('latin-1'))
|
||||
elif numcomponents == 2:
|
||||
if isPy2:
|
||||
byteList.append(chr(QtGui.qGray( rgb )))
|
||||
byteList.append(chr(QtGui.qAlpha( rgb )))
|
||||
else:
|
||||
byteList.append(chr(QtGui.qGray( rgb )).encode('latin-1'))
|
||||
byteList.append(chr(QtGui.qAlpha( rgb )).encode('latin-1'))
|
||||
elif numcomponents == 3:
|
||||
if isPy2:
|
||||
byteList.append(chr(QtGui.qRed( rgb )))
|
||||
byteList.append(chr(QtGui.qGreen( rgb )))
|
||||
byteList.append(chr(QtGui.qBlue( rgb )))
|
||||
else:
|
||||
byteList.append(chr(QtGui.qRed( rgb )).encode('latin-1'))
|
||||
byteList.append(chr(QtGui.qGreen( rgb )).encode('latin-1'))
|
||||
byteList.append(chr(QtGui.qBlue( rgb )).encode('latin-1'))
|
||||
elif numcomponents == 4:
|
||||
if isPy2:
|
||||
byteList.append(chr(QtGui.qRed( rgb )))
|
||||
byteList.append(chr(QtGui.qGreen( rgb )))
|
||||
byteList.append(chr(QtGui.qBlue( rgb )))
|
||||
byteList.append(chr(QtGui.qAlpha( rgb )))
|
||||
else:
|
||||
byteList.append(chr(QtGui.qRed( rgb )).encode('latin-1'))
|
||||
byteList.append(chr(QtGui.qGreen( rgb )).encode('latin-1'))
|
||||
byteList.append(chr(QtGui.qBlue( rgb )).encode('latin-1'))
|
||||
byteList.append(chr(QtGui.qAlpha( rgb )).encode('latin-1'))
|
||||
#line += numcomponents
|
||||
|
||||
bytes = b"".join(byteList)
|
||||
img.setValue(size, numcomponents, bytes)
|
||||
except:
|
||||
print("Draft: unable to load texture")
|
||||
return None
|
||||
else:
|
||||
return img
|
||||
return None
|
||||
|
||||
loadTexture = draftutils.gui_utils.load_texture
|
||||
load_texture = draftutils.gui_utils.load_texture
|
||||
|
||||
getMovableChildren = draftutils.utils.get_movable_children
|
||||
get_movable_children = draftutils.utils.get_movable_children
|
||||
|
||||
@@ -1218,8 +1218,9 @@ def offsetWire(wire,dvec,bind=False,occ=False,widthList=None, offsetMode=None, a
|
||||
'dvec' vector to offset is now derived (and can be ignored) in this function if widthList and alignList are provided - 'dvec' to be obsolete in future ?
|
||||
'''
|
||||
|
||||
# Accept 'wire' as a list of edges, use the list directly, or previously a wire
|
||||
if isinstance(wire,Part.Wire):
|
||||
# Accept 'wire' as a list of edges (use the list directly), or previously as a wire or a face (Draft Wire with MakeFace True or False supported)
|
||||
|
||||
if isinstance(wire,Part.Wire) or isinstance(wire,Part.Face):
|
||||
edges = wire.Edges # Seems has repeatedly sortEdges, remark out here - edges = Part.__sortEdges__(wire.Edges)
|
||||
elif isinstance(wire, list):
|
||||
if isinstance(wire[0],Part.Edge):
|
||||
@@ -1273,7 +1274,7 @@ def offsetWire(wire,dvec,bind=False,occ=False,widthList=None, offsetMode=None, a
|
||||
firstDir = 1
|
||||
firstAlign = 'Center'
|
||||
except:
|
||||
print ("alignListC[0] has no value ") # Should no longer happen for ArchWall - as aligns are 'filled in' by ArchWall
|
||||
pass # Should no longer happen for ArchWall - as aligns are 'filled in' by ArchWall
|
||||
|
||||
# If not provided by alignListC checked above, check the direction of offset in dvec (not 'align')
|
||||
|
||||
|
||||
@@ -106,7 +106,26 @@ class DraftModification(unittest.TestCase):
|
||||
self.assertTrue(obj.Start.isEqual(c, 1e-12),
|
||||
"'{}' failed".format(operation))
|
||||
|
||||
def test_offset(self):
|
||||
def test_offset_open(self):
|
||||
"""Create a wire, then produce an offset copy."""
|
||||
operation = "Draft Offset"
|
||||
_msg(" Test '{}'".format(operation))
|
||||
a = Vector(0, 2, 0)
|
||||
b = Vector(2, 4, 0)
|
||||
c = Vector(5, 2, 0)
|
||||
_msg(" Wire")
|
||||
_msg(" a={0}, b={1}".format(a, b))
|
||||
_msg(" c={0}".format(c))
|
||||
wire = Draft.makeWire([a, b, c])
|
||||
App.ActiveDocument.recompute()
|
||||
|
||||
offset = Vector(-1, 1, 0)
|
||||
_msg(" Offset")
|
||||
_msg(" vector={}".format(offset))
|
||||
obj = Draft.offset(wire, offset, copy=True)
|
||||
self.assertTrue(obj, "'{}' failed".format(operation))
|
||||
|
||||
def test_offset_closed(self):
|
||||
"""Create a rectangle, then produce an offset copy."""
|
||||
operation = "Draft Offset"
|
||||
_msg(" Test '{}'".format(operation))
|
||||
|
||||
612
src/Mod/Draft/draftutils/gui_utils.py
Normal file
612
src/Mod/Draft/draftutils/gui_utils.py
Normal file
@@ -0,0 +1,612 @@
|
||||
"""This module provides GUI utility functions for the Draft Workbench.
|
||||
|
||||
This module should contain auxiliary functions which require
|
||||
the graphical user interface (GUI).
|
||||
"""
|
||||
## @package gui_utils
|
||||
# \ingroup DRAFT
|
||||
# \brief This module provides utility functions for the Draft Workbench
|
||||
|
||||
# ***************************************************************************
|
||||
# * (c) 2009, 2010 *
|
||||
# * Yorik van Havre <yorik@uncreated.net>, Ken Cline <cline@frii.com> *
|
||||
# * (c) 2019 Eliud Cabrera Castillo <e.cabrera-castillo@tum.de> *
|
||||
# * *
|
||||
# * This file is part of the FreeCAD CAx development system. *
|
||||
# * *
|
||||
# * This program is free software; you can redistribute it and/or modify *
|
||||
# * it under the terms of the GNU Lesser General Public License (LGPL) *
|
||||
# * as published by the Free Software Foundation; either version 2 of *
|
||||
# * the License, or (at your option) any later version. *
|
||||
# * for detail see the LICENCE text file. *
|
||||
# * *
|
||||
# * FreeCAD is distributed in the hope that it will be useful, *
|
||||
# * but WITHOUT ANY WARRANTY; without even the implied warranty of *
|
||||
# * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
|
||||
# * GNU Library General Public License for more details. *
|
||||
# * *
|
||||
# * You should have received a copy of the GNU Library General Public *
|
||||
# * License along with FreeCAD; if not, write to the Free Software *
|
||||
# * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 *
|
||||
# * USA *
|
||||
# * *
|
||||
# ***************************************************************************
|
||||
|
||||
|
||||
import FreeCAD
|
||||
import FreeCADGui
|
||||
from .utils import _msg
|
||||
from .utils import _wrn
|
||||
# from .utils import _log
|
||||
from .utils import _tr
|
||||
from .utils import getParam
|
||||
from pivy import coin
|
||||
from PySide import QtGui
|
||||
# from PySide import QtSvg # for load_texture
|
||||
import os
|
||||
import math
|
||||
import six
|
||||
|
||||
|
||||
def get_3d_view():
|
||||
"""Return the current 3D view.
|
||||
|
||||
Returns
|
||||
-------
|
||||
Gui::View3DInventor
|
||||
Return the current `ActiveView` in the active document,
|
||||
or the first `Gui::View3DInventor` view found.
|
||||
|
||||
Return `None` if the graphical interface is not available.
|
||||
"""
|
||||
if FreeCAD.GuiUp:
|
||||
v = FreeCADGui.ActiveDocument.ActiveView
|
||||
if "View3DInventor" in str(type(v)):
|
||||
return v
|
||||
|
||||
# print("Debug: Draft: Warning, not working in active view")
|
||||
v = FreeCADGui.ActiveDocument.mdiViewsOfType("Gui::View3DInventor")
|
||||
if v:
|
||||
return v[0]
|
||||
|
||||
_wrn(_tr("No graphical interface"))
|
||||
return None
|
||||
|
||||
|
||||
get3DView = get_3d_view
|
||||
|
||||
|
||||
def autogroup(obj):
|
||||
"""Adds a given object to the defined Draft autogroup, if applicable.
|
||||
|
||||
This function only works if the graphical interface is available.
|
||||
It checks that the `FreeCAD.draftToolBar` class is available,
|
||||
which contains the group to use to automatically store
|
||||
new created objects.
|
||||
|
||||
Originally, it worked with standard groups (`App::DocumentObjectGroup`),
|
||||
and Arch Workbench containers like `'Site'`, `'Building'`, `'Floor'`,
|
||||
and `'BuildingPart'`.
|
||||
|
||||
Now it works with Draft Layers.
|
||||
|
||||
Parameters
|
||||
----------
|
||||
obj : App::DocumentObject
|
||||
Any type of object that will be stored in the group.
|
||||
"""
|
||||
doc = FreeCAD.ActiveDocument
|
||||
if FreeCAD.GuiUp:
|
||||
view = FreeCADGui.ActiveDocument.ActiveView
|
||||
if hasattr(FreeCADGui, "draftToolBar"):
|
||||
if (hasattr(FreeCADGui.draftToolBar, "autogroup")
|
||||
and not FreeCADGui.draftToolBar.isConstructionMode()):
|
||||
if FreeCADGui.draftToolBar.autogroup is not None:
|
||||
g = doc.getObject(FreeCADGui.draftToolBar.autogroup)
|
||||
if g:
|
||||
found = False
|
||||
for o in g.Group:
|
||||
if o.Name == obj.Name:
|
||||
found = True
|
||||
if not found:
|
||||
gr = g.Group
|
||||
gr.append(obj)
|
||||
g.Group = gr
|
||||
else:
|
||||
# Arch active container
|
||||
a = view.getActiveObject("Arch")
|
||||
if a:
|
||||
a.addObject(obj)
|
||||
|
||||
|
||||
def dim_symbol(symbol=None, invert=False):
|
||||
"""Return the specified dimension symbol.
|
||||
|
||||
Parameters
|
||||
----------
|
||||
symbol : int, optional
|
||||
It defaults to `None`, in which it gets the value from the parameter
|
||||
database, `get_param("dimsymbol", 0)`.
|
||||
|
||||
A numerical value defines different markers
|
||||
* 0, `SoSphere`
|
||||
* 1, `SoMarkerSet` with a circle
|
||||
* 2, `SoSeparator` with a `soCone`
|
||||
* 3, `SoSeparator` with a `SoFaceSet`
|
||||
* 4, `SoSeparator` with a `SoLineSet`, calling `dim_dash`
|
||||
* Otherwise, `SoSphere`
|
||||
|
||||
invert : bool, optional
|
||||
It defaults to `False`.
|
||||
If it is `True` and `symbol=2`, the cone will be rotated
|
||||
-90 degrees around the Z axis, otherwise the rotation is positive,
|
||||
+90 degrees.
|
||||
|
||||
Returns
|
||||
-------
|
||||
Coin.SoNode
|
||||
A `Coin.SoSphere`, or `Coin.SoMarkerSet` (circle),
|
||||
or `Coin.SoSeparator` (cone, face, line)
|
||||
that will be used as a dimension symbol.
|
||||
"""
|
||||
if symbol is None:
|
||||
symbol = getParam("dimsymbol", 0)
|
||||
|
||||
if symbol == 0:
|
||||
return coin.SoSphere()
|
||||
elif symbol == 1:
|
||||
marker = coin.SoMarkerSet()
|
||||
marker.markerIndex = FreeCADGui.getMarkerIndex("circle", 9)
|
||||
return marker
|
||||
elif symbol == 2:
|
||||
marker = coin.SoSeparator()
|
||||
t = coin.SoTransform()
|
||||
t.translation.setValue((0, -2, 0))
|
||||
t.center.setValue((0, 2, 0))
|
||||
if invert:
|
||||
t.rotation.setValue(coin.SbVec3f((0, 0, 1)), -math.pi/2)
|
||||
else:
|
||||
t.rotation.setValue(coin.SbVec3f((0, 0, 1)), math.pi/2)
|
||||
c = coin.SoCone()
|
||||
c.height.setValue(4)
|
||||
marker.addChild(t)
|
||||
marker.addChild(c)
|
||||
return marker
|
||||
elif symbol == 3:
|
||||
marker = coin.SoSeparator()
|
||||
c = coin.SoCoordinate3()
|
||||
c.point.setValues([(-1, -2, 0), (0, 2, 0),
|
||||
(1, 2, 0), (0, -2, 0)])
|
||||
f = coin.SoFaceSet()
|
||||
marker.addChild(c)
|
||||
marker.addChild(f)
|
||||
return marker
|
||||
elif symbol == 4:
|
||||
return dimDash((-1.5, -1.5, 0), (1.5, 1.5, 0))
|
||||
else:
|
||||
_wrn(_tr("Symbol not implemented. Use a default symbol."))
|
||||
return coin.SoSphere()
|
||||
|
||||
|
||||
dimSymbol = dim_symbol
|
||||
|
||||
|
||||
def dim_dash(p1, p2):
|
||||
"""Return a SoSeparator with a line used to make dimension dashes.
|
||||
|
||||
It is used by `dim_symbol` to create line end symbols
|
||||
like `'Tick-2'`, `'DimOvershoot'`, and `'ExtOvershoot'` dashes.
|
||||
|
||||
Parameters
|
||||
----------
|
||||
p1 : tuple of three floats or Base::Vector3
|
||||
A point to define a line vertex.
|
||||
|
||||
p2 : tuple of three floats or Base::Vector3
|
||||
A point to define a line vertex.
|
||||
|
||||
Returns
|
||||
-------
|
||||
Coin.SoSeparator
|
||||
A Coin object with a `SoLineSet` created from `p1` and `p2`
|
||||
as vertices.
|
||||
"""
|
||||
dash = coin.SoSeparator()
|
||||
v = coin.SoVertexProperty()
|
||||
v.vertex.set1Value(0, p1)
|
||||
v.vertex.set1Value(1, p2)
|
||||
line = coin.SoLineSet()
|
||||
line.vertexProperty = v
|
||||
dash.addChild(line)
|
||||
return dash
|
||||
|
||||
|
||||
dimDash = dim_dash
|
||||
|
||||
|
||||
def remove_hidden(objectslist):
|
||||
"""Return only the visible objects in the list.
|
||||
|
||||
This function only works if the graphical interface is available
|
||||
as the `Visibility` attribute is a property of the view provider
|
||||
(`obj.ViewObject`).
|
||||
|
||||
Parameters
|
||||
----------
|
||||
objectslist : list of App::DocumentObject
|
||||
List of any type of object.
|
||||
|
||||
Returns
|
||||
-------
|
||||
list
|
||||
Return a copy of the input list without those objects
|
||||
for which `obj.ViewObject.Visibility` is `False`.
|
||||
|
||||
If the graphical interface is not loaded
|
||||
the returned list is just a copy of the input list.
|
||||
"""
|
||||
newlist = objectslist[:]
|
||||
for obj in objectslist:
|
||||
if obj.ViewObject:
|
||||
if not obj.ViewObject.isVisible():
|
||||
newlist.remove(obj)
|
||||
_msg(_tr("Visibility off; removed from list: ") + obj.Label)
|
||||
return newlist
|
||||
|
||||
|
||||
removeHidden = remove_hidden
|
||||
|
||||
|
||||
def format_object(target, origin=None):
|
||||
"""Apply visual properties from the Draft toolbar or another object.
|
||||
|
||||
This function only works if the graphical interface is available
|
||||
as the visual properties are attributes of the view provider
|
||||
(`obj.ViewObject`).
|
||||
|
||||
Parameters
|
||||
----------
|
||||
target : App::DocumentObject
|
||||
Any type of scripted object.
|
||||
|
||||
This object will adopt the applicable visual properties,
|
||||
`FontSize`, `TextColor`, `LineWidth`, `PointColor`, `LineColor`,
|
||||
and `ShapeColor`, defined in the Draft toolbar
|
||||
(`FreeCADGui.draftToolBar`) or will adopt
|
||||
the properties from the `origin` object.
|
||||
|
||||
The `target` is also placed in the construction group
|
||||
if the construction mode in the Draft toolbar is active.
|
||||
|
||||
origin : App::DocumentObject, optional
|
||||
It defaults to `None`.
|
||||
If it exists, it will provide the visual properties to assign
|
||||
to `target`, with the exception of `BoundingBox`, `Proxy`,
|
||||
`RootNode` and `Visibility`.
|
||||
"""
|
||||
if not target:
|
||||
return
|
||||
obrep = target.ViewObject
|
||||
if not obrep:
|
||||
return
|
||||
ui = None
|
||||
if FreeCAD.GuiUp:
|
||||
if hasattr(FreeCADGui, "draftToolBar"):
|
||||
ui = FreeCADGui.draftToolBar
|
||||
if ui:
|
||||
doc = FreeCAD.ActiveDocument
|
||||
if ui.isConstructionMode():
|
||||
col = fcol = ui.getDefaultColor("constr")
|
||||
gname = getParam("constructiongroupname", "Construction")
|
||||
grp = doc.getObject(gname)
|
||||
if not grp:
|
||||
grp = doc.addObject("App::DocumentObjectGroup", gname)
|
||||
grp.addObject(target)
|
||||
if hasattr(obrep, "Transparency"):
|
||||
obrep.Transparency = 80
|
||||
else:
|
||||
col = ui.getDefaultColor("ui")
|
||||
fcol = ui.getDefaultColor("face")
|
||||
col = (float(col[0]), float(col[1]), float(col[2]), 0.0)
|
||||
fcol = (float(fcol[0]), float(fcol[1]), float(fcol[2]), 0.0)
|
||||
lw = ui.linewidth
|
||||
fs = ui.fontsize
|
||||
if not origin or not hasattr(origin, 'ViewObject'):
|
||||
if "FontSize" in obrep.PropertiesList:
|
||||
obrep.FontSize = fs
|
||||
if "TextColor" in obrep.PropertiesList:
|
||||
obrep.TextColor = col
|
||||
if "LineWidth" in obrep.PropertiesList:
|
||||
obrep.LineWidth = lw
|
||||
if "PointColor" in obrep.PropertiesList:
|
||||
obrep.PointColor = col
|
||||
if "LineColor" in obrep.PropertiesList:
|
||||
obrep.LineColor = col
|
||||
if "ShapeColor" in obrep.PropertiesList:
|
||||
obrep.ShapeColor = fcol
|
||||
else:
|
||||
matchrep = origin.ViewObject
|
||||
for p in matchrep.PropertiesList:
|
||||
if p not in ("DisplayMode", "BoundingBox",
|
||||
"Proxy", "RootNode", "Visibility"):
|
||||
if p in obrep.PropertiesList:
|
||||
if not obrep.getEditorMode(p):
|
||||
if hasattr(getattr(matchrep, p), "Value"):
|
||||
val = getattr(matchrep, p).Value
|
||||
else:
|
||||
val = getattr(matchrep, p)
|
||||
try:
|
||||
setattr(obrep, p, val)
|
||||
except Exception:
|
||||
pass
|
||||
if matchrep.DisplayMode in obrep.listDisplayModes():
|
||||
obrep.DisplayMode = matchrep.DisplayMode
|
||||
if (hasattr(matchrep, "DiffuseColor")
|
||||
and hasattr(obrep, "DiffuseColor")):
|
||||
obrep.DiffuseColor = matchrep.DiffuseColor
|
||||
|
||||
|
||||
formatObject = format_object
|
||||
|
||||
|
||||
def get_selection(gui=FreeCAD.GuiUp):
|
||||
"""Return the current selected objects.
|
||||
|
||||
This function only works if the graphical interface is available
|
||||
as the selection module only works on the 3D view.
|
||||
|
||||
It wraps around `FreeCADGui.Selection.getSelection`
|
||||
|
||||
Parameters
|
||||
----------
|
||||
gui : bool, optional
|
||||
It defaults to the value of `FreeCAD.GuiUp`, which is `True`
|
||||
when the interface exists, and `False` otherwise.
|
||||
|
||||
This value can be set to `False` to simulate
|
||||
when the interface is not available.
|
||||
|
||||
Returns
|
||||
-------
|
||||
list of App::DocumentObject
|
||||
Returns a list of objects in the current selection.
|
||||
It can be an empty list if no object is selected.
|
||||
|
||||
If the interface is not available, it returns `None`.
|
||||
"""
|
||||
if gui:
|
||||
return FreeCADGui.Selection.getSelection()
|
||||
return None
|
||||
|
||||
|
||||
getSelection = get_selection
|
||||
|
||||
|
||||
def get_selection_ex(gui=FreeCAD.GuiUp):
|
||||
"""Return the current selected objects together with their subelements.
|
||||
|
||||
This function only works if the graphical interface is available
|
||||
as the selection module only works on the 3D view.
|
||||
|
||||
It wraps around `FreeCADGui.Selection.getSelectionEx`
|
||||
|
||||
Parameters
|
||||
----------
|
||||
gui : bool, optional
|
||||
It defaults to the value of `FreeCAD.GuiUp`, which is `True`
|
||||
when the interface exists, and `False` otherwise.
|
||||
|
||||
This value can be set to `False` to simulate
|
||||
when the interface is not available.
|
||||
|
||||
Returns
|
||||
-------
|
||||
list of Gui::SelectionObject
|
||||
Returns a list of `Gui::SelectionObject` in the current selection.
|
||||
It can be an empty list if no object is selected.
|
||||
|
||||
If the interface is not available, it returns `None`.
|
||||
|
||||
Selection objects
|
||||
-----------------
|
||||
One `Gui::SelectionObject` has attributes that indicate which specific
|
||||
subelements, that is, vertices, wires, and faces, were selected.
|
||||
This can be useful to operate on the subelements themselves.
|
||||
If `G` is a `Gui::SelectionObject`
|
||||
* `G.Object` is the selected object
|
||||
* `G.ObjectName` is the name of the selected object
|
||||
* `G.HasSubObjects` is `True` if there are subelements in the selection
|
||||
* `G.SubObjects` is a tuple of the subelements' shapes
|
||||
* `G.SubElementNames` is a tuple of the subelements' names
|
||||
|
||||
`SubObjects` and `SubElementNames` should be empty tuples
|
||||
if `HasSubObjects` is `False`.
|
||||
"""
|
||||
if gui:
|
||||
return FreeCADGui.Selection.getSelectionEx()
|
||||
return None
|
||||
|
||||
|
||||
getSelectionEx = get_selection_ex
|
||||
|
||||
|
||||
def select(objs=None, gui=FreeCAD.GuiUp):
|
||||
"""Unselects everything and selects only the given list of objects.
|
||||
|
||||
This function only works if the graphical interface is available
|
||||
as the selection module only works on the 3D view.
|
||||
|
||||
Parameters
|
||||
----------
|
||||
objs : list of App::DocumentObject, optional
|
||||
It defaults to `None`.
|
||||
Any type of scripted object.
|
||||
It may be a list of objects or a single object.
|
||||
|
||||
gui : bool, optional
|
||||
It defaults to the value of `FreeCAD.GuiUp`, which is `True`
|
||||
when the interface exists, and `False` otherwise.
|
||||
|
||||
This value can be set to `False` to simulate
|
||||
when the interface is not available.
|
||||
"""
|
||||
if gui:
|
||||
FreeCADGui.Selection.clearSelection()
|
||||
if objs:
|
||||
if not isinstance(objs, list):
|
||||
objs = [objs]
|
||||
for obj in objs:
|
||||
if obj:
|
||||
FreeCADGui.Selection.addSelection(obj)
|
||||
|
||||
|
||||
def load_texture(filename, size=None, gui=FreeCAD.GuiUp):
|
||||
"""Return a Coin.SoSFImage to use as a texture for a 2D plane.
|
||||
|
||||
This function only works if the graphical interface is available
|
||||
as the visual properties that can be applied to a shape
|
||||
are attributes of the view provider (`obj.ViewObject`).
|
||||
|
||||
Parameters
|
||||
----------
|
||||
filename : str
|
||||
A path to a pixel image file (PNG) that can be used as a texture
|
||||
on the face of an object.
|
||||
|
||||
size : tuple of two int, or a single int, optional
|
||||
It defaults to `None`.
|
||||
If a tuple is given, the two values define the width and height
|
||||
in pixels to which the loaded image will be scaled.
|
||||
If it is a single value, it is used for both dimensions.
|
||||
|
||||
If it is `None`, the size will be determined from the `QImage`
|
||||
created from `filename`.
|
||||
|
||||
CURRENTLY the input `size` parameter IS NOT USED.
|
||||
It always uses the `QImage` to determine this information.
|
||||
|
||||
gui : bool, optional
|
||||
It defaults to the value of `FreeCAD.GuiUp`, which is `True`
|
||||
when the interface exists, and `False` otherwise.
|
||||
|
||||
This value can be set to `False` to simulate
|
||||
when the interface is not available.
|
||||
|
||||
Returns
|
||||
-------
|
||||
coin.SoSFImage
|
||||
An image object with the appropriate size, number of components
|
||||
(grayscale, grayscale and transparency, color,
|
||||
color and transparency), and byte data.
|
||||
|
||||
It returns `None` if the interface is not available,
|
||||
or if there is a problem creating the image.
|
||||
"""
|
||||
if gui:
|
||||
# from pivy import coin
|
||||
# from PySide import QtGui, QtSvg
|
||||
try:
|
||||
p = QtGui.QImage(filename)
|
||||
|
||||
if p.isNull():
|
||||
_wrn("load_texture: " + _tr("image is Null"))
|
||||
|
||||
if not os.path.exists(filename):
|
||||
raise FileNotFoundError(-1,
|
||||
_tr("filename does not exist "
|
||||
"on the system or "
|
||||
"on the resource file"),
|
||||
filename)
|
||||
|
||||
# This is buggy so it was de-activated.
|
||||
#
|
||||
# TODO: allow SVGs to use resolutions
|
||||
# if size and (".svg" in filename.lower()):
|
||||
# # this is a pattern, not a texture
|
||||
# if isinstance(size, int):
|
||||
# size = (size, size)
|
||||
# svgr = QtSvg.QSvgRenderer(filename)
|
||||
# p = QtGui.QImage(size[0], size[1],
|
||||
# QtGui.QImage.Format_ARGB32)
|
||||
# pa = QtGui.QPainter()
|
||||
# pa.begin(p)
|
||||
# svgr.render(pa)
|
||||
# pa.end()
|
||||
# else:
|
||||
# p = QtGui.QImage(filename)
|
||||
size = coin.SbVec2s(p.width(), p.height())
|
||||
buffersize = p.byteCount()
|
||||
width = size[0]
|
||||
height = size[1]
|
||||
numcomponents = int(float(buffersize) / (width * height))
|
||||
|
||||
img = coin.SoSFImage()
|
||||
byteList = []
|
||||
# isPy2 = sys.version_info.major < 3
|
||||
isPy2 = six.PY2
|
||||
|
||||
# The SoSFImage needs to be filled with bytes.
|
||||
# The pixel information is converted into a Qt color, gray,
|
||||
# red, green, blue, or transparency (alpha),
|
||||
# depending on the input image.
|
||||
#
|
||||
# If Python 2 is used, the color is turned into a character,
|
||||
# which is of type 'byte', and added to the byte list.
|
||||
# If Python 3 is used, characters are unicode strings,
|
||||
# so they need to be encoded into 'latin-1'
|
||||
# to produce the correct bytes for the list.
|
||||
for y in range(height):
|
||||
# line = width*numcomponents*(height-(y));
|
||||
for x in range(width):
|
||||
rgb = p.pixel(x, y)
|
||||
if numcomponents == 1 or numcomponents == 2:
|
||||
gray = chr(QtGui.qGray(rgb))
|
||||
if isPy2:
|
||||
byteList.append(gray)
|
||||
else:
|
||||
byteList.append(gray.encode('latin-1'))
|
||||
|
||||
if numcomponents == 2:
|
||||
alpha = chr(QtGui.qAlpha(rgb))
|
||||
if isPy2:
|
||||
byteList.append(alpha)
|
||||
else:
|
||||
byteList.append(alpha.encode('latin-1'))
|
||||
elif numcomponents == 3 or numcomponents == 4:
|
||||
red = chr(QtGui.qRed(rgb))
|
||||
green = chr(QtGui.qGreen(rgb))
|
||||
blue = chr(QtGui.qBlue(rgb))
|
||||
|
||||
if isPy2:
|
||||
byteList.append(red)
|
||||
byteList.append(green)
|
||||
byteList.append(blue)
|
||||
else:
|
||||
byteList.append(red.encode('latin-1'))
|
||||
byteList.append(green.encode('latin-1'))
|
||||
byteList.append(blue.encode('latin-1'))
|
||||
|
||||
if numcomponents == 4:
|
||||
alpha = chr(QtGui.qAlpha(rgb))
|
||||
if isPy2:
|
||||
byteList.append(alpha)
|
||||
else:
|
||||
byteList.append(alpha.encode('latin-1'))
|
||||
# line += numcomponents
|
||||
|
||||
_bytes = b"".join(byteList)
|
||||
img.setValue(size, numcomponents, _bytes)
|
||||
except FileNotFoundError as exc:
|
||||
_wrn("load_texture: {0}, {1}".format(exc.strerror,
|
||||
exc.filename))
|
||||
return None
|
||||
except Exception as exc:
|
||||
_wrn(str(exc))
|
||||
_wrn("load_texture: " + _tr("unable to load texture"))
|
||||
return None
|
||||
else:
|
||||
return img
|
||||
return None
|
||||
|
||||
|
||||
loadTexture = load_texture
|
||||
@@ -74,6 +74,8 @@ def importFrd(
|
||||
|
||||
m = read_frd_result(filename)
|
||||
result_mesh_object = None
|
||||
res_obj = None
|
||||
|
||||
if len(m["Nodes"]) > 0:
|
||||
mesh = importToolsFem.make_femmesh(m)
|
||||
result_mesh_object = ObjectsFem.makeMeshResult(
|
||||
@@ -166,15 +168,29 @@ def importFrd(
|
||||
|
||||
else:
|
||||
error_message = (
|
||||
"We have nodes but no results in frd file, "
|
||||
"which means we only have a mesh in frd file. "
|
||||
"Usually this happens for analysis type 'NOANALYSIS' "
|
||||
"or if CalculiX returned no results because "
|
||||
"of nonpositive jacobian determinant in at least one element.\n"
|
||||
"Nodes, but no results found in frd file. "
|
||||
"It means there only is a mesh but no results in frd file. "
|
||||
"Usually this happens for: \n"
|
||||
"- analysis type 'NOANALYSIS'\n"
|
||||
"- if CalculiX returned no results "
|
||||
"(happens on nonpositive jacobian determinant in at least one element)\n"
|
||||
"- just no frd results where requestet in input file "
|
||||
"(neither 'node file' nor 'el file' in output section')\n"
|
||||
)
|
||||
Console.PrintMessage(error_message)
|
||||
|
||||
# create a result obj, even if we have no results but a result mesh in frd file
|
||||
# see error message above for more information
|
||||
if not res_obj:
|
||||
if result_name_prefix:
|
||||
results_name = ("{}_Results".format(result_name_prefix))
|
||||
else:
|
||||
results_name = ("Results".format(result_name_prefix))
|
||||
res_obj = ObjectsFem.makeResultMechanical(FreeCAD.ActiveDocument, results_name)
|
||||
res_obj.Mesh = result_mesh_object
|
||||
# TODO, node numbers in result obj could be set
|
||||
if analysis:
|
||||
analysis.addObject(result_mesh_object)
|
||||
analysis.addObject(res_obj)
|
||||
|
||||
if FreeCAD.GuiUp:
|
||||
if analysis:
|
||||
@@ -186,6 +202,9 @@ def importFrd(
|
||||
Console.PrintError(
|
||||
"Problem on frd file import. No nodes found in frd file.\n"
|
||||
)
|
||||
# None will be returned
|
||||
# or would it be better to raise an exception if there are not even nodes in frd file
|
||||
|
||||
return res_obj
|
||||
|
||||
|
||||
|
||||
@@ -215,12 +215,6 @@ TaskAttacher::TaskAttacher(Gui::ViewProviderDocumentObject *ViewProvider,QWidget
|
||||
Gui::Document* document = Gui::Application::Instance->getDocument(ViewProvider->getObject()->getDocument());
|
||||
connectDelObject = document->signalDeletedObject.connect(bnd1);
|
||||
connectDelDocument = document->signalDeleteDocument.connect(bnd2);
|
||||
|
||||
// set tooltips because the ones in the .ui file are not taken for QuantitySpinBoxes (see bug https://freecadweb.org/tracker/view.php?id=4059)
|
||||
// FIXME: remove this once the bug is fixed
|
||||
ui->attachmentOffsetRoll->setTooltipLE(QString::fromUtf8("Rotation around the x-axis\nNote: The placement is expressed in local coordinate system\nof object being attached."));
|
||||
ui->attachmentOffsetPitch->setTooltipLE(QString::fromUtf8("Rotation around the y-axis\nNote: The placement is expressed in local coordinate system\nof object being attached."));
|
||||
ui->attachmentOffsetYaw->setTooltipLE(QString::fromUtf8("Rotation around the z-axis\nNote: The placement is expressed in local coordinate system\nof object being attached."));
|
||||
}
|
||||
|
||||
TaskAttacher::~TaskAttacher()
|
||||
@@ -745,10 +739,12 @@ void TaskAttacher::updateAttachmentOffsetUI()
|
||||
ui->attachmentOffsetPitch->setEnabled(!bRotationBound);
|
||||
ui->attachmentOffsetRoll->setEnabled(!bRotationBound);
|
||||
|
||||
QString tooltip = bRotationBound ? tr("Not editable because rotation of AttachmentOffset is bound by expressions.") : QString();
|
||||
ui->attachmentOffsetYaw->setToolTip(tooltip);
|
||||
ui->attachmentOffsetPitch->setToolTip(tooltip);
|
||||
ui->attachmentOffsetRoll->setToolTip(tooltip);
|
||||
if (bRotationBound) {
|
||||
QString tooltip = tr("Not editable because rotation of AttachmentOffset is bound by expressions.");
|
||||
ui->attachmentOffsetYaw->setToolTip(tooltip);
|
||||
ui->attachmentOffsetPitch->setToolTip(tooltip);
|
||||
ui->attachmentOffsetRoll->setToolTip(tooltip);
|
||||
}
|
||||
|
||||
bBlock = false;
|
||||
ui->attachmentOffsetX->blockSignals(bBlock);
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
#/******************************************************************************
|
||||
# * Copyright (c) 2012 Jan Rheinländer <jrheinlaender@users.sourceforge.net> *
|
||||
# * *
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
#/******************************************************************************
|
||||
# * Copyright (c) 2012 Jan Rheinländer <jrheinlaender@users.sourceforge.net> *
|
||||
# * *
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
#/******************************************************************************
|
||||
# * Copyright (c) 2012 Jan Rheinländer <jrheinlaender@users.sourceforge.net> *
|
||||
# * *
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
#/******************************************************************************
|
||||
# * Copyright (c) 2012 Jan Rheinländer <jrheinlaender@users.sourceforge.net> *
|
||||
# * *
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
#/******************************************************************************
|
||||
# * Copyright (c) 2012 Jan Rheinländer <jrheinlaender@users.sourceforge.net> *
|
||||
# * *
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
"""
|
||||
Shaft Wizard
|
||||
"""
|
||||
|
||||
Reference in New Issue
Block a user