Commit 2a038e00 authored by Maxime Perrotin's avatar Maxime Perrotin
Browse files

Parse graphical model in PR backend

parent de3bd218
...@@ -148,9 +148,9 @@ new feature: ...@@ -148,9 +148,9 @@ new feature:
- Update the on-the-fly parser for syntax checks in the graphical editor (ogParser.py) - Update the on-the-fly parser for syntax checks in the graphical editor (ogParser.py)
- Create a graphical symbol for the new feature (in sdlSymbols.py) - Create a graphical symbol for the new feature (in sdlSymbols.py)
- Update the renderer to draw the symbol (Renderer.py) - Update the renderer to draw the symbol (Renderer.py)
- Update the backend that saves the model to phrase representation (Pr.py)
- Create an icon and add the new symbol to the palette - Create an icon and add the new symbol to the palette
- Update the statechart renderer (Statechart.py) - Update the statechart renderer (Statechart.py)
- Update the backend that saves the model to phrase representation (Pr.py)
- Update other backends that can be impacted, such as code generators (AdaGenerator.py, etc.) - Update other backends that can be impacted, such as code generators (AdaGenerator.py, etc.)
5) Syntax checker in ogParser.py 5) Syntax checker in ogParser.py
...@@ -209,6 +209,14 @@ class ContinuousSignal(HorizontalSymbol): ...@@ -209,6 +209,14 @@ class ContinuousSignal(HorizontalSymbol):
super(ContinuousSignal, self).set_shape(width, height) super(ContinuousSignal, self).set_shape(width, height)
And you may need to add your new symbol to the properties of other symbols.
For example _insertable_followers gives the list of signals that the tool will
allow you to place after (or next to) the currently selected symbol.
The "state" symbol has this property:
_insertable_followers = ['Input', 'Connect', 'ContinuousSignal']
7) Update the renderer to see some first result: Renderer.py 7) Update the renderer to see some first result: Renderer.py
Since the parser is ready and the symbol is defined, it is now possible to Since the parser is ready and the symbol is defined, it is now possible to
...@@ -238,8 +246,9 @@ def _continuous_signal(ast, scene, parent, states): ...@@ -238,8 +246,9 @@ def _continuous_signal(ast, scene, parent, states):
states=states) states=states)
return cont return cont
And then you must call the render function from the State renderer, since And then you must call the render function from the State and Terminator
the continuous signals are generated below states, just like Inputs: renderers, since the continuous signals are generated below states,
just like Inputs:
@render.register(ogAST.State) @render.register(ogAST.State)
def _state(ast, scene, states, terminators, parent=None): def _state(ast, scene, states, terminators, parent=None):
...@@ -248,4 +257,24 @@ def _state(ast, scene, states, terminators, parent=None): ...@@ -248,4 +257,24 @@ def _state(ast, scene, states, terminators, parent=None):
render(exit, scene=scene, parent=new_state, states=states) render(exit, scene=scene, parent=new_state, states=states)
(...) (...)
8) Update the graphical parser backend (Pr.py)
In order to save the model or make syntax checks, we need to make sure that
the graphical model parser recognises the new symbol.
The principle is the same as for the renderer - a singledispatch visitor
pattern, but on the graphical symbols instead of the AST.
It is therefore straightforward to parse - just add a new function that
mimicks an existing one and register it to singledispatch.
@generate.register(sdlSymbols.ContinuousSignal)
def _continuous_signal(symbol, recursive=True, **kwargs):
''' "Provided" symbol or branch if recursive is set '''
result = common('PROVIDED', symbol)
if recursive:
result.extend(recursive_aligned(symbol))
return result
As in 7), also make sure that the parent symbol (here: state) can recursively
parse the new children.
...@@ -194,6 +194,15 @@ def _input(symbol, recursive=True, **kwargs): ...@@ -194,6 +194,15 @@ def _input(symbol, recursive=True, **kwargs):
return result return result
@generate.register(sdlSymbols.ContinuousSignal)
def _continuous_signal(symbol, recursive=True, **kwargs):
''' "Provided" symbol or branch if recursive is set '''
result = common('PROVIDED', symbol)
if recursive:
result.extend(recursive_aligned(symbol))
return result
@generate.register(sdlSymbols.Connect) @generate.register(sdlSymbols.Connect)
def _connect(symbol, recursive=True, **kwargs): def _connect(symbol, recursive=True, **kwargs):
''' Connect symbol or branch if recursive is set ''' ''' Connect symbol or branch if recursive is set '''
...@@ -325,7 +334,8 @@ def _state(symbol, recursive=True, nextstate=True, composite=False, cpy=False, ...@@ -325,7 +334,8 @@ def _state(symbol, recursive=True, nextstate=True, composite=False, cpy=False,
Indent.indent += 1 Indent.indent += 1
# Generate code for INPUT and CONNECT symbols # Generate code for INPUT and CONNECT symbols
for each in (symb for symb in symbol.childSymbols() for each in (symb for symb in symbol.childSymbols()
if isinstance(symb, sdlSymbols.Input)): if isinstance(symb, (sdlSymbols.Input,
sdlSymbols.ContinuousSignal))):
result.extend(generate(each)) result.extend(generate(each))
Indent.indent -= 1 Indent.indent -= 1
result.append(u'ENDSTATE;') result.append(u'ENDSTATE;')
......
...@@ -2756,17 +2756,12 @@ def continuous_signal(root, parent, context): ...@@ -2756,17 +2756,12 @@ def continuous_signal(root, parent, context):
# Keep track of the number of terminator statements in the transition # Keep track of the number of terminator statements in the transition
# useful if we want to render graphs from the SDL model # useful if we want to render graphs from the SDL model
terminators = len(context.terminators) terminators = len(context.terminators)
i.trigger, err0, warn0 = expression(root.getChild(0), context) i.trigger, exp_err, exp_warn = expression(root.getChild(0), context)
i.inputString = i.trigger.inputString
for child in root.children[1:]: for child in root.children[1:]:
if child.type == lexer.CIF: if child.type == lexer.CIF:
# Get symbol coordinates # Get symbol coordinates
i.pos_x, i.pos_y, i.width, i.height = cif(child) i.pos_x, i.pos_y, i.width, i.height = cif(child)
# # Report errors with symbol coordinates
# errors = [[e, [i.pos_x or 0, i.pos_y or 0], []] for e in errors]
# warnings = [[w, [i.pos_x or 0, i.pos_y or 0], []]
# for w in warnings]
elif child.type == lexer.INT: elif child.type == lexer.INT:
# Priority # Priority
i.priority = int(child.text) i.priority = int(child.text)
...@@ -2788,7 +2783,10 @@ def continuous_signal(root, parent, context): ...@@ -2788,7 +2783,10 @@ def continuous_signal(root, parent, context):
pass pass
else: else:
warnings.append('Unsupported INPUT child type: {}' warnings.append('Unsupported INPUT child type: {}'
.format(child.type)) .format(child.type))
# Report errors in the expression with symbol coordinates
errors.extend([[e, [i.pos_x or 0, i.pos_y or 0], []] for e in exp_err])
warnings.extend([[w, [i.pos_x or 0, i.pos_y or 0], []] for w in exp_warn])
# At the end of the input parsing, get the the list of terminators that # At the end of the input parsing, get the the list of terminators that
# follow the input transition by making a diff with the list at process # follow the input transition by making a diff with the list at process
# level (we counted the number of terminators before parsing the input) # level (we counted the number of terminators before parsing the input)
...@@ -2796,8 +2794,6 @@ def continuous_signal(root, parent, context): ...@@ -2796,8 +2794,6 @@ def continuous_signal(root, parent, context):
return i, errors, warnings return i, errors, warnings
def input_part(root, parent, context): def input_part(root, parent, context):
''' Parse an INPUT - set of TASTE provided interfaces ''' ''' Parse an INPUT - set of TASTE provided interfaces '''
i = ogAST.Input() i = ogAST.Input()
......
Supports Markdown
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