Draft: Make ShapeString editable by double-click - fixes #5885

* Draft: Make ShapeString editable - fixes #5885
This commit is contained in:
marioalexis84
2022-04-08 12:47:41 -03:00
committed by GitHub
parent 929c89f700
commit aa2ebb9601
7 changed files with 183 additions and 78 deletions

View File

@@ -197,6 +197,7 @@ SET(Draft_view_providers
draftviewproviders/view_wire.py
draftviewproviders/view_wpproxy.py
draftviewproviders/view_hatch.py
draftviewproviders/view_shapestring.py
draftviewproviders/README.md
)

View File

@@ -349,6 +349,8 @@ from draftobjects.shapestring import (ShapeString,
_ShapeString)
from draftmake.make_shapestring import (make_shapestring,
makeShapeString)
if App.GuiUp:
from draftviewproviders.view_shapestring import ViewProviderShapeString
# shape 2d view
from draftobjects.shape2dview import (Shape2DView,

View File

@@ -46,9 +46,9 @@ import DraftVecUtils
import draftutils.utils as utils
import draftguitools.gui_base_original as gui_base_original
import draftguitools.gui_tool_utils as gui_tool_utils
import drafttaskpanels.task_shapestring as task_shapestring
import draftutils.todo as todo
from drafttaskpanels.task_shapestring import ShapeStringTaskPanelCmd
from draftutils.translate import translate
from draftutils.messages import _msg, _err
@@ -70,7 +70,6 @@ class ShapeString(gui_base_original.Creator):
def Activated(self):
"""Execute when the command is called."""
super(ShapeString, self).Activated(name="ShapeString")
self.creator = gui_base_original.Creator
if self.ui:
self.ui.sourceCmd = self
self.taskmode = utils.getParam("UiMode", 1)
@@ -81,8 +80,9 @@ class ShapeString(gui_base_original.Creator):
del self.task
except AttributeError:
pass
self.task = task_shapestring.ShapeStringTaskPanel()
self.task.sourceCmd = self
self.task = ShapeStringTaskPanelCmd(self)
self.call = self.view.addEventCallback("SoEvent", self.task.action)
_msg(translate("draft", "Pick ShapeString location point"))
todo.ToDo.delay(Gui.Control.showDialog, self.task)
else:
self.dialog = None

View File

@@ -33,7 +33,7 @@ import draftutils.gui_utils as gui_utils
from draftobjects.shapestring import ShapeString
if App.GuiUp:
from draftviewproviders.view_base import ViewProviderDraft
from draftviewproviders.view_shapestring import ViewProviderShapeString
def make_shapestring(String, FontFile, Size=100, Tracking=0):
@@ -60,7 +60,7 @@ def make_shapestring(String, FontFile, Size=100, Tracking=0):
obj.Tracking = Tracking
if App.GuiUp:
ViewProviderDraft(obj.ViewObject)
ViewProviderShapeString(obj.ViewObject)
gui_utils.format_object(obj)
obrep = obj.ViewObject
if "PointSize" in obrep.PropertiesList: obrep.PointSize = 1 # hide the segment end points

View File

@@ -33,12 +33,12 @@ import PySide.QtGui as QtGui
import FreeCAD as App
import FreeCADGui as Gui
import Draft
import Draft_rc
import DraftVecUtils
import draftguitools.gui_tool_utils as gui_tool_utils
from FreeCAD import Units as U
from DraftVecUtils import toString
from draftutils.utils import get_param
from draftutils.translate import translate
from draftutils.messages import _msg, _err
@@ -47,44 +47,39 @@ True if Draft_rc.__name__ else False
class ShapeStringTaskPanel:
"""TaskPanel for Draft_ShapeString."""
"""Base class for Draft_ShapeString task panel."""
def __init__(self):
self.form = QtGui.QWidget()
def __init__(self, point=App.Vector(0,0,0), size=10, string="", font=""):
self.form = Gui.PySideUic.loadUi(":/ui/TaskShapeString.ui")
self.form.setObjectName("ShapeStringTaskPanel")
self.form.setWindowTitle(translate("draft", "ShapeString"))
layout = QtGui.QVBoxLayout(self.form)
uiFile = QtCore.QFile(":/ui/TaskShapeString.ui")
loader = Gui.UiLoader()
self.task = loader.load(uiFile)
layout.addWidget(self.task)
self.form.setWindowIcon(QtGui.QIcon(":/icons/Draft_ShapeString.svg"))
qStart = U.Quantity(0.0, U.Length)
self.task.sbX.setProperty('rawValue', qStart.Value)
self.task.sbX.setProperty('unit', qStart.getUserPreferred()[2])
self.task.sbY.setProperty('rawValue', qStart.Value)
self.task.sbY.setProperty('unit', qStart.getUserPreferred()[2])
self.task.sbZ.setProperty('rawValue', qStart.Value)
self.task.sbZ.setProperty('unit', qStart.getUserPreferred()[2])
self.task.sbHeight.setProperty('rawValue', 10.0)
self.task.sbHeight.setProperty('unit', qStart.getUserPreferred()[2])
unit_length = App.Units.Quantity(0.0, App.Units.Length).getUserPreferred()[2]
self.form.sbX.setProperty('rawValue', point.x)
self.form.sbX.setProperty('unit', unit_length)
self.form.sbY.setProperty('rawValue', point.y)
self.form.sbY.setProperty('unit', unit_length)
self.form.sbZ.setProperty('rawValue', point.z)
self.form.sbZ.setProperty('unit', unit_length)
self.form.sbHeight.setProperty('rawValue', size)
self.form.sbHeight.setProperty('unit', unit_length)
self.stringText = translate("draft", "Default")
self.task.leString.setText(self.stringText)
self.stringText = string if string else translate("draft", "Default")
self.form.leString.setText(self.stringText)
self.platWinDialog("Overwrite")
self.task.fcFontFile.setFileName(Draft.getParam("FontFile", ""))
self.fileSpec = Draft.getParam("FontFile", "")
self.point = App.Vector(0.0, 0.0, 0.0)
self.fileSpec = font if font else get_param("FontFile", "")
self.form.fcFontFile.setFileName(self.fileSpec)
self.point = point
self.pointPicked = False
# Default for the "DontUseNativeFontDialog" preference:
self.font_dialog_pref = False
# Dummy attribute used by gui_tools_utils.getPoint in action method
self.node = None
QtCore.QObject.connect(self.task.fcFontFile, QtCore.SIGNAL("fileNameSelected(const QString&)"), self.fileSelect)
QtCore.QObject.connect(self.task.pbReset, QtCore.SIGNAL("clicked()"), self.resetPoint)
self.point = None
self.view = Draft.get3DView()
self.call = self.view.addEventCallback("SoEvent", self.action)
_msg(translate("draft", "Pick ShapeString location point:"))
QtCore.QObject.connect(self.form.fcFontFile, QtCore.SIGNAL("fileNameSelected(const QString&)"), self.fileSelect)
QtCore.QObject.connect(self.form.pbReset, QtCore.SIGNAL("clicked()"), self.resetPoint)
def fileSelect(self, fn):
"""Assign the selected file."""
@@ -102,7 +97,7 @@ class ShapeStringTaskPanel:
if arg["Key"] == "ESCAPE":
self.reject()
elif arg["Type"] == "SoLocation2Event": # mouse movement detection
self.point,ctrlPoint,info = gui_tool_utils.getPoint(self.sourceCmd, arg, noTracker=True)
self.point,ctrlPoint,info = gui_tool_utils.getPoint(self, arg, noTracker=True)
if not self.pointPicked:
self.setPoint(self.point)
elif arg["Type"] == "SoMouseButtonEvent":
@@ -112,36 +107,10 @@ class ShapeStringTaskPanel:
def setPoint(self, point):
"""Assign the selected point."""
self.task.sbX.setProperty('rawValue', point.x)
self.task.sbY.setProperty('rawValue', point.y)
self.task.sbZ.setProperty('rawValue', point.z)
self.form.sbX.setProperty('rawValue', point.x)
self.form.sbY.setProperty('rawValue', point.y)
self.form.sbZ.setProperty('rawValue', point.z)
def createObject(self):
"""Create object in the current document."""
dquote = '"'
String = dquote + self.task.leString.text() + dquote
FFile = dquote + str(self.fileSpec) + dquote
Size = str(U.Quantity(self.task.sbHeight.text()).Value)
Tracking = str(0.0)
x = U.Quantity(self.task.sbX.text()).Value
y = U.Quantity(self.task.sbY.text()).Value
z = U.Quantity(self.task.sbZ.text()).Value
ssBase = App.Vector(x, y, z)
# this try block is almost identical to the one in DraftTools
try:
qr, sup, points, fil = self.sourceCmd.getStrings()
Gui.addModule("Draft")
self.sourceCmd.commit(translate("draft", "Create ShapeString"),
['ss=Draft.make_shapestring(String=' + String + ', FontFile=' + FFile + ', Size=' + Size + ', Tracking=' + Tracking + ')',
'plm=FreeCAD.Placement()',
'plm.Base=' + DraftVecUtils.toString(ssBase),
'plm.Rotation.Q=' + qr,
'ss.Placement=plm',
'ss.Support=' + sup,
'Draft.autogroup(ss)'])
except Exception:
_err("Draft_ShapeString: error delaying commit\n")
def platWinDialog(self, flag):
"""Handle the type of dialog depending on the platform."""
@@ -166,25 +135,104 @@ class ShapeStringTaskPanel:
elif flag == "Restore":
ParamGroup.SetBool("DontUseNativeDialog", self.font_dialog_pref)
class ShapeStringTaskPanelCmd(ShapeStringTaskPanel):
"""Task panel for Draft_ShapeString."""
def __init__(self, sourceCmd):
super().__init__()
self.sourceCmd = sourceCmd
def accept(self):
"""Execute when clicking the OK button."""
self.createObject()
if self.call:
self.view.removeEventCallback("SoEvent", self.call)
Gui.ActiveDocument.resetEdit()
Gui.Snapper.off()
self.sourceCmd.creator.finish(self.sourceCmd)
self.platWinDialog("Restore")
self.reject()
return True
def reject(self):
"""Run when clicking the Cancel button."""
if self.call:
self.view.removeEventCallback("SoEvent", self.call)
Gui.ActiveDocument.resetEdit()
Gui.Snapper.off()
self.sourceCmd.creator.finish(self.sourceCmd)
self.sourceCmd.finish()
self.platWinDialog("Restore")
return True
def createObject(self):
"""Create object in the current document."""
dquote = '"'
String = dquote + self.form.leString.text() + dquote
FFile = dquote + str(self.fileSpec) + dquote
Size = str(App.Units.Quantity(self.form.sbHeight.text()).Value)
Tracking = str(0.0)
x = App.Units.Quantity(self.form.sbX.text()).Value
y = App.Units.Quantity(self.form.sbY.text()).Value
z = App.Units.Quantity(self.form.sbZ.text()).Value
ssBase = App.Vector(x, y, z)
# this try block is almost identical to the one in DraftTools
try:
qr, sup, points, fil = self.sourceCmd.getStrings()
Gui.addModule("Draft")
self.sourceCmd.commit(translate("draft", "Create ShapeString"),
['ss=Draft.make_shapestring(String=' + String + ', FontFile=' + FFile + ', Size=' + Size + ', Tracking=' + Tracking + ')',
'plm=FreeCAD.Placement()',
'plm.Base=' + toString(ssBase),
'plm.Rotation.Q=' + qr,
'ss.Placement=plm',
'ss.Support=' + sup,
'Draft.autogroup(ss)'])
except Exception:
_err("Draft_ShapeString: error delaying commit\n")
class ShapeStringTaskPanelEdit(ShapeStringTaskPanel):
"""Task panel for Draft ShapeString object in edit mode."""
def __init__(self, vobj):
base = vobj.Object.Placement.Base
size = vobj.Object.Size.Value
string = vobj.Object.String
font = vobj.Object.FontFile
super().__init__(base, size, string, font)
self.pointPicked = True
self.vobj = vobj
self.call = Gui.activeView().addEventCallback("SoEvent", self.action)
def accept(self):
x = App.Units.Quantity(self.form.sbX.text()).Value
y = App.Units.Quantity(self.form.sbY.text()).Value
z = App.Units.Quantity(self.form.sbZ.text()).Value
base = App.Vector(x, y, z)
size = App.Units.Quantity(self.form.sbHeight.text()).Value
string = self.form.leString.text()
font_file = self.fileSpec
o = "FreeCAD.ActiveDocument.getObject(\"" + self.vobj.Object.Name + "\")"
Gui.doCommand(o+".Placement.Base=" + toString(base))
Gui.doCommand(o+".Size=" + str(size))
Gui.doCommand(o+".String=\"" + string + "\"")
Gui.doCommand(o+".FontFile=\"" + font_file + "\"")
Gui.doCommand("FreeCAD.ActiveDocument.recompute()")
self.reject()
return True
def reject(self):
self.vobj.Document.resetEdit()
return True
def finish(self):
Gui.activeView().removeEventCallback("SoEvent", self.call)
Gui.Snapper.off()
Gui.Control.closeDialog()
return None
## @}

View File

@@ -27,7 +27,6 @@
## \addtogroup draftviewproviders
# @{
import FreeCAD as App
import FreeCADGui as Gui
import DraftGui

View File

@@ -0,0 +1,55 @@
#***************************************************************************
#* *
#* Copyright (c) 2022 Mario Passaglia *
#* *
#* 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. *
#* *
#* This program 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 this program; if not, write to the Free Software *
#* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 *
#* USA *
#* *
#***************************************************************************
"""Provides the viewprovider code for the Shapestring object."""
import FreeCADGui as Gui
from draftviewproviders.view_base import ViewProviderDraft
from drafttaskpanels.task_shapestring import ShapeStringTaskPanelEdit
class ViewProviderShapeString(ViewProviderDraft):
def __init__(self,vobj):
vobj.Proxy = self
def getIcon(self):
return ":/icons/Draft_ShapeString.svg"
def setEdit(self, vobj, mode):
self.wb_before_edit = Gui.activeWorkbench()
Gui.activateWorkbench("DraftWorkbench")
self.task = ShapeStringTaskPanelEdit(vobj)
Gui.Control.showDialog(self.task)
return True
def unsetEdit(self,vobj,mode):
self.task.finish()
Gui.activateWorkbench(self.wb_before_edit.name())
return True