Arch: New UI for the survey tool

This commit is contained in:
Yorik van Havre
2017-09-22 16:10:51 -03:00
parent f228c37676
commit f3953a45e3

View File

@@ -188,7 +188,7 @@ def removeComponents(objectsList,host=None):
if o in a:
a.remove(o)
h.Objects = a
def makeComponent(baseobj=None,name="Component",delete=False):
'''makeComponent([baseobj]): creates an undefined, non-parametric Arch
component from the given base object'''
@@ -212,7 +212,7 @@ def makeComponent(baseobj=None,name="Component",delete=False):
obj.Shape = baseobj
Draft.select(obj)
return obj
def cloneComponent(obj):
'''cloneComponent(obj): Creates a clone of an object as an undefined component'''
c = makeComponent()
@@ -455,7 +455,7 @@ def getShapeFromMesh(mesh,fast=True,tolerance=0.001,flat=False,cut=True):
print("getShapeFromMesh: error removing splitter")
#pass
return solid
#if not mesh.isSolid():
# print "getShapeFromMesh: non-solid mesh, using slow method"
faces = []
@@ -725,55 +725,51 @@ def getAllChildren(objectlist):
obs.append(c)
return obs
class _SurveyObserver:
"an observer for the survey() function"
def __init__(self,callback):
self.callback = callback
self.cancellable = False
self.selection = []
self.labels = []
def addSelection(self,document, object, element, position):
self.cancellable = False
self.callback(True)
def clearSelection(self,document):
if self.cancellable:
self.callback(True)
else:
self.cancellable = True
def survey(callback=False):
"""survey(): starts survey mode, where you can click edges and faces to get their lengths or area.
Clicking on no object (on an empty area) stops survey mode."""
Clicking on no object (on an empty area) resets the count."""
if not callback:
if hasattr(FreeCAD,"SurveyObserver"):
for label in FreeCAD.SurveyObserver.labels:
FreeCAD.ActiveDocument.removeObject(label)
FreeCADGui.Selection.removeObserver(FreeCAD.SurveyObserver)
del FreeCAD.SurveyObserver
if FreeCAD.GuiUp:
if hasattr(FreeCADGui,"draftToolBar"):
FreeCADGui.draftToolBar.offUi()
FreeCADGui.Control.closeDialog()
if hasattr(FreeCAD,"SurveyDialog"):
del FreeCAD.SurveyDialog
else:
FreeCAD.SurveyObserver = _SurveyObserver(callback=survey)
FreeCADGui.Selection.addObserver(FreeCAD.SurveyObserver)
if FreeCAD.GuiUp:
if hasattr(FreeCADGui,"draftToolBar"):
FreeCADGui.draftToolBar.selectUi(callback=survey)
FreeCAD.SurveyDialog = SurveyTaskPanel()
FreeCADGui.Control.showDialog(FreeCAD.SurveyDialog)
else:
sel = FreeCADGui.Selection.getSelectionEx()
if not sel:
if hasattr(FreeCAD,"SurveyObserver"):
for label in FreeCAD.SurveyObserver.labels:
FreeCAD.ActiveDocument.removeObject(label)
FreeCADGui.Selection.removeObserver(FreeCAD.SurveyObserver)
del FreeCAD.SurveyObserver
if FreeCAD.GuiUp:
if hasattr(FreeCADGui,"draftToolBar"):
FreeCADGui.draftToolBar.offUi()
else:
if hasattr(FreeCAD,"SurveyObserver"):
if hasattr(FreeCAD,"SurveyObserver"):
if not sel:
if FreeCAD.SurveyObserver.labels:
for label in FreeCAD.SurveyObserver.labels:
FreeCAD.ActiveDocument.removeObject(label)
tl = FreeCAD.SurveyObserver.totalLength
ta = FreeCAD.SurveyObserver.totalArea
FreeCAD.SurveyObserver.labels = []
FreeCAD.SurveyObserver.selection = []
FreeCAD.SurveyObserver.totalLength = 0
FreeCAD.SurveyObserver.totalArea = 0
FreeCAD.SurveyObserver.totalVolume = 0
if not FreeCAD.SurveyObserver.cancellable:
FreeCAD.Console.PrintMessage("\n---- Reset ----\n\n")
FreeCAD.SurveyObserver.cancellable = True
if hasattr(FreeCAD,"SurveyDialog"):
FreeCAD.SurveyDialog.newline(tl,ta)
else:
FreeCADGui.Selection.removeObserver(FreeCAD.SurveyObserver)
del FreeCAD.SurveyObserver
FreeCADGui.Control.closeDialog()
if hasattr(FreeCAD,"SurveyDialog"):
del FreeCAD.SurveyDialog
else:
FreeCAD.SurveyObserver.cancellable = False
basesel = FreeCAD.SurveyObserver.selection
newsels = []
for o in sel:
@@ -805,18 +801,25 @@ def survey(callback=False):
t = t.encode("utf8").replace("^3","³")
anno.LabelText = "v " + t
FreeCAD.Console.PrintMessage("Object: " + n + ", Element: Whole, Volume: " + utf8_decode(t) + "\n")
FreeCAD.SurveyObserver.totalVolume += u.Value
elif o.Object.Shape.Faces:
u = FreeCAD.Units.Quantity(o.Object.Shape.Area,FreeCAD.Units.Area)
t = u.getUserPreferred()[0]
t = t.encode("utf8").replace("^2","²")
anno.LabelText = "a " + t
FreeCAD.Console.PrintMessage("Object: " + n + ", Element: Whole, Area: " + utf8_decode(t) + "\n")
FreeCAD.SurveyObserver.totalArea += u.Value
if hasattr(FreeCAD,"SurveyDialog"):
FreeCAD.SurveyDialog.update(2,t)
else:
u = FreeCAD.Units.Quantity(o.Object.Shape.Length,FreeCAD.Units.Length)
t = u.getUserPreferred()[0]
t = t.encode("utf8")
anno.LabelText = "l " + t
FreeCAD.Console.PrintMessage("Object: " + n + ", Element: Whole, Length: " + utf8_decode(t) + "\n")
FreeCAD.SurveyObserver.totalLength += u.Value
if hasattr(FreeCAD,"SurveyDialog"):
FreeCAD.SurveyDialog.update(1,t)
if FreeCAD.GuiUp and t:
if showUnit:
QtGui.qApp.clipboard().setText(t)
@@ -841,12 +844,18 @@ def survey(callback=False):
t = t.encode("utf8").replace("^2","²")
anno.LabelText = "a " + t
FreeCAD.Console.PrintMessage("Object: " + n + ", Element: " + el + ", Area: "+ utf8_decode(t) + "\n")
FreeCAD.SurveyObserver.totalArea += u.Value
if hasattr(FreeCAD,"SurveyDialog"):
FreeCAD.SurveyDialog.update(2,t)
elif "Edge" in el:
u= FreeCAD.Units.Quantity(e.Length,FreeCAD.Units.Length)
t = u.getUserPreferred()[0]
t = t.encode("utf8")
anno.LabelText = "l " + t
FreeCAD.Console.PrintMessage("Object: " + n + ", Element: " + el + ", Length: " + utf8_decode(t) + "\n")
FreeCAD.SurveyObserver.totalLength += u.Value
if hasattr(FreeCAD,"SurveyDialog"):
FreeCAD.SurveyDialog.update(1,t)
elif "Vertex" in el:
u = FreeCAD.Units.Quantity(e.Z,FreeCAD.Units.Length)
t = u.getUserPreferred()[0]
@@ -860,6 +869,213 @@ def survey(callback=False):
QtGui.qApp.clipboard().setText(str(u.Value))
FreeCAD.SurveyObserver.selection.extend(newsels)
if hasattr(FreeCAD,"SurveyObserver"):
if FreeCAD.SurveyObserver.totalLength or FreeCAD.SurveyObserver.totalArea or FreeCAD.SurveyObserver.totalVolume:
msg = " Total:"
if FreeCAD.SurveyObserver.totalLength:
u = FreeCAD.Units.Quantity(FreeCAD.SurveyObserver.totalLength,FreeCAD.Units.Length)
t = u.getUserPreferred()[0]
t = t.encode("utf8")
msg += " Length: " + t
if FreeCAD.SurveyObserver.totalArea:
u = FreeCAD.Units.Quantity(FreeCAD.SurveyObserver.totalArea,FreeCAD.Units.Area)
t = u.getUserPreferred()[0]
t = t.encode("utf8").replace("^2","²")
msg += " Area: " + t
if FreeCAD.SurveyObserver.totalVolume:
u = FreeCAD.Units.Quantity(FreeCAD.SurveyObserver.totalVolume,FreeCAD.Units.Volume)
t = u.getUserPreferred()[0]
t = t.encode("utf8").replace("^3","³")
msg += " Volume: " + t
FreeCAD.Console.PrintMessage(msg+"\n")
class _SurveyObserver:
"an observer for the survey() function"
def __init__(self,callback):
self.callback = callback
self.selection = []
self.labels = []
self.totalLength = 0
self.totalArea = 0
self.totalVolume = 0
self.cancellable = False
self.doubleclear = False
def addSelection(self,document, object, element, position):
self.doubleclear = False
self.callback(True)
def clearSelection(self,document):
if not self.doubleclear:
self.doubleclear = True
else:
self.callback(True)
class SurveyTaskPanel:
"A task panel for the survey tool"
def __init__(self):
self.form = QtGui.QWidget()
self.form.setWindowIcon(QtGui.QIcon(":/icons/Arch_Survey.svg"))
layout = QtGui.QVBoxLayout(self.form)
llayout = QtGui.QHBoxLayout()
self.descr = QtGui.QLineEdit()
llayout.addWidget(self.descr)
self.addButton = QtGui.QPushButton()
llayout.addWidget(self.addButton)
layout.addLayout(llayout)
self.tree = QtGui.QTreeWidget()
self.tree.setColumnCount(3)
layout.addWidget(self.tree)
blayout = QtGui.QHBoxLayout()
self.clearButton = QtGui.QPushButton()
blayout.addWidget(self.clearButton)
self.copyLength = QtGui.QPushButton()
blayout.addWidget(self.copyLength)
self.copyArea = QtGui.QPushButton()
blayout.addWidget(self.copyArea)
layout.addLayout(blayout)
self.export = QtGui.QPushButton()
layout.addWidget(self.export)
QtCore.QObject.connect(self.addButton, QtCore.SIGNAL("clicked()"), self.setText)
QtCore.QObject.connect(self.clearButton, QtCore.SIGNAL("clicked()"), self.clear)
QtCore.QObject.connect(self.copyLength, QtCore.SIGNAL("clicked()"), self.clipLength)
QtCore.QObject.connect(self.copyArea, QtCore.SIGNAL("clicked()"), self.clipArea)
QtCore.QObject.connect(self.export, QtCore.SIGNAL("clicked()"), self.exportCSV)
QtCore.QObject.connect(self.tree, QtCore.SIGNAL("itemClicked(QTreeWidgetItem*,int)"), self.setDescr)
self.retranslateUi(self)
item = QtGui.QTreeWidgetItem(self.tree)
self.tree.setCurrentItem(item)
def retranslateUi(self,dlg):
self.form.setWindowTitle(QtGui.QApplication.translate("Arch", "Survey", None))
self.addButton.setText(QtGui.QApplication.translate("Arch", "Set description", None))
self.clearButton.setText(QtGui.QApplication.translate("Arch", "Clear", None))
self.copyLength.setText(QtGui.QApplication.translate("Arch", "Copy Length", None))
self.copyArea.setText(QtGui.QApplication.translate("Arch", "Copy Area", None))
self.export.setText(QtGui.QApplication.translate("Arch", "Export CSV", None))
self.tree.setHeaderLabels([QtGui.QApplication.translate("Arch", "Description", None),
QtGui.QApplication.translate("Arch", "Length", None),
QtGui.QApplication.translate("Arch", "Area", None)])
def isAllowedAlterSelection(self):
return True
def isAllowedAlterView(self):
return True
def getStandardButtons(self):
return int(QtGui.QDialogButtonBox.Close)
def reject(self):
if hasattr(FreeCAD,"SurveyObserver"):
for label in FreeCAD.SurveyObserver.labels:
FreeCAD.ActiveDocument.removeObject(label)
FreeCADGui.Selection.removeObserver(FreeCAD.SurveyObserver)
del FreeCAD.SurveyObserver
return True
def clear(self):
FreeCADGui.Selection.clearSelection()
def clipLength(self):
if hasattr(FreeCAD,"SurveyObserver"):
u = FreeCAD.Units.Quantity(FreeCAD.SurveyObserver.totalLength,FreeCAD.Units.Length)
t = u.getUserPreferred()[0]
t = t.encode("utf8")
if FreeCAD.ParamGet("User parameter:BaseApp/Preferences/Mod/Arch").GetBool("surveyUnits",True):
QtGui.qApp.clipboard().setText(t)
else:
QtGui.qApp.clipboard().setText(str(u.Value/u.getUserPreferred()[1]))
def clipArea(self):
if hasattr(FreeCAD,"SurveyObserver"):
u = FreeCAD.Units.Quantity(FreeCAD.SurveyObserver.totalArea,FreeCAD.Units.Area)
t = u.getUserPreferred()[0]
t = t.encode("utf8").replace("^2","²")
if FreeCAD.ParamGet("User parameter:BaseApp/Preferences/Mod/Arch").GetBool("surveyUnits",True):
QtGui.qApp.clipboard().setText(t)
else:
QtGui.qApp.clipboard().setText(str(u.Value/u.getUserPreferred()[1]))
def newline(self,length=0,area=0):
FreeCADGui.Selection.clearSelection()
item = QtGui.QTreeWidgetItem(self.tree)
if length or area:
item.setText(0,QtGui.QApplication.translate("Arch", "Total", None))
item.setToolTip(0,"total")
f = QtGui.QFont()
f.setBold(True)
item.setFont(0,f)
item.setFont(1,f)
item.setFont(2,f)
else:
item.setText(0,self.descr.text())
self.descr.setText("")
self.tree.setCurrentItem(item)
if length:
u = FreeCAD.Units.Quantity(length,FreeCAD.Units.Length)
t = u.getUserPreferred()[0]
item.setText(1,t)
if area:
u = FreeCAD.Units.Quantity(area,FreeCAD.Units.Area)
t = u.getUserPreferred()[0]
t = t.replace(u"^2",u"²")
item.setText(2,t)
if length or area:
item = QtGui.QTreeWidgetItem(self.tree)
self.tree.setCurrentItem(item)
def update(self,column,txt):
item = QtGui.QTreeWidgetItem(self.tree)
self.tree.setCurrentItem(item)
item.setText(column,txt.decode("utf8"))
def setDescr(self,item,col):
self.descr.setText(item.text(0))
def setText(self):
item = self.tree.currentItem()
if item:
item.setText(0,self.descr.text())
self.descr.setText("")
def exportCSV(self):
import csv
rows = self.tree.topLevelItemCount()
if rows:
filename = QtGui.QFileDialog.getSaveFileName(QtGui.qApp.activeWindow(), translate("Arch","Export CSV File"), None, "CSV file (*.csv)");
if filename:
with open(filename[0].encode("utf8"), 'wb') as csvfile:
csvfile = csv.writer(csvfile,delimiter="\t")
suml = 0
for i in range(rows):
item = self.tree.topLevelItem(i)
row = []
row.append(item.text(0))
if item.text(1):
u = FreeCAD.Units.Quantity(item.text(1))
if item.toolTip(0) == "total":
row.append("=SUM(B"+str(suml+1)+":B"+str(i)+")")
else:
row.append(u.Value/u.getUserPreferred()[1])
row.append(u.getUserPreferred()[2])
else:
row.extend(["",""])
if item.text(2):
t = item.text(2).replace(u"²",u"^2")
u = FreeCAD.Units.Quantity(t)
if item.toolTip(0) == "total":
row.append("=SUM(D"+str(suml+1)+":D"+str(i)+")")
else:
row.append(u.Value/u.getUserPreferred()[1])
row.append(u.getUserPreferred()[2])
else:
row.extend(["",""])
csvfile.writerow(row)
if item.toolTip(0) == "total":
suml = i+1
print("successfully exported ",filename[0])
def toggleIfcBrepFlag(obj):