/* * ****************************************************************************** * MontiCore Language Workbench * Copyright (c) 2015, MontiCore, All rights reserved. * * This project is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 3.0 of the License, or (at your option) any later version. * This library is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public * License along with this project. If not, see <http://www.gnu.org/licenses/>. * ****************************************************************************** */ package de.monticore.types.prettyprint; import java.util.Iterator; import de.monticore.literals.prettyprint.LiteralsPrettyPrinterConcreteVisitor; import de.monticore.prettyprint.IndentPrinter; import de.monticore.types.types._ast.ASTComplexArrayType; import de.monticore.types.types._ast.ASTComplexReferenceType; import de.monticore.types.types._ast.ASTConstantsTypes; import de.monticore.types.types._ast.ASTPrimitiveArrayType; import de.monticore.types.types._ast.ASTPrimitiveType; import de.monticore.types.types._ast.ASTQualifiedName; import de.monticore.types.types._ast.ASTSimpleReferenceType; import de.monticore.types.types._ast.ASTTypeArguments; import de.monticore.types.types._ast.ASTTypeParameters; import de.monticore.types.types._ast.ASTTypeVariableDeclaration; import de.monticore.types.types._ast.ASTTypesNode; import de.monticore.types.types._ast.ASTVoidType; import de.monticore.types.types._ast.ASTWildcardType; import de.monticore.types.types._visitor.TypesVisitor; import de.se_rwth.commons.Names; /** * This class is responsible for pretty-printing types of the common type system. It is implemented * using the Visitor pattern. The Visitor pattern traverses a tree in depth first, the visit and * ownVisit-methods are called when a node is traversed, the endVisit methods are called when the * whole subtree of a node has been traversed. The ownVisit-Methods stop the automatic traversal * order and allow to explictly visit subtrees by calling getVisitor().startVisit(ASTNode) * * @author Martin Schindler */ public class TypesPrettyPrinterConcreteVisitor extends LiteralsPrettyPrinterConcreteVisitor implements TypesVisitor { private TypesVisitor realThis = this; /** * Constructor. * * @param parent the parent pretty printer, needed to give control to the embedded pretty printer * when embedding is detected. * @param printer the printer to write to. */ public TypesPrettyPrinterConcreteVisitor(IndentPrinter printer) { super(printer); } /** * Prints qualified names * * @param a qualified name */ @Override public void visit(ASTQualifiedName a) { getPrinter().print(Names.getQualifiedName(a.getParts())); } /** * Prints an array of a complex array type * * @param a array type */ @Override public void handle(ASTComplexArrayType a) { // print primitive type a.getComponentType().accept(getRealThis()); // print dimension for (int i = 0; i < a.getDimensions(); i++) { getPrinter().print("[]"); } } /** * Prints an array of a primitive array type * * @param a array type */ @Override public void handle(ASTPrimitiveArrayType a) { // print primitive type a.getComponentType().accept(getRealThis()); // print dimension for (int i = 0; i < a.getDimensions(); i++) { getPrinter().print("[]"); } } /** * Prints a void type. * * @param a void type */ @Override public void visit(ASTVoidType a) { getPrinter().print("void"); } /** * Prints a primitive type. * * @param a primitive type */ @Override public void visit(ASTPrimitiveType a) { switch (a.getPrimitive()) { case ASTConstantsTypes.BOOLEAN: getPrinter().print("boolean"); break; case ASTConstantsTypes.BYTE: getPrinter().print("byte"); break; case ASTConstantsTypes.CHAR: getPrinter().print("char"); break; case ASTConstantsTypes.SHORT: getPrinter().print("short"); break; case ASTConstantsTypes.INT: getPrinter().print("int"); break; case ASTConstantsTypes.FLOAT: getPrinter().print("float"); break; case ASTConstantsTypes.LONG: getPrinter().print("long"); break; case ASTConstantsTypes.DOUBLE: getPrinter().print("double"); break; default: getPrinter().print(""); } } /** * Prints a simple reference type * * @param a simple reference type */ @Override public void visit(ASTSimpleReferenceType a) { // print qualified name getPrinter().print(Names.getQualifiedName(a.getNames())); // optional type arguments are printed automatically by visitor concept } /** * Prints a complex reference type * * @param a complex reference type */ @Override public void handle(ASTComplexReferenceType a) { printList(a.getSimpleReferenceTypes().iterator(), "."); } /** * Prints type arguments (Generics) * * @param a type arguments */ @Override public void handle(ASTTypeArguments a) { getPrinter().print("<"); printList(a.getTypeArguments().iterator(), ", "); getPrinter().print(">"); } /** * Prints a wildcard type of a type argument (Generics) * * @param a wildcard type */ @Override public void handle(ASTWildcardType a) { getPrinter().print("?"); if (a.getUpperBound().isPresent()) { getPrinter().print(" extends "); a.getUpperBound().get().accept(getRealThis()); } else if (a.getLowerBound().isPresent()) { getPrinter().print(" super "); a.getLowerBound().get().accept(getRealThis()); } } /** * Prints type parameters (Generics) * * @param a type parameters */ @Override public void handle(ASTTypeParameters a) { if (!a.getTypeVariableDeclarations().isEmpty()) { getPrinter().print("<"); printList(a.getTypeVariableDeclarations().iterator(), ", "); getPrinter().print(">"); } } /** * Prints a type variable declaration (Generics) * * @param a type variable declaration */ @Override public void handle(ASTTypeVariableDeclaration a) { getPrinter().print(a.getName()); if (a.getUpperBounds() != null && !a.getUpperBounds().isEmpty()) { getPrinter().print(" extends "); printList(a.getUpperBounds().iterator(), "& "); } } /** * Prints a list * * @param iter iterator for the list * @param seperator string for seperating list */ protected void printList(Iterator<? extends ASTTypesNode> iter, String seperator) { // print by iterate through all items String sep = ""; while (iter.hasNext()) { getPrinter().print(sep); iter.next().accept(getRealThis()); sep = seperator; } } /** * This method prettyprints a given node from type grammar. * * @param a A node from type grammar. * @return String representation. */ public String prettyprint(ASTTypesNode a) { getPrinter().clearBuffer(); a.accept(getRealThis()); return getPrinter().getContent(); } /** * @see de.monticore.types.types._visitor.TypesVisitor#setRealThis(de.monticore.types.types._visitor.TypesVisitor) */ @Override public void setRealThis(TypesVisitor realThis) { this.realThis = realThis; } /** * @see de.monticore.types.types._visitor.TypesVisitor#getRealThis() */ @Override public TypesVisitor getRealThis() { return realThis; } }