/**
   * Builds the FSTModel of the feature project and creates a list of all directives with valid
   * colors
   *
   * @return the directive list
   */
  private void createDirectiveList() {
    directiveMap.clear();
    validDirectiveList.clear();
    FSTModel model = project.getFSTModel();
    if (model == null) {
      composer.buildFSTModel();
      model = project.getFSTModel();
    }
    if (model == null) {
      return;
    }

    int index = 0;
    for (FSTFeature fstFeature : model.getFeatures()) {
      for (FSTRole role : fstFeature.getRoles()) {
        if (file.equals(role.getFile())) {
          for (FSTDirective dir : role.getDirectives()) {
            directiveMap.put(dir.getId(), dir);
            index++;
          }
        }
      }
    }

    for (int i = 0; i < index; i++) {
      FSTDirective dir = directiveMap.get(i);
      if (dir != null && ColorList.isValidColor(dir.getColor())) {
        validDirectiveList.add(dir);
      }
    }
  }
Example #2
0
 private int getLastChildLine(FSTDirective directive, int lastLine) {
   for (FSTDirective child : directive.getChildren()) {
     int childEnd = child.getEndLine();
     if (child.getEndLength() > 0) {
       childEnd++;
     }
     lastLine = Math.max(childEnd, lastLine);
     lastLine = Math.max(getLastChildLine(child, lastLine), lastLine);
   }
   return lastLine;
 }
Example #3
0
  private boolean hasChildAtLine(FSTDirective directive, int line, boolean hasValidColor) {
    for (FSTDirective child : directive.getChildren()) {
      int start = child.getStartLine();
      int end = child.getEndLine();

      if (line >= start
          && line <= end
          && (!hasValidColor || child.getColor() != FeatureColor.NO_COLOR.getValue())) {
        return true;
      }
      if (hasChildAtLine(child, line, hasValidColor)) {
        return true;
      }
    }
    return false;
  }
Example #4
0
 /** Creates a new overview ruler annotation. */
 private void createOverViewRuler(
     AnnotationModelEvent event, FSTDirective directive, final int color, Position newPos) {
   ColorAnnotation ca = new ColorAnnotation(color, newPos, ColorAnnotation.TYPE_OVERVIEW);
   ca.setText(directive.toString());
   annotations.add(ca);
   event.annotationAdded(ca);
 }
Example #5
0
  /**
   * Builds the FSTModel of the feature project and creates a list of all directives with valid
   * colors
   *
   * @return the directive list
   */
  private void createDirectiveList() {
    directiveMap.clear();
    validDirectiveList.clear();
    FSTModel model = project.getFSTModel();
    if (model == null || model.getClasses().isEmpty()) {
      composer.buildFSTModel();
      model = project.getFSTModel();
    }
    if (model == null) {
      return;
    }

    for (FSTFeature fstFeature : model.getFeatures()) {
      for (FSTRole role : fstFeature.getRoles()) {
        if (file.equals(role.getFile())) {
          for (FSTDirective dir : role.getDirectives()) {
            directiveMap.put(dir.getId(), dir);
            validDirectiveList.add(dir);
          }
        }
      }
    }
  }
  @Override
  public LinkedList<FSTDirective> buildModelDirectivesForFile(Vector<String> lines) {
    // for preprocessor outline
    Stack<FSTDirective> directivesStack = new Stack<FSTDirective>();
    LinkedList<FSTDirective> directivesList = new LinkedList<FSTDirective>();
    int id = 0;

    for (int i = 0; i < lines.size(); i++) {
      String line = lines.get(i);

      // if line is preprocessor directive
      if (containsRegex(line, "//\\s*#")) {
        FSTDirectiveCommand command = null;

        if (containsRegex(line, "//\\s*#if[ (]")) { // 1
          command = FSTDirectiveCommand.IF;
        } else if (containsRegex(line, "//\\s*#ifdef[ (]")) { // 2
          command = FSTDirectiveCommand.IFDEF;
        } else if (containsRegex(line, "//\\s*#ifndef[ (]")) { // 3
          command = FSTDirectiveCommand.IFNDEF;
        } else if (containsRegex(line, "//\\s*#elif[ (]")) { // 4
          command = FSTDirectiveCommand.ELIF;
        } else if (containsRegex(line, "//\\s*#elifdef[ (]")) { // 5
          command = FSTDirectiveCommand.ELIFDEF;
        } else if (containsRegex(line, "//\\s*#elifndef[ (]")) { // 6
          command = FSTDirectiveCommand.ELIFNDEF;
        } else if (containsRegex(line, "//\\s*#else")) { // 7
          command = FSTDirectiveCommand.ELSE;
        } else if (containsRegex(line, "//\\s*#condition[ (]")) { // 8
          command = FSTDirectiveCommand.CONDITION;
        } else if (containsRegex(line, "//\\s*#define[ (]")) { // 9
          command = FSTDirectiveCommand.DEFINE;
        } else if (containsRegex(line, "//\\s*#undefine[ (]")) { // 10
          command = FSTDirectiveCommand.UNDEFINE;
        } else if (!containsRegex(line, "//\\s*#endif")) { // 11
          continue;
        }

        if (command == null) {
          if (!directivesStack.isEmpty()) {
            directivesStack.peek().setEndLine(i, line.length());
            while (!directivesStack.isEmpty()) {
              FSTDirective parent = directivesStack.pop();
              if (parent.getCommand() != FSTDirectiveCommand.ELIF
                  && parent.getCommand() != FSTDirectiveCommand.ELIFDEF
                  && parent.getCommand() != FSTDirectiveCommand.ELIFNDEF
                  && parent.getCommand() != FSTDirectiveCommand.ELSE) {
                break;
              }
            }
          }
        } else {
          FSTDirective directive = new FSTDirective();

          if (command == FSTDirectiveCommand.ELSE) {
            if (!directivesStack.isEmpty()) {
              directivesStack.peek().setEndLine(i, 0);
              directive.setFeatureName(directivesStack.peek().getFeatureName());
            }
          } else if (command == FSTDirectiveCommand.ELIF
              || command == FSTDirectiveCommand.ELIFDEF
              || command == FSTDirectiveCommand.ELIFNDEF) {
            if (!directivesStack.isEmpty()) {
              directivesStack.peek().setEndLine(i, 0);
            }
          }

          directive.setCommand(command);

          Matcher m = patternCommands.matcher(line);
          line = m.replaceAll("").trim();

          if (directive.getFeatureName() == null) {
            directive.setFeatureName(getFeatureName(line));
          }
          directive.setExpression(line);
          directive.setStartLine(i, 0);
          directive.setId(id++);

          if (directivesStack.isEmpty()) {
            directivesList.add(directive);
          } else {
            directivesStack.peek().addChild(directive);
          }

          if (command != FSTDirectiveCommand.DEFINE
              && command != FSTDirectiveCommand.UNDEFINE
              && command != FSTDirectiveCommand.CONDITION) directivesStack.push(directive);
        }
      }
    }
    return directivesList;
  }
  /** Creates the color annotations from the FSTDirectives. */
  private void createAnnotations() {
    AnnotationModelEvent event = new AnnotationModelEvent(this);

    Iterator<FSTDirective> it = validDirectiveList.descendingIterator();
    while (it.hasNext()) {
      FSTDirective dir = it.next();
      try {
        int startline = dir.getStartLine();
        int endline = dir.getEndLine();
        for (int i = startline; i <= endline; i++) {
          if (i < endline || dir.getEndLength() > 0) {
            int lineLength = document.getLineLength(i);
            int lineOffset = document.getLineOffset(i);

            if (i == endline) {
              lineLength = dir.getEndLength();
            }
            if (i == startline) {
              lineOffset += dir.getStartOffset();
              lineLength -= dir.getStartOffset();
            }

            Position newPos = new Position(lineOffset, lineLength);

            if (!annotatedPositions.containsKey(i)) {
              if (!ColorList.isValidColor(dir.getColor())) break;
              ColorAnnotation ca =
                  new ColorAnnotation(
                      dir.getColor(),
                      new Position(lineOffset, lineLength),
                      ColorAnnotation.TYPE_IMAGE);
              annotations.add(ca);
              event.annotationAdded(ca);

              if (highlighting) {
                ca =
                    new ColorAnnotation(
                        dir.getColor(),
                        newPos,
                        i == startline
                            ? ColorAnnotation.TYPE_HIGHLIGHT_OVERVIEW
                            : ColorAnnotation.TYPE_HIGHLIGHT);
                annotations.add(ca);
                event.annotationAdded(ca);
              } else if (i == startline) {
                ca = new ColorAnnotation(dir.getColor(), newPos, ColorAnnotation.TYPE_OVERVIEW);
                annotations.add(ca);
                event.annotationAdded(ca);
              }

              annotatedPositions.put(i, newPos);
            } else if (highlighting) {
              Position oldPos = annotatedPositions.get(i);
              int oldOffset = oldPos.getOffset();
              int oldLength = oldPos.getLength();
              int wholeOffset = oldOffset;
              int wholeLength = oldLength;

              if (oldOffset > lineOffset) {
                ColorAnnotation ca =
                    new ColorAnnotation(
                        dir.getColor(),
                        new Position(lineOffset, oldOffset - lineOffset),
                        ColorAnnotation.TYPE_HIGHLIGHT);
                annotations.add(ca);
                event.annotationAdded(ca);
                wholeOffset = lineOffset;
                wholeLength += oldOffset - lineOffset;
              }
              int newOffset = oldOffset + oldLength;
              int newLength = lineLength - (newOffset - lineOffset);
              if (newLength > 0) {
                newPos.setOffset(newOffset);
                newPos.setLength(newLength);

                ColorAnnotation ca =
                    new ColorAnnotation(dir.getColor(), newPos, ColorAnnotation.TYPE_HIGHLIGHT);
                annotations.add(ca);
                event.annotationAdded(ca);

                wholeLength += newLength;
              }
              annotatedPositions.put(i, new Position(wholeOffset, wholeLength));
            }
          }
        }
      } catch (BadLocationException e) {
        UIPlugin.getDefault().logError(e);
      }
    }

    fireModelChanged(event);
  }
  /**
   * Assigns the mapped colors to the FSTDirectives from the changed document.
   *
   * @return the directive list
   */
  private void updateDirectives() {
    ListIterator<FSTDirective> newDirIt = getNewDirectives().listIterator(0);

    while (newDirIt.hasNext()) {
      FSTDirective newDir = newDirIt.next();
      FSTDirective oldDir = directiveMap.get(newDir.getId());

      if (oldDir != null
          && newDir.getCommand() == oldDir.getCommand()
          && newDir.getFeatureName().equals(oldDir.getFeatureName())) {

        oldDir.setStartLine(newDir.getStartLine(), newDir.getStartOffset());
        oldDir.setEndLine(newDir.getEndLine(), newDir.getEndLength());
      } else {
        directiveMap.clear();
        return;
      }

      if (newDir.hasChildren()) {
        for (FSTDirective newDirChild : newDir.getChildrenList()) {
          newDirIt.add(newDirChild);
          newDirIt.previous();
        }
      }
    }
  }
Example #9
0
  /** Creates the color annotations from the FSTDirectives. */
  private void createAnnotations() {
    AnnotationModelEvent event = new AnnotationModelEvent(this);

    for (FSTDirective directive : validDirectiveList) {
      if (directive == null) {
        continue;
      }
      try {
        int startline = directive.getStartLine();
        int endline = getLastChildLine(directive, directive.getEndLine());
        final int color = directive.getColor();
        int overViewStartOffset = document.getLineOffset(startline);
        int overViewLength = 0;
        for (int line = startline; line <= endline; line++) {
          int length = document.getLineLength(line);
          if (line < endline || directive.getEndLength() > 0) {
            int lineOffset = document.getLineOffset(line);

            if (line == directive.getEndLine()) {
              length = directive.getEndLength();
            }
            if (line == startline) {
              lineOffset += directive.getStartOffset();
              length -= directive.getStartOffset();
            }

            if (hasChildAtLine(directive, line)) {
              length = 1;
            }

            if (overViewStartOffset != -1 && hasChildAtLineWithColor(directive, line)) {
              Position overViewPos = new Position(overViewStartOffset, overViewLength);
              createOverViewRuler(event, directive, color, overViewPos);
              overViewStartOffset = -1;
              overViewLength = 0;
            } else if (!hasChildAtLineWithColor(directive, line)) {
              if (overViewStartOffset == -1) {
                overViewStartOffset = document.getLineOffset(line);
              }
              overViewLength += document.getLineLength(line);
            }

            FSTDirective parent = directive.getParent();
            while (parent != null) {
              lineOffset++;
              if (length > 1) {
                length--;
              }
              parent = parent.getParent();
            }
            Position newPos = new Position(lineOffset, length);

            if (!hasChildAtLine(directive, line)) {
              // bar at the left of the editor
              ColorAnnotation ca = new ColorAnnotation(color, newPos, ColorAnnotation.TYPE_IMAGE);
              ca.setText(directive.toString());
              annotations.add(ca);
              event.annotationAdded(ca);
            }
            if (!hasChildAtLine(directive, line)) {
              // bar at the right of the editor

            }
            if (highlighting) {
              // background colors
              ColorAnnotation ca =
                  new ColorAnnotation(color, newPos, ColorAnnotation.TYPE_HIGHLIGHT);
              ca.setText(directive.toDependencyString());
              annotations.add(ca);
              event.annotationAdded(ca);
            }
          }
        }
        if (overViewStartOffset != -1) {
          Position overViewPos = new Position(overViewStartOffset, overViewLength);
          createOverViewRuler(event, directive, color, overViewPos);
          overViewStartOffset = -1;
          overViewLength = 0;
        }
      } catch (BadLocationException e) {
        LogService.getInstance().log(LogLevel.DEBUG, e.getMessage());
      }
    }

    fireModelChanged(event);
  }
  @Override
  public Object[] getChildren(Object parentElement) {
    Object[] obj = null;
    if (parentElement instanceof FSTClass) {
      // get all fields, methods, directives and invariants
      final TreeSet<FSTMethod> methods = new TreeSet<FSTMethod>();
      final TreeSet<FSTField> fields = new TreeSet<FSTField>();
      final TreeSet<FSTInvariant> invariants = new TreeSet<FSTInvariant>();
      final TreeSet<FSTDirective> directives = new TreeSet<FSTDirective>();
      final TreeSet<FSTClassFragment> innerClasses = new TreeSet<FSTClassFragment>();

      for (FSTRole role : ((FSTClass) parentElement).getRoles()) {
        invariants.addAll(role.getClassFragment().getInvariants());
        for (FSTMethod fstMethod : role.getMethods()) {
          if (fstMethod.getParent() instanceof FSTClassFragment) methods.add(fstMethod);
        }
        fields.addAll(role.getFields());
        TreeSet<FSTDirective> roleDirectives = role.getDirectives();
        for (FSTDirective directive : roleDirectives) {
          if (directive.getParent() == null) {
            directives.add(directive);
          }
        }
        innerClasses.addAll(role.getInnerClasses());
      }

      obj =
          new IRoleElement
              [methods.size()
                  + fields.size()
                  + invariants.size()
                  + directives.size()
                  + innerClasses.size()];
      int pos = 0;
      System.arraycopy(invariants.toArray(), 0, obj, pos, invariants.size());
      System.arraycopy(fields.toArray(), 0, obj, pos += invariants.size(), fields.size());
      System.arraycopy(methods.toArray(), 0, obj, pos += fields.size(), methods.size());
      System.arraycopy(directives.toArray(), 0, obj, pos += methods.size(), directives.size());
      System.arraycopy(
          innerClasses.toArray(), 0, obj, pos += directives.size(), innerClasses.size());

      return filter(obj);
    } else if (parentElement instanceof FSTMethod) {
      // get all the roles that belong to a method

      Set<FSTRole> roleList = new HashSet<FSTRole>();
      Set<FSTMethod> methods = new HashSet<FSTMethod>();
      for (FSTRole role : ((FSTMethod) parentElement).getRole().getFSTClass().getRoles()) {
        for (FSTMethod m : role.getAllMethods()) {
          if ( // m.isOwn(role.file) &&
          // ((FSTMethod)parentElement).isOwn(role.file) &&
          m.getFullName().equals(((FSTMethod) parentElement).getFullName())) {
            if (m.hasContract()) {
              roleList.add(
                  new FSTContractedRole(role.getFile(), role.getFeature(), role.getFSTClass()));
            } else {
              roleList.add(role);
            }
            methods.add(m);
            break;
          }
        }
      }

      List<String> featureOrder =
          CorePlugin.getFeatureProject(((FSTMethod) parentElement).getRole().getFile())
              .getFeatureModel()
              .getFeatureOrderList();

      if (((FSTMethod) parentElement).getFSTDirectives().size() == 0) {
        obj = new FSTRole[roleList.size()];
        int index = 0;
        for (String featureName : featureOrder) {

          for (Iterator<FSTRole> it = roleList.iterator(); it.hasNext(); ) {
            FSTRole next = it.next();
            if (next.getFeature().getName().equals(featureName)) {
              obj[index++] = next;
              it.remove();
              break;
            }
          }
        }
      } else {
        List<FSTDirective> dirs = new ArrayList<>();
        for (FSTRole role : roleList) {
          if (role.getMethods().contains(parentElement)) {
            // equals works correct?
            for (FSTMethod method : role.getMethods()) {
              if (method.equals(parentElement)) {
                dirs.addAll(method.getFSTDirectives());
                break;
              }
            }
          }
        }
        return dirs.toArray();
      }

    } else if (parentElement instanceof FSTInvariant) {
      // get all the roles that belong to an invariant
      LinkedList<FSTRole> roleList = new LinkedList<FSTRole>();
      for (FSTRole role : ((FSTInvariant) parentElement).getRole().getFSTClass().getRoles()) {
        for (FSTInvariant i : role.getClassFragment().getInvariants()) {
          if (((FSTInvariant) parentElement).getFullName().equals(i.getFullName())) {
            roleList.add(role);
            break;
          }
        }
      }

      return filter(roleList.toArray());
    } else if (parentElement instanceof FSTField) {
      // get all the roles that belong to a field
      LinkedList<FSTRole> roleList = new LinkedList<FSTRole>();
      for (FSTRole role : ((FSTField) parentElement).getRole().getFSTClass().getRoles()) {
        for (FSTField f : role.getAllFields()) {
          if (f.getFullName().equals(((FSTField) parentElement).getFullName())) {
            roleList.add(role);
            break;
          }
        }
      }
      return filter(roleList.toArray());
    } else if (parentElement instanceof FSTDirective) {
      return ((FSTDirective) parentElement).getRoleElementChildren();
    } else if (parentElement instanceof FSTClassFragment) {
      final TreeSet<FSTMethod> methods = new TreeSet<FSTMethod>();
      final TreeSet<FSTField> fields = new TreeSet<FSTField>();
      final TreeSet<FSTClassFragment> innerClasses = new TreeSet<FSTClassFragment>();
      final TreeSet<FSTInvariant> invariants = new TreeSet<FSTInvariant>();

      FSTClassFragment innerClassCast = (FSTClassFragment) parentElement;

      invariants.addAll(innerClassCast.getInvariants());
      LinkedList<FSTClassFragment> allFragments =
          innerClassCast.getRole().getAllEqualFSTFragments(innerClassCast);
      for (FSTClassFragment fstClassFragment : allFragments) {
        methods.addAll(fstClassFragment.getMethods());
        fields.addAll(fstClassFragment.getFields());
      }
      innerClasses.addAll(innerClassCast.getInnerClasses());

      obj =
          new IRoleElement
              [methods.size() + fields.size() + invariants.size() + innerClasses.size()];
      int pos = 0;
      System.arraycopy(invariants.toArray(), 0, obj, pos, invariants.size());
      System.arraycopy(fields.toArray(), 0, obj, pos += invariants.size(), fields.size());
      System.arraycopy(methods.toArray(), 0, obj, pos += fields.size(), methods.size());
      System.arraycopy(innerClasses.toArray(), 0, obj, pos += methods.size(), innerClasses.size());
    }

    return filter(obj);
  }