Commit 537361d0 authored by Maxime Perrotin's avatar Maxime Perrotin

add basic support for optional fields

Depends on dmt >= 2.1.24
parent 430050bb
......@@ -34,6 +34,7 @@ LICENSE: LGPL - see LICENSE file
CHANGELOG:
1.6.9 - Add basic support for optional fields
1.6.7 - Fix CPU usage of polling thread
1.6.6 - Fix timestamp of autogenerated MSC files
1.6.5 - GUI can display default values if set in ASN.1 models
......
......@@ -16,7 +16,7 @@
__author__ = "Maxime Perrotin"
__license__ = "LGPLv3"
__version__ = "1.6.8"
__version__ = "1.6.9"
__url__ = "https://taste.tools"
import sys
......@@ -39,6 +39,7 @@ CHOICE_LIST = Qt.UserRole + 1 # list of strings (enumerants)
INTMAP = Qt.UserRole + 5 # for enum/choice: map string-numerical value
PLOTTERS = Qt.UserRole + 4
ASN1TYPE = Qt.UserRole
OPTIONAL = Qt.UserRole + 6
class myTextEdit(QTextEdit):
......@@ -86,7 +87,8 @@ reads the value from the editor and place it back in the model '''
super(TreeDelegate, self).__init__(oParent)
def createEditor(self, parent, option, index):
''' Define the delegate (editor) to use for a given cell.
''' Define the delegate (editor) to use for a given cell. This function
is called when the user clicks on a cell.
index.data() returns the actual value, and index.data(role) points
to some user data when role >= 32. 32 is Qt.UserRole. '''
def update_model(editor, index, event):
......@@ -219,9 +221,12 @@ class asn1Editor(QTreeView):
def __init__(self, parent=None):
super(asn1Editor, self).__init__(parent)
self.model = QStandardItemModel(1, 4)
self.model.setHorizontalHeaderLabels(['Field', 'Type',
'Constraints', 'Value'])
self.model = QStandardItemModel(1, 5) # 5 columns
self.model.setHorizontalHeaderLabels(['Field', # field name
'Type', # hidden
'Constraints', # hidden
'Value', # editable
'Present']) # optionality flag
self.delegate = TreeDelegate()
self.setItemDelegate(self.delegate)
# Set selection mode and behavior to allow multiple rows to be selected
......@@ -415,16 +420,12 @@ class asn1Editor(QTreeView):
value = ''
asnType = None
if asnType == 'INTEGER':
# TESTED OK
dest.Set(int(value))
elif asnType == 'REAL':
# TESTED OK
dest.Set(float(value))
elif asnType == 'BOOLEAN':
# TESTED OK
dest.Set(True if value == 'True' else False)
elif asnType == 'ENUMERATED':
# TESTED OK
intMappings = self.model.item(row, 3).data(INTMAP)
for enumerant, num in intMappings.viewitems():
if enumerant == value:
......@@ -854,7 +855,12 @@ class asn1Editor(QTreeView):
# Set the text for the constraint and add it to the 3rd column:
constraint = QStandardItem('(%d..%d)' % (elem["minR"], elem["maxR"]))
constraint.setData(QBrush(QColor("gray")), Qt.ForegroundRole)
return {"value": val, "constraint": constraint}
present = QStandardItem()
present.setData (elem['isOptional'], OPTIONAL)
if elem['isOptional']:
present.setCheckState(Qt.Checked)
present.setCheckable(True)
return {"value": val, "constraint": constraint, "present": present}
def addReal(self, elem):
# Set default value (min range):
......@@ -873,7 +879,12 @@ class asn1Editor(QTreeView):
# Set the text for the constraint and add it to the 3rd column:
constraint = QStandardItem('(%.2f..%.2f)' % (elem["minR"], elem["maxR"]))
constraint.setData(QBrush(QColor("gray")), Qt.ForegroundRole)
return {"value": val, "constraint": constraint}
present = QStandardItem()
if elem['isOptional']:
present.setCheckState (Qt.Checked)
present.setCheckable(True)
present.setData (elem['isOptional'], OPTIONAL)
return {"value": val, "constraint": constraint, "present": present}
def addEnum(self, elem):
# Set default value (first enum value)
......@@ -883,7 +894,12 @@ class asn1Editor(QTreeView):
val.setData(elem["values"], CHOICE_LIST) # enum values
val.setData(elem["valuesInt"], INTMAP) # mapping name - value
constraint = QStandardItem()
return {"value": val, "constraint": constraint}
present = QStandardItem()
if elem['isOptional']:
present.setCheckState (Qt.Checked)
present.setCheckable(True)
present.setData (elem['isOptional'], OPTIONAL)
return {"value": val, "constraint": constraint, "present" : present}
def addString(self, elem):
# Set default value (empty string)
......@@ -903,7 +919,12 @@ class asn1Editor(QTreeView):
constraintStr = 'SIZE(%d..%d)' % (elem["minSize"], elem["maxSize"])
constraint = QStandardItem(constraintStr)
constraint.setData(QBrush(QColor("gray")), Qt.ForegroundRole)
return {"value": val, "constraint": constraint}
present = QStandardItem()
if elem['isOptional']:
present.setCheckState (Qt.Checked)
present.setCheckable(True)
present.setData (elem['isOptional'], OPTIONAL)
return {"value": val, "constraint": constraint, "present": present}
def addBool(self, elem):
# Set default value (True or False)
......@@ -912,41 +933,61 @@ class asn1Editor(QTreeView):
val.setData(elem["type"], ASN1TYPE) # type (BOOLEAN)
val.setData(['True', 'False'], CHOICE_LIST) # enum values
constraint = QStandardItem()
return {"value": val, "constraint": constraint}
present = QStandardItem()
if elem['isOptional']:
present.setCheckState (Qt.Checked)
present.setCheckable(True)
present.setData (elem['isOptional'], OPTIONAL)
return {"value": val, "constraint": constraint, "present": present}
def addSequence(self, elem, parent):
types = []
values = []
constraints = []
presence = []
for child in elem["children"]:
field = self.addItem(child)
parent.appendRow(field["item"])
types.append(field["type"])
values.append(field["value"])
constraints.append(field["constraint"])
parent.appendRow (field["item"])
types.append (field["type"])
values.append (field["value"])
constraints.append (field["constraint"])
presence.append (field["present"])
parent.appendColumn(types)
parent.appendColumn(constraints)
parent.appendColumn(values)
parent.appendColumn(presence)
constraint = QStandardItem()
val = QStandardItem()
return {"value": val, "constraint": constraint}
val = QStandardItem()
present = QStandardItem()
if elem['isOptional']:
present.setCheckState (Qt.Checked)
present.setCheckable(True)
present.setData (elem['isOptional'], OPTIONAL)
present.setCheckable (elem['isOptional'])
return {"value": val, "constraint": constraint, "present": present}
def addSeqOf(self, elem, parent):
types = []
values = []
constraints = []
presence = []
for i in range(elem["maxSize"]):
elem["seqoftype"]["id"] = "elem_%d" % i
field = self.addItem(elem["seqoftype"])
parent.appendRow(field["item"])
types.append(field["type"])
values.append(field["value"])
constraints.append(field["constraint"])
parent.appendRow (field["item"])
types.append (field["type"])
values.append (field["value"])
constraints.append (field["constraint"])
presence.append (field["present"])
parent.appendColumn(types)
parent.appendColumn(constraints)
parent.appendColumn(values)
parent.appendColumn(presence)
if elem["minSize"] == elem["maxSize"]:
constraintStr = 'SIZE(%d)' % elem["minSize"]
else:
......@@ -957,32 +998,46 @@ class asn1Editor(QTreeView):
val.setData(elem["type"], ASN1TYPE) # type (SEQOF)
val.setData(elem["minSize"], MIN_RANGE) # min number of elements
val.setData(elem["maxSize"], MAX_RANGE) # max number of elements
return {"value": val, "constraint": constraint}
present = QStandardItem()
present.setData (elem['isOptional'], OPTIONAL)
if elem['isOptional']:
present.setCheckState (Qt.Checked)
present.setCheckable(True)
return {"value": val, "constraint": constraint, "present": present}
def addChoice(self, elem, parent):
types = []
values = []
constraints = []
presence = []
ids = []
for choice in elem["choices"]:
field = self.addItem(choice)
ids.append(choice["id"])
parent.appendRow(field["item"])
types.append(field["type"])
values.append(field["value"])
constraints.append(field["constraint"])
ids.append (choice["id"])
parent.appendRow (field["item"])
types.append (field["type"])
values.append (field["value"])
constraints.append (field["constraint"])
presence.append (field["present"])
parent.appendColumn(types)
parent.appendColumn(constraints)
parent.appendColumn(values)
parent.appendColumn(presence)
val = QStandardItem(ids[0]) # default value: first choice
# Define type attributes, later used to define the proper cell editor
val.setData(elem["type"], ASN1TYPE) # type (CHOICE)
val.setData(ids, CHOICE_LIST) # choice values
val.setData(elem["type"], ASN1TYPE) # type (CHOICE)
val.setData(ids, CHOICE_LIST) # choice values
val.setData(elem["choiceIdx"], INTMAP) # mapping name - DV value
constraint = QStandardItem()
return {"value": val, "constraint": constraint}
present = QStandardItem()
if elem['isOptional']:
present.setCheckState (Qt.Checked)
present.setCheckable(True)
present.setData (elem['isOptional'], OPTIONAL)
return {"value": val, "constraint": constraint, "present": present}
def addItem(self, elem):
# Add field name on the first column:
......@@ -990,6 +1045,7 @@ class asn1Editor(QTreeView):
# Add type on the second column in gray:
asnType = QStandardItem(elem["type"])
asnType.setData(QBrush(QColor("gray")), Qt.ForegroundRole)
# elem['isOptional'] is true if the field is marked OPTIONAL in ASN.1
# get the Value and Contraints fields for the different types:
if elem["type"] == 'INTEGER':
......@@ -1011,7 +1067,11 @@ class asn1Editor(QTreeView):
else:
raise TypeError('Unsupported type: ' + elem["type"])
sys.exit(-1)
return {"item": field, "type": asnType, "value": data["value"], "constraint": data["constraint"]}
return {"item": field,
"type": asnType,
"value": data["value"],
"constraint": data["constraint"],
"present" : data["present"]}
class asn1Viewer(asn1Editor):
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment