From 0852ae0ab845a22f3c7113c32bd088c2626ebac7 Mon Sep 17 00:00:00 2001
From: Florian Lugou <florian.lugou@telecom-paristech.fr>
Date: Thu, 21 Apr 2016 09:32:04 +0000
Subject: [PATCH] first step in adding library function call and fix for
 TGCNote box being too wide and various other fixes related to zooming or
 library functions

---
 src/avatartranslator/AvatarArithmeticOp.java  |    2 +-
 src/avatartranslator/AvatarAttribute.java     |    6 +-
 src/avatartranslator/AvatarBlock.java         |   24 +-
 src/avatartranslator/AvatarGuard.java         |    2 +-
 .../AvatarLibraryFunction.java                |  155 ++-
 src/avatartranslator/AvatarSpecification.java |   13 +-
 src/avatartranslator/AvatarStateMachine.java  |    2 +-
 .../AvatarStateMachineOwner.java              |   66 +
 src/avatartranslator/AvatarSyntaxChecker.java |    8 +-
 src/avatartranslator/AvatarTerm.java          |   10 +-
 src/avatartranslator/AvatarTermFunction.java  |    2 +-
 src/avatartranslator/AvatarTransition.java    |    6 +-
 src/avatartranslator/AvatarTuple.java         |    2 +-
 .../AvatarSpecificationSimulation.java        |    3 +
 .../tocppsim/AVATAR2CPPSIM.java               |    1 +
 .../toexecutable/AVATAR2CPOSIX.java           |    1 +
 .../toproverif/AVATAR2ProVerif.java           |    3 +
 src/avatartranslator/totpn/AVATAR2TPN.java    |    1 +
 .../toturtle/AVATAR2TURTLE.java               |    1 +
 .../touppaal/AVATAR2UPPAAL.java               |    1 +
 src/myutil/GraphicLib.java                    |    8 +-
 src/ui/AvatarDesignPanelTranslator.java       | 1113 ++++++++---------
 src/ui/CheckingError.java                     |    6 +-
 src/ui/ColorManager.java                      |    1 +
 src/ui/MainGUI.java                           |   12 +-
 src/ui/TDiagramPanel.java                     |  129 +-
 src/ui/TGCNote.java                           |  179 ++-
 .../TGCScalableWithoutInternalComponent.java  |    5 +-
 src/ui/TGComponent.java                       |    4 +
 src/ui/TGComponentManager.java                |    6 +
 src/ui/TGUIAction.java                        |    3 +
 src/ui/avatarbd/AvatarBDBlock.java            |  472 +++----
 src/ui/avatarbd/AvatarBDDataType.java         |   10 +-
 src/ui/avatarbd/AvatarBDLibraryFunction.java  |  290 +++--
 src/ui/avatarbd/AvatarBDPanel.java            |   22 +-
 src/ui/avatarbd/AvatarBDPragma.java           |   28 +-
 .../avatarbd/AvatarBDStateMachineOwner.java   |    2 +
 .../AvatarSMDLibraryFunctionCall.java         |  277 ++++
 src/ui/avatarsmd/AvatarSMDToolBar.java        |    6 +
 src/ui/window/JBirdPanel.java                 |    4 +-
 .../window/JDialogAvatarLibraryFunction.java  |  103 +-
 41 files changed, 1735 insertions(+), 1254 deletions(-)
 create mode 100644 src/avatartranslator/AvatarStateMachineOwner.java
 create mode 100644 src/ui/avatarsmd/AvatarSMDLibraryFunctionCall.java

diff --git a/src/avatartranslator/AvatarArithmeticOp.java b/src/avatartranslator/AvatarArithmeticOp.java
index 226c2847a4..b2e23c233d 100644
--- a/src/avatartranslator/AvatarArithmeticOp.java
+++ b/src/avatartranslator/AvatarArithmeticOp.java
@@ -63,7 +63,7 @@ public class AvatarArithmeticOp extends AvatarTerm {
         this.term2 = _term2;
     }
 
-    public static AvatarArithmeticOp createFromString (AvatarBlock block, String toParse) {
+    public static AvatarArithmeticOp createFromString (AvatarStateMachineOwner block, String toParse) {
         for (String op: AvatarArithmeticOp.knownOp) {
             int indexOp = toParse.indexOf (op);
             if (indexOp != -1) {
diff --git a/src/avatartranslator/AvatarAttribute.java b/src/avatartranslator/AvatarAttribute.java
index 4ac268ebfb..6bf3a5233c 100644
--- a/src/avatartranslator/AvatarAttribute.java
+++ b/src/avatartranslator/AvatarAttribute.java
@@ -59,10 +59,10 @@ public class AvatarAttribute extends AvatarLeftHand {
     private AvatarType type;
     private String initialValue;
 
-    private AvatarBlock block;
+    private AvatarStateMachineOwner block;
 
 
-    public AvatarAttribute(String _name, AvatarType _type, AvatarBlock _block, Object _referenceObject) {
+    public AvatarAttribute (String _name, AvatarType _type, AvatarStateMachineOwner _block, Object _referenceObject) {
         super(_name, _referenceObject);
         /*if (_type == -1) {
           TraceManager.addDev("- - - - - - - - - - - - " + _name + ": " + _type);
@@ -77,7 +77,7 @@ public class AvatarAttribute extends AvatarLeftHand {
         this.block = _block;
     }
 
-    public AvatarBlock getBlock () {
+    public AvatarStateMachineOwner getBlock () {
         return this.block;
     }
 
diff --git a/src/avatartranslator/AvatarBlock.java b/src/avatartranslator/AvatarBlock.java
index 836ddf535b..0c5779aee5 100644
--- a/src/avatartranslator/AvatarBlock.java
+++ b/src/avatartranslator/AvatarBlock.java
@@ -50,7 +50,7 @@ import java.util.*;
 import myutil.*;
 
 
-public class AvatarBlock extends AvatarElement {
+public class AvatarBlock extends AvatarElement implements AvatarStateMachineOwner {
 
     private AvatarBlock father;
     private LinkedList<AvatarAttribute> attributes;
@@ -139,13 +139,8 @@ public class AvatarBlock extends AvatarElement {
 	return asm.getNbOfASMGraphicalElements();
     }
 
-
-    public AvatarConstant getAvatarConstantWithName(String _name) {
-        return this.avspec.getAvatarConstantWithName (_name);
-    }
-
-    public void addConstant (AvatarConstant _constant) {
-        this.avspec.addConstant (_constant);
+    public AvatarSpecification getAvatarSpecification () {
+        return this.avspec;
     }
 
     public void addAttribute(AvatarAttribute _aa) {
@@ -304,7 +299,7 @@ public class AvatarBlock extends AvatarElement {
         return null;
     }
 
-    public boolean isAValidMethodCall(String _s) {
+    public static boolean isAValidMethodCall (AvatarStateMachineOwner owner, String _s) {
         int i;
 
         //TraceManager.addDev("****** method=" + _s);
@@ -326,7 +321,7 @@ public class AvatarBlock extends AvatarElement {
 
         String method = _s.substring(0, index0);
 
-        AvatarMethod am = getAvatarMethodWithName(method);
+        AvatarMethod am = owner.getAvatarMethodWithName(method);
         if (am == null) {
             //TraceManager.addDev("Method not found");
             return false;
@@ -353,12 +348,12 @@ public class AvatarBlock extends AvatarElement {
             // Must check tha validity of this action
 
             if (am.getListOfAttributes().get(i).isInt()) {
-                if (AvatarSyntaxChecker.isAValidIntExpr(null, this, actions[i].trim()) < 0) {
+                if (AvatarSyntaxChecker.isAValidIntExpr(null, owner, actions[i].trim()) < 0) {
                     return false;
                 }
             } else {
                 // Assume it is a bool attribute
-                if (AvatarSyntaxChecker.isAValidBoolExpr(null, this, actions[i].trim()) < 0) {
+                if (AvatarSyntaxChecker.isAValidBoolExpr(null, owner, actions[i].trim()) < 0) {
                     return false;
                 }
             }
@@ -392,7 +387,7 @@ public class AvatarBlock extends AvatarElement {
 
                     for(i=0; i<actions.length; i++) {
                         //TraceManager.addDev("params=" + retparams +  " actions=" + actions[i]);
-                        aa = getAvatarAttributeWithName(actions[i].trim());
+                        aa = owner.getAvatarAttributeWithName(actions[i].trim());
                         if (aa == null) {
                             //TraceManager.addDev("Failed for attribute " + actions[i]);
                             return false;
@@ -401,7 +396,7 @@ public class AvatarBlock extends AvatarElement {
 
                 } else {
                     // Only one param.
-                    aa = getAvatarAttributeWithName(retparams);
+                    aa = owner.getAvatarAttributeWithName(retparams);
                     if (aa == null) {
                         //TraceManager.addDev("Failed for return attribute " + retparams);
                         return false;
@@ -418,7 +413,6 @@ public class AvatarBlock extends AvatarElement {
         //TraceManager.addDev("Ok for method " + _s);
 
         return true;
-
     }
 
     public AvatarStateMachineElement getStateMachineElementFromReferenceObject(Object _o) {
diff --git a/src/avatartranslator/AvatarGuard.java b/src/avatartranslator/AvatarGuard.java
index 7ffe785375..34da46a4d1 100644
--- a/src/avatartranslator/AvatarGuard.java
+++ b/src/avatartranslator/AvatarGuard.java
@@ -68,7 +68,7 @@ public abstract class AvatarGuard {
         return index;
     }
 
-    public static AvatarGuard createFromString (AvatarBlock block, String _guard) {
+    public static AvatarGuard createFromString (AvatarStateMachineOwner block, String _guard) {
         if (_guard == null)
             return new AvatarGuardEmpty ();
 
diff --git a/src/avatartranslator/AvatarLibraryFunction.java b/src/avatartranslator/AvatarLibraryFunction.java
index ea7bcb180e..600f08e3c8 100644
--- a/src/avatartranslator/AvatarLibraryFunction.java
+++ b/src/avatartranslator/AvatarLibraryFunction.java
@@ -59,7 +59,7 @@ import java.util.Iterator;
  * @version 1.0 04.07.2016
  * @author Florian LUGOU
  */
-public class AvatarLibraryFunction extends AvatarElement implements AvatarTranslator {
+public class AvatarLibraryFunction extends AvatarElement implements AvatarTranslator, AvatarStateMachineOwner {
 
     /**
      * The list of parameters of the function. Their values should never be reaffected.
@@ -118,18 +118,157 @@ public class AvatarLibraryFunction extends AvatarElement implements AvatarTransl
      */
     public AvatarLibraryFunction (String name, AvatarSpecification avspec, Object referenceObject) {
         super(name, referenceObject);
+
         this.avspec = avspec;
+
+        this.parameters = new LinkedList<AvatarAttribute> ();
+        this.signals = new LinkedList<AvatarSignal> ();
+        this.returnAttributes = new LinkedList<AvatarAttribute> ();
+        this.attributes = new LinkedList<AvatarAttribute> ();
+        this.methods = new LinkedList<AvatarMethod> ();
+
+        this.asm = new AvatarStateMachine ("statemachineoffunction__" + name, referenceObject);
+    }
+
+    @Override
+    public AvatarSpecification getAvatarSpecification () {
+        return this.avspec;
     }
 
     /**
-     * Look for an attribute in the list of local attributes, parameters and return values.
+     * Return the list of parameters of the function.
      *
-     * @param name
-     *      The name of the attribute to look for.
+     * @return The list of parameters.
+     */
+    public LinkedList<AvatarAttribute> getParameters () {
+        return this.parameters;
+    }
+
+    /**
+     * Add a parameter for this function.
+     *
+     * @param attr
+     *      The parameter to add.
+     */
+    public void addParameter (AvatarAttribute attr) {
+        this.parameters.add (attr);
+    }
+
+    /**
+     * Return the list of signals.
+     *
+     * @return The list of signals.
+     */
+    public LinkedList<AvatarSignal> getSignals () {
+        return this.signals;
+    }
+
+    /**
+     * Add a signal.
      *
-     * @return The corresponding attribute if found, null otherwise.
+     * @param signal
+     *      The signal to add.
      */
-    public AvatarAttribute getAttributeWithName (String name) {
+    public void addSignal (AvatarSignal signal) {
+        this.signals.add (signal);
+    }
+
+    @Override
+    public AvatarSignal getAvatarSignalWithName (String signalName) {
+        for (AvatarSignal signal: this.signals)
+            if (signal.getName ().equals (signalName))
+                return signal;
+
+        return null;
+    }
+
+    /**
+     * Return the list of return values.
+     *
+     * @return The list of return values.
+     */
+    public LinkedList<AvatarAttribute> getReturnAttributes () {
+        return this.returnAttributes;
+    }
+
+    /**
+     * Add a return value.
+     *
+     * @param returnAttribute
+     *      The return value to add.
+     */
+    public void addReturnAttribute (AvatarAttribute returnAttribute) {
+        this.returnAttributes.add (returnAttribute);
+    }
+
+    /**
+     * Return the list of attributes local to the function.
+     *
+     * @return The list of local attributes.
+     */
+    public LinkedList<AvatarAttribute> getLocalAttributes () {
+        return this.attributes;
+    }
+
+    @Override
+    public LinkedList<AvatarAttribute> getAttributes () {
+        LinkedList<AvatarAttribute> result = new LinkedList<AvatarAttribute> ();
+
+        for (AvatarAttribute attr: this.attributes)
+            result.add (attr);
+        for (AvatarAttribute attr: this.returnAttributes)
+            result.add (attr);
+        for (AvatarAttribute attr: this.parameters)
+            result.add (attr);
+
+        return result;
+    }
+
+    /**
+     * Add an attribute local to this function.
+     *
+     * @param attribute
+     *      The local attribute to add.
+     */
+    public void addAttribute (AvatarAttribute attribute) {
+        this.attributes.add (attribute);
+    }
+
+    /**
+     * Return the list of methods.
+     *
+     * @return The list of methods used by this function.
+     */
+    public LinkedList<AvatarMethod> getMethods () {
+        return this.methods;
+    }
+
+    @Override
+    public AvatarMethod getAvatarMethodWithName (String methodName) {
+        for (AvatarMethod method: this.methods)
+            if (method.getName ().equals (methodName))
+                return method;
+
+        return null;
+    }
+
+    /**
+     * Add a method.
+     *
+     * @param method
+     *      The method to add to this function.
+     */
+    public void addMethod (AvatarMethod method) {
+        this.methods.add (method);
+    }
+
+    @Override
+    public AvatarStateMachine getStateMachine () {
+        return this.asm;
+    }
+
+    @Override
+    public AvatarAttribute getAvatarAttributeWithName (String name) {
         for (AvatarAttribute attr: this.parameters)
             if (attr.getName ().equals (name))
                 return attr;
@@ -364,7 +503,7 @@ public class AvatarLibraryFunction extends AvatarElement implements AvatarTransl
 
         AvatarActionOnSignal asme = new AvatarActionOnSignal (this.name + "__" + _asme.getName (), arg.signalsMapping.get (_asme.getSignal ()), arg.referenceObject);
         for (String s: _asme.getValues ()) {
-            AvatarAttribute attr = this.getAttributeWithName (s);
+            AvatarAttribute attr = this.getAvatarAttributeWithName (s);
             if (attr == null)
                 asme.addValue (s);
             else
@@ -426,7 +565,7 @@ public class AvatarLibraryFunction extends AvatarElement implements AvatarTransl
         AvatarRandom asme = new AvatarRandom (this.name + "__" + _asme.getName (), arg.referenceObject);
         asme.setValues (_asme.getMinValue (), _asme.getMaxValue ());
         asme.setFunctionId (_asme.getFunctionId ());
-        asme.setVariable (arg.placeholdersMapping.get (this.getAttributeWithName (_asme.getVariable ())).getName ());
+        asme.setVariable (arg.placeholdersMapping.get (this.getAvatarAttributeWithName (_asme.getVariable ())).getName ());
 
         this.translateNext (asme, _asme, arg);
     }
diff --git a/src/avatartranslator/AvatarSpecification.java b/src/avatartranslator/AvatarSpecification.java
index 92f71b5512..f76ccf962e 100644
--- a/src/avatartranslator/AvatarSpecification.java
+++ b/src/avatartranslator/AvatarSpecification.java
@@ -58,9 +58,9 @@ public class AvatarSpecification extends AvatarElement {
     private LinkedList<AvatarRelation> relations;
 
     /**
-     * The list of all library calls that can be called.
+     * The list of all library functions that can be called.
      */
-    private LinkedList<AvatarLibraryFunctionCall> libraryCalls;
+    private LinkedList<AvatarLibraryFunction> libraryFunctions;
 
     private String applicationCode;
 
@@ -86,9 +86,16 @@ public class AvatarSpecification extends AvatarElement {
         this.constants.add (AvatarConstant.FALSE);
         this.constants.add (AvatarConstant.TRUE);
 
-        this.libraryCalls = new LinkedList<AvatarLibraryFunctionCall> ();
+        this.libraryFunctions = new LinkedList<AvatarLibraryFunction> ();
     }
 
+    public LinkedList<AvatarLibraryFunction> getListOfLibraryFunctions () {
+        return this.libraryFunctions;
+    }
+
+    public void addLibraryFunction (AvatarLibraryFunction libraryFunction) {
+        this.libraryFunctions.add (libraryFunction);
+    }
 
     // For code generation
     public void addApplicationCode(String _code) {
diff --git a/src/avatartranslator/AvatarStateMachine.java b/src/avatartranslator/AvatarStateMachine.java
index 5652673704..c5fdf3f612 100644
--- a/src/avatartranslator/AvatarStateMachine.java
+++ b/src/avatartranslator/AvatarStateMachine.java
@@ -1225,7 +1225,7 @@ public class AvatarStateMachine extends AvatarElement {
         return name + id;
     }
 
-    public void handleUnfollowedStartState(AvatarBlock _block) {
+    public void handleUnfollowedStartState(AvatarStateMachineOwner _block) {
         if (startState.nbOfNexts() == 0) {
             AvatarStopState stopState = new AvatarStopState("__StopState", startState.getReferenceObject());
             AvatarTransition at = new AvatarTransition(_block, "__toStop", startState.getReferenceObject());
diff --git a/src/avatartranslator/AvatarStateMachineOwner.java b/src/avatartranslator/AvatarStateMachineOwner.java
new file mode 100644
index 0000000000..40587b4819
--- /dev/null
+++ b/src/avatartranslator/AvatarStateMachineOwner.java
@@ -0,0 +1,66 @@
+/* Copyright or (C) or Copr. GET / ENST, Telecom-Paris, Ludovic Apvrille
+ *
+ * ludovic.apvrille AT enst.fr
+ *
+ * This software is a computer program whose purpose is to allow the
+ * edition of TURTLE analysis, design and deployment diagrams, to
+ * allow the generation of RT-LOTOS or Java code from this diagram,
+ * and at last to allow the analysis of formal validation traces
+ * obtained from external tools, e.g. RTL from LAAS-CNRS and CADP
+ * from INRIA Rhone-Alpes.
+ *
+ * This software is governed by the CeCILL  license under French law and
+ * abiding by the rules of distribution of free software.  You can  use,
+ * modify and/ or redistribute the software under the terms of the CeCILL
+ * license as circulated by CEA, CNRS and INRIA at the following URL
+ * "http://www.cecill.info".
+ *
+ * As a counterpart to the access to the source code and  rights to copy,
+ * modify and redistribute granted by the license, users are provided only
+ * with a limited warranty  and the software's author,  the holder of the
+ * economic rights,  and the successive licensors  have only  limited
+ * liability.
+ *
+ * In this respect, the user's attention is drawn to the risks associated
+ * with loading,  using,  modifying and/or developing or reproducing the
+ * software by the user in light of its specific status of free software,
+ * that may mean  that it is complicated to manipulate,  and  that  also
+ * therefore means  that it is reserved for developers  and  experienced
+ * professionals having in-depth computer knowledge. Users are therefore
+ * encouraged to load and test the software's suitability as regards their
+ * requirements in conditions enabling the security of their systems and/or
+ * data to be ensured and,  more generally, to use and operate it in the
+ * same conditions as regards security.
+ *
+ * The fact that you are presently reading this means that you have had
+ * knowledge of the CeCILL license and that you accept its terms.
+ */
+
+package avatartranslator;
+
+import java.util.LinkedList;
+
+/**
+ *
+ * @version 1.0 04.15.2016
+ * @author Florian LUGOU
+ */
+public interface AvatarStateMachineOwner {
+    public String getName ();
+    public AvatarStateMachine getStateMachine ();
+    public AvatarSignal getAvatarSignalWithName (String signalName);
+    public AvatarMethod getAvatarMethodWithName (String methodName);
+
+    /**
+     * Look for an attribute in the list of local attributes, parameters and return values.
+     *
+     * @param name
+     *      The name of the attribute to look for.
+     *
+     * @return The corresponding attribute if found, null otherwise.
+     */
+    public AvatarAttribute getAvatarAttributeWithName (String attributeName);
+
+    public AvatarSpecification getAvatarSpecification ();
+    public LinkedList<AvatarAttribute> getAttributes ();
+}
diff --git a/src/avatartranslator/AvatarSyntaxChecker.java b/src/avatartranslator/AvatarSyntaxChecker.java
index d682aaa286..93b1c28db3 100644
--- a/src/avatartranslator/AvatarSyntaxChecker.java
+++ b/src/avatartranslator/AvatarSyntaxChecker.java
@@ -58,7 +58,7 @@ public class AvatarSyntaxChecker  {
     public AvatarSyntaxChecker() {
     }
 
-    public static int isAValidGuard(AvatarSpecification _as, AvatarBlock _ab, String _guard) {
+    public static int isAValidGuard(AvatarSpecification _as, AvatarStateMachineOwner _ab, String _guard) {
         //TraceManager.addDev("Evaluating (non modified) guard:" + _guard);
 
         String tmp = _guard.replaceAll(" ", "").trim();
@@ -91,7 +91,7 @@ public class AvatarSyntaxChecker  {
         //return parse(_as, _ab, "guard", _guard);
     }
 
-    public static int isAValidIntExpr(AvatarSpecification _as, AvatarBlock _ab, String _expr) {
+    public static int isAValidIntExpr(AvatarSpecification _as, AvatarStateMachineOwner _ab, String _expr) {
         if (_expr.trim().length() == 0) {
             return 0;
         }
@@ -118,7 +118,7 @@ public class AvatarSyntaxChecker  {
 
     }
 
-    public static int isAValidBoolExpr(AvatarSpecification _as, AvatarBlock _ab, String _expr) {
+    public static int isAValidBoolExpr(AvatarSpecification _as, AvatarStateMachineOwner _ab, String _expr) {
         if (_expr.trim().length() == 0) {
             return 0;
         }
@@ -145,7 +145,7 @@ public class AvatarSyntaxChecker  {
         // OLD return parse(_as, _ab, "actionbool", _expr);
     }
 
-    public static int isAValidVariableExpr(AvatarSpecification _as, AvatarBlock _ab, String _expr) {
+    public static int isAValidVariableExpr(AvatarSpecification _as, AvatarStateMachineOwner _ab, String _expr) {
         int index0 = _expr.indexOf("=");
         if (index0 == -1) {
             return -1;
diff --git a/src/avatartranslator/AvatarTerm.java b/src/avatartranslator/AvatarTerm.java
index 61e59a55db..47b5a7a260 100644
--- a/src/avatartranslator/AvatarTerm.java
+++ b/src/avatartranslator/AvatarTerm.java
@@ -60,7 +60,7 @@ public abstract class AvatarTerm extends AvatarElement {
         super (_name, _referenceObject);
     }
 
-    public static AvatarTerm createFromString (AvatarBlock block, String toParse) {
+    public static AvatarTerm createFromString (AvatarStateMachineOwner block, String toParse) {
         if (toParse == null || toParse.isEmpty ())
             return null;
 
@@ -82,7 +82,7 @@ public abstract class AvatarTerm extends AvatarElement {
             return result;
         TraceManager.addDev ("AvatarAttribute '" + toParse + "' couldn't be parsed");
 
-        result = block.getAvatarConstantWithName (toParse);
+        result = block.getAvatarSpecification ().getAvatarConstantWithName (toParse);
         if (result != null)
             return result;
 
@@ -90,14 +90,14 @@ public abstract class AvatarTerm extends AvatarElement {
             // TODO: replace that by a true AvatarNumeric
             int i = Integer.parseInt (toParse);
             result = new AvatarConstant (toParse, block);
-            block.addConstant ((AvatarConstant) result);
+            block.getAvatarSpecification ().addConstant ((AvatarConstant) result);
             return result;
         } catch (NumberFormatException e) { }
 
         // Consider that new names are constants
         if (AvatarTerm.isValidName (toParse)) {
             result = new AvatarConstant (toParse, block);
-            block.addConstant ((AvatarConstant) result);
+            block.getAvatarSpecification ().addConstant ((AvatarConstant) result);
             return result;
         }
         //TraceManager.addDev ("AvatarConstant '" + toParse + "' couldn't be parsed");
@@ -106,7 +106,7 @@ public abstract class AvatarTerm extends AvatarElement {
         return new AvatarTermRaw (toParse, block);
     }
 
-    public static AvatarAction createActionFromString (AvatarBlock block, String toParse) {
+    public static AvatarAction createActionFromString (AvatarStateMachineOwner block, String toParse) {
         AvatarAction result = null;
 
         int indexEq = toParse.indexOf("=");
diff --git a/src/avatartranslator/AvatarTermFunction.java b/src/avatartranslator/AvatarTermFunction.java
index 96822a1833..f49e0387b0 100644
--- a/src/avatartranslator/AvatarTermFunction.java
+++ b/src/avatartranslator/AvatarTermFunction.java
@@ -60,7 +60,7 @@ public class AvatarTermFunction extends AvatarTerm implements AvatarAction {
         this.method = _method;
     }
 
-    public static AvatarTermFunction createFromString (AvatarBlock block, String toParse) {
+    public static AvatarTermFunction createFromString (AvatarStateMachineOwner block, String toParse) {
         int indexLParen = toParse.indexOf ("(");
         String methodName;
         AvatarTuple argsTuple;
diff --git a/src/avatartranslator/AvatarTransition.java b/src/avatartranslator/AvatarTransition.java
index eb2ede6d2a..edf1be1988 100644
--- a/src/avatartranslator/AvatarTransition.java
+++ b/src/avatartranslator/AvatarTransition.java
@@ -54,11 +54,11 @@ public class AvatarTransition extends AvatarStateMachineElement {
     private AvatarGuard guard;
     private String minDelay = "", maxDelay = "";
     private String minCompute = "", maxCompute = "";
-    private AvatarBlock block;
+    private AvatarStateMachineOwner block;
 
     private LinkedList<AvatarAction> actions; // actions on variable, or method call
 
-    public AvatarTransition(AvatarBlock _block, String _name, Object _referenceObject) {
+    public AvatarTransition (AvatarStateMachineOwner _block, String _name, Object _referenceObject) {
         super(_name, _referenceObject);
         actions = new LinkedList<AvatarAction>();
         this.guard = new AvatarGuardEmpty ();
@@ -90,7 +90,7 @@ public class AvatarTransition extends AvatarStateMachineElement {
         return this.actions;
     }
 
-    public AvatarBlock getBlock () {
+    public AvatarStateMachineOwner getBlock () {
         return this.block;
     }
 
diff --git a/src/avatartranslator/AvatarTuple.java b/src/avatartranslator/AvatarTuple.java
index 632f7a4dea..d9243f6dc7 100644
--- a/src/avatartranslator/AvatarTuple.java
+++ b/src/avatartranslator/AvatarTuple.java
@@ -59,7 +59,7 @@ public class AvatarTuple extends AvatarLeftHand {
         this.components = new LinkedList<AvatarTerm> ();
     }
 
-    public static AvatarTuple createFromString (AvatarBlock block, String toParse) {
+    public static AvatarTuple createFromString (AvatarStateMachineOwner block, String toParse) {
         AvatarTuple result = null;
 
         int indexLParen = toParse.indexOf ("(");
diff --git a/src/avatartranslator/directsimulation/AvatarSpecificationSimulation.java b/src/avatartranslator/directsimulation/AvatarSpecificationSimulation.java
index 2523099d89..5face2bd21 100644
--- a/src/avatartranslator/directsimulation/AvatarSpecificationSimulation.java
+++ b/src/avatartranslator/directsimulation/AvatarSpecificationSimulation.java
@@ -153,6 +153,9 @@ public class AvatarSpecificationSimulation  {
 
         // Remove composite states
         avspec.removeCompositeStates();
+        
+        // Remove library function calls
+        avspec.removeLibraryFunctionCalls ();
 
         // Remove timers
         avspec.removeTimers();
diff --git a/src/avatartranslator/tocppsim/AVATAR2CPPSIM.java b/src/avatartranslator/tocppsim/AVATAR2CPPSIM.java
index 872010023a..117708d7b1 100644
--- a/src/avatartranslator/tocppsim/AVATAR2CPPSIM.java
+++ b/src/avatartranslator/tocppsim/AVATAR2CPPSIM.java
@@ -93,6 +93,7 @@ public class AVATAR2CPPSIM{
 		optimize = _optimize;
 		warnings = new Vector();
 		avspec.removeCompositeStates();
+                avspec.removeLibraryFunctionCalls ();
 		transBlocks.clear();
 		//REMOVE ALL RANDOM SEQUENCES? removeAllRandomSequences();
 		//TraceManager.addDev("->   Spec:" + avspec.toString());
diff --git a/src/avatartranslator/toexecutable/AVATAR2CPOSIX.java b/src/avatartranslator/toexecutable/AVATAR2CPOSIX.java
index 0376c43aca..aae5bb85d3 100755
--- a/src/avatartranslator/toexecutable/AVATAR2CPOSIX.java
+++ b/src/avatartranslator/toexecutable/AVATAR2CPOSIX.java
@@ -136,6 +136,7 @@ public class AVATAR2CPOSIX {
         taskFiles = new Vector<TaskFile>();
 
         avspec.removeCompositeStates();
+        avspec.removeLibraryFunctionCalls ();
         avspec.removeTimers();
 
 
diff --git a/src/avatartranslator/toproverif/AVATAR2ProVerif.java b/src/avatartranslator/toproverif/AVATAR2ProVerif.java
index 0d93a560b7..5eb5eebe3c 100755
--- a/src/avatartranslator/toproverif/AVATAR2ProVerif.java
+++ b/src/avatartranslator/toproverif/AVATAR2ProVerif.java
@@ -177,6 +177,9 @@ public class AVATAR2ProVerif implements AvatarTranslator {
 
         // TODO: What are composite states ?
         this.avspec.removeCompositeStates();
+
+        this.avspec.removeLibraryFunctionCalls ();
+
         this.avspec.removeTimers();
 
         this.dummyDataCounter = 0;
diff --git a/src/avatartranslator/totpn/AVATAR2TPN.java b/src/avatartranslator/totpn/AVATAR2TPN.java
index 9a4dd1270a..096ee084b4 100755
--- a/src/avatartranslator/totpn/AVATAR2TPN.java
+++ b/src/avatartranslator/totpn/AVATAR2TPN.java
@@ -95,6 +95,7 @@ public class AVATAR2TPN {
         tpn = new TPN();
 
         avspec.removeCompositeStates();
+        avspec.removeLibraryFunctionCalls ();
         avspec.removeTimers();
 
         makeBlocks();
diff --git a/src/avatartranslator/toturtle/AVATAR2TURTLE.java b/src/avatartranslator/toturtle/AVATAR2TURTLE.java
index 9a4597315c..2209c39c92 100644
--- a/src/avatartranslator/toturtle/AVATAR2TURTLE.java
+++ b/src/avatartranslator/toturtle/AVATAR2TURTLE.java
@@ -75,6 +75,7 @@ public class AVATAR2TURTLE {
 		//System.out.println("generate TM");
 		//tmlmodeling.removeAllRandomSequences();
 		spec.removeCompositeStates();
+        spec.removeLibraryFunctionCalls ();
 		
         tm = new TURTLEModeling();
         checkingErrors = new Vector();
diff --git a/src/avatartranslator/touppaal/AVATAR2UPPAAL.java b/src/avatartranslator/touppaal/AVATAR2UPPAAL.java
index 223c5d699f..4338806bfb 100755
--- a/src/avatartranslator/touppaal/AVATAR2UPPAAL.java
+++ b/src/avatartranslator/touppaal/AVATAR2UPPAAL.java
@@ -157,6 +157,7 @@ public class AVATAR2UPPAAL {
         spec = new UPPAALSpec();
 
         avspec.removeCompositeStates();
+        avspec.removeLibraryFunctionCalls ();
         avspec.removeTimers();
         avspec.makeRobustness();
 	LinkedList<String> uppaalPragmas = avspec.getSafetyPragmas();
diff --git a/src/myutil/GraphicLib.java b/src/myutil/GraphicLib.java
index 57d3730f04..8f3dbedd33 100755
--- a/src/myutil/GraphicLib.java
+++ b/src/myutil/GraphicLib.java
@@ -432,10 +432,10 @@ public final class GraphicLib {
     }
     
     public static boolean isInRectangle(int x1, int y1, int x, int y, int width, int height) {
-        if ((x1 >= x) && ((x + width) >= x1) && (y1 >= y) && ((y + height) >= y1)) {
-            return true;
-        }
-        return false;
+        return  x1 >= x         &&
+                x + width >= x1 &&
+                y1 >= y         &&
+                y + height >= y1;
     }
 	
 	public static Point putPointOnRectangle(int x1, int y1, int x, int y, int width, int height) {
diff --git a/src/ui/AvatarDesignPanelTranslator.java b/src/ui/AvatarDesignPanelTranslator.java
index 34dc0dfc37..87ec00e98f 100644
--- a/src/ui/AvatarDesignPanelTranslator.java
+++ b/src/ui/AvatarDesignPanelTranslator.java
@@ -108,22 +108,22 @@ public class AvatarDesignPanelTranslator {
                 as.addApplicationCode(abdp.getMainCode());
             }
         }
-	typeAttributesMap = new HashMap<String, Vector>();
-	nameTypeMap = new HashMap<String,String>();
+        typeAttributesMap = new HashMap<String, Vector>();
+        nameTypeMap = new HashMap<String,String>();
         createLibraryFunctions (as, libraryFunctions);
         createBlocks(as, blocks);
         createRelationsBetweenBlocks(as, blocks);
         makeBlockStateMachines(as);
-	/*for (String s: nameTypeMap.keySet()){
-	    System.out.println(s + " "+ nameTypeMap.get(s));
-	    System.out.println(typeAttributesMap.get(nameTypeMap.get(s)).size());
-	} */
+        /*for (String s: nameTypeMap.keySet()){
+          System.out.println(s + " "+ nameTypeMap.get(s));
+          System.out.println(typeAttributesMap.get(nameTypeMap.get(s)).size());
+          } */
         createPragmas(as, blocks);
 
         TraceManager.addDev("Removing else guards");
         as.removeElseGuards();
         TraceManager.addDev("Removing else guards ... done");
-	//System.out.println(as.toString());
+        //System.out.println(as.toString());
         return as;
     }
 
@@ -172,10 +172,10 @@ public class AvatarDesignPanelTranslator {
         Iterator iterator = adp.getAvatarBDPanel().getComponentList().listIterator();
         TGComponent tgc;
         AvatarBDPragma tgcn;
-	AvatarBDSafetyPragma tgsp;
+        AvatarBDSafetyPragma tgsp;
         String values [];
         String tmp;
-	LinkedList<AvatarPragma> pragmaList;
+        LinkedList<AvatarPragma> pragmaList;
         while(iterator.hasNext()) {
             tgc = (TGComponent)(iterator.next());
             if (tgc instanceof AvatarBDPragma) {
@@ -200,18 +200,18 @@ public class AvatarDesignPanelTranslator {
                                 }
                             }
                             _as.addPragma(tmpPragma);
-                        //TraceManager.addDev("Adding pragma:" + tmp);
+                            //TraceManager.addDev("Adding pragma:" + tmp);
                         }
                     }
                 }
             }
-	    if (tgc instanceof AvatarBDSafetyPragma) {
-		tgsp = (AvatarBDSafetyPragma)tgc;
+            if (tgc instanceof AvatarBDSafetyPragma) {
+                tgsp = (AvatarBDSafetyPragma)tgc;
                 values = tgsp.getValues();
-		for (String s: values){
-		    _as.addSafetyPragma(s);
-		}
-	    }
+                for (String s: values){
+                    _as.addSafetyPragma(s);
+                }
+            }
         }
     }
 
@@ -292,17 +292,17 @@ public class AvatarDesignPanelTranslator {
                           if ((ta.getType() == TAttribute.NATURAL) || (ta.getType() == TAttribute.INTEGER) || (ta.getType() == TAttribute.BOOLEAN)) {
                           ret = ret  + tmp + " ";
                           } else if (ta.getType() == TAttribute.OTHER) {
-                          // Must find all subsequent types
-                          types = adp.getAvatarBDPanel().getAttributesOfDataType(ta.getTypeOther());
-                          if (types == null) {
-                          TraceManager.addDev("Invalid Pragma " + 1);
-                          return null;
-
-                          } else {
-                          for(int j=0; j<types.size(); j++) {
-                          ret = ret + tmp + "__" + ((TAttribute)(types.elementAt(j))).getId() + " ";
-                          }
-                          }
+                        // Must find all subsequent types
+                        types = adp.getAvatarBDPanel().getAttributesOfDataType(ta.getTypeOther());
+                        if (types == null) {
+                        TraceManager.addDev("Invalid Pragma " + 1);
+                        return null;
+
+                        } else {
+                        for(int j=0; j<types.size(); j++) {
+                        ret = ret + tmp + "__" + ((TAttribute)(types.elementAt(j))).getId() + " ";
+                        }
+                        }
                           }
 
                           }
@@ -454,10 +454,9 @@ public class AvatarDesignPanelTranslator {
         TraceManager.addDev("Reworked pragma: " + ret);
 
         return ret.trim();
-
     }
 
-    public void addRegularAttribute(AvatarBlock _ab, TAttribute _a, String _preName) {
+    private AvatarAttribute createRegularAttribute (AvatarStateMachineOwner _ab, TAttribute _a, String _preName) {
         AvatarType type = AvatarType.UNDEFINED;
         if (_a.getType() == TAttribute.INTEGER){
             type = AvatarType.INTEGER;
@@ -470,11 +469,131 @@ public class AvatarDesignPanelTranslator {
         }
         AvatarAttribute aa = new AvatarAttribute(_preName + _a.getId(), type, _ab, _a);
         aa.setInitialValue(_a.getInitialValue());
-        _ab.addAttribute(aa);
+
+        return aa;
+    }
+
+    public void addRegularAttribute(AvatarBlock _ab, TAttribute _a, String _preName) {
+        _ab.addAttribute(this.createRegularAttribute (_ab, _a, _preName));
     }
 
     public void createLibraryFunctions (AvatarSpecification _as, LinkedList<AvatarBDLibraryFunction> _libraryFunctions) {
-        // TODO: translate this as a block
+        for (AvatarBDLibraryFunction libraryFunction: _libraryFunctions) {
+            AvatarLibraryFunction alf = new AvatarLibraryFunction (libraryFunction.getFunctionName (), _as, libraryFunction);
+            _as.addLibraryFunction (alf);
+            listE.addCor(alf, libraryFunction);
+            libraryFunction.setAVATARID(alf.getID());
+
+            // Create parameters
+            for (TAttribute attr: libraryFunction.getParameters ())
+                if (attr.getType() == TAttribute.INTEGER
+                        || attr.getType() == TAttribute.NATURAL
+                        || attr.getType() == TAttribute.BOOLEAN
+                        || attr.getType() == TAttribute.TIMER)
+                    alf.addParameter (this.createRegularAttribute (alf, attr, ""));
+                else {
+                    // other
+                    Vector<TAttribute> types = adp.getAvatarBDPanel ().getAttributesOfDataType (attr.getTypeOther ());
+                    if (types == null) {
+                        CheckingError ce = new CheckingError(CheckingError.STRUCTURE_ERROR, "Unknown data type:  " + attr.getTypeOther() + " used in " + alf.getName());
+                        // TODO: adapt
+                        // ce.setAvatarBlock(ab);
+                        ce.setTDiagramPanel(adp.getAvatarBDPanel());
+                        addCheckingError(ce);
+                        return;
+                    } else {
+                        if (types.isEmpty ()) {
+                            CheckingError ce = new CheckingError(CheckingError.STRUCTURE_ERROR, "Data type definition must contain at least one attribute:  " + alf.getName());
+                            ce.setTDiagramPanel(adp.getAvatarBDPanel());
+                            addCheckingError(ce);
+                        } else {
+                            nameTypeMap.put (libraryFunction.getFunctionName()+"."+attr.getId(), attr.getTypeOther());
+                            typeAttributesMap.put (attr.getTypeOther(), types);
+                            for (TAttribute type: types)
+                                alf.addParameter (this.createRegularAttribute (alf, type, attr.getId() + "__"));
+                        }
+                    }
+                }
+
+            // Create return values
+            for (TAttribute attr: libraryFunction.getReturnAttributes ())
+                if (attr.getType() == TAttribute.INTEGER
+                        || attr.getType() == TAttribute.NATURAL
+                        || attr.getType() == TAttribute.BOOLEAN
+                        || attr.getType() == TAttribute.TIMER)
+                    alf.addReturnAttribute (this.createRegularAttribute (alf, attr, ""));
+                else {
+                    // other
+                    Vector<TAttribute> types = adp.getAvatarBDPanel ().getAttributesOfDataType (attr.getTypeOther ());
+                    if (types == null) {
+                        CheckingError ce = new CheckingError(CheckingError.STRUCTURE_ERROR, "Unknown data type:  " + attr.getTypeOther() + " used in " + alf.getName());
+                        ce.setTDiagramPanel(adp.getAvatarBDPanel());
+                        addCheckingError(ce);
+                        return;
+                    } else {
+                        if (types.isEmpty ()) {
+                            CheckingError ce = new CheckingError(CheckingError.STRUCTURE_ERROR, "Data type definition must contain at least one attribute:  " + alf.getName());
+                            ce.setTDiagramPanel(adp.getAvatarBDPanel());
+                            addCheckingError(ce);
+                        } else {
+                            nameTypeMap.put (libraryFunction.getFunctionName()+"."+attr.getId(), attr.getTypeOther());
+                            typeAttributesMap.put (attr.getTypeOther(), types);
+                            for (TAttribute type: types)
+                                alf.addReturnAttribute (this.createRegularAttribute (alf, type, attr.getId() + "__"));
+                        }
+                    }
+                }
+
+            // Create attributes
+            for (TAttribute attr: libraryFunction.getAttributes ())
+                if (attr.getType() == TAttribute.INTEGER
+                        || attr.getType() == TAttribute.NATURAL
+                        || attr.getType() == TAttribute.BOOLEAN
+                        || attr.getType() == TAttribute.TIMER)
+                    alf.addReturnAttribute (this.createRegularAttribute (alf, attr, ""));
+                else {
+                    // other
+                    Vector<TAttribute> types = adp.getAvatarBDPanel ().getAttributesOfDataType (attr.getTypeOther ());
+                    if (types == null) {
+                        CheckingError ce = new CheckingError(CheckingError.STRUCTURE_ERROR, "Unknown data type:  " + attr.getTypeOther() + " used in " + alf.getName());
+                        ce.setTDiagramPanel(adp.getAvatarBDPanel());
+                        addCheckingError(ce);
+                        return;
+                    } else {
+                        if (types.isEmpty ()) {
+                            CheckingError ce = new CheckingError(CheckingError.STRUCTURE_ERROR, "Data type definition must contain at least one attribute:  " + alf.getName());
+                            ce.setTDiagramPanel(adp.getAvatarBDPanel());
+                            addCheckingError(ce);
+                        } else {
+                            nameTypeMap.put (libraryFunction.getFunctionName()+"."+attr.getId(), attr.getTypeOther());
+                            typeAttributesMap.put (attr.getTypeOther(), types);
+                            for (TAttribute type: types)
+                                alf.addAttribute (this.createRegularAttribute (alf, type, attr.getId() + "__"));
+                        }
+                    }
+                }
+
+                // Create methods
+                for (ui.AvatarMethod uiam: libraryFunction.getMethods ()) {
+                    avatartranslator.AvatarMethod atam = new avatartranslator.AvatarMethod (uiam.getId (), uiam);
+                    atam.setImplementationProvided (uiam.isImplementationProvided());
+                    alf.addMethod (atam);
+                    this.makeParameters (alf, atam, uiam);
+                    this.makeReturnParameters (alf, libraryFunction, atam, uiam);
+                }
+
+                // Create signals
+                for (ui.AvatarSignal uias: libraryFunction.getSignals ()) {
+                    avatartranslator.AvatarSignal atas;
+                    if (uias.getInOut() == uias.IN)
+                        atas = new avatartranslator.AvatarSignal(uias.getId(), avatartranslator.AvatarSignal.IN, uias);
+                    else
+                        atas = new avatartranslator.AvatarSignal(uias.getId(), avatartranslator.AvatarSignal.OUT, uias);
+
+                    alf.addSignal (atas);
+                    this.makeParameters (alf, atas, uias);
+                }
+        }
     }
 
     public void createBlocks(AvatarSpecification _as, LinkedList<AvatarBDBlock> _blocks) {
@@ -510,7 +629,7 @@ public class AvatarDesignPanelTranslator {
                     addRegularAttribute(ab, a, "");
                 } else {
                     // other
-                   // TraceManager.addDev(" -> Other type found: " + a.getTypeOther());
+                    // TraceManager.addDev(" -> Other type found: " + a.getTypeOther());
                     types = adp.getAvatarBDPanel().getAttributesOfDataType(a.getTypeOther());
                     if (types == null) {
                         CheckingError ce = new CheckingError(CheckingError.STRUCTURE_ERROR, "Unknown data type:  " + a.getTypeOther() + " used in " + ab.getName());
@@ -525,8 +644,8 @@ public class AvatarDesignPanelTranslator {
                             ce.setTDiagramPanel(adp.getAvatarBDPanel());
                             addCheckingError(ce);
                         } else {
-			    nameTypeMap.put(block.getBlockName()+"."+a.getId(), a.getTypeOther());
-			    typeAttributesMap.put(a.getTypeOther(), types);
+                            nameTypeMap.put(block.getBlockName()+"."+a.getId(), a.getTypeOther());
+                            typeAttributesMap.put(a.getTypeOther(), types);
                             for(int j=0; j<types.size(); j++) {
                                 addRegularAttribute(ab, (TAttribute)(types.elementAt(j)), a.getId() + "__");
                             }
@@ -580,13 +699,15 @@ public class AvatarDesignPanelTranslator {
 
     public void makeBlockStateMachines(AvatarSpecification _as) {
         // Make state machine of blocks
-        for(AvatarBlock block: _as.getListOfBlocks()) {
-            makeStateMachine(_as, block);
-        }
+        for(AvatarBlock block: _as.getListOfBlocks())
+            this.makeStateMachine(_as, block);
 
+        // Make state machine of library functions
+        for (AvatarLibraryFunction libraryFunction: _as.getListOfLibraryFunctions ())
+            this.makeStateMachine (_as, libraryFunction);
     }
 
-    public void makeReturnParameters(AvatarBlock _ab, AvatarBDBlock _block, avatartranslator.AvatarMethod _atam, ui.AvatarMethod _uiam) {
+    public void makeReturnParameters(AvatarStateMachineOwner _ab, AvatarBDStateMachineOwner _block, avatartranslator.AvatarMethod _atam, ui.AvatarMethod _uiam) {
         String rt = _uiam.getReturnType().trim();
         AvatarAttribute aa;
         Vector types;
@@ -603,23 +724,23 @@ public class AvatarDesignPanelTranslator {
         } else {
             types = adp.getAvatarBDPanel().getAttributesOfDataType(rt);
             if (types == null) {
-                CheckingError ce = new CheckingError(CheckingError.STRUCTURE_ERROR, "Unknown data type:  " + rt + " declared as a return parameter of a method of " + _block.getName());
-                ce.setAvatarBlock(_ab);
+                CheckingError ce = new CheckingError(CheckingError.STRUCTURE_ERROR, "Unknown data type:  " + rt + " declared as a return parameter of a method of " + _block.getOwnerName());
+                // TODO: adapt
+                // ce.setAvatarBlock(_ab);
                 ce.setTDiagramPanel(adp.getAvatarBDPanel());
                 addCheckingError(ce);
                 return;
             } else {
                 for(int j=0; j<types.size(); j++) {
                     ta = (TAttribute)(types.elementAt(j));
-                    if (ta.getType() == TAttribute.INTEGER){
+                    if (ta.getType() == TAttribute.INTEGER)
                         type = AvatarType.INTEGER;
-                    } else if (ta.getType() == TAttribute.NATURAL){
+                    else if (ta.getType() == TAttribute.NATURAL)
                         type = AvatarType.INTEGER;
-                    } else if (ta.getType() == TAttribute.BOOLEAN) {
+                    else if (ta.getType() == TAttribute.BOOLEAN)
                         type = AvatarType.BOOLEAN;
-                    } else {
+                    else
                         type = AvatarType.INTEGER;
-                    }
                     aa = new AvatarAttribute("return__" + j, type, _ab, _block);
                     _atam.addReturnParameter(aa);
                 }
@@ -628,7 +749,7 @@ public class AvatarDesignPanelTranslator {
 
     }
 
-    public void makeParameters(AvatarBlock _block, avatartranslator.AvatarMethod _atam, ui.AvatarMethod _uiam) {
+    public void makeParameters(AvatarStateMachineOwner _block, avatartranslator.AvatarMethod _atam, ui.AvatarMethod _uiam) {
         String typeIds[] = _uiam.getTypeIds();
         String types[] = _uiam.getTypes();
         AvatarAttribute aa;
@@ -641,7 +762,8 @@ public class AvatarDesignPanelTranslator {
             if (v == null) {
                 if (AvatarType.getType(types[i]) == AvatarType.UNDEFINED) {
                     CheckingError ce = new CheckingError(CheckingError.STRUCTURE_ERROR, "Unknown data type:  \"" + types[i] + "\" declared in method " + _atam + " of block " + _block.getName());
-                    ce.setAvatarBlock(_block);
+                    // TODO: adapt
+                    // ce.setAvatarBlock(_block);
                     ce.setTDiagramPanel(adp.getAvatarBDPanel());
                     addCheckingError(ce);
                 }
@@ -666,11 +788,12 @@ public class AvatarDesignPanelTranslator {
         }
     }
 
-    public void manageAttribute(String _name, AvatarBlock _ab, AvatarActionOnSignal _aaos, TDiagramPanel _tdp, TGComponent _tgc, String _idOperator) {
+    public void manageAttribute (String _name, AvatarStateMachineOwner _ab, AvatarActionOnSignal _aaos, TDiagramPanel _tdp, TGComponent _tgc, String _idOperator) {
         TAttribute ta =  adp.getAvatarBDPanel().getAttribute(_name, _ab.getName());
         if (ta == null) {
             CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed parameter: " + _name + " in signal expression: " + _idOperator);
-            ce.setAvatarBlock(_ab);
+            // TODO: adapt
+            // ce.setAvatarBlock(_ab);
             ce.setTDiagramPanel(_tdp);
             ce.setTGComponent(_tgc);
             addCheckingError(ce);
@@ -700,7 +823,8 @@ public class AvatarDesignPanelTranslator {
             aa = _ab.getAvatarAttributeWithName((String)(v.get(i)));
             if (aa == null) {
                 CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed parameter: " + _name + " in signal expression: " + _idOperator);
-                ce.setAvatarBlock(_ab);
+                // TODO: adapt
+                // ce.setAvatarBlock(_ab);
                 ce.setTDiagramPanel(_tdp);
                 ce.setTGComponent(_tgc);
                 addCheckingError(ce);
@@ -712,657 +836,484 @@ public class AvatarDesignPanelTranslator {
         }
     }
 
-    public void makeStateMachine(AvatarSpecification _as, AvatarBlock _ab) {
-        AvatarBDBlock block = (AvatarBDBlock)(listE.getTG(_ab));
-        if (block == null) {
-            CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "No corresponding graphical block for  " + _ab.getName());
-            ce.setAvatarBlock(_ab);
-            ce.setTDiagramPanel(adp.getAvatarBDPanel());
-            addCheckingError(ce);
-            return;
+    private void translateAvatarSMDSendSignal (TDiagramPanel tdp, AvatarSpecification _as, AvatarStateMachineOwner _ab, AvatarSMDSendSignal asmdss) throws CheckingError {
+        AvatarStateMachine asm = _ab.getStateMachine ();
+        avatartranslator.AvatarSignal atas = _ab.getAvatarSignalWithName (asmdss.getSignalName ());
+        if (atas == null)
+            throw new CheckingError (CheckingError.BEHAVIOR_ERROR, "Unknown signal: " + asmdss.getSignalName());
+
+        // Get relation of that signal
+        if (_ab instanceof AvatarBlock) {
+            // Note that for library functions, signals are just placeholders so they don't need to be connected to anything
+            AvatarRelation ar = _as.getAvatarRelationWithSignal (atas);
+            if (ar == null)
+                throw new CheckingError (CheckingError.BEHAVIOR_ERROR, "Signal used for sending in " + asmdss.getValue() + " is not connected to a channel");
         }
 
-        AvatarSMDPanel asmdp = block.getAvatarSMDPanel();
-        String name = block.getBlockName();
-        TDiagramPanel tdp;
+        AvatarActionOnSignal aaos = new AvatarActionOnSignal ("action_on_signal", atas, asmdss);
+        if (asmdss.hasCheckableAccessibility())
+            aaos.setCheckable();
 
-        int size = checkingErrors.size();
+        if (aaos.isReceiving ())
+            throw new CheckingError(CheckingError.BEHAVIOR_ERROR, "A receiving signal is used for sending: " + asmdss.getValue());
 
-        if (asmdp == null) {
-            return;
+        if (asmdss.getNbOfValues() == -1)
+            throw new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed signal: " + asmdss.getValue());
+
+        for(int i=0; i<asmdss.getNbOfValues(); i++) {
+            String tmp = asmdss.getValue(i);
+            if (tmp.isEmpty ())
+                throw new CheckingError(CheckingError.BEHAVIOR_ERROR, "Empty parameter in signal expression: " + asmdss.getValue());
+
+            this.manageAttribute (tmp, _ab, aaos, tdp, asmdss, asmdss.getValue());
         }
 
-        tdp = (TDiagramPanel)asmdp;
+        if (aaos.getNbOfValues () != atas.getListOfAttributes ().size ())
+            throw new CheckingError (CheckingError.BEHAVIOR_ERROR, "Badly formed signal sending: " + asmdss.getValue() + " -> nb of parameters does not match definition");
 
-        // search for start state
-        LinkedList list = asmdp.getComponentList();
-        Iterator iterator = list.listIterator();
-        TGComponent tgc;
-        AvatarSMDStartState tss = null;
-        int cptStart = 0;
-        while(iterator.hasNext()) {
-            tgc = (TGComponent)(iterator.next());
-            if (tgc instanceof AvatarSMDStartState){
-                tss = (AvatarSMDStartState)tgc;
-                cptStart ++;
+        // Checking expressions passed as parameter
+        for (int i=0; i<aaos.getNbOfValues(); i++) {
+            String theVal = aaos.getValue(i);
+            if (atas.getListOfAttributes ().get (i).isInt ()) {
+                if (AvatarSyntaxChecker.isAValidIntExpr (_as, _ab, theVal) < 0)
+                    throw new CheckingError (CheckingError.BEHAVIOR_ERROR, "Badly formed signal receiving: " + asmdss.getValue() + " -> value at index #" + i + " does not match definition");
+            } else {
+                // We assume it is a bool attribute
+                if (AvatarSyntaxChecker.isAValidBoolExpr(_as, _ab, theVal) < 0)
+                    throw new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed signal receiving: " + asmdss.getValue() + " -> value at index #" + i + " does not match definition");
             }
         }
 
-        if (tss == null) {
-            CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "No start state in the state machine diagram of " + name);
-            ce.setAvatarBlock(_ab);
-            ce.setTDiagramPanel(tdp);
-            addCheckingError(ce);
-            return;
-        }
+        this.listE.addCor (aaos, asmdss);
+        asmdss.setAVATARID (aaos.getID());
+        asm.addElement (aaos);
+    }
 
-        if (cptStart > 1) {
-            CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "More than one start state in the state machine diagram of " + name);
-            ce.setAvatarBlock(_ab);
-            ce.setTDiagramPanel(tdp);
-            addCheckingError(ce);
-            return;
+
+    private void translateAvatarSMDReceiveSignal (TDiagramPanel tdp, AvatarSpecification _as, AvatarStateMachineOwner _ab, AvatarSMDReceiveSignal asmdrs) throws CheckingError {
+        AvatarStateMachine asm = _ab.getStateMachine ();
+        avatartranslator.AvatarSignal atas = _ab.getAvatarSignalWithName (asmdrs.getSignalName ());
+        if (atas == null)
+            throw new CheckingError (CheckingError.BEHAVIOR_ERROR, "Unknown signal: " + asmdrs.getSignalName());
+
+        // Get relation of that signal
+        if (_ab instanceof AvatarBlock) {
+            // Note that for library functions, signals are just placeholders so they don't need to be connected to anything
+            AvatarRelation ar = _as.getAvatarRelationWithSignal (atas);
+            if (ar == null)
+                throw new CheckingError (CheckingError.BEHAVIOR_ERROR, "Signal used for receiving in " + asmdrs.getValue() + " is not connected to a channel");
         }
 
-        // This shall also be true for all composite state: at most one start state!
-        tgc = checkForStartStateOfCompositeStates(asmdp);
-        if (tgc != null) {
-            CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "More than one start state in composite state");
-            ce.setAvatarBlock(_ab);
-            ce.setTDiagramPanel(tdp);
-            ce.setTGComponent(tgc);
-            addCheckingError(ce);
-            return;
+        AvatarActionOnSignal aaos = new AvatarActionOnSignal ("action_on_signal", atas, asmdrs);
+        if (asmdrs.hasCheckableAccessibility())
+            aaos.setCheckable();
+
+        if (aaos.isSending())
+            throw new CheckingError(CheckingError.BEHAVIOR_ERROR, "A sending signal is used for receiving: " + asmdrs.getValue());
+
+        if (asmdrs.getNbOfValues() == -1)
+            throw new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed signal: " + asmdrs.getValue());
+
+        for(int i=0; i<asmdrs.getNbOfValues(); i++) {
+            String tmp = asmdrs.getValue(i);
+            if (tmp.isEmpty ())
+                throw new CheckingError(CheckingError.BEHAVIOR_ERROR, "Empty parameter in signal expression: " + asmdrs.getValue());
+
+            this.manageAttribute (tmp, _ab, aaos, tdp, asmdrs, asmdrs.getValue());
         }
 
-        // First pass: creating AVATAR components, but no interconnection between them
-        iterator = asmdp.getAllComponentList().listIterator();
-        AvatarSMDReceiveSignal asmdrs;
-        AvatarSMDSendSignal asmdss;
-        AvatarSMDRandom asmdrand;
+        if (aaos.getNbOfValues () != atas.getListOfAttributes ().size ())
+            throw new CheckingError (CheckingError.BEHAVIOR_ERROR, "Badly formed signal receiving: " + asmdrs.getValue() + " -> nb of parameters does not match definition");
 
-        AvatarStateMachine asm = _ab.getStateMachine();
-        avatartranslator.AvatarSignal atas;
-        AvatarActionOnSignal aaos;
-        AvatarAttribute aa;
-        AvatarStopState astop;
-        AvatarStartState astart;
-        AvatarState astate;
-        AvatarRandom arandom;
-        AvatarSetTimer asettimer;
-        AvatarResetTimer aresettimer;
-        AvatarExpireTimer aexpiretimer;
-        AvatarRelation ar;
-        int i;
-        String tmp;
-        TAttribute ta;
+        // Checking expressions passed as parameter
+        for (int i=0; i<aaos.getNbOfValues(); i++) {
+            String theVal = aaos.getValue(i);
+            if (atas.getListOfAttributes ().get (i).isInt ()) {
+                if (AvatarSyntaxChecker.isAValidIntExpr (_as, _ab, theVal) < 0)
+                    throw new CheckingError (CheckingError.BEHAVIOR_ERROR, "Badly formed signal receiving: " + asmdrs.getValue() + " -> value at index #" + i + " does not match definition");
+            } else {
+                // We assume it is a bool attribute
+                if (AvatarSyntaxChecker.isAValidBoolExpr(_as, _ab, theVal) < 0)
+                    throw new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed signal receiving: " + asmdrs.getValue() + " -> value at index #" + i + " does not match definition");
+            }
+        }
 
-        int choiceID = 0;
-        int error;
-        String tmp1, tmp2;
+        this.listE.addCor (aaos, asmdrs);
+        asmdrs.setAVATARID (aaos.getID());
+        asm.addElement (aaos);
+    }
 
-        while(iterator.hasNext()) {
-            tgc = (TGComponent)(iterator.next());
+    private void translateAvatarSMDState (TDiagramPanel tdp, AvatarSpecification _as, AvatarStateMachineOwner _ab, AvatarSMDState tgc) throws CheckingError {
+        AvatarStateMachine asm = _ab.getStateMachine ();
+        AvatarState astate = asm.getStateWithName(tgc.getValue());
+        if (astate == null) {
+            astate = new AvatarState (tgc.getValue(), tgc);
+            asm.addElement (astate);
+        }
 
-            // Receive signal
-            if (tgc instanceof AvatarSMDReceiveSignal) {
-                asmdrs = (AvatarSMDReceiveSignal)tgc;
-                atas = _ab.getAvatarSignalWithName(asmdrs.getSignalName());
-                if (atas == null) {
-                    CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Unknown signal: " + asmdrs.getSignalName());
-                    ce.setAvatarBlock(_ab);
-                    ce.setTDiagramPanel(tdp);
-                    ce.setTGComponent(tgc);
-                    addCheckingError(ce);
+        if (tgc.hasCheckableAccessibility ())
+            astate.setCheckable ();
 
-                } else {
-                    // Get relation of that signal
-                    ar = _as.getAvatarRelationWithSignal(atas);
-                    if (ar == null) {
-                        CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Signal used for receiving in " + asmdrs.getValue() + " is not connected to a channel");
-                        ce.setAvatarBlock(_ab);
-                        ce.setTDiagramPanel(tdp);
-                        ce.setTGComponent(tgc);
-                        addCheckingError(ce);
-                        //_as.addBroadcastSignal(atas);
-                    }
-                    aaos = new AvatarActionOnSignal("action_on_signal", atas, tgc);
-                    if (asmdrs.hasCheckableAccessibility()) {
-                        aaos.setCheckable();
-                    }
-                    if (aaos.isSending()) {
-                        CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "A sending signal is used for receiving: " + asmdrs.getValue());
-                        ce.setAvatarBlock(_ab);
-                        ce.setTDiagramPanel(tdp);
-                        ce.setTGComponent(tgc);
-                        addCheckingError(ce);
-                    }
-                    if (asmdrs.getNbOfValues() == -1){
-                        CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed signal: " + asmdrs.getValue());
-                        ce.setAvatarBlock(_ab);
-                        ce.setTDiagramPanel(tdp);
-                        ce.setTGComponent(tgc);
-                        addCheckingError(ce);
-                    } else {
-                        for(i=0; i<asmdrs.getNbOfValues(); i++) {
-                            tmp = asmdrs.getValue(i);
-                            if (tmp.length() == 0) {
-                                CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed parameter: " + tmp + " in signal expression: " + asmdrs.getValue());
-                                ce.setAvatarBlock(_ab);
-                                ce.setTDiagramPanel(tdp);
-                                ce.setTGComponent(tgc);
-                                addCheckingError(ce);
-                            } else {
-                                manageAttribute(tmp, _ab, aaos, tdp, tgc, asmdrs.getValue());
-                            }
-                        }
+        // Executable code
+        astate.addEntryCode(((AvatarSMDState)(tgc)).getEntryCode());
 
-                        if (aaos.getNbOfValues() != atas.getListOfAttributes().size()) {
-                            CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed signal receiving: " + asmdrs.getValue() + " -> nb of parameters does not match definition");
-                            TraceManager.addDev(" ERROR NB: in signal : " + aaos.getNbOfValues() + " in signal def:" + atas.getListOfAttributes().size() + " NAME=" + atas.getName());
-                            ce.setAvatarBlock(_ab);
-                            ce.setTDiagramPanel(tdp);
-                            ce.setTGComponent(tgc);
-                            addCheckingError(ce);
-                        } else {
+        this.listE.addCor (astate, tgc);
+        astate.addReferenceObject (tgc);
+        tgc.setAVATARID (astate.getID());
+    }
 
-                            // Checking expressions passed as parameter
-                            for(i=0; i<aaos.getNbOfValues(); i++) {
-                                String theVal = aaos.getValue(i);
-                                if (atas.getListOfAttributes().get(i).isInt()) {
-                                    if (AvatarSyntaxChecker.isAValidIntExpr(_as, _ab, theVal) < 0) {
-                                        CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed signal receiving: " + asmdrs.getValue() + " -> value at index #" + i + " does not match definition");
-                                        //TraceManager.addDev(" ERROR NB: in signal : " + aaos.getNbOfValues() + " in signal def:" + atas.getListOfAttributes().size() + " NAME=" + atas.getName());
-                                        ce.setAvatarBlock(_ab);
-                                        ce.setTDiagramPanel(tdp);
-                                        ce.setTGComponent(tgc);
-                                        addCheckingError(ce);
-                                    }
-                                } else {
-                                    // We assume it is a bool attribute
-                                    if (AvatarSyntaxChecker.isAValidBoolExpr(_as, _ab, theVal) < 0) {
-                                        CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed signal receiving: " + asmdrs.getValue() + " -> value at index #" + i + " does not match definition");
-                                        //TraceManager.addDev(" ERROR NB: in signal : " + aaos.getNbOfValues() + " in signal def:" + atas.getListOfAttributes().size() + " NAME=" + atas.getName());
-                                        ce.setAvatarBlock(_ab);
-                                        ce.setTDiagramPanel(tdp);
-                                        ce.setTGComponent(tgc);
-                                        addCheckingError(ce);
-                                    }
-                                }
-                            }
-                        }
-                        //adag.setActionValue(makeTIFAction(asmdrs.getValue(), "?"));
-                        listE.addCor(aaos, tgc);
-                        tgc.setAVATARID(aaos.getID());
-                        asm.addElement(aaos);
-                    }
-                }
+    private void translateAvatarSMDRandom (TDiagramPanel tdp, AvatarSpecification _as, AvatarStateMachineOwner _ab, AvatarSMDRandom asmdrand) throws CheckingError {
+        AvatarStateMachine asm = _ab.getStateMachine ();
+        AvatarRandom arandom = new AvatarRandom ("random", asmdrand);
+        String tmp1 = modifyString (asmdrand.getMinValue());
+        int error = AvatarSyntaxChecker.isAValidIntExpr(_as, _ab, tmp1);
+        if (error < 0)
+            this.makeError (error, tdp, _ab, asmdrand, "min value of random", tmp1);
 
-                // Send signals
-            } else if (tgc instanceof AvatarSMDSendSignal) {
-                asmdss = (AvatarSMDSendSignal)tgc;
-                atas = _ab.getAvatarSignalWithName(asmdss.getSignalName());
+        String tmp2 = modifyString(asmdrand.getMaxValue());
+        error = AvatarSyntaxChecker.isAValidIntExpr(_as, _ab, tmp2);
+        if (error < 0)
+            this.makeError (error, tdp, _ab, asmdrand, "max value of random", tmp2);
 
-                if (atas == null) {
-                    CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Unknown signal: " + asmdss.getSignalName());
-                    ce.setAvatarBlock(_ab);
-                    ce.setTDiagramPanel(tdp);
-                    ce.setTGComponent(tgc);
-                    addCheckingError(ce);
-                } else {
-                    // Get relation of that signal
-                    ar = _as.getAvatarRelationWithSignal(atas);
-                    if (ar == null) {
-                        CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Signal used for sending in " + asmdss.getValue() + " is not connected to a channel");
-                        ce.setAvatarBlock(_ab);
-                        ce.setTDiagramPanel(tdp);
-                        ce.setTGComponent(tgc);
-                        addCheckingError(ce);
-                        //_as.addBroadcastSignal(atas);
-                    }
+        arandom.setValues (tmp1, tmp2);
+        arandom.setFunctionId (asmdrand.getFunctionId());
 
-                    aaos = new AvatarActionOnSignal("action_on_signal", atas, tgc);
-                    if (asmdss.hasCheckableAccessibility()) {
-                        aaos.setCheckable();
-                    }
-                    if (aaos.isReceiving()) {
-                        CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "A sending signal is used for receiving: " + asmdss.getValue());
-                        ce.setAvatarBlock(_ab);
-                        ce.setTDiagramPanel(tdp);
-                        ce.setTGComponent(tgc);
-                        addCheckingError(ce);
-                    }
-                    if (asmdss.getNbOfValues() == -1) {
-                        CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed signal: " + asmdss.getValue());
-                        ce.setAvatarBlock(_ab);
-                        ce.setTDiagramPanel(tdp);
-                        ce.setTGComponent(tgc);
-                        addCheckingError(ce);
-                    } else {
-                        //TraceManager.addDev("Nb of values in signal" + atas.getName() + " :" + atas.getListOfAttributes().size());
-                        //TraceManager.addDev("Nb of values in admdss :" + asmdss.getNbOfValues());
-
-                        for(i=0; i<asmdss.getNbOfValues(); i++) {
-                            tmp = asmdss.getValue(i);
-                            if (tmp.length() == 0) {
-                                CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed parameter: " + tmp + " in signal expression: " + asmdss.getValue());
-                                ce.setAvatarBlock(_ab);
-                                ce.setTDiagramPanel(tdp);
-                                ce.setTGComponent(tgc);
-                                addCheckingError(ce);
-                            } else {
-                                manageAttribute(tmp, _ab, aaos, tdp, tgc, asmdss.getValue());
-                            }
-                        }
-                        if (aaos.getNbOfValues() != atas.getListOfAttributes().size()) {
-                            CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed signal sending: " + asmdss.getValue() + " -> nb of parameters does not match definition");
-                            TraceManager.addDev(" ERROR NB: in signal : " + aaos.getNbOfValues() + " in signal def:" + atas.getListOfAttributes().size() + " NAME=" + atas.getName());
-                            ce.setAvatarBlock(_ab);
-                            ce.setTDiagramPanel(tdp);
-                            ce.setTGComponent(tgc);
-                            addCheckingError(ce);
-                        }  else {
-
-                            // Checking expressions passed as parameter
-                            //TraceManager.addDev("Block = " + _ab.getName());
-                            for(i=0; i<aaos.getNbOfValues(); i++) {
-                                String theVal = aaos.getValue(i);
-                                if (atas.getListOfAttributes().get(i).isInt()) {
-                                    if (AvatarSyntaxChecker.isAValidIntExpr(_as, _ab, theVal) < 0) {
-                                        CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed signal sending: " + asmdss.getValue() + " -> value at index #" + i + " does not match definition");
-                                        //TraceManager.addDev(" ERROR NB: in signal : " + aaos.getNbOfValues() + " in signal def:" + atas.getListOfAttributes().size() + " NAME=" + atas.getName());
-                                        ce.setAvatarBlock(_ab);
-                                        ce.setTDiagramPanel(tdp);
-                                        ce.setTGComponent(tgc);
-                                        addCheckingError(ce);
-                                    }
-                                } else {
-                                    // We assume it is a bool attribute
-                                    if (AvatarSyntaxChecker.isAValidBoolExpr(_as, _ab, theVal) < 0) {
-                                        CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed signal sending: " + asmdss.getValue() + " -> value at index #" + i + " does not match definition");
-                                        //TraceManager.addDev(" ERROR NB: in signal : " + aaos.getNbOfValues() + " in signal def:" + atas.getListOfAttributes().size() + " NAME=" + atas.getName());
-                                        ce.setAvatarBlock(_ab);
-                                        ce.setTDiagramPanel(tdp);
-                                        ce.setTGComponent(tgc);
-                                        addCheckingError(ce);
-                                    }
-                                }
-                            }
-                        }
+        tmp1 = modifyString(asmdrand.getVariable());
+        AvatarAttribute aa = _ab.getAvatarAttributeWithName (tmp1);
 
-                        // Check that tmp is the identifier of an attribute
-                        /*aa = _ab.getAvatarAttributeWithName(tmp);
-                          if (aa == null) {
-                          CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed parameter: " + tmp + " in signal expression: " + asmdss.getValue());
-                          ce.setAvatarBlock(_ab);
-                          ce.setTDiagramPanel(tdp);
-                          ce.setTGComponent(tgc);
-                          addCheckingError(ce);
-                          } else {
-                          aaos.addValue(tmp);
-                          }*/
-                        //adag.setActionValue(makeTIFAction(asmdrs.getValue(), "?"));
-                        listE.addCor(aaos, tgc);
-                        tgc.setAVATARID(aaos.getID());
-                        asm.addElement(aaos);
-                    }
-                }
+        if (aa == null)
+            this.makeError (-3, tdp, _ab, asmdrand, "random", tmp1);
+        // Checking type of variable -> must be an int
+        else if (!(aa.isInt()))
+            this.makeError (error, tdp, _ab, asmdrand, ": variable of random must be of type \"int\"", tmp2);
 
-                // State
-            } else if (tgc instanceof AvatarSMDState) {
-                //TraceManager.addDev("Value = " + tgc.getValue());
-                astate = asm.getStateWithName(tgc.getValue());
-                if (astate == null) {
-                    astate = new AvatarState(tgc.getValue(), tgc);
-                    asm.addElement(astate);
-                }
-                if (tgc.hasCheckableAccessibility()) {
-                    astate.setCheckable();
-                    TraceManager.addDev("Setting as checkable : " + tgc.getValue());
-                }
+        arandom.setVariable (tmp1);
 
-                // Executable code
-                astate.addEntryCode(((AvatarSMDState)(tgc)).getEntryCode());
-                //_ab.addGlobalCode(((AvatarSMDState)(tgc)).getGlobalCode());
+        asm.addElement (arandom);
+        listE.addCor (arandom, asmdrand);
+        asmdrand.setAVATARID (arandom.getID());
+    }
 
-                listE.addCor(astate, tgc);
-                astate.addReferenceObject(tgc);
-                tgc.setAVATARID(astate.getID());
+    private void translateAvatarSMDSetTimer (TDiagramPanel tdp, AvatarSpecification _as, AvatarStateMachineOwner _ab, AvatarSMDSetTimer asmdst) throws CheckingError {
+        AvatarStateMachine asm = _ab.getStateMachine ();
+        String tmp = asmdst.getTimerName();
+        AvatarAttribute aa = _ab.getAvatarAttributeWithName(tmp);
+        if (aa == null)
+            throw new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed timer parameter: " + tmp + " in timer setting");
+
+        if (aa.getType() != AvatarType.TIMER)
+            throw new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed parameter: " + tmp + " in timer setting: shall be a parameter of type \"Timer\"");
+
+        tmp = this.modifyString (asmdst.getTimerValue ());
+        int error = AvatarSyntaxChecker.isAValidIntExpr (_as, _ab, tmp);
+        if (error < 0)
+            this.makeError(error, tdp, _ab, asmdst, "value of the timer setting", tmp);
+
+        AvatarSetTimer asettimer = new AvatarSetTimer("settimer__" + aa.getName(), asmdst);
+        asettimer.setTimer (aa);
+        asettimer.setTimerValue (tmp);
+        asm.addElement (asettimer);
+        this.listE.addCor (asettimer, asmdst);
+        asmdst.setAVATARID (asettimer.getID());
+    }
 
+    private void translateAvatarSMDResetTimer (TDiagramPanel tdp, AvatarSpecification _as, AvatarStateMachineOwner _ab, AvatarSMDResetTimer asmdrt) throws CheckingError {
+        AvatarStateMachine asm = _ab.getStateMachine ();
+        String tmp = asmdrt.getTimerName();
+        AvatarAttribute aa = _ab.getAvatarAttributeWithName (tmp);
+        if (aa == null)
+            throw new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed timer parameter: " + tmp + " in timer reset");
+
+        if (aa.getType() != AvatarType.TIMER)
+            throw new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed parameter: " + tmp + " in timer reset: shall be a parameter of type \"Timer\"");
+
+        AvatarResetTimer aresettimer = new AvatarResetTimer("resettimer__" + aa.getName(), asmdrt);
+        aresettimer.setTimer (aa);
+        asm.addElement(aresettimer);
+        this.listE.addCor (aresettimer, asmdrt);
+        asmdrt.setAVATARID (aresettimer.getID());
+    }
 
-                // Choice
-            } else if (tgc instanceof AvatarSMDChoice) {
-                astate = new AvatarState("choice__" + choiceID, tgc);
-                choiceID ++;
-                asm.addElement(astate);
-                listE.addCor(astate, tgc);
-                tgc.setAVATARID(astate.getID());
+    private void translateAvatarSMDExpireTimer (TDiagramPanel tdp, AvatarSpecification _as, AvatarStateMachineOwner _ab, AvatarSMDExpireTimer asmdet) throws CheckingError {
+        AvatarStateMachine asm = _ab.getStateMachine ();
+        String tmp = asmdet.getTimerName();
+        AvatarAttribute aa = _ab.getAvatarAttributeWithName (tmp);
+        if (aa == null)
+            throw new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed timer parameter: " + tmp + " in timer expiration");
+
+        if (aa.getType() != AvatarType.TIMER)
+            throw new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed parameter: " + tmp + " in timer expiration: shall be a parameter of type \"Timer\"");
+
+        AvatarExpireTimer aexpiretimer = new AvatarExpireTimer("expiretimer__" + aa.getName(), asmdet);
+        aexpiretimer.setTimer(aa);
+        asm.addElement(aexpiretimer);
+        this.listE.addCor(aexpiretimer, asmdet);
+        asmdet.setAVATARID(aexpiretimer.getID());
+    }
 
-                // Random
-            } else if (tgc instanceof AvatarSMDRandom) {
-                asmdrand = (AvatarSMDRandom)tgc;
-		//TraceManager.addDev("rand1");
-                arandom = new AvatarRandom("random", tgc);
-                tmp1 = modifyString(asmdrand.getMinValue());
-                error = AvatarSyntaxChecker.isAValidIntExpr(_as, _ab, tmp1);
-                if (error < 0) {
-                    makeError(error, tdp, _ab, tgc, "min value of random", tmp1);
-                }
-                tmp2 = modifyString(asmdrand.getMaxValue());
-                error = AvatarSyntaxChecker.isAValidIntExpr(_as, _ab, tmp1);
-                if (error < 0) {
-                    makeError(error, tdp, _ab, tgc, "max value of random", tmp2);
-                }
-                arandom.setValues(tmp1, tmp2);
-                arandom.setFunctionId(asmdrand.getFunctionId());
-		//TraceManager.addDev("rand2");
+    public void makeStateMachine (AvatarSpecification _as, AvatarStateMachineOwner _ab) {
+        AvatarBDStateMachineOwner block = (AvatarBDStateMachineOwner) listE.getTG (_ab);
+        AvatarStateMachine asm = _ab.getStateMachine ();
 
-                tmp1 = modifyString(asmdrand.getVariable());
-                aa = _ab.getAvatarAttributeWithName(tmp1);
+        if (block == null) {
+            CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "No corresponding graphical block for " + _ab.getName());
+            // TODO: adapt
+            // ce.setAvatarBlock(_ab);
+            ce.setTDiagramPanel(adp.getAvatarBDPanel());
+            addCheckingError(ce);
+            return;
+        }
 
-                if (aa == null) {
-		    //TraceManager.addDev("rand3");
-                    makeError(-3, tdp, _ab, tgc, "random", tmp1);
-                } else {
-		    //TraceManager.addDev("rand4");
-                    // Checking type of variable -> must be an int
-                    if (!(aa.isInt())) {
-                        makeError(error, tdp, _ab, tgc, ": variable of random must be of type \"int\"", tmp2);
-                    }
-                }
+        AvatarSMDPanel asmdp = block.getAvatarSMDPanel();
+        if (asmdp == null)
+            return;
 
-                arandom.setVariable(tmp1);
+        String name = block.getOwnerName();
 
-                asm.addElement(arandom);
-                listE.addCor(arandom, tgc);
-                tgc.setAVATARID(arandom.getID());
+        int size = checkingErrors.size();
 
-                // Set timer
-            } else if (tgc instanceof AvatarSMDSetTimer) {
-                tmp = ((AvatarSMDSetTimer)tgc).getTimerName();
-                aa = _ab.getAvatarAttributeWithName(tmp);
-                if (aa == null) {
-                    CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed timer parameter: " + tmp + " in timer setting");
-                    ce.setAvatarBlock(_ab);
-                    ce.setTDiagramPanel(tdp);
-                    ce.setTGComponent(tgc);
-                    addCheckingError(ce);
-                } else {
-                    if (aa.getType() != AvatarType.TIMER) {
-                        CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed parameter: " + tmp + " in timer setting: shall be a parameter of type \"Timer\"");
-                        ce.setAvatarBlock(_ab);
-                        ce.setTDiagramPanel(tdp);
-                        ce.setTGComponent(tgc);
-                        addCheckingError(ce);
-                    } else {
-                        tmp = modifyString(((AvatarSMDSetTimer)tgc).getTimerValue());
-                        error = AvatarSyntaxChecker.isAValidIntExpr(_as, _ab, tmp);
-                        if (error < 0) {
-                            makeError(error, tdp, _ab, tgc, "value of the timer setting", tmp);
-                        }
-                        asettimer = new AvatarSetTimer("settimer__" + aa.getName(), tgc);
-                        asettimer.setTimer(aa);
-                        asettimer.setTimerValue(tmp);
-                        asm.addElement(asettimer);
-                        listE.addCor(asettimer, tgc);
-                        tgc.setAVATARID(asettimer.getID());
-                    }
-                }
+        TDiagramPanel tdp = (TDiagramPanel) asmdp;
 
-                // Reset timer
-            } else if (tgc instanceof AvatarSMDResetTimer) {
-                tmp = ((AvatarSMDResetTimer)tgc).getTimerName();
-                aa = _ab.getAvatarAttributeWithName(tmp);
-                if (aa == null) {
-                    CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed timer parameter: " + tmp + " in timer reset");
-                    ce.setAvatarBlock(_ab);
+        // search for start state
+        AvatarSMDStartState tss = null;
+        for (TGComponent tgc: asmdp.getComponentList ())
+            if (tgc instanceof AvatarSMDStartState) {
+                if (tss == null)
+                    tss = (AvatarSMDStartState) tgc;
+                else {
+                    CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "More than one start state in the state machine diagram of " + name);
                     ce.setTDiagramPanel(tdp);
-                    ce.setTGComponent(tgc);
                     addCheckingError(ce);
-                } else {
-                    if (aa.getType() != AvatarType.TIMER) {
-                        CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed parameter: " + tmp + " in timer reset: shall be a parameter of type \"Timer\"");
-                        ce.setAvatarBlock(_ab);
-                        ce.setTDiagramPanel(tdp);
-                        ce.setTGComponent(tgc);
-                        addCheckingError(ce);
-                    } else {
-                        aresettimer = new AvatarResetTimer("resettimer__" + aa.getName(), tgc);
-                        aresettimer.setTimer(aa);
-                        asm.addElement(aresettimer);
-                        listE.addCor(aresettimer, tgc);
-                        tgc.setAVATARID(aresettimer.getID());
-                    }
+                    return;
                 }
+            }
 
-                // Expire timer
-            } else if (tgc instanceof AvatarSMDExpireTimer) {
-                tmp = ((AvatarSMDExpireTimer)tgc).getTimerName();
-                aa = _ab.getAvatarAttributeWithName(tmp);
-                if (aa == null) {
-                    CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed timer parameter: " + tmp + " in timer expiration");
-                    ce.setAvatarBlock(_ab);
-                    ce.setTDiagramPanel(tdp);
-                    ce.setTGComponent(tgc);
-                    addCheckingError(ce);
-                } else {
-                    if (aa.getType() != AvatarType.TIMER) {
-                        CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed parameter: " + tmp + " in timer expiration: shall be a parameter of type \"Timer\"");
-                        ce.setAvatarBlock(_ab);
-                        ce.setTDiagramPanel(tdp);
-                        ce.setTGComponent(tgc);
-                        addCheckingError(ce);
-                    } else {
-                        aexpiretimer = new AvatarExpireTimer("expiretimer__" + aa.getName(), tgc);
-                        aexpiretimer.setTimer(aa);
-                        asm.addElement(aexpiretimer);
-                        listE.addCor(aexpiretimer, tgc);
-                        tgc.setAVATARID(aexpiretimer.getID());
-                    }
-                }
+        if (tss == null) {
+            CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "No start state in the state machine diagram of " + name);
+            ce.setTDiagramPanel(tdp);
+            addCheckingError(ce);
+            return;
+        }
 
-                // Start state
-            } else if (tgc instanceof AvatarSMDStartState) {
-                astart = new AvatarStartState("start", tgc);
-                listE.addCor(astart, tgc);
-                tgc.setAVATARID(astart.getID());
-                asm.addElement(astart);
-                if (tgc.getFather() == null) {
-                    asm.setStartState(astart);
-                }
+        // This shall also be true for all composite state: at most one start state!
+        if (checkForStartStateOfCompositeStates (asmdp) != null) {
+            CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "More than one start state in composite state");
+            ce.setTDiagramPanel(tdp);
+            addCheckingError(ce);
+            return;
+        }
 
+        int choiceID = 0;
+        // First pass: creating AVATAR components, but no interconnection between them
+        for (TGComponent tgc: asmdp.getAllComponentList ())
+            try {
+                // Receive signal
+                if (tgc instanceof AvatarSMDReceiveSignal)
+                    this.translateAvatarSMDReceiveSignal (tdp, _as, _ab, (AvatarSMDReceiveSignal) tgc);
+                // Send signals
+                else if (tgc instanceof AvatarSMDSendSignal)
+                    this.translateAvatarSMDSendSignal (tdp, _as, _ab, (AvatarSMDSendSignal) tgc);
+                // State
+                else if (tgc instanceof AvatarSMDState)
+                    this.translateAvatarSMDState (tdp, _as, _ab, (AvatarSMDState) tgc);
+                // Choice
+                else if (tgc instanceof AvatarSMDChoice) {
+                    AvatarState astate = new AvatarState ("choice__" + choiceID, tgc);
+                    choiceID ++;
+                    asm.addElement (astate);
+                    listE.addCor (astate, tgc);
+                    tgc.setAVATARID (astate.getID());
+                }
+                // Random
+                else if (tgc instanceof AvatarSMDRandom)
+                    this.translateAvatarSMDRandom (tdp, _as, _ab, (AvatarSMDRandom) tgc);
+                // Set timer
+                else if (tgc instanceof AvatarSMDSetTimer)
+                    this.translateAvatarSMDSetTimer (tdp, _as, _ab, (AvatarSMDSetTimer) tgc);
+                // Reset timer
+                else if (tgc instanceof AvatarSMDResetTimer)
+                    this.translateAvatarSMDResetTimer (tdp, _as, _ab, (AvatarSMDResetTimer) tgc);
+                // Expire timer
+                else if (tgc instanceof AvatarSMDExpireTimer)
+                    this.translateAvatarSMDExpireTimer (tdp, _as, _ab, (AvatarSMDExpireTimer) tgc);
+                // Start state
+                else if (tgc instanceof AvatarSMDStartState) {
+                    AvatarStartState astart = new AvatarStartState("start", tgc);
+                    this.listE.addCor (astart, tgc);
+                    tgc.setAVATARID (astart.getID());
+                    asm.addElement(astart);
+                    if (tgc.getFather() == null)
+                        asm.setStartState(astart);
                 // Stop state
-            } else if (tgc instanceof AvatarSMDStopState) {
-                astop = new AvatarStopState("stop", tgc);
-                listE.addCor(astop, tgc);
-                tgc.setAVATARID(astop.getID());
-                asm.addElement(astop);
+                } else if (tgc instanceof AvatarSMDStopState) {
+                    AvatarStopState astop = new AvatarStopState ("stop", tgc);
+                    this.listE.addCor(astop, tgc);
+                    tgc.setAVATARID(astop.getID());
+                    asm.addElement(astop);
+                }
+            } catch (CheckingError ce) {
+                // TODO: adapt
+                // ce.setAvatarBlock (_ab);
+                ce.setTDiagramPanel (tdp);
+                ce.setTGComponent (tgc);
+                ce.addMessagePrefix ("State Machine of " + name + ": ");
+                this.addCheckingError (ce);
             }
-        }
 
-        if (checkingErrors.size() != size) {
+        if (checkingErrors.size() != size)
             return;
-        }
 
         // Remove all internal start states
         asm.removeAllInternalStartStates();
 
         // Make hierachy between states and elements
-        iterator = asmdp.getAllComponentList().listIterator();
-        AvatarStateMachineElement element1, element2;
-        while(iterator.hasNext()) {
-            tgc = (TGComponent)(iterator.next());
-            if ((tgc != null) && (tgc.getFather() != null)) {
-                element1 = (AvatarStateMachineElement)(listE.getObject(tgc));
-                element2 = (AvatarStateMachineElement)(listE.getObject(tgc.getFather()));
-                if ((element1 != null) && (element2 != null) && (element2 instanceof AvatarState)) {
-                    element1.setState((AvatarState)element2);
-                }
+        for (TGComponent tgc: asmdp.getAllComponentList ())
+            if (tgc != null && tgc.getFather() != null) {
+                AvatarStateMachineElement element1 = (AvatarStateMachineElement)(listE.getObject(tgc));
+                AvatarStateMachineElement element2 = (AvatarStateMachineElement)(listE.getObject(tgc.getFather()));
+                if (element1 != null && element2 != null && element2 instanceof AvatarState)
+                    element1.setState ((AvatarState) element2);
             }
-        }
 
         // Make next: handle transitions
-        iterator = asmdp.getAllComponentList().listIterator();
-        AvatarSMDConnector asmdco;
-        AvatarTransition at;
-        TGComponent tgc1, tgc2;
-        Vector <String> vs;
-
-        while(iterator.hasNext()) {
-            tgc = (TGComponent)(iterator.next());
+        for (TGComponent tgc: asmdp.getAllComponentList ())
             if (tgc instanceof AvatarSMDConnector) {
-                asmdco = (AvatarSMDConnector)tgc;
-                tgc1 = tdp.getComponentToWhichBelongs(asmdco.getTGConnectingPointP1());
-                tgc2 = tdp.getComponentToWhichBelongs(asmdco.getTGConnectingPointP2());
-                if ((tgc1 == null) || (tgc2 == null)) {
+                AvatarSMDConnector asmdco = (AvatarSMDConnector) tgc;
+                TGComponent tgc1 = tdp.getComponentToWhichBelongs (asmdco.getTGConnectingPointP1());
+                TGComponent tgc2 = tdp.getComponentToWhichBelongs (asmdco.getTGConnectingPointP2());
+                if (tgc1 == null || tgc2 == null)
                     TraceManager.addDev("Tgcs null in Avatar translation");
-                } else {
-                    element1 = (AvatarStateMachineElement)(listE.getObject(tgc1));
-                    element2 = (AvatarStateMachineElement)(listE.getObject(tgc2));
-                    if ((element1 != null) && (element2 != null)) {
-                        at = new AvatarTransition(_ab, "avatar transition", tgc);
+                else {
+                    AvatarStateMachineElement element1 = (AvatarStateMachineElement)(listE.getObject(tgc1));
+                    AvatarStateMachineElement element2 = (AvatarStateMachineElement)(listE.getObject(tgc2));
+                    if (element1 != null && element2 != null) {
+                        AvatarTransition at = new AvatarTransition (_ab, "avatar transition", tgc);
 
                         // Guard
-                        tmp = modifyString(asmdco.getGuard());
-
+                        String tmp = modifyString (asmdco.getGuard());
                         AvatarGuard guard = AvatarGuard.createFromString (_ab, tmp);
-                        if (guard.isElseGuard()) {
+                        if (guard.isElseGuard())
                             at.setGuard(guard);
-                        } else {
-                            error = AvatarSyntaxChecker.isAValidGuard(_as, _ab, tmp);
-                            if (error < 0) {
-                                makeError(error, tdp, _ab, tgc, "transition guard", tmp);
-                            } else {
-                                at.setGuard(guard);
-                            }
+                        else {
+                            int error = AvatarSyntaxChecker.isAValidGuard (_as, _ab, tmp);
+                            if (error < 0)
+                                this.makeError (error, tdp, _ab, tgc, "transition guard", tmp);
+                            else
+                                at.setGuard (guard);
                         }
 
                         // Delays
-                        tmp1 = modifyString(asmdco.getAfterMinDelay());
-                        error = AvatarSyntaxChecker.isAValidIntExpr(_as, _ab, tmp1);
+                        String tmp1 = modifyString (asmdco.getAfterMinDelay ());
+                        int error = AvatarSyntaxChecker.isAValidIntExpr (_as, _ab, tmp1);
                         if (error < 0) {
-                            makeError(error, tdp, _ab, tgc, "after min delay", tmp1);
+                            this.makeError (error, tdp, _ab, tgc, "after min delay", tmp1);
                             tmp1 = null;
                         }
-                        tmp2 = modifyString(asmdco.getAfterMaxDelay());
-                        error = AvatarSyntaxChecker.isAValidIntExpr(_as, _ab, tmp2);
+                        String tmp2 = modifyString (asmdco.getAfterMaxDelay ());
+                        error = AvatarSyntaxChecker.isAValidIntExpr (_as, _ab, tmp2);
                         if (error < 0) {
-                            makeError(error, tdp, _ab, tgc, "after max delay", tmp2);
+                            this.makeError(error, tdp, _ab, tgc, "after max delay", tmp2);
                             tmp2 = null;
                         }
 
-                        if ((tmp1 != null) && (tmp2 != null)) {
+                        if (tmp1 != null && tmp2 != null)
                             at.setDelays(tmp1, tmp2);
-                        }
 
                         // Compute min and max
-                        tmp1 = modifyString(asmdco.getComputeMinDelay());
-                        error = AvatarSyntaxChecker.isAValidIntExpr(_as, _ab, tmp1);
+                        tmp1 = modifyString (asmdco.getComputeMinDelay ());
+                        error = AvatarSyntaxChecker.isAValidIntExpr (_as, _ab, tmp1);
                         if (error < 0) {
-                            makeError(error, tdp, _ab, tgc, "compute min ", tmp1);
+                            this.makeError (error, tdp, _ab, tgc, "compute min ", tmp1);
                             tmp1 = null;
                         }
                         tmp2 = modifyString(asmdco.getComputeMaxDelay());
                         error = AvatarSyntaxChecker.isAValidIntExpr(_as, _ab, tmp2);
                         if (error < 0) {
-                            makeError(error, tdp, _ab, tgc, "compute max ", tmp2);
+                            this.makeError (error, tdp, _ab, tgc, "compute max ", tmp2);
                             tmp2 = null;
                         }
 
-                        if ((tmp1 != null) && (tmp2 != null)) {
+                        if (tmp1 != null && tmp2 != null)
                             at.setComputes(tmp1, tmp2);
-                        }
-
-
 
                         // Actions
-                        vs = asmdco.getActions();
-                        for(String s: vs) {
+                        for(String s: asmdco.getActions())
                             if (s.trim().length() > 0) {
                                 s = modifyString(s.trim());
-                                // Variable assignation or method call?
-
-                                //TraceManager.addDev("IsAVariable Assignation: " + s + " -> " + isAVariableAssignation(s));
 
+                                // Variable assignation or method call?
                                 if (!isAVariableAssignation(s)) {
                                     // Method call
-				    int index2 = s.indexOf(";");
-				    if (index2 != -1) {
-					makeError(error, tdp, _ab, tgc, "transition action", s);
-				    }
+                                    int index2 = s.indexOf(";");
+                                    if (index2 != -1)
+                                        this.makeError(error, tdp, _ab, tgc, "transition action", s);
+
                                     s = modifyStringMethodCall(s, _ab.getName());
-                                    if(!_ab.isAValidMethodCall(s)) {
+                                    if (!AvatarBlock.isAValidMethodCall (_ab, s)) {
                                         CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formed transition method call: " + s);
-                                        ce.setAvatarBlock(_ab);
+                                        // TODO: adapt
+                                        // ce.setAvatarBlock(_ab);
                                         ce.setTDiagramPanel(tdp);
                                         ce.setTGComponent(tgc);
                                         addCheckingError(ce);
-                                    } else {
+                                    } else
                                         at.addAction(s);
-                                    }
                                 } else {
                                     // Variable assignation
-                                    error = AvatarSyntaxChecker.isAValidVariableExpr(_as, _ab, s);
-                                    if (error < 0) {
-                                        makeError(error, tdp, _ab, tgc, "transition action", s);
-                                    } else {
-                                        at.addAction(s);
-                                    }
+                                    error = AvatarSyntaxChecker.isAValidVariableExpr (_as, _ab, s);
+                                    if (error < 0)
+                                        this.makeError (error, tdp, _ab, tgc, "transition action", s);
+                                    else
+                                        at.addAction (s);
                                 }
                             }
-                        }
 
-                        element1.addNext(at);
-                        at.addNext(element2);
-                        listE.addCor(at, tgc);
-                        tgc.setAVATARID(at.getID());
-                        asm.addElement(at);
-
-			// Check for after on composite transitions
-			if (at.hasDelay() && (element1 instanceof AvatarState) && asm.isACompositeTransition(at)) {
-			    CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "After clause cannot be used on composite transitions. Use timers instead.");
-			    ce.setAvatarBlock(_ab);
-			    ce.setTDiagramPanel(tdp);
-			    ce.setTGComponent(tgc);
-			    addCheckingError(ce);
-			}
+                        element1.addNext (at);
+                        at.addNext (element2);
+                        this.listE.addCor (at, tgc);
+                        tgc.setAVATARID (at.getID());
+                        asm.addElement (at);
+
+                        // Check for after on composite transitions
+                        if (at.hasDelay() && element1 instanceof AvatarState && asm.isACompositeTransition(at)) {
+                            CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "After clause cannot be used on composite transitions. Use timers instead.");
+                            // TODO: adapt
+                            // ce.setAvatarBlock(_ab);
+                            ce.setTDiagramPanel(tdp);
+                            ce.setTGComponent(tgc);
+                            addCheckingError(ce);
+                        }
                     }
                 }
             }
-        }
 
         asm.handleUnfollowedStartState(_ab);
 
         // Investigate all states -> put warnings for all empty transitions from a state to the same one (infinite loop)
         int nb;
-        for(AvatarStateMachineElement asmee: asm.getListOfElements()) {
-            if (asmee instanceof AvatarState) {
-                nb = ((AvatarState)asmee).hasEmptyTransitionsOnItself(asm);
-                if (nb > 0) {
-                    CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "State(s) " + asmee.getName() + " has " + nb + " empty transition(s) on itself");
-                    ce.setAvatarBlock(_ab);
-                    ce.setTDiagramPanel(tdp);
-                    ce.setTGComponent((TGComponent)(asmee.getReferenceObject()));
-                    addWarning(ce);
-                }
+        for (AvatarStateMachineElement asmee: asm.getListOfElements())
+            if (asmee instanceof AvatarState && ((AvatarState)asmee).hasEmptyTransitionsOnItself(asm) > 0) {
+                CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "State(s) " + asmee.getName() + " has empty transitions on itself");
+                // TODO: adapt
+                // ce.setAvatarBlock(_ab);
+                ce.setTDiagramPanel(tdp);
+                ce.setTGComponent((TGComponent)(asmee.getReferenceObject()));
+                addWarning(ce);
             }
-        }
-
-
-
-
     }
 
-    private void makeError(int _error, TDiagramPanel _tdp, AvatarBlock _ab, TGComponent _tgc, String _info, String _element) {
+    private void makeError(int _error, TDiagramPanel _tdp, AvatarStateMachineOwner _ab, TGComponent _tgc, String _info, String _element) {
         if (_error == -3) {
             CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Undeclared variable in " + _info + ": " + _element);
-            ce.setAvatarBlock(_ab);
+            // TODO: adapt
+            // ce.setAvatarBlock(_ab);
             ce.setTDiagramPanel(_tdp);
             ce.setTGComponent(_tgc);
             addCheckingError(ce);
         } else {
             CheckingError ce = new CheckingError(CheckingError.BEHAVIOR_ERROR, "Badly formatted " + _info + ": " + _element);
-            ce.setAvatarBlock(_ab);
+            // TODO: adapt
+            // ce.setAvatarBlock(_ab);
             ce.setTDiagramPanel(_tdp);
             ce.setTGComponent(_tgc);
             addCheckingError(ce);
@@ -1574,7 +1525,7 @@ public class AvatarDesignPanelTranslator {
     }
 
     public void checkForAfterOnCompositeTransition() {
-	
+
     }
 
 
diff --git a/src/ui/CheckingError.java b/src/ui/CheckingError.java
index cb00ca9b92..ffb962788d 100755
--- a/src/ui/CheckingError.java
+++ b/src/ui/CheckingError.java
@@ -52,7 +52,7 @@ import tmltranslator.*;
 
 
 
-public class CheckingError {
+public class CheckingError extends Exception {
     
     public final static int STRUCTURE_ERROR = 0;
     public final static int BEHAVIOR_ERROR = 1;
@@ -83,6 +83,10 @@ public class CheckingError {
     public void setTClass(TClass _t) {
         t = _t;
     }
+
+    public void addMessagePrefix (String prefix) {
+        this.message = prefix + this.message;
+    }
 	
     public void setAvatarBlock(AvatarBlock _ab) {
         ab = _ab;
diff --git a/src/ui/ColorManager.java b/src/ui/ColorManager.java
index a6cc20c252..e961268acc 100755
--- a/src/ui/ColorManager.java
+++ b/src/ui/ColorManager.java
@@ -157,6 +157,7 @@ public class ColorManager {
     public static  Color AVATAR_DATATYPE = new Color(156, 220, 162);
     public static  Color AVATAR_SEND_SIGNAL = new Color(128, 180, 205);
     public static  Color AVATAR_RECEIVE_SIGNAL = new Color(128, 180, 205);
+    public static  Color AVATAR_LIBRARY_FUNCTION_CALL = new Color(128, 180, 205);
     //public static final Color AVATAR_GUARD = new Color(128, 180, 205);
     public static  Color AVATAR_GUARD = new Color(0, 89, 26);
     //public static final Color AVATAR_TIME = new Color(108, 92, 67);
diff --git a/src/ui/MainGUI.java b/src/ui/MainGUI.java
index 68dee3080f..68300f49c2 100755
--- a/src/ui/MainGUI.java
+++ b/src/ui/MainGUI.java
@@ -5410,19 +5410,17 @@ public  class MainGUI implements ActionListener, WindowListener, KeyListener, Pe
         }
     }
 
-    public void removeAvatarBlock(TURTLEPanel tp, String s)     {
-        if (!(tp instanceof AvatarDesignPanel)) {
+    public void removeAvatarBlock (TURTLEPanel tp, String s) {
+        if (!(tp instanceof AvatarDesignPanel))
             return;
-        }
 
-        for(int i = 0; i<tp.tabbedPane.getTabCount(); i++) {
+        for (int i=0; i<tp.tabbedPane.getTabCount(); i++)
             if (tp.tabbedPane.getTitleAt(i).equals(s)) {
                 tp.tabbedPane.removeTabAt(i);
                 tp.panels.removeElementAt(i);
-                setPanelMode();
+                this.setPanelMode();
                 return;
             }
-        }
     }
 
     public void removeTMLCPrimitiveComponent(TURTLEPanel tp, String s)  {
@@ -8106,6 +8104,8 @@ public  class MainGUI implements ActionListener, WindowListener, KeyListener, Pe
             actionOnButton(TGComponentManager.COMPONENT, TGComponentManager.AVATARSMD_SEND_SIGNAL);
         } else if (command.equals(actions[TGUIAction.ASMD_RECEIVE_SIGNAL].getActionCommand())) {
             actionOnButton(TGComponentManager.COMPONENT, TGComponentManager.AVATARSMD_RECEIVE_SIGNAL);
+        } else if (command.equals(actions[TGUIAction.ASMD_LIBRARY_FUNCTION_CALL].getActionCommand())) {
+            actionOnButton(TGComponentManager.COMPONENT, TGComponentManager.AVATARSMD_LIBRARY_FUNCTION_CALL);
         } else if (command.equals(actions[TGUIAction.ASMD_PARALLEL].getActionCommand())) {
             actionOnButton(TGComponentManager.COMPONENT, TGComponentManager.AVATARSMD_PARALLEL);
         } else if (command.equals(actions[TGUIAction.ASMD_STATE].getActionCommand())) {
diff --git a/src/ui/TDiagramPanel.java b/src/ui/TDiagramPanel.java
index 7b823d703a..32719e11e2 100755
--- a/src/ui/TDiagramPanel.java
+++ b/src/ui/TDiagramPanel.java
@@ -281,14 +281,23 @@ public abstract class TDiagramPanel extends JPanel implements GenericTree {
         return (int)(Math.round(12*zoom));
     }
 
+    private FontMetrics savedFontMetrics = null;
+    public int stringWidth (Graphics g, String str) {
+        if (this.savedFontMetrics == null)
+            this.savedFontMetrics = g.getFontMetrics (new Font (Font.SANS_SERIF, Font.PLAIN, this.getFontSize ()));
+        return this.savedFontMetrics.stringWidth (str);
+    }
+
     public void setZoom(double _zoom) {
         if (_zoom < zoom) {
             if (zoom > 0.199) {
                 zoom = _zoom;
+                this.savedFontMetrics = null;
             }
         } else {
             if (zoom < 5) {
                 zoom = _zoom;
+                this.savedFontMetrics = null;
             }
         }
     }
@@ -385,118 +394,88 @@ public abstract class TDiagramPanel extends JPanel implements GenericTree {
         }
     }
 
+    private Font fontToUse = null;
     public void paintMycomponents(Graphics g, boolean b, double w, double h) {
+        if (this.fontToUse == null)
+            this.fontToUse = g.getFont ();
+        else
+            g.setFont (fontToUse);
 
-        lastGraphics = g;
-        drawingMain = b;
-
-        //TraceManager.addDev("Nb of components: " + componentList.size());
-
-        /*if (!zoomed) {
-          zoomed = true;*/
-        //Graphics2D g2 = (Graphics2D)g;
-        //g2.scale(0.75, 0.75);
-        //}
+        this.lastGraphics = g;
+        this.drawingMain = b;
 
-        if (!overcomeShowing) {
-            if (!isShowing()) {
-                TraceManager.addDev("Not showing!" + tp);
-                return;
-            }
+        if (!this.overcomeShowing && !this.isShowing()) {
+            TraceManager.addDev("Not showing!" + tp);
+            return;
         }
 
-        //TraceManager.addDev("Draw");
-
         try {
-            super.paintComponent(g);
+            super.paintComponent (g);
         } catch (Exception e) {
             TraceManager.addDev("Got exception: " + e.getMessage());
             return;
         }
 
-        //TraceManager.addDev("Draw 1");
-
-        //ZoomGraphics g = new ZoomGraphics(gr, zoom);
-        if (!draw) {
+        if (!this.draw)
             return;
-        }
-
-        //TraceManager.addDev("Draw 2");
 
         // Draw Components
-        if ((w != 1.0) ||(h != 1.0)) {
-            ((Graphics2D)g).scale(w, h);
-            isScaled = true;
+        if (w != 1.0 || h != 1.0) {
+            ((Graphics2D) g).scale (w, h);
+            this.isScaled = true;
         } else {
-            isScaled = false;
+            this.isScaled = false;
         }
-        //TraceManager.addDev("Draw 3");
 
+        // Draw every non hidden component
         TGComponent tgc;
         for(int i=this.componentList.size()-1; i>=0; i--) {
             tgc = this.componentList.get(i);
-            if (!tgc.isHidden()) {
-                //TraceManager.addDev("Painting " + tgc.getName() + " x=" + tgc.getX() + " y=" + tgc.getY());
-                tgc.draw(g);
-                if (mgui.getTypeButtonSelected() != TGComponentManager.EDIT) {
-                    tgc.drawTGConnectingPoint(g, mgui.getIdButtonSelected());
-                }
-                if (mode == MOVE_CONNECTOR_HEAD) {
-                    tgc.drawTGConnectingPoint(g, type);
-                }
-
-                if (javaVisible) {
-                    if (tgc.hasPostJavaCode() || tgc.hasPreJavaCode()) {
-                        tgc.drawJavaCode(g);
-                    }
-                }
+            if (tgc.isHidden())
+                continue;
 
+            tgc.draw (g);
+            if (this.mgui.getTypeButtonSelected () != TGComponentManager.EDIT)
+                tgc.drawTGConnectingPoint (g, this.mgui.getIdButtonSelected());
 
+            if (this.mode == MOVE_CONNECTOR_HEAD) 
+                tgc.drawTGConnectingPoint (g, this.type);
 
-                /*if (internalCommentVisible) {
-                  ifi (tgc.hasInternalComment()) {
-                  tgc.drawInternalComment(g);
-                  }
-                  }*/
-
-                /*if ((attributesOn) && (tgc instanceof WithAttributes)) {
-                //TraceManager.addDev("Attributes to de drawn for" + tgc);
-                tgc.drawAttributes(g, ((WithAttributes)tgc).getAttributes());
-                }*/
-            }
+            if (this.javaVisible && (tgc.hasPostJavaCode () || tgc.hasPreJavaCode ()))
+                tgc.drawJavaCode (g);
         }
 
         // Draw name of component selected
-        if (componentPointed != null) {
-            String name1 = componentPointed.getName();
-            if (componentPointed.hasFather()) {
-                name1 = componentPointed.getTopLevelName() + ": " + name1;
-            }
-            //g.setColor(Color.black);
-            //g.drawString(name, 20, 20);
-            //mgui.setStatusBarText(name1);
+        if (this.componentPointed != null) {
+            String name1 = this.componentPointed.getName ();
+            if (this.componentPointed.hasFather ())
+                name1 = this.componentPointed.getTopLevelName () + ": " + name1;
         }
 
         //Draw component being added
-        if (mode == ADDING_CONNECTOR) {
+        if (this.mode == ADDING_CONNECTOR) {
             // Drawing connector
             g.setColor(Color.red);
-            drawConnectorBeingAdded(g);
+            this.drawConnectorBeingAdded(g);
             g.drawLine(x1, y1, x2, y2);
         }
 
-        if (mode == SELECTING_COMPONENTS) {
+        if (this.mode == SELECTING_COMPONENTS) {
             g.setColor(Color.black);
-            GraphicLib.dashedRect(g, Math.min(initSelectX, currentSelectX), Math.min(initSelectY, currentSelectY), Math.abs(currentSelectX -  initSelectX), Math.abs(currentSelectY - initSelectY));
+            GraphicLib.dashedRect (g,
+                    Math.min(this.initSelectX, this.currentSelectX),
+                    Math.min(this.initSelectY, this.currentSelectY),
+                    Math.abs(this.currentSelectX - this.initSelectX),
+                    Math.abs(this.currentSelectY - this.initSelectY));
         }
 
-        if (((mode == SELECTED_COMPONENTS) || (mode == MOVING_SELECTED_COMPONENTS)) && (selectedTemp)) {
-            if (showSelectionZone) {
-                if (mode == MOVING_SELECTED_COMPONENTS) {
+        if ((this.mode == SELECTED_COMPONENTS || this.mode == MOVING_SELECTED_COMPONENTS) && this.selectedTemp) {
+            if (this.showSelectionZone) {
+                if (this.mode == MOVING_SELECTED_COMPONENTS)
                     g.setColor(ColorManager.MOVING_0);
-                } else {
+                else
                     g.setColor(ColorManager.POINTER_ON_ME_0);
-                }
+
                 GraphicLib.setMediumStroke(g);
             } else {
                 g.setColor(ColorManager.NORMAL_0);
@@ -527,10 +506,8 @@ public abstract class TDiagramPanel extends JPanel implements GenericTree {
             }
         }
 
-        if (b) {
+        if (b)
             mgui.drawBird();
-        }
-
     }
 
     public boolean isScaled() {
diff --git a/src/ui/TGCNote.java b/src/ui/TGCNote.java
index 751b9f1f43..bb1346febb 100755
--- a/src/ui/TGCNote.java
+++ b/src/ui/TGCNote.java
@@ -67,26 +67,25 @@ public class TGCNote extends TGCScalableWithoutInternalComponent {
 
     protected Color myColor;
 
-    private Font myFont, myFontB;
+    private Font myFontB;
     private int maxFontSize = 30;
     private int minFontSize = 4;
-    private int currentFontSize = -1;
+    private int currentFontSize;
 
     protected Graphics graphics;
 
     public TGCNote(int _x, int _y, int _minX, int _maxX, int _minY, int _maxY, boolean _pos, TGComponent _father, TDiagramPanel _tdp)  {
         super(_x, _y, _minX, _maxX, _minY, _maxY, _pos, _father, _tdp);
 
-        width = 150;
-        height = 30;
-        minWidth = 20;
-        minHeight = 10;
+        this.width = 150;
+        this.height = 30;
+        this.minWidth = 20;
+        this.minHeight = 10;
 
-        oldScaleFactor = tdp.getZoom();
+        this.oldScaleFactor = tdp.getZoom();
 
-        nbConnectingPoint = 0;
-        //addTGConnectingPointsComment();
-	int len = makeTGConnectingPointsComment(16);
+        this.nbConnectingPoint = 0;
+	int len = this.makeTGConnectingPointsComment(16);
 	int decw = 0;
 	int dech = 0;
 	for(int i=0; i<2; i++) {
@@ -101,130 +100,100 @@ public class TGCNote extends TGCScalableWithoutInternalComponent {
 	    len += 8;
 	}
 
-        moveable = true;
-        editable = true;
-        removable = true;
+        this.moveable = true;
+        this.editable = true;
+        this.removable = true;
 
-        name = "UML Note";
-        value = "UML note:\nDouble-click to edit";
+        this.currentFontSize = tdp.getFontSize();
 
-        myImageIcon = IconManager.imgic320;
+        this.name = "UML Note";
+        this.value = "UML note:\nDouble-click to edit";
+
+        this.myImageIcon = IconManager.imgic320;
     }
 
     public String[] getValues() {
-        return values;
+        return this.values;
     }
 
 
-    public void internalDrawing(Graphics g) {
-        Font f = g.getFont();
-        Font fold = f;
-
-        /*if (!tdp.isScaled()) {
-          graphics = g;
-          }*/
-
-        if (((rescaled) && (!tdp.isScaled())) || myFont == null) {
-            currentFontSize = tdp.getFontSize();
-            //System.out.println("Rescaled, font size = " + currentFontSize + " height=" + height);
-            //            myFont = f.deriveFont((float)currentFontSize);
-            //myFontB = myFont.deriveFont(Font.BOLD);
-
-            if (rescaled) {
-                rescaled = false;
-            }
+    public void internalDrawing (Graphics graph) {
+        if (this.rescaled && !this.tdp.isScaled()) {
+            this.rescaled = false;
+            this.currentFontSize = this.tdp.getFontSize();
         }
 
-        if (values == null) {
-            makeValue();
-        }
+        graph.setFont (graph.getFont ().deriveFont (this.currentFontSize));
 
-        int h  = g.getFontMetrics().getHeight();
-        Color c = g.getColor();
+        if (this.values == null)
+            this.makeValue ();
 
-        int desiredWidth = minWidth;
-        for(int i=0; i< values.length; i++) {
-            desiredWidth = Math.max(desiredWidth, g.getFontMetrics().stringWidth(values[i]) + marginX);
-        }
+        int h  = graph.getFontMetrics ().getHeight();
+        Color c = graph.getColor();
 
-        int desiredHeight = (values.length * currentFontSize) + textY + 1;
+        int desiredWidth = this.minWidth;
+        for(int i=0; i< this.values.length; i++)
+            /* !!! WARNING !!!
+             * Note that here we use TDiagramPanel.stringWidth instead of graph.getFontMetrics().stringWidth
+             * Indeed, TGComponent (and so TGCNote) objects are drawn twice when the bird view is enabled.
+             * First, they are drawn on the TDiagramPanel and then on the bird view.
+             * Problem is that we compute the width for this element (which will be further used for isOnMe
+             * for instance) so that it matches the text inside of it. It is thus important that the width of
+             * the strings - that will affect the width of the component - is the same each time it is drawn.
+             * For some unknown reasons, even if the current Font of the Graphics object is the same, the
+             * FontMetrics object derived from it is not the same (ascent and descent are different) so for
+             * the same text and the same Font, width would still change if we used the FontMetrics fetched
+             * from the Graphics object.
+             * Thus we use a saved FontMetrics object in TDiagramPanel that only changes when zoom changes.
+             */
+            desiredWidth = Math.max (desiredWidth, this.tdp.stringWidth(graph, this.values[i]) + this.marginX);
 
-        //TraceManager.addDev("resize: " + desiredWidth + "," + desiredHeight);
 
-        if ((desiredWidth != width) || (desiredHeight != height)) {
-            resize(desiredWidth, desiredHeight);
-        }
+        int desiredHeight = (this.values.length * this.currentFontSize) + this.textY + 1;
 
-        g.drawLine(x, y, x+width, y);
-        g.drawLine(x, y, x, y+height);
-        g.drawLine(x, y+height, x+width-limit, y+height);
-        g.drawLine(x+width, y, x+width, y+height - limit);
+        if (desiredWidth != this.width || desiredHeight != this.height)
+            this.resize (desiredWidth, desiredHeight);
 
-        g.setColor(ColorManager.UML_NOTE_BG);
-        int [] px1 = {x+1, x+width, x + width, x + width-limit, x+1};
-        int [] py1 = {y+1, y+1, y+height-limit, y+height, y+height};
-        g.fillPolygon(px1, py1, 5);
-        g.setColor(c);
+        graph.drawLine(this.x, this.y, this.x+this.width, this.y);
+        graph.drawLine(this.x, this.y, this.x, this.y+this.height);
+        graph.drawLine(this.x, this.y+this.height, this.x+this.width-this.limit, this.y+this.height);
+        graph.drawLine(this.x+this.width, this.y, this.x+this.width, this.y+this.height - this.limit);
 
-        int [] px = {x+width, x + width - 4, x+width-10, x + width-limit};
-        int [] py = {y+height-limit, y + height - limit + 3, y + height - limit + 2, y +height};
-        g.drawPolygon(px, py, 4);
+        graph.setColor(ColorManager.UML_NOTE_BG);
+        int [] px1 = {this.x+1, this.x+this.width, this.x + this.width, this.x + this.width-this.limit, this.x+1};
+        int [] py1 = {this.y+1, this.y+1, this.y+this.height-this.limit, this.y+this.height, this.y+this.height};
+        graph.fillPolygon(px1, py1, 5);
+        graph.setColor(c);
 
-        if (g.getColor() == ColorManager.NORMAL_0) {
-            g.setColor(ColorManager.UML_NOTE);
-        }
-        g.fillPolygon(px, py, 4);
+        int [] px = {this.x+this.width, this.x + this.width - 4, this.x+this.width-10, this.x + this.width-this.limit};
+        int [] py = {this.y+this.height-this.limit, this.y + this.height - this.limit + 3, this.y + this.height - this.limit + 2, this.y +this.height};
+        graph.drawPolygon(px, py, 4);
 
-        g.setColor(Color.black);
-        for (int i = 0; i<values.length; i++) {
-            //TraceManager.addDev("x+texX=" + (x + textX) + " y+textY=" + y + textY + i* h + ": " + values[i]);
-            g.drawString(values[i], x + textX, y + textY + (i+1)* currentFontSize);
-        }
-        g.setColor(c);
+        if (c == ColorManager.NORMAL_0)
+            graph.setColor(ColorManager.UML_NOTE);
 
+        graph.fillPolygon (px, py, 4);
+
+        graph.setColor(c);
+        for (int i = 0; i<this.values.length; i++)
+            graph.drawString(this.values[i], this.x + this.textX, this.y + this.textY + (i+1)* this.currentFontSize);
     }
 
     public void makeValue() {
-        values = Conversion.wrapText(value);
-        //checkMySize();
+        values = Conversion.wrapText (value);
     }
 
-    /*public void checkMySize() {
-      if (myg == null) {
-      return;
-      }
-      int desiredWidth = minWidth;
-      for(int i=0; i< values.length; i++) {
-      desiredWidth = Math.max(desiredWidth, myg.getFontMetrics().stringWidth(values[i]) + marginX);
-      }
-
-      int desiredHeight = values.length * myg.getFontMetrics().getHeight() + marginY;
-
-      if ((desiredWidth != width) || (desiredHeight != height)) {
-      resize(desiredWidth, desiredHeight);
-      }
-      }*/
-
     public boolean editOndoubleClick(JFrame frame) {
-        String oldValue = value;
+        String oldValue = this.value;
 
         JDialogNote jdn = new JDialogNote(frame, "Setting the note", value);
-        //jdn.setLocation(200, 150);
         GraphicLib.centerOnParent(jdn);
         jdn.show(); // blocked until dialog has been closed
 
-        String s = jdn.getText();
-        if ((s != null) && (s.length() > 0) && (!s.equals(oldValue))) {
-            String tmp = s;
-            /*s = GTURTLEModeling.removeForbiddenCharactersFromInput(s);
-              s = Conversion.replaceAllChar(s, '&', " ");
-              s = Conversion.replaceAllChar(s, '"', " ");
-
-              if(s.compareTo(tmp) != 0) {
-              JOptionPane.showMessageDialog(frame, "Forbidden characters have been removed from the note", "Error", JOptionPane.INFORMATION_MESSAGE);
-              }*/
-            setValue(s);
-            makeValue();
+        String s = jdn.getText ();
+        if (s != null && s.length() > 0 && !s.equals(oldValue)) {
+            this.setValue (s);
+            this.makeValue ();
             return true;
         }
         return false;
@@ -253,9 +222,9 @@ public class TGCNote extends TGCScalableWithoutInternalComponent {
     }
 
     protected String translateExtraParam() {
-        if (values == null) {
-            makeValue();
-        }
+        if (values == null)
+            this.makeValue();
+
         StringBuffer sb = new StringBuffer("<extraparam>\n");
         for(int i=0; i<values.length; i++) {
             sb.append("<Line value=\"");
diff --git a/src/ui/TGCScalableWithoutInternalComponent.java b/src/ui/TGCScalableWithoutInternalComponent.java
index ba53d0d516..3fc320f573 100755
--- a/src/ui/TGCScalableWithoutInternalComponent.java
+++ b/src/ui/TGCScalableWithoutInternalComponent.java
@@ -15,6 +15,7 @@
    license as circulated by CEA, CNRS and INRIA at the following URL
    "http://www.cecill.info".
 
+
    As a counterpart to the access to the source code and  rights to copy,
    modify and redistribute granted by the license, users are provided only
    with a limited warranty  and the software's author,  the holder of the
@@ -46,6 +47,8 @@
 
 package ui;
 
+import myutil.TraceManager;
+
 //import java.awt.*;
 
 public abstract class TGCScalableWithoutInternalComponent extends TGCWithoutInternalComponent implements ScalableTGComponent {
@@ -56,7 +59,7 @@ public abstract class TGCScalableWithoutInternalComponent extends TGCWithoutInte
         super(_x, _y, _minX, _maxX, _minY, _maxY, _pos, _father, _tdp);
     }
 
-    public void rescale(double scaleFactor){
+    public void rescale (double scaleFactor){
         rescaled = true;
 
         dwidth = (width + dwidth) / oldScaleFactor * scaleFactor;
diff --git a/src/ui/TGComponent.java b/src/ui/TGComponent.java
index b144c5d353..6f0a59427f 100755
--- a/src/ui/TGComponent.java
+++ b/src/ui/TGComponent.java
@@ -66,6 +66,7 @@ import ui.tmlcd.*;
 import ui.tmlcompd.*;
 import ui.tmldd.*;
 import ui.tree.*;
+import ui.avatarbd.AvatarBDPragma;
 
 import tmltranslator.*;
 
@@ -865,7 +866,10 @@ public abstract class TGComponent implements CDElement, GenericTree {
         RunningInfo ri;
         LoadInfo li;
         ColorManager.setColor(g, state, 0);
+        Font font = new Font (Font.SANS_SERIF, Font.PLAIN, this.tdp.getFontSize ());
+        g.setFont (font);
         internalDrawing(g);
+        g.setFont (font);
         repaint = false;
         drawInternalComponents(g);
         GraphicLib.setNormalStroke(g);
diff --git a/src/ui/TGComponentManager.java b/src/ui/TGComponentManager.java
index e8f57cd089..18d4820560 100755
--- a/src/ui/TGComponentManager.java
+++ b/src/ui/TGComponentManager.java
@@ -362,6 +362,7 @@ public class TGComponentManager {
     public static final int AVATARSMD_SET_TIMER = 5109;
     public static final int AVATARSMD_RESET_TIMER = 5110;
     public static final int AVATARSMD_EXPIRE_TIMER = 5111;
+    public static final int AVATARSMD_LIBRARY_FUNCTION_CALL = 5112;
 
     // AVATAR RD -> starts at 5200
     public static final int AVATARRD_REQUIREMENT = 5200;
@@ -515,6 +516,9 @@ public class TGComponentManager {
         case AVATARSMD_SEND_SIGNAL:
             tgc = new AvatarSMDSendSignal(x, y, tdp.getMinX(), tdp.getMaxX(), tdp.getMinY(), tdp.getMaxY(), false, null, tdp);
             break;
+        case AVATARSMD_LIBRARY_FUNCTION_CALL:
+            tgc = new AvatarSMDLibraryFunctionCall (x, y, tdp.getMinX(), tdp.getMaxX(), tdp.getMinY(), tdp.getMaxY(), false, null, tdp);
+            break;
         case AVATARSMD_RECEIVE_SIGNAL:
             tgc = new AvatarSMDReceiveSignal(x, y, tdp.getMinX(), tdp.getMaxX(), tdp.getMinY(), tdp.getMaxY(), false, null, tdp);
             break;
@@ -1289,6 +1293,8 @@ public class TGComponentManager {
             return AVATARSMD_SEND_SIGNAL;
         } else if (tgc instanceof AvatarSMDReceiveSignal) {
             return AVATARSMD_RECEIVE_SIGNAL;
+        } else if (tgc instanceof AvatarSMDLibraryFunctionCall) {
+            return AVATARSMD_LIBRARY_FUNCTION_CALL;
         } else if (tgc instanceof AvatarSMDParallel) {
             return AVATARSMD_PARALLEL;
         } else if (tgc instanceof AvatarSMDState) {
diff --git a/src/ui/TGUIAction.java b/src/ui/TGUIAction.java
index a4691fae08..3b2d79bc07 100755
--- a/src/ui/TGUIAction.java
+++ b/src/ui/TGUIAction.java
@@ -344,6 +344,7 @@ public class TGUIAction extends AbstractAction {
     public static final int ASMD_STOP = 294;
     public static final int ASMD_SEND_SIGNAL = 296;
     public static final int ASMD_RECEIVE_SIGNAL = 297;
+    public static final int ASMD_LIBRARY_FUNCTION_CALL = 432;
     public static final int ASMD_PARALLEL = 298;
     public static final int ASMD_STATE = 299;
     public static final int ASMD_CHOICE = 325;
@@ -1061,6 +1062,8 @@ public class TGUIAction extends AbstractAction {
         actions[ASMD_STOP] = new TAction("add-asmd-stop", "Add Stop", IconManager.imgic210, IconManager.imgic210, "Stop", "Add a termination state to the currently opened AVATAR state machine diagram", 0);
         actions[ASMD_SEND_SIGNAL] = new TAction("add-asmd-sendsignal", "Send signal", IconManager.imgic904, IconManager.imgic904, "Send signal", "Add a send signal operator to the currently opened AVATAR state machine diagram", 0);
         actions[ASMD_RECEIVE_SIGNAL] = new TAction("add-asmd-receivesignal", "Receive signal", IconManager.imgic908, IconManager.imgic908, "Receive signal", "Add a receive signal operator to the currently opened AVATAR state machine diagram", 0);
+        // TODO: change icon
+        actions[ASMD_LIBRARY_FUNCTION_CALL] = new TAction("add-asmd-libraryfunctioncall", "Library function call", IconManager.imgic904, IconManager.imgic904, "Library function call", "Add a library function call to the currently opened AVATAR state machine diagram", 0);
         actions[ASMD_PARALLEL] = new TAction("add-asmd-parallel", "Parallel", IconManager.imgic206, IconManager.imgic206, "Parallel", "Add a parallel operator to the currently opened AVATAR state machine diagram", 0);
         actions[ASMD_STATE] = new TAction("add-asmd-state", "State", IconManager.imgic5036, IconManager.imgic5036, "State", "Add a new state to the currently opened AVATAR state machine diagram", 0);
         actions[ASMD_CHOICE] = new TAction("add-asmd-choice", "Add Choice", IconManager.imgic208, IconManager.imgic208, "Choice", "Add a choice - non-deterministic or guarded - to the currently opened AVATAR state machine diagram", 0);
diff --git a/src/ui/avatarbd/AvatarBDBlock.java b/src/ui/avatarbd/AvatarBDBlock.java
index 5bff4a48da..6beca3f43a 100644
--- a/src/ui/avatarbd/AvatarBDBlock.java
+++ b/src/ui/avatarbd/AvatarBDBlock.java
@@ -69,7 +69,6 @@ public class AvatarBDBlock extends TGCScalableWithInternalComponent implements S
     private int maxFontSize = 12;
     private int minFontSize = 4;
     private int currentFontSize = -1;
-    private boolean displayText = true;
     private int textX = 7;
 
     private int limitName = -1;
@@ -135,8 +134,8 @@ public class AvatarBDBlock extends TGCScalableWithInternalComponent implements S
         setValue(name);
         oldValue = value;
 
-        currentFontSize = maxFontSize;
         oldScaleFactor = tdp.getZoom();
+        currentFontSize = (int) (maxFontSize*oldScaleFactor);
 
         myImageIcon = IconManager.imgic700;
 
@@ -147,277 +146,291 @@ public class AvatarBDBlock extends TGCScalableWithInternalComponent implements S
         actionOnAdd();
     }
 
-    public void internalDrawing(Graphics g) {
+    @Override
+    public void internalDrawing (Graphics graph) {
+        Font font = graph.getFont ();
+        this.internalDrawingAux (graph);
+        graph.setFont (font);
+    }
+
+    public void internalDrawingAux (Graphics graph) {
+        // Draw outer rectangle (for border)
+        Color c = graph.getColor ();
+        graph.drawRect (this.x, this.y, this.width, this.height);
+
+        // Draw inner rectangle
+        graph.setColor (ColorManager.AVATAR_BLOCK);
+        graph.fillRect (this.x+1, this.y+1, this.width-1, this.height-1);
+        graph.setColor (c);
+
+        // limits
+        this.limitName = -1;
+        this.limitAttr = -1;
+        this.limitMethod = -1;
+
+        // h retains the coordinate along X where an element was last drawn
+        int h = 0;
+
+        int textY1 = (int) (this.textY1 * this.tdp.getZoom ());
+        int textX = (int) (this.textX * this.tdp.getZoom ());
+
+        // Draw icon
+        this.iconIsDrawn = this.width > IconManager.iconSize + 2*textX && height > IconManager.iconSize + 2*textX;
+        if (this.iconIsDrawn)
+            graph.drawImage (IconManager.img5100, this.x + this.width - IconManager.iconSize - textX, this.y + textX, null);
+
+
+        Font font = graph.getFont ();
+
         String ster;
-        if (!isCryptoBlock) {
+        if (!this.isCryptoBlock)
             ster = "<<" + stereotype + ">>";
-        } else {
+        else
             ster = "<<" + stereotypeCrypto + ">>";
-        }
-        Font f = g.getFont();
-        Font fold = f;
 
-        //TraceManager.addDev("Avatar Block width=" + width + " height=" + height);
-
-        if ((rescaled) && (!tdp.isScaled())) {
-
-            if (currentFontSize == -1) {
-                currentFontSize = f.getSize();
-            }
-            rescaled = false;
-            // Must set the font size ..
-            // Find the biggest font not greater than max_font size
-            // By Increment of 1
-            // Or decrement of 1
-            // If font is less than 4, no text is displayed
-
-            int maxCurrentFontSize = Math.max(0, Math.min(height, maxFontSize));
-            int w0, w1, w2;
-            f = f.deriveFont((float)maxCurrentFontSize);
-            g.setFont(f);
-            //System.out.println("max current font size:" + maxCurrentFontSize);
-            while(maxCurrentFontSize > (minFontSize-1)) {
-                w0 = g.getFontMetrics().stringWidth(value);
-                w1 = g.getFontMetrics().stringWidth(ster);
-                w2 = Math.min(w0, w1);
-                if (w2 < (width - (2*textX))) {
+        if (this.rescaled && !this.tdp.isScaled ()) {
+            this.rescaled = false;
+            // Must set the font size...
+            // Incrementally find the biggest font not greater than max_font size
+            // If font is less than min_font, no text is displayed
+
+            // This is the maximum font size possible
+            int maxCurrentFontSize = Math.max (0, Math.min (this.height, (int) (this.maxFontSize*this.tdp.getZoom ())));
+            font = font.deriveFont ((float) maxCurrentFontSize);
+
+            // Try to decrease font size until we get below the minimum
+            while (maxCurrentFontSize > (this.minFontSize*this.tdp.getZoom () - 1)) {
+                // Compute width of name of the function
+                int w0 = graph.getFontMetrics (font).stringWidth (this.value);
+                // Compute width of string stereotype
+                int w1 = graph.getFontMetrics (font).stringWidth (ster);
+
+                // if one of the two width is small enough use this font size
+                if (Math.min (w0, w1) < this.width - (2*this.textX))
                     break;
-                }
+
+                // Decrease font size
                 maxCurrentFontSize --;
-                f = f.deriveFont((float)maxCurrentFontSize);
-                g.setFont(f);
+                // Scale the font
+                font = font.deriveFont ((float) maxCurrentFontSize);
             }
-            currentFontSize = maxCurrentFontSize;
 
-            if(currentFontSize <minFontSize) {
-                displayText = false;
-            } else {
-                displayText = true;
-                f = f.deriveFont((float)currentFontSize);
-                g.setFont(f);
+            // Box is too damn small
+            if (this.currentFontSize < this.minFontSize*this.tdp.getZoom ()) {
+                maxCurrentFontSize ++;
+                // Scale the font
+                font = font.deriveFont ((float) maxCurrentFontSize);
             }
 
-        }
-
-        //System.out.println("Current font size:" + currentFontSize);
+            // Use this font
+            graph.setFont (font);
+            this.currentFontSize = maxCurrentFontSize;
+        } else
+            font = font.deriveFont (this.currentFontSize);
 
-        Color c = g.getColor();
-        g.draw3DRect(x, y, width, height, true);
+        graph.setFont (font.deriveFont (Font.BOLD));
+        h = graph.getFontMetrics ().getAscent () + graph.getFontMetrics ().getLeading () + textY1;
 
-        //g.setColor(ColorManager.AVATAR_BLOCK);
-        Color avat = ColorManager.AVATAR_BLOCK;
-        g.setColor(new Color(avat.getRed(), avat.getGreen(), Math.min(255, avat.getBlue() + (getMyDepth() * 10))));
-        g.fill3DRect(x+1, y+1, width-1, height-1, true);
-        g.setColor(c);
+        if (h + graph.getFontMetrics ().getDescent () + textY1 >= this.height)
+            return;
 
-        // Strings
-        int w;
-        int h = 0;
-        if (displayText) {
-            f = f.deriveFont((float)currentFontSize);
-            Font f0 = g.getFont();
-            g.setFont(f.deriveFont(Font.BOLD));
-
-            w = g.getFontMetrics().stringWidth(ster);
-            h =  currentFontSize + (int)(textY1 * tdp.getZoom());
-            if ((w < (2*textX + width)) && (h < height)) {
-                g.drawString(ster, x + (width - w)/2, y +h);
-            }
-            g.setFont(f0);
-            w  = g.getFontMetrics().stringWidth(value);
-            h = 2* (currentFontSize + (int)(textY1 * tdp.getZoom()));
-            if ((w < (2*textX + width)) && (h < height)) {
-                g.drawString(value, x + (width - w)/2, y + h);
+        // Write stereotype if small enough
+        int w = graph.getFontMetrics ().stringWidth (ster);
+        if (w + 2*textX < this.width)
+            graph.drawString (ster, this.x + (this.width - w)/2, this.y + h);
+        else {
+            // try to draw with "..." instead
+            if (!this.isCryptoBlock)
+                ster = this.stereotype;
+            else
+                ster = this.stereotypeCrypto;
+
+            for (int stringLength = ster.length ()-1; stringLength >= 0; stringLength--) {
+                String abbrev = "<<" + ster.substring (0, stringLength) + "...>>";
+                w = graph.getFontMetrics ().stringWidth (abbrev);
+                if (w + 2*textX < this.width) {
+                    graph.drawString (abbrev, this.x + (this.width - w)/2, this.y + h);
+                    break;
+                }
             }
-            limitName = y + h;
-        } else {
-            limitName = -1;
         }
 
-        g.setFont(fold);
+        // Write value if small enough
+        graph.setFont (font);
+        h += graph.getFontMetrics ().getHeight () + textY1;
+        if (h + graph.getFontMetrics ().getDescent () + textY1 >= this.height)
+            return;
 
-        h = h +2;
-        if (h < height) {
-            g.drawLine(x, y+h, x+width, y+h);
+        w = graph.getFontMetrics ().stringWidth (this.value);
+        if (w + 2*textX < this.width)
+            graph.drawString (this.value, this.x + (this.width - w)/2, this.y + h);
+        else {
+            // try to draw with "..." instead
+            for (int stringLength = this.value.length ()-1; stringLength >= 0; stringLength--) {
+                String abbrev = this.value.substring (0, stringLength) + "...";
+                w = graph.getFontMetrics ().stringWidth (abbrev);
+                if (w + 2*textX < this.width) {
+                    graph.drawString (abbrev, this.x + (this.width - w)/2, this.y + h);
+                    break;
+                }
+            }
         }
 
-        // Icon
-        if ((width>30) && (height > (iconSize + 2*textX))) {
-            iconIsDrawn = true;
-            g.drawImage(IconManager.img5100, x + width - iconSize - textX, y + textX, null);
-        } else {
-            iconIsDrawn = false;
-        }
+        h += graph.getFontMetrics ().getDescent () + textY1;
 
-        int cpt = h;
-        // Attributes
-        if (((AvatarBDPanel)tdp).areAttributesVisible()) {
-            limitAttr = -1;
-            int index = 0;
-            String attr;
+        // Update lower bound of text
+        this.limitName = this.y + h;
 
-            TAttribute a;
+        if (h + textY1 >= this.height)
+            return;
 
-            int si = Math.min(12, (int)((float)currentFontSize - 2));
+        // Draw separator
+        graph.drawLine (this.x, this.y+h, this.x+this.width, this.y+h);
 
-            f = g.getFont();
-            f = f.deriveFont((float)si);
-            g.setFont(f);
-            int step = si + 2;
+        if (! ((AvatarBDPanel) this.tdp).areAttributesVisible ())
+            return;
 
-            while(index < this.myAttributes.size()) {
-                cpt += step ;
-                if (cpt >= (height - textX)) {
-                    break;
-                }
-                a = this.myAttributes.get(index);
-                attr = a.toAvatarString();
-                w = g.getFontMetrics().stringWidth(attr);
-                if ((w + (2 * textX) + 1) < width) {
-                    g.drawString(attr, x + textX, y + cpt);
-                    if (a.getConfidentialityVerification() > 0) {
-                        //TraceManager.addDev("Drawing confidentiality for " + a.getId());
-                        drawConfidentialityVerification(a.getConfidentialityVerification(), g, x, y+cpt);
-                    }
-                    limitAttr = y + cpt;
-                } else {
-                    attr = "...";
-                    w = g.getFontMetrics().stringWidth(attr);
-                    if ((w + textX + 2) < width) {
-                        g.drawString(attr, x + textX + 1, y + cpt);
-
-                        limitAttr = y + cpt;
-                    } else {
-                        // skip attribute
-                        cpt -= step;
+        // Set font size
+        // int attributeFontSize = Math.min (12, this.currentFontSize - 2);
+        int attributeFontSize = this.currentFontSize*5/6;
+        graph.setFont (font.deriveFont ((float) attributeFontSize));
+        int step = graph.getFontMetrics ().getHeight ();
+
+        h += textY1;
+
+        // Attributes 
+        for (TAttribute attr: this.myAttributes) {
+            h += step;
+            if (h >= this.height - textX) {
+                this.limitAttr = this.y + this.height;
+                return;
+            }
+
+            // Get the string for this parameter
+            String attrString = attr.toAvatarString ();
+
+            // Try to draw it
+            w = graph.getFontMetrics ().stringWidth (attrString);
+            if (w + 2*textX < this.width)
+                graph.drawString (attrString, this.x + textX, this.y + h);
+            else {
+                // If we can't, try to draw with "..." instead
+                int stringLength;
+                for (stringLength = attrString.length ()-1; stringLength >= 0; stringLength--) {
+                    String abbrev = attrString.substring (0, stringLength) + "...";
+                    w = graph.getFontMetrics ().stringWidth (abbrev);
+                    if (w + 2*textX < this.width) {
+                        graph.drawString (abbrev, this.x + textX, this.y + h);
+                        break;
                     }
                 }
-                index ++;
+
+                if (stringLength < 0)
+                    // skip attribute
+                    h -= step;
             }
-        } else {
-            limitAttr = -1;
         }
 
-        // Methods
-        if (((AvatarBDPanel)tdp).areAttributesVisible()) {
-            limitMethod = -1;
-            if (this.myMethods.size() > 0) {
-                if (cpt < height) {
-                    cpt += textY1;
-                    g.drawLine(x, y+cpt, x+width, y+cpt);
-                    cpt += textY1;
-                }
-            }
+        h += graph.getFontMetrics ().getDescent () + textY1;
 
-            int index = 0;
-            String method;
-            AvatarMethod am;
+        // Remember the end of attributes
+        this.limitAttr = this.y + h;
 
-            int si = Math.min(12, (int)((float)currentFontSize - 2));
+        if (h + textY1 >= this.height)
+            return;
 
-            f = g.getFont();
-            f = f.deriveFont((float)si);
-            g.setFont(f);
-            int step = si + 2;
+        graph.drawLine (this.x, this.y+h, this.x+this.width, this.y+h);
+        h += textY1;
 
-            while(index < this.myMethods.size()) {
-                cpt += step ;
-                if (cpt >= (height - textX)) {
-                    break;
-                }
-                am = this.myMethods.get (index);
-                method = "~ " + am.toString();
-                w = g.getFontMetrics().stringWidth(method);
-                if ((w + (2 * textX) + 1) < width) {
-                    g.drawString(method, x + textX, y + cpt);
-                    limitMethod = y + cpt;
-                } else {
-                    method = "...";
-                    w = g.getFontMetrics().stringWidth(method);
-                    if ((w + textX + 2) < width) {
-                        g.drawString(method, x + textX + 1, y + cpt);
-                        limitMethod = y + cpt;
-                    } else {
-                        // skip attribute
-                        cpt -= step;
+        // Methods
+        for (AvatarMethod method: this.myMethods) {
+            h += step;
+            if (h >= this.height - textX) {
+                this.limitMethod = this.y + this.height;
+                return;
+            }
+
+            // Get the string for this method
+            String methodString = "~ " + method.toString ();
+
+            w = graph.getFontMetrics ().stringWidth (methodString);
+            if (w + 2*textX < this.width)
+                graph.drawString (methodString, this.x + textX, this.y + h);
+            else {
+                // If we can't, try to draw with "..." instead
+                int stringLength;
+                for (stringLength = methodString.length ()-1; stringLength >= 0; stringLength--) {
+                    String abbrev = methodString.substring (0, stringLength) + "...";
+                    w = graph.getFontMetrics ().stringWidth (abbrev);
+                    if (w + 2*textX < this.width) {
+                        graph.drawString (abbrev, this.x + textX, this.y + h);
+                        break;
                     }
                 }
-                index ++;
+
+                if (stringLength < 0)
+                    // skip method
+                    h -= step;
             }
-        } else {
-            limitMethod = -1;
         }
 
-        // Signals
-        if (((AvatarBDPanel)tdp).areAttributesVisible()) {
-
-            if (this.mySignals.size() > 0) {
-                if (cpt < height) {
-                    cpt += textY1;
-                    g.drawLine(x, y+cpt, x+width, y+cpt);
-                    cpt += textY1;
-                }
-            }
+        h += graph.getFontMetrics ().getDescent () + textY1;
 
-            int index = 0;
-            String signal;
-            AvatarSignal as;
+        // Remember limit of methods
+        this.limitMethod = this.y + h;
 
-            int si = Math.min(12, (int)((float)currentFontSize - 2));
+        if (h + textY1 >= this.height)
+            return;
 
-            f = g.getFont();
-            f = f.deriveFont((float)si);
-            g.setFont(f);
-            int step = si + 2;
+        graph.drawLine (this.x, this.y+h, this.x+this.width, this.y+h);
+        h += textY1;
 
-            while(index < this.mySignals.size()) {
-                cpt += step ;
-                if (cpt >= (height - textX)) {
-                    break;
-                }
-                as = this.mySignals.get (index);
-                signal = "~ " + as.toString();
-                w = g.getFontMetrics().stringWidth(signal);
-                if ((w + (2 * textX) + 1) < width) {
-                    g.drawString(signal, x + textX, y + cpt);
-                } else {
-                    signal = "...";
-                    w = g.getFontMetrics().stringWidth(signal);
-                    if ((w + textX + 2) < width) {
-                        g.drawString(signal, x + textX + 1, y + cpt);
-                    } else {
-                        // skip attribute
-                        cpt -= step;
+        // Signals
+        for (AvatarSignal signal: this.mySignals) {
+            h += step;
+            if (h >= this.height - textX)
+                return;
+
+            String signalString = "~ " + signal.toString ();
+            w = graph.getFontMetrics ().stringWidth (signalString);
+            if (w + 2*textX < this.width)
+                graph.drawString (signalString, this.x + textX, this.y + h);
+            else {
+                // If we can't, try to draw with "..." instead
+                int stringLength;
+                for (stringLength = signalString.length ()-1; stringLength >= 0; stringLength--) {
+                    String abbrev = signalString.substring (0, stringLength) + "...";
+                    w = graph.getFontMetrics ().stringWidth (abbrev);
+                    if (w + 2*textX < this.width) {
+                        graph.drawString (abbrev, this.x + textX, this.y + h);
+                        break;
                     }
                 }
-                index ++;
-            }
-        }
 
-        // Global code
-        if (hasGlobalCode()) {
-            w = g.getFontMetrics().stringWidth(GLOBAL_CODE_INFO);
-            if ((w < (2*textX + width)) && (y+cpt < height)) {
-                g.drawString(GLOBAL_CODE_INFO, x + (width - w)/2, y +cpt);
+                if (stringLength < 0)
+                    // skip signal
+                    h -= step;
             }
-
         }
 
+        h += graph.getFontMetrics ().getDescent () + textY1;
 
+        if (h + textY1 >= this.height)
+            return;
 
-        g.setFont(fold);
+        graph.drawLine (this.x, this.y+h, this.x+this.width, this.y+h);
+        h += textY1;
 
-        /*int w  = g.getFontMetrics().stringWidth(ster);
-          Font f = g.getFont();
-          g.setFont(f.deriveFont(Font.BOLD));
-          g.drawString(ster, x + (width - w)/2, y + textY1);
-          g.setFont(f);
-          w  = g.getFontMetrics().stringWidth(value);
-          g.drawString(value, x + (width - w)/2, y + textY2);*/
+        // Global code
+        if (hasGlobalCode()) {
+            h += step;
+            if (h >= this.height - textX)
+                return;
 
-        // Icon
-        //g.drawImage(IconManager.imgic1100.getImage(), x + 4, y + 4, null);
-        //g.drawImage(IconManager.img9, x + width - 20, y + 4, null);
+            w = graph.getFontMetrics ().stringWidth (GLOBAL_CODE_INFO);
+            if (w + 2*textX < this.width)
+                graph.drawString (GLOBAL_CODE_INFO, this.x + (this.width - w)/2, this.y + h);
+        }
     }
 
 
@@ -465,6 +478,7 @@ public class AvatarBDBlock extends TGCScalableWithInternalComponent implements S
     }
 
     public boolean editOndoubleClick(JFrame frame, int _x, int _y) {
+        int textX = (int) (this.textX * this.tdp.getZoom ());
         if (iconIsDrawn) {
             if (GraphicLib.isInRectangle(_x, _y, x + width - iconSize - textX, y + textX, iconSize, iconSize)) {
                 tdp.selectTab(getValue());
@@ -472,7 +486,7 @@ public class AvatarBDBlock extends TGCScalableWithInternalComponent implements S
             }
         }
         // On the name ?
-        if ((((limitName == -1) && (displayText) && (_y <= (y + 2*currentFontSize)))) || ((displayText) && (_y < limitName))) {
+        if ((limitName == -1 && _y <= y + 2*currentFontSize) || _y < limitName) {
             oldValue = value;
 
             //String text = getName() + ": ";
@@ -590,7 +604,7 @@ public class AvatarBDBlock extends TGCScalableWithInternalComponent implements S
     }
 
     public boolean acceptSwallowedTGComponent(TGComponent tgc) {
-        if (tgc instanceof AvatarBDBlock) {
+        if (tgc instanceof AvatarBDBlock || tgc instanceof AvatarBDLibraryFunction) {
             return true;
         }
 
@@ -635,6 +649,9 @@ public class AvatarBDBlock extends TGCScalableWithInternalComponent implements S
             //tgc.setCd(x, y);
         }
 
+        else if (tgc instanceof AvatarBDLibraryFunction)
+            ((AvatarBDLibraryFunction) tgc).resizeWithFather ();
+
         // else unknown*/
 
         //add it
@@ -927,6 +944,15 @@ public class AvatarBDBlock extends TGCScalableWithInternalComponent implements S
         return list;
     }
 
+    public LinkedList<AvatarBDLibraryFunction> getFullLibraryFunctionList () {
+        LinkedList<AvatarBDLibraryFunction> list = new LinkedList<AvatarBDLibraryFunction> ();
+        for (int i=0; i<nbInternalTGComponent; i++)
+            if (this.tgcomponent[i] instanceof AvatarBDLibraryFunction)
+                list.add ((AvatarBDLibraryFunction) this.tgcomponent[i]);
+
+        return list;
+    }
+
     public boolean hasInternalBlockWithName(String name) {
         LinkedList<AvatarBDBlock> list  = getFullBlockList();
         for(AvatarBDBlock b: list) {
diff --git a/src/ui/avatarbd/AvatarBDDataType.java b/src/ui/avatarbd/AvatarBDDataType.java
index b464e0e82d..fd3a932d9a 100644
--- a/src/ui/avatarbd/AvatarBDDataType.java
+++ b/src/ui/avatarbd/AvatarBDDataType.java
@@ -78,7 +78,7 @@ public class AvatarBDDataType extends TGCScalableWithInternalComponent  {
 	
 	
 	// TAttribute, AvatarMethod, AvatarSignal
-	protected Vector myAttributes;
+	protected Vector<TAttribute> myAttributes;
 	
 	public String oldValue;
     
@@ -112,7 +112,7 @@ public class AvatarBDDataType extends TGCScalableWithInternalComponent  {
         
         myImageIcon = IconManager.imgic700;
 		
-		myAttributes = new Vector();
+		myAttributes = new Vector<TAttribute> ();
 		
 		actionOnAdd();
     }
@@ -233,7 +233,7 @@ public class AvatarBDDataType extends TGCScalableWithInternalComponent  {
 				if (cpt >= (height - textX)) {
 					break;
 				}
-				a = (TAttribute)(myAttributes.get(index));
+				a = myAttributes.get(index);
 				attr = a.toString();
 				w = g.getFontMetrics().stringWidth(attr);
 				if ((w + (2 * textX) + 1) < width) {
@@ -366,7 +366,7 @@ public class AvatarBDDataType extends TGCScalableWithInternalComponent  {
         StringBuffer sb = new StringBuffer("<extraparam>\n");
         for(int i=0; i<myAttributes.size(); i++) {
             //System.out.println("Attribute:" + i);
-            a = (TAttribute)(myAttributes.elementAt(i));
+            a = myAttributes.elementAt(i);
             //System.out.println("Attribute:" + i + " = " + a.getId());
             //value = value + a + "\n";
             sb.append("<Attribute access=\"");
@@ -450,7 +450,7 @@ public class AvatarBDDataType extends TGCScalableWithInternalComponent  {
         return TGComponentManager.AVATARBD_PORT_CONNECTOR;
 	}
 	
-	public Vector getAttributeList() {
+	public Vector<TAttribute> getAttributeList() {
 		return myAttributes;
 	}
     
diff --git a/src/ui/avatarbd/AvatarBDLibraryFunction.java b/src/ui/avatarbd/AvatarBDLibraryFunction.java
index 9c84bde989..b1893deeb9 100644
--- a/src/ui/avatarbd/AvatarBDLibraryFunction.java
+++ b/src/ui/avatarbd/AvatarBDLibraryFunction.java
@@ -55,7 +55,7 @@ import javax.swing.JOptionPane;
 import myutil.GraphicLib;
 import myutil.TraceManager;
 
-import ui.TGCScalableWithInternalComponent;
+import ui.TGCScalableWithoutInternalComponent;
 import ui.TAttribute;
 import ui.TGComponent;
 import ui.TDiagramPanel;
@@ -67,6 +67,7 @@ import ui.TGComponentManager;
 import ui.AvatarSignal;
 import ui.AvatarMethod;
 import ui.AvatarDesignPanel;
+import ui.SwallowedTGComponent;
 import ui.avatarsmd.AvatarSMDPanel;
 import ui.window.JDialogAvatarLibraryFunction;
 
@@ -76,7 +77,7 @@ import ui.window.JDialogAvatarLibraryFunction;
  * @version 1.0 04.08.2016
  * @author Florian LUGOU
  */
-public class AvatarBDLibraryFunction extends TGCScalableWithInternalComponent implements AvatarBDStateMachineOwner {
+public class AvatarBDLibraryFunction extends TGCScalableWithoutInternalComponent implements SwallowedTGComponent, AvatarBDStateMachineOwner {
 
     /**
      * Stereotype for standard library function.
@@ -104,7 +105,7 @@ public class AvatarBDLibraryFunction extends TGCScalableWithInternalComponent im
     private static final int paddingHorizontal = 7;
 
     /**
-     * The vertical spacing before and after text.
+     * The vertical spacing between lines.
      */
     private static final int paddingVertical   = 3;
 
@@ -128,11 +129,6 @@ public class AvatarBDLibraryFunction extends TGCScalableWithInternalComponent im
      */
     private int currentFontSize = -1;
 
-    /**
-     * Equals True when the box is large enough for the text to be displayed.
-     */
-    private boolean displayText = true;
-
     /**
      * Equals True when the box is large enough for the icon to be drawn.
      */
@@ -235,8 +231,8 @@ public class AvatarBDLibraryFunction extends TGCScalableWithInternalComponent im
             // TODO: throw exception
         }
 
-        this.currentFontSize = this.maxFontSize;
         this.oldScaleFactor = this.tdp.getZoom();
+        this.currentFontSize = (int) (AvatarBDLibraryFunction.maxFontSize * this.oldScaleFactor);
 
         // TODO: change that
         this.myImageIcon = IconManager.imgic700;
@@ -333,14 +329,40 @@ public class AvatarBDLibraryFunction extends TGCScalableWithInternalComponent im
      *      The {@link Graphics} object used to draw this component.
      */
     private void internalDrawingAux (Graphics graph) {
+        // Draw outer rectangle (for border)
+        Color c = graph.getColor ();
+        graph.drawRect (this.x, this.y, this.width, this.height);
+
+        // Draw inner rectangle
+        graph.setColor (ColorManager.AVATAR_LIBRARYFUNCTION);
+        graph.fillRect (this.x+1, this.y+1, this.width-1, this.height-1);
+        graph.setColor (c);
+
+        // limits
+        this.limitName = -1;
+        this.limitParameters = -1;
+        this.limitSignals = -1;
+
+        // h retains the coordinate along X where an element was last drawn
+        int h = 0;
+
+        int paddingVertical = (int) (AvatarBDLibraryFunction.paddingVertical * this.tdp.getZoom ());
+        int paddingHorizontal = (int) (AvatarBDLibraryFunction.paddingHorizontal * this.tdp.getZoom ());
+
+        // Draw icon
+        this.iconIsDrawn = this.width > IconManager.iconSize + 2*paddingHorizontal && height > IconManager.iconSize + 2*paddingHorizontal;
+        if (this.iconIsDrawn)
+            graph.drawImage (IconManager.img5100, this.x + this.width - IconManager.iconSize - paddingHorizontal, this.y + paddingHorizontal, null);
+
+
+        Font font = graph.getFont ();
+
         String ster;
         if (!this.isCrypto)
             ster = "<<" + stereotype + ">>";
         else
             ster = "<<" + stereotypeCrypto + ">>";
 
-        Font font = graph.getFont ();
-
         if (this.rescaled && !this.tdp.isScaled ()) {
             this.rescaled = false;
             // Must set the font size...
@@ -348,18 +370,18 @@ public class AvatarBDLibraryFunction extends TGCScalableWithInternalComponent im
             // If font is less than min_font, no text is displayed
 
             // This is the maximum font size possible
-            int maxCurrentFontSize = Math.max (0, Math.min (this.height, this.maxFontSize));
+            int maxCurrentFontSize = Math.max (0, Math.min (this.height, (int) (AvatarBDLibraryFunction.maxFontSize*this.tdp.getZoom ())));
             font = font.deriveFont ((float) maxCurrentFontSize);
 
             // Try to decrease font size until we get below the minimum
-            while (maxCurrentFontSize > (this.minFontSize - 1)) {
+            while (maxCurrentFontSize > (AvatarBDLibraryFunction.minFontSize*this.tdp.getZoom () - 1)) {
                 // Compute width of name of the function
                 int w0 = graph.getFontMetrics (font).stringWidth (this.value);
                 // Compute width of string stereotype
                 int w1 = graph.getFontMetrics (font).stringWidth (ster);
 
                 // if one of the two width is small enough use this font size
-                if (Math.min (w0, w1) < this.width - (2*this.paddingHorizontal))
+                if (Math.min (w0, w1) < this.width - (2*paddingHorizontal))
                     break;
 
                 // Decrease font size
@@ -368,59 +390,72 @@ public class AvatarBDLibraryFunction extends TGCScalableWithInternalComponent im
                 font = font.deriveFont ((float) maxCurrentFontSize);
             }
 
+            // Box is too damn small
+            if (this.currentFontSize < AvatarBDLibraryFunction.minFontSize*this.tdp.getZoom ()) {
+                maxCurrentFontSize ++;
+                // Scale the font
+                font = font.deriveFont ((float) maxCurrentFontSize);
+            }
+
             // Use this font
             graph.setFont (font);
             this.currentFontSize = maxCurrentFontSize;
+        } else
+            font = font.deriveFont (this.currentFontSize);
 
-            // if font is two small don't display the text
-            this.displayText = this.currentFontSize >= this.minFontSize;
-        }
-
-        // Draw outer rectangle (for border)
-        Color c = graph.getColor ();
-        graph.drawRect (this.x, this.y, this.width, this.height);
-
-        // Draw inner rectangle
-        graph.setColor (ColorManager.AVATAR_LIBRARYFUNCTION);
-        graph.fillRect (this.x+1, this.y+1, this.width-1, this.height-1);
-        graph.setColor (c);
-
-        // limits
-        this.limitName = -1;
-        this.limitParameters = -1;
-        this.limitSignals = -1;
-
-        // h retains the coordinate along X where an element was last drawn
-        int h = 0;
-
-        // Draw icon
-        this.iconIsDrawn = this.width > IconManager.iconSize + 2*this.paddingHorizontal && height > IconManager.iconSize + 2*paddingHorizontal;
-        if (this.iconIsDrawn)
-            graph.drawImage (IconManager.img5100, this.x + this.width - IconManager.iconSize - this.paddingHorizontal, this.y + paddingHorizontal, null);
+        graph.setFont (font.deriveFont (Font.BOLD));
+        h = graph.getFontMetrics ().getAscent () + graph.getFontMetrics ().getLeading () + paddingVertical;
 
-        if (!this.displayText)
+        if (h + graph.getFontMetrics ().getDescent () + paddingVertical >= this.height)
             return;
 
-        int paddingVertical = (int) (this.paddingVertical * this.tdp.getZoom ());
-
         // Write stereotype if small enough
-        graph.setFont (font.deriveFont (Font.BOLD));
         int w = graph.getFontMetrics ().stringWidth (ster);
-        h = graph.getFontMetrics ().getAscent () + graph.getFontMetrics ().getLeading () + paddingVertical;
-        if (w + 2*this.paddingHorizontal < this.width && h + graph.getFontMetrics ().getDescent () + paddingVertical < this.height)
+        if (w + 2*paddingHorizontal < this.width)
             graph.drawString (ster, this.x + (this.width - w)/2, this.y + h);
+        else {
+            // try to draw with "..." instead
+            if (!this.isCrypto)
+                ster = this.stereotype;
+            else
+                ster = this.stereotypeCrypto;
+
+            for (int stringLength = ster.length ()-1; stringLength >= 0; stringLength--) {
+                String abbrev = "<<" + ster.substring (0, stringLength) + "...>>";
+                w = graph.getFontMetrics ().stringWidth (abbrev);
+                if (w + 2*paddingHorizontal < this.width) {
+                    graph.drawString (abbrev, this.x + (this.width - w)/2, this.y + h);
+                    break;
+                }
+            }
+        }
 
         // Write value if small enough
         graph.setFont (font);
-        w = graph.getFontMetrics ().stringWidth (this.value);
         h += graph.getFontMetrics ().getHeight () + paddingVertical;
-        if (w + 2*this.paddingHorizontal < this.width && h + graph.getFontMetrics ().getDescent () + paddingVertical < this.height)
+        if (h + graph.getFontMetrics ().getDescent () + paddingVertical >= this.height)
+            return;
+
+        w = graph.getFontMetrics ().stringWidth (this.value);
+        if (w + 2*paddingHorizontal < this.width)
             graph.drawString (this.value, this.x + (this.width - w)/2, this.y + h);
+        else {
+            // try to draw with "..." instead
+            for (int stringLength = this.value.length ()-1; stringLength >= 0; stringLength--) {
+                String abbrev = this.value.substring (0, stringLength) + "...";
+                w = graph.getFontMetrics ().stringWidth (abbrev);
+                if (w + 2*paddingHorizontal < this.width) {
+                    graph.drawString (abbrev, this.x + (this.width - w)/2, this.y + h);
+                    break;
+                }
+            }
+        }
+
+        h += graph.getFontMetrics ().getDescent () + paddingVertical;
 
         // Update lower bound of text
         this.limitName = this.y + h;
 
-        h += paddingVertical;
         if (h + paddingVertical >= this.height)
             return;
 
@@ -431,7 +466,8 @@ public class AvatarBDLibraryFunction extends TGCScalableWithInternalComponent im
             return;
 
         // Set font size
-        int attributeFontSize = Math.min (12, this.currentFontSize - 2);
+        // int attributeFontSize = Math.min (12, this.currentFontSize - 2);
+        int attributeFontSize = this.currentFontSize*5/6;
         graph.setFont (font.deriveFont ((float) attributeFontSize));
         int step = graph.getFontMetrics ().getHeight ();
 
@@ -440,7 +476,7 @@ public class AvatarBDLibraryFunction extends TGCScalableWithInternalComponent im
         // Parameters
         for (TAttribute attr: this.parameters) {
             h += step;
-            if (h >= this.height - this.paddingHorizontal) {
+            if (h >= this.height - paddingHorizontal) {
                 this.limitParameters = this.y + this.height;
                 return;
             }
@@ -450,16 +486,16 @@ public class AvatarBDLibraryFunction extends TGCScalableWithInternalComponent im
 
             // Try to draw it
             w = graph.getFontMetrics ().stringWidth (attrString);
-            if (w + 2*this.paddingHorizontal < this.width)
-                graph.drawString (attrString, this.x + this.paddingHorizontal, this.y + h);
+            if (w + 2*paddingHorizontal < this.width)
+                graph.drawString (attrString, this.x + paddingHorizontal, this.y + h);
             else {
                 // If we can't, try to draw with "..." instead
                 int stringLength;
                 for (stringLength = attrString.length ()-1; stringLength >= 0; stringLength--) {
                     String abbrev = attrString.substring (0, stringLength) + "...";
                     w = graph.getFontMetrics ().stringWidth (abbrev);
-                    if (w + 2*this.paddingHorizontal < this.width) {
-                        graph.drawString (abbrev, this.x + this.paddingHorizontal, this.y + h);
+                    if (w + 2*paddingHorizontal < this.width) {
+                        graph.drawString (abbrev, this.x + paddingHorizontal, this.y + h);
                         break;
                     }
                 }
@@ -470,95 +506,91 @@ public class AvatarBDLibraryFunction extends TGCScalableWithInternalComponent im
             }
         }
 
+        h += graph.getFontMetrics ().getDescent () + paddingVertical;
+
         // Remember the end of parameters
         this.limitParameters = this.y + h;
 
-        // Signals
-        if (this.signals.size() > 0) {
-            h += paddingVertical;
-
-            if (h + paddingVertical >= this.height)
-                return;
+        if (h + paddingVertical >= this.height)
+            return;
 
-            graph.drawLine(this.x, this.y+h, this.x+this.width, this.y+h);
-            h += paddingVertical;
+        graph.drawLine (this.x, this.y+h, this.x+this.width, this.y+h);
+        h += paddingVertical;
 
-            for (AvatarSignal signal: this.signals) {
-                h += step ;
-                if (h >= this.height - this.paddingHorizontal) {
-                    this.limitSignals = this.y + this.height;
-                    return;
-                }
+        // Signals
+        for (AvatarSignal signal: this.signals) {
+            h += step ;
+            if (h >= this.height - paddingHorizontal) {
+                this.limitSignals = this.y + this.height;
+                return;
+            }
 
-                String signalString = "~ " + signal.toString ();
-                w = graph.getFontMetrics ().stringWidth (signalString);
-                if (w + 2*this.paddingHorizontal < this.width)
-                    graph.drawString (signalString, this.x + this.paddingHorizontal, this.y + h);
-                else {
-                    // If we can't, try to draw with "..." instead
-                    int stringLength;
-                    for (stringLength = signalString.length ()-1; stringLength >= 0; stringLength--) {
-                        String abbrev = signalString.substring (0, stringLength) + "...";
-                        w = graph.getFontMetrics ().stringWidth (abbrev);
-                        if (w + 2*this.paddingHorizontal < this.width) {
-                            graph.drawString (abbrev, this.x + this.paddingHorizontal, this.y + h);
-                            break;
-                        }
+            String signalString = "~ " + signal.toString ();
+            w = graph.getFontMetrics ().stringWidth (signalString);
+            if (w + 2*paddingHorizontal < this.width)
+                graph.drawString (signalString, this.x + paddingHorizontal, this.y + h);
+            else {
+                // If we can't, try to draw with "..." instead
+                int stringLength;
+                for (stringLength = signalString.length ()-1; stringLength >= 0; stringLength--) {
+                    String abbrev = signalString.substring (0, stringLength) + "...";
+                    w = graph.getFontMetrics ().stringWidth (abbrev);
+                    if (w + 2*paddingHorizontal < this.width) {
+                        graph.drawString (abbrev, this.x + paddingHorizontal, this.y + h);
+                        break;
                     }
-
-                    if (stringLength < 0)
-                        // skip signal
-                        h -= step;
                 }
-            }
 
-            // Remember limit of signals
-            this.limitSignals = this.y + h;
+                if (stringLength < 0)
+                    // skip signal
+                    h -= step;
+            }
         }
 
-        // Return Attributes
-        if (this.returnAttributes.size() > 0) {
-            h += paddingVertical;
+        h += graph.getFontMetrics ().getDescent () + paddingVertical;
 
-            if (h + paddingVertical >= this.height)
-                return;
+        // Remember limit of signals
+        this.limitSignals = this.y + h;
 
-            graph.drawLine(this.x, this.y+h, this.x+this.width, this.y+h);
-            h += paddingVertical;
+        if (h + paddingVertical >= this.height)
+            return;
 
-            for (TAttribute attr: this.returnAttributes) {
-                h += step;
-                if (h >= this.height - this.paddingHorizontal)
-                    return;
+        graph.drawLine (this.x, this.y+h, this.x+this.width, this.y+h);
+        h += paddingVertical;
 
-                // Get the string for this return attribute
-                String attrString = attr.toAvatarString ();
-
-                w = graph.getFontMetrics ().stringWidth (attrString);
-                if (w + 2*this.paddingHorizontal < this.width)
-                    graph.drawString (attrString, this.x + this.paddingHorizontal, this.y + h);
-                else {
-                    // If we can't, try to draw with "..." instead
-                    int stringLength;
-                    for (stringLength = attrString.length ()-1; stringLength >= 0; stringLength--) {
-                        String abbrev = attrString.substring (0, stringLength) + "...";
-                        w = graph.getFontMetrics ().stringWidth (abbrev);
-                        if (w + 2*this.paddingHorizontal < this.width) {
-                            graph.drawString (abbrev, this.x + this.paddingHorizontal, this.y + h);
-                            break;
-                        }
-                    }
+        // Return Attributes
+        for (TAttribute attr: this.returnAttributes) {
+            h += step;
+            if (h >= this.height - paddingHorizontal)
+                return;
+
+            // Get the string for this return attribute
+            String attrString = attr.toAvatarString ();
 
-                    if (stringLength < 0)
-                        // skip signal
-                        h -= step;
+            w = graph.getFontMetrics ().stringWidth (attrString);
+            if (w + 2*paddingHorizontal < this.width)
+                graph.drawString (attrString, this.x + paddingHorizontal, this.y + h);
+            else {
+                // If we can't, try to draw with "..." instead
+                int stringLength;
+                for (stringLength = attrString.length ()-1; stringLength >= 0; stringLength--) {
+                    String abbrev = attrString.substring (0, stringLength) + "...";
+                    w = graph.getFontMetrics ().stringWidth (abbrev);
+                    if (w + 2*paddingHorizontal < this.width) {
+                        graph.drawString (abbrev, this.x + paddingHorizontal, this.y + h);
+                        break;
+                    }
                 }
+
+                if (stringLength < 0)
+                    // skip signal
+                    h -= step;
             }
         }
     }
 
     @Override
-    public TGComponent isOnOnlyMe (int x1, int y1) {
+    public TGComponent isOnMe (int x1, int y1) {
 
         if (GraphicLib.isInRectangle(x1, y1, this.x, this.y, this.width, this.height))
             return this;
@@ -568,11 +600,12 @@ public class AvatarBDLibraryFunction extends TGCScalableWithInternalComponent im
 
     @Override
     public boolean editOndoubleClick(JFrame frame, int _x, int _y) {
+        int paddingHorizontal = (int) (AvatarBDLibraryFunction.paddingHorizontal*this.tdp.getZoom ());
         if (this.iconIsDrawn && GraphicLib.isInRectangle(
                     _x,
                     _y,
-                    this.x + this.width - IconManager.iconSize - this.paddingHorizontal,
-                    this.y + this.paddingHorizontal,
+                    this.x + this.width - IconManager.iconSize - paddingHorizontal,
+                    this.y + paddingHorizontal,
                     IconManager.iconSize,
                     IconManager.iconSize)) {
             this.tdp.selectTab (this.getValue ());
@@ -996,6 +1029,17 @@ public class AvatarBDLibraryFunction extends TGCScalableWithInternalComponent im
         return null;
     }
 
+    @Override
+    public void resizeWithFather() {
+        if (this.father != null && this.father instanceof AvatarBDBlock) {
+            // Too large to fit in the father? -> resize it!
+            this.resizeToFatherSize();
+
+            this.setCdRectangle (0, this.father.getWidth() - this.getWidth(), 0, this.father.getHeight() - this.getHeight());
+            this.setMoveCd (this.x, this.y);
+        }
+    }
+
     @Override
     public Vector<AvatarMethod> getMethodList () {
         return new Vector<AvatarMethod> (this.methods);
diff --git a/src/ui/avatarbd/AvatarBDPanel.java b/src/ui/avatarbd/AvatarBDPanel.java
index 5ac42b43b8..8bb76c3041 100644
--- a/src/ui/avatarbd/AvatarBDPanel.java
+++ b/src/ui/avatarbd/AvatarBDPanel.java
@@ -106,17 +106,21 @@ public class AvatarBDPanel extends TDiagramPanel {
     }
 
     public boolean actionOnRemove(TGComponent tgc) {
-        //System.out.println("Action on remove!");
-        if (tgc instanceof AvatarBDBlock) {
-            AvatarBDBlock abdb = (AvatarBDBlock)(tgc);
-            //System.out.println(" *** add tclass *** name=" + tmlt.getTaskName());
-            mgui.removeAvatarBlock(tp, abdb.getBlockName());
-            LinkedList<AvatarBDBlock> list  = abdb.getFullBlockList();
-            for(AvatarBDBlock b: list) {
-                mgui.removeAvatarBlock(tp, b.getBlockName());
+        if (tgc instanceof AvatarBDStateMachineOwner) {
+            AvatarBDStateMachineOwner abdb = (AvatarBDStateMachineOwner) tgc;
+            this.mgui.removeAvatarBlock (tp, abdb.getOwnerName());
+            if (tgc instanceof AvatarBDBlock) {
+                LinkedList<AvatarBDBlock> list  = ((AvatarBDBlock) abdb).getFullBlockList();
+                for(AvatarBDBlock b: list)
+                    mgui.removeAvatarBlock(tp, b.getBlockName());
+
+                for(AvatarBDLibraryFunction b: ((AvatarBDBlock) abdb).getFullLibraryFunctionList())
+                    mgui.removeAvatarBlock (tp, b.getFunctionName());
             }
+
             return true;
         }
+
         return false;
     }
 
@@ -486,7 +490,7 @@ public class AvatarBDPanel extends TDiagramPanel {
         return null;
     }
 
-    public Vector getAttributesOfDataType(String _name) {
+    public Vector<TAttribute> getAttributesOfDataType(String _name) {
         for (TGComponent tgc: this.componentList)
             if (tgc instanceof AvatarBDDataType) {
                 AvatarBDDataType adt = (AvatarBDDataType)tgc;
diff --git a/src/ui/avatarbd/AvatarBDPragma.java b/src/ui/avatarbd/AvatarBDPragma.java
index 370ec031f8..95f7df21e3 100755
--- a/src/ui/avatarbd/AvatarBDPragma.java
+++ b/src/ui/avatarbd/AvatarBDPragma.java
@@ -160,12 +160,23 @@ public class AvatarBDPragma extends TGCScalableWithoutInternalComponent {
         int h  = g.getFontMetrics().getHeight();
         Color c = g.getColor();
 
-        int desiredWidth = minWidth;
-	desiredWidth = Math.max(desiredWidth, 2*g.getFontMetrics().stringWidth("Property Pragma") + marginX+ textX);
-	
-        for(int i=0; i< values.length; i++) {
-            desiredWidth = Math.max(desiredWidth, g.getFontMetrics().stringWidth(values[i]) + marginX+textX);
-        }
+        /* !!! WARNING !!!
+         * Note that here we use TDiagramPanel.stringWidth instead of graph.getFontMetrics().stringWidth
+         * Indeed, TGComponent (and so TGCNote) objects are drawn twice when the bird view is enabled.
+         * First, they are drawn on the TDiagramPanel and then on the bird view.
+         * Problem is that we compute the width for this element (which will be further used for isOnMe
+         * for instance) so that it matches the text inside of it. It is thus important that the width of
+         * the strings - that will affect the width of the component - is the same each time it is drawn.
+         * For some unknown reasons, even if the current Font of the Graphics object is the same, the
+         * FontMetrics object derived from it is not the same (ascent and descent are different) so for
+         * the same text and the same Font, width would still change if we used the FontMetrics fetched
+         * from the Graphics object.
+         * Thus we use a saved FontMetrics object in TDiagramPanel that only changes when zoom changes.
+         */
+	int desiredWidth = Math.max(this.minWidth, 2*this.tdp.stringWidth(g, "Property Pragma") + marginX+ textX);
+        for(int i=0; i< values.length; i++)
+            desiredWidth = Math.max(desiredWidth, this.tdp.stringWidth(g, values[i]) + marginX+textX);
+
 //	currentFontSize= 5;
         int desiredHeight = ((models.size() + properties.size()+4)*currentFontSize) + textY + 1;
 
@@ -195,10 +206,10 @@ public class AvatarBDPragma extends TGCScalableWithoutInternalComponent {
         }
         g.fillPolygon(px, py, 4);
 
-        g.setColor(Color.black);	
+        g.setColor(c);	
 	
 	int i = 1;
-	Font heading = new Font("heading", Font.BOLD, 14);
+	Font heading = new Font("heading", Font.BOLD, this.tdp.getFontSize ()*7/6);
 	g.setFont(heading);
 	g.drawString("Model Pragma", x+textX, y+textY + currentFontSize);
 	g.setFont(fold);
@@ -206,6 +217,7 @@ public class AvatarBDPragma extends TGCScalableWithoutInternalComponent {
 	    g.drawString(s, x + textX, y + textY + (i+1)* currentFontSize);
 	    i++;
 	}
+        // FIXME: why the empty string ?
 	g.drawString(" ", x+ textX, y+ textY+(i+1)*currentFontSize);
 	i++;
 	g.drawLine(x, y+textY/2+i*currentFontSize, x+width, y+textY/2+i*currentFontSize);
diff --git a/src/ui/avatarbd/AvatarBDStateMachineOwner.java b/src/ui/avatarbd/AvatarBDStateMachineOwner.java
index 0eeaf4839e..1ab012c943 100755
--- a/src/ui/avatarbd/AvatarBDStateMachineOwner.java
+++ b/src/ui/avatarbd/AvatarBDStateMachineOwner.java
@@ -43,6 +43,7 @@ import java.util.Vector;
 import ui.AvatarSignal;
 import ui.AvatarMethod;
 import ui.TAttribute;
+import ui.avatarsmd.AvatarSMDPanel;
 
 /**
  * This interface represent block diagram elements that are associated to a state machine.
@@ -64,4 +65,5 @@ public interface AvatarBDStateMachineOwner {
     public Vector<AvatarMethod> getAllMethodList ();
 
     public String getOwnerName ();
+    public AvatarSMDPanel getAvatarSMDPanel ();
 }
diff --git a/src/ui/avatarsmd/AvatarSMDLibraryFunctionCall.java b/src/ui/avatarsmd/AvatarSMDLibraryFunctionCall.java
new file mode 100644
index 0000000000..f2102d5e75
--- /dev/null
+++ b/src/ui/avatarsmd/AvatarSMDLibraryFunctionCall.java
@@ -0,0 +1,277 @@
+/* Copyright or (C) or Copr. GET / ENST, Telecom-Paris, Ludovic Apvrille
+ *
+ * ludovic.apvrille AT enst.fr
+ *
+ * This software is a computer program whose purpose is to allow the
+ * edition of TURTLE analysis, design and deployment diagrams, to
+ * allow the generation of RT-LOTOS or Java code from this diagram,
+ * and at last to allow the analysis of formal validation traces
+ * obtained from external tools, e.g. RTL from LAAS-CNRS and CADP
+ * from INRIA Rhone-Alpes.
+ *
+ * This software is governed by the CeCILL  license under French law and
+ * abiding by the rules of distribution of free software.  You can  use,
+ * modify and/ or redistribute the software under the terms of the CeCILL
+ * license as circulated by CEA, CNRS and INRIA at the following URL
+ * "http://www.cecill.info".
+ *
+ * As a counterpart to the access to the source code and  rights to copy,
+ * modify and redistribute granted by the license, users are provided only
+ * with a limited warranty  and the software's author,  the holder of the
+ * economic rights,  and the successive licensors  have only  limited
+ * liability.
+ *
+ * In this respect, the user's attention is drawn to the risks associated
+ * with loading,  using,  modifying and/or developing or reproducing the
+ * software by the user in light of its specific status of free software,
+ * that may mean  that it is complicated to manipulate,  and  that  also
+ * therefore means  that it is reserved for developers  and  experienced
+ * professionals having in-depth computer knowledge. Users are therefore
+ * encouraged to load and test the software's suitability as regards their
+ * requirements in conditions enabling the security of their systems and/or
+ * data to be ensured and,  more generally, to use and operate it in the
+ * same conditions as regards security.
+ *
+ * The fact that you are presently reading this means that you have had
+ * knowledge of the CeCILL license and that you accept its terms.
+ */
+
+package ui.avatarsmd;
+
+import java.util.LinkedList;
+
+import java.awt.Graphics;
+import java.awt.Font;
+import java.awt.Color;
+
+import ui.TAttribute;
+import ui.AvatarSignal;
+import ui.BasicErrorHighlight;
+import ui.TGCScalableWithoutInternalComponent;
+import ui.TGComponent;
+import ui.TDiagramPanel;
+import ui.TGConnectingPoint;
+import ui.IconManager;
+import ui.ErrorHighlight;
+import ui.ColorManager;
+import ui.TGComponentManager;
+import ui.avatarbd.AvatarBDLibraryFunction;
+
+/**
+* @version 1.0 04.18.2016
+* @author Florian LUGOU
+*/
+public class AvatarSMDLibraryFunctionCall extends TGCScalableWithoutInternalComponent implements BasicErrorHighlight {
+    private LinkedList<TAttribute> parameters;
+    private LinkedList<AvatarSignal> signals;
+    private LinkedList<TAttribute> returnAttributes;
+
+    private AvatarBDLibraryFunction libraryFunction;
+
+    protected int lineLength = 5;
+    protected int textX =  5;
+    protected int textY =  15;
+    protected int arc = 5;
+    protected int linebreak = 10;
+
+    protected int stateOfError = 0; // Not yet checked
+
+    public AvatarSMDLibraryFunctionCall (int _x, int _y, int _minX, int _maxX, int _minY, int _maxY, boolean _pos, TGComponent _father, TDiagramPanel _tdp)  {
+        super(_x, _y, _minX, _maxX, _minY, _maxY, _pos, _father, _tdp);
+
+        this.width = 200;
+        this.height = 20;
+        this.minWidth = 30;
+
+        this.nbConnectingPoint = 2;
+        this.connectingPoint = new TGConnectingPoint[2];
+        this.connectingPoint[0] = new AvatarSMDConnectingPoint (this, 0, -lineLength, true, false, 0.5, 0.0);
+        this.connectingPoint[1] = new AvatarSMDConnectingPoint (this, 0, lineLength, false, true, 0.5, 1.0);
+
+        this.addTGConnectingPointsComment();
+
+        this.moveable = true;
+        this.editable = true;
+        this.removable = true;
+        this.userResizable = true;
+
+        this.name = "Library function call";
+        this.value = "";
+
+        // TODO: change that
+        this.myImageIcon = IconManager.imgic904;
+    }
+
+    public void internalDrawing(Graphics graph) {
+        Font font = graph.getFont ();
+
+        this.value = this.prettyPrint ();
+
+        int stringWidth = graph.getFontMetrics().stringWidth (this.value);
+        int elementWidth = Math.max (this.minWidth, stringWidth + 2 * this.textX);
+        if (elementWidth != this.width && !this.tdp.isScaled()) {
+            this.setCd (x + this.width/2 - elementWidth/2, y);
+            this.width = elementWidth;            //updateConnectingPoints();
+        }
+
+        Color c = graph.getColor();
+        if (this.stateOfError > 0)  {
+            switch(stateOfError) {
+                case ErrorHighlight.OK:
+                    graph.setColor (ColorManager.AVATAR_LIBRARY_FUNCTION_CALL);
+                    break;
+                default:
+                    graph.setColor (ColorManager.UNKNOWN_BOX_ACTION);
+            }
+
+            // Making the polygon
+            int [] px1 = {this.x, this.x+this.linebreak, this.x+this.width-this.linebreak, this.x+this.width, this.x+this.width-this.linebreak, this.x+this.linebreak};
+            int [] py1 = {this.y+this.height/2, this.y, this.y, this.y+this.height/2, this.y+this.height, this.y+this.height};
+            graph.fillPolygon(px1, py1, 6);
+            graph.setColor(c);
+        }
+
+        graph.drawLine(this.x+this.linebreak, this.y, this.x+this.width-this.linebreak, this.y);
+        graph.drawLine(this.x+this.linebreak, this.y+this.height, this.x+this.width-this.linebreak, this.y+this.height);
+        graph.drawLine(this.x+this.linebreak, this.y, this.x, this.y+this.height/2);
+        graph.drawLine(this.x, this.y+this.height/2, this.x+this.linebreak, this.y+this.height);
+        graph.drawLine(this.x+this.width-this.linebreak, this.y, this.x+this.width, this.y+this.height/2);
+        graph.drawLine(this.x+this.width-this.linebreak, this.y+this.height, this.x+this.width, this.y+this.height/2);
+
+        graph.drawLine (this.x+this.width/2, this.y, this.x+this.width/2, this.y - this.lineLength);
+        graph.drawLine (this.x+this.width/2, this.y+this.height, this.x+this.width/2, this.y + this.lineLength + this.height);
+
+        graph.drawString (this.value, this.x + (this.width - stringWidth) / 2 , this.y + this.textY);
+    }
+
+    public TGComponent isOnMe(int _x, int _y) {
+        if (_x < this.x || _x > this.x + this.width || _y > this.y + this.height || _y < this.y)
+            return null;
+
+        if (_x < this.x + this.linebreak) {
+            int x0 = _x - this.x;
+            int y0 = _y - this.y - this.height/2;
+            if (y0 >= - this.height/(2*this.linebreak)*this.x && y0 <= this.height/(2*this.linebreak)*this.x)
+                return this;
+            return null;
+        }
+
+        if (_x > this.x + this.width - this.linebreak) {
+            int x0 = _x - this.x - this.width + this.linebreak;
+            int y0 = _y - this.y - this.height/2;
+            if (y0 >= - this.height/2 + this.height/(2*this.linebreak)*x0 && y0 <= this.height/2 - this.height/(2*this.linebreak)*x0)
+                return this;
+            return null;
+        }
+
+        return this;
+    }
+
+    /*
+
+    public String getSignalName() {
+        if (value == null) {
+            return null;
+        }
+
+        if (value.length() == 0) {
+            return "";
+        }
+
+        int index = value.indexOf('(');
+        if (index == -1) {
+            return value;
+        }
+        return value.substring(0, index).trim();
+    }
+
+    // Return -1 in case of error
+    public int getNbOfValues() {
+        return AvatarSignal.getNbOfValues(value);
+    }
+
+    // Return null in case of error
+    public String getValue(int _index) {
+        return AvatarSignal.getValue(value, _index);
+    }
+
+    public boolean editOndoubleClick(JFrame frame) {
+        Vector signals = tdp.getMGUI().getAllSignals();
+        //TraceManager.addDev("Nb of signals:" + signals.size());
+
+        JDialogAvatarSignal jdas = new JDialogAvatarSignal(frame, "Setting send signal",  value, signals, true);
+        jdas.setSize(350, 300);
+        GraphicLib.centerOnParent(jdas);
+        jdas.show(); // blocked until dialog has been closed
+
+        if (jdas.hasBeenCancelled()) {
+            return false;
+        }
+
+        String val = jdas.getSignal();
+
+        if (val.indexOf('(') == -1) {
+            val += "()";
+        }
+
+        // valid signal?
+        if (AvatarSignal.isAValidUseSignal(val)) {
+            value = val;
+            return true;
+        }
+
+        JOptionPane.showMessageDialog(frame,
+                                      "Could not change the setting of the signal: invalid declaration",
+                                      "Error",
+                                      JOptionPane.INFORMATION_MESSAGE);
+        return false;
+
+    }
+    */
+
+    public String prettyPrint () {
+        if (this.libraryFunction == null)
+            return "";
+
+        StringBuilder builder = new StringBuilder ();
+        boolean first = true;
+
+        if (!this.returnAttributes.isEmpty ()) {
+            for (TAttribute attr: this.returnAttributes) {
+                if (first)
+                    first = false;
+                else
+                    builder.append (", ");
+
+                builder.append (attr.getId ());
+            }
+
+            builder.append (" = ");
+        }
+
+        builder.append (this.libraryFunction.getFunctionName ());
+        builder.append (" (");
+
+        first = true;
+        for (TAttribute attr: this.parameters) {
+            if (first)
+                first = false;
+            else
+                builder.append (", ");
+
+            builder.append (attr.getId ());
+        }
+
+        builder.append (")");
+
+        return builder.toString ();
+    }
+
+    public int getDefaultConnector() {
+        return TGComponentManager.AVATARSMD_CONNECTOR;
+    }
+
+    public void setStateAction(int _stateAction) {
+        stateOfError = _stateAction;
+    }
+}
diff --git a/src/ui/avatarsmd/AvatarSMDToolBar.java b/src/ui/avatarsmd/AvatarSMDToolBar.java
index 43d32d3e3a..0acdbb160a 100755
--- a/src/ui/avatarsmd/AvatarSMDToolBar.java
+++ b/src/ui/avatarsmd/AvatarSMDToolBar.java
@@ -69,6 +69,7 @@ public class AvatarSMDToolBar extends TToolBar {
         mgui.actions[TGUIAction.ASMD_STOP].setEnabled(b);
 		mgui.actions[TGUIAction.ASMD_SEND_SIGNAL].setEnabled(b);
         mgui.actions[TGUIAction.ASMD_RECEIVE_SIGNAL].setEnabled(b);
+        mgui.actions[TGUIAction.ASMD_LIBRARY_FUNCTION_CALL].setEnabled(b);
 		mgui.actions[TGUIAction.ASMD_PARALLEL].setEnabled(b);
 		mgui.actions[TGUIAction.ASMD_STATE].setEnabled(b);
 		mgui.actions[TGUIAction.ASMD_CHOICE].setEnabled(b);
@@ -147,6 +148,11 @@ public class AvatarSMDToolBar extends TToolBar {
         
         button = this.add(mgui.actions[TGUIAction.ASMD_RECEIVE_SIGNAL]);
         button.addMouseListener(mgui.mouseHandler);
+		
+		this.addSeparator();
+        
+        button = this.add(mgui.actions[TGUIAction.ASMD_LIBRARY_FUNCTION_CALL]);
+        button.addMouseListener(mgui.mouseHandler);
         
         
         this.addSeparator();
diff --git a/src/ui/window/JBirdPanel.java b/src/ui/window/JBirdPanel.java
index 82f30ba4b5..09f07cb169 100755
--- a/src/ui/window/JBirdPanel.java
+++ b/src/ui/window/JBirdPanel.java
@@ -50,8 +50,6 @@ import javax.swing.*;
 import java.awt.*;
 import java.awt.event.*;
 
-
-
 import ui.*;
 
 
@@ -180,4 +178,4 @@ public class JBirdPanel extends JPanel implements MouseListener, MouseMotionList
         return go;
     }
     
-}
\ No newline at end of file
+}
diff --git a/src/ui/window/JDialogAvatarLibraryFunction.java b/src/ui/window/JDialogAvatarLibraryFunction.java
index 67d8c54898..23186924a3 100755
--- a/src/ui/window/JDialogAvatarLibraryFunction.java
+++ b/src/ui/window/JDialogAvatarLibraryFunction.java
@@ -753,8 +753,18 @@ public class JDialogAvatarLibraryFunction extends javax.swing.JDialog implements
             a = new TAttribute(accessIndex, identifier, value, typeIndex);
         a.isAvatar = true;
 
+        int index;
+        Object old = null;
+        if (modify) {
+            index = this.listAttribute[tabIndex].getSelectedIndex ();
+            old = this.attributes[tabIndex].remove (index);
+        } else
+            index = this.attributes[tabIndex].size ();
+
         //checks whether an attribute with this identifier already belongs to the list
         if (this.attributes[0].contains (a) || this.attributes[2].contains (a) || this.attributes[3].contains (a)) {
+            if (modify)
+                this.attributes[tabIndex].add (index, old);
             JOptionPane.showMessageDialog (this,
                                           "Bad Identifier: another attribute or parameter already has the same name.",
                                           "Error",
@@ -763,33 +773,10 @@ public class JDialogAvatarLibraryFunction extends javax.swing.JDialog implements
             return;
         }
 
-        if (modify) {
-            int index = this.listAttribute[tabIndex].getSelectedIndex ();
-            this.attributes[tabIndex].remove (index);
-            this.attributes[tabIndex].add (index, a);
-            this.listAttribute[tabIndex].setListData (this.attributes[tabIndex].toArray ());
-            this.listAttribute[tabIndex].setSelectedIndex(index);
-        } else {
-            this.attributes[tabIndex].add (a);
-            this.listAttribute[tabIndex].setListData (this.attributes[tabIndex].toArray ());
-            this.listAttribute[tabIndex].setSelectedIndex(this.attributes[tabIndex].size () - 1);
-        }
-
+        this.attributes[tabIndex].add (index, a);
+        this.listAttribute[tabIndex].setListData (this.attributes[tabIndex].toArray ());
+        this.listAttribute[tabIndex].setSelectedIndex(index);
         this.listAttribute[tabIndex].requestFocus ();
-
-        /*
-        if (attributes.contains(a)) {
-            index = attributes.indexOf(a);
-            a = (TAttribute)(attributes.elementAt(index));
-            a.setAccess(i);
-            if (j == TAttribute.OTHER) {
-                a.setTypeOther(o2.toString());
-            }
-            a.setType(j);
-            a.setInitialValue(value);
-            //attributes.removeElementAt(index);
-        }
-        */
     }
 
     private void addMethod (boolean modify) {
@@ -811,11 +798,19 @@ public class JDialogAvatarLibraryFunction extends javax.swing.JDialog implements
         }
 
         am.setImplementationProvided(false);
-        
-        AvatarMethod amtmp;
+
+        int index;
+        Object old = null;
+        if (modify) {
+            index = this.listAttribute[4].getSelectedIndex ();
+            old = this.attributes[4].remove (index);
+        } else
+            index = this.attributes[4].size ();
 
         // Checks whether the same method already belongs to the list
         if (this.attributes[4].contains (am)) {
+            if (modify)
+                this.attributes[4].add (index, old);
             JOptionPane.showMessageDialog (this,
                                           "This method already exists",
                                           "Error",
@@ -824,23 +819,10 @@ public class JDialogAvatarLibraryFunction extends javax.swing.JDialog implements
             return;
         }
 
-        if (modify) {
-            int index = this.listAttribute[4].getSelectedIndex ();
-            this.attributes[4].remove (index);
-            this.attributes[4].add (index, am);
-            this.listAttribute[4].setListData (this.attributes[4].toArray ());
-            this.listAttribute[4].setSelectedIndex(index);
-        } else {
-            this.attributes[4].add (am);
-            this.listAttribute[4].setListData (this.attributes[4].toArray ());
-            this.listAttribute[4].setSelectedIndex(this.attributes[4].size () - 1);
-        }
+        this.attributes[4].add (index, am);
+        this.listAttribute[4].setListData (this.attributes[4].toArray ());
+        this.listAttribute[4].setSelectedIndex(index);
         this.listAttribute[4].requestFocus ();
-
-            /*
-        {
-        }
-        */
     }
 
     private void addSignal (boolean modify) {
@@ -861,8 +843,19 @@ public class JDialogAvatarLibraryFunction extends javax.swing.JDialog implements
             return;
         }
 
+        int index;
+        Object old = null;
+        if (modify) {
+            index = this.listAttribute[1].getSelectedIndex ();
+            old = this.attributes[1].remove (index);
+        } else
+            index = this.attributes[1].size ();
+
+
         // Checks whether the same signal already belongs to the list
         if (this.attributes[1].contains (as)) {
+            if (modify)
+                this.attributes[1].add (index, old);
             JOptionPane.showMessageDialog (this,
                                           "This signal already exists",
                                           "Error",
@@ -871,26 +864,10 @@ public class JDialogAvatarLibraryFunction extends javax.swing.JDialog implements
             return;
         }
 
-        if (modify) {
-            int index = this.listAttribute[1].getSelectedIndex ();
-            this.attributes[1].remove (index);
-            this.attributes[1].add (index, as);
-            this.listAttribute[1].setListData (this.attributes[1].toArray ());
-            this.listAttribute[1].setSelectedIndex(index);
-        } else {
-            this.attributes[1].add(as);
-            this.listAttribute[1].setListData(this.attributes[1].toArray ());
-            this.listAttribute[1].setSelectedIndex(this.attributes[1].size () - 1);
-        }
-
+        this.attributes[1].add (index, as);
+        this.listAttribute[1].setListData (this.attributes[1].toArray ());
+        this.listAttribute[1].setSelectedIndex(index);
         this.listAttribute[1].requestFocus ();
-
-                /*
-            {
-                signals.removeElementAt(index);
-                signals.add(index, as);
-            }
-            */
     }
 
     private void handleModify () {
-- 
GitLab