Tutorial | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | Downloads


QVT Tutorial - 5

A mapping transforms one or more sourceobjects into one or more targetobjects. It has a name, may have parameters and conditions (when-clause for pre-conditions, where-clause for post-conditions: however, there doesn't seem to be a real use for a post-condition yet).
A mapping consists of three sections: init, population and end. "init" and "end" are optional, "Population" is obligatory. However, the keyword "Population" can be omitted.

In our first mapping, the root object "Project" is transformed into a "Model". The Name of the Model should be the Title of the Project. More important, the automata of the Model should be the bodies of the Project:

mapping Project::ProjectToModel(): Model {
 Name := self.Title;
 automata := self.bodies -> map toAutomaton();
}

A very useful feature of Eclipse is the AutoComplete function ("Default Proposals"). When the AutoComplete dialog doesn't appear, you can press "Ctrl + Space". When you press it while the dialog already is visible, a list with standard functions appears ("Template Proposals").

Before the Project can be transformed, the Automata should be transformed first. We create a new mapping toAutomaton(), and lets add a constraint to this mapping: only transform the Automaton if its name starts with a capital "A":

mapping MMA::Automaton::toAutomaton() : MMB::Automaton 
when { self.Name.startsWith("A"); }
{
 Name := self.Name;
 modes := self.locations -> map toMode();
 transistions := self.locations.outgoingEdges -> map toTransition();
 log("Name of the Automaton: " + Name);
}

Note the "MMA::" and "MMB::" prefixes in the mapping declaration. Without prefix, QVT doesn't know which automaton Class we mean.
We just copy the name from the Automaton. Before we can complete the transformation of an Automaton, the modes and transitions should be transformed first. The modes should be the locations or the source model. But how can we transform the edges to transitions?
We can just use "self.locations.outgoingEdges". The result of this statement is an OrderedSet which contains all Edges of all Locations of the Automaton we are transforming. Finally, display the Name of the Automaton which is being transformed.

Two more mappings need to be defined: toMode() and toTransition(). Location is more or less the "key" object of our metamodel. Furthermore, Edge is a little difficult to transform. How could we possibly know the sourceMode and targetMode of a Transition? And would it be a problem if we had chosen to transform the Transitions before we transformed the Modes?

To solve the latter problem, we will need the Resolve functions. Continue...