1b8ac356ae27165d95d691e177bd8974b7dbb7953Didier Villevalois/* 2b8ac356ae27165d95d691e177bd8974b7dbb7953Didier Villevalois * Copyright (C) 2007-2010 Júlio Vilmar Gesser. 36a40f1d719abd0ecb45240fe0242b2ddf59299e4matozoid * Copyright (C) 2011, 2013-2016 The JavaParser Team. 4b8ac356ae27165d95d691e177bd8974b7dbb7953Didier Villevalois * 5b8ac356ae27165d95d691e177bd8974b7dbb7953Didier Villevalois * This file is part of JavaParser. 676f5dc9d043237e8ada0e6597d6c8d48b67f6d8fFederico Tomassetti * 7edc1e4cc00cc9feceef094cc24c472abffe5aec2Federico Tomassetti * JavaParser can be used either under the terms of 8edc1e4cc00cc9feceef094cc24c472abffe5aec2Federico Tomassetti * a) the GNU Lesser General Public License as published by 9edc1e4cc00cc9feceef094cc24c472abffe5aec2Federico Tomassetti * the Free Software Foundation, either version 3 of the License, or 10edc1e4cc00cc9feceef094cc24c472abffe5aec2Federico Tomassetti * (at your option) any later version. 1176f5dc9d043237e8ada0e6597d6c8d48b67f6d8fFederico Tomassetti * b) the terms of the Apache License 12b8ac356ae27165d95d691e177bd8974b7dbb7953Didier Villevalois * 13edc1e4cc00cc9feceef094cc24c472abffe5aec2Federico Tomassetti * You should have received a copy of both licenses in LICENCE.LGPL and 14edc1e4cc00cc9feceef094cc24c472abffe5aec2Federico Tomassetti * LICENCE.APACHE. Please refer to those files for details. 15b8ac356ae27165d95d691e177bd8974b7dbb7953Didier Villevalois * 16b8ac356ae27165d95d691e177bd8974b7dbb7953Didier Villevalois * JavaParser is distributed in the hope that it will be useful, 17b8ac356ae27165d95d691e177bd8974b7dbb7953Didier Villevalois * but WITHOUT ANY WARRANTY; without even the implied warranty of 18b8ac356ae27165d95d691e177bd8974b7dbb7953Didier Villevalois * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 19b8ac356ae27165d95d691e177bd8974b7dbb7953Didier Villevalois * GNU Lesser General Public License for more details. 20b8ac356ae27165d95d691e177bd8974b7dbb7953Didier Villevalois */ 21482bcecc5d4726b676b208d7efb64572db718cb7matozoid 229985c47e3b2a6ce9b434e787a2a035e2a7aadb4amatozoidpackage com.github.javaparser.utils; 2317229be0bf37d47628d6055ca0252d3f80724590Federico Tomassetti 24fddcb49c8fa1e47ea9a20901d5982619b63fa523matozoidimport com.github.javaparser.Position; 25482bcecc5d4726b676b208d7efb64572db718cb7matozoidimport com.github.javaparser.Range; 26df6c84c0a13f505da7fd0f64626fb5d18fd49619Nicholas Smithimport com.github.javaparser.ast.Node; 27515a9392928c14a60dc9dfa42a98198a4d877534Danny van Bruggenimport com.github.javaparser.ast.NodeList; 28df6c84c0a13f505da7fd0f64626fb5d18fd49619Nicholas Smithimport com.github.javaparser.ast.body.ClassOrInterfaceDeclaration; 29df6c84c0a13f505da7fd0f64626fb5d18fd49619Nicholas Smithimport com.github.javaparser.ast.body.FieldDeclaration; 30df6c84c0a13f505da7fd0f64626fb5d18fd49619Nicholas Smithimport com.github.javaparser.ast.body.MethodDeclaration; 31df6c84c0a13f505da7fd0f64626fb5d18fd49619Nicholas Smithimport com.github.javaparser.ast.expr.AnnotationExpr; 3263eebf8a57420ae4b79550e744624144d9f80570Maximilien CRUZimport com.github.javaparser.ast.nodeTypes.NodeWithAnnotations; 33d7828ee5f27be2f10dda026372898126aeae24b7Danny van Bruggenimport com.github.javaparser.ast.nodeTypes.NodeWithType; 34d7828ee5f27be2f10dda026372898126aeae24b7Danny van Bruggenimport com.github.javaparser.ast.type.Type; 3517229be0bf37d47628d6055ca0252d3f80724590Federico Tomassetti 36fddcb49c8fa1e47ea9a20901d5982619b63fa523matozoidimport java.util.List; 37fddcb49c8fa1e47ea9a20901d5982619b63fa523matozoid 38fddcb49c8fa1e47ea9a20901d5982619b63fa523matozoidimport static java.lang.Integer.signum; 39fddcb49c8fa1e47ea9a20901d5982619b63fa523matozoid 40a9b8b3f9589842f3bef8a48a2f0493e4fe157e65Federico Tomassettipublic final class PositionUtils { 41a9b8b3f9589842f3bef8a48a2f0493e4fe157e65Federico Tomassetti 42a9b8b3f9589842f3bef8a48a2f0493e4fe157e65Federico Tomassetti private PositionUtils() { 43a9b8b3f9589842f3bef8a48a2f0493e4fe157e65Federico Tomassetti // prevent instantiation 44a9b8b3f9589842f3bef8a48a2f0493e4fe157e65Federico Tomassetti } 45ab8df80e3284f5b991b47ae8d3b86f5730900169Federico Tomassetti 46482bcecc5d4726b676b208d7efb64572db718cb7matozoid public static <T extends Node> void sortByBeginPosition(List<T> nodes) { 47920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti sortByBeginPosition(nodes, false); 48920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti } 49920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti 50482bcecc5d4726b676b208d7efb64572db718cb7matozoid public static <T extends Node> void sortByBeginPosition(NodeList<T> nodes) { 51515a9392928c14a60dc9dfa42a98198a4d877534Danny van Bruggen sortByBeginPosition(nodes, false); 52515a9392928c14a60dc9dfa42a98198a4d877534Danny van Bruggen } 53515a9392928c14a60dc9dfa42a98198a4d877534Danny van Bruggen 54482bcecc5d4726b676b208d7efb64572db718cb7matozoid public static <T extends Node> void sortByBeginPosition(List<T> nodes, final boolean ignoringAnnotations) { 55515a9392928c14a60dc9dfa42a98198a4d877534Danny van Bruggen nodes.sort((o1, o2) -> PositionUtils.compare(o1, o2, ignoringAnnotations)); 56515a9392928c14a60dc9dfa42a98198a4d877534Danny van Bruggen } 57515a9392928c14a60dc9dfa42a98198a4d877534Danny van Bruggen 58482bcecc5d4726b676b208d7efb64572db718cb7matozoid public static boolean areInOrder(Node a, Node b) { 59920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti return areInOrder(a, b, false); 60920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti } 61920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti 62482bcecc5d4726b676b208d7efb64572db718cb7matozoid public static boolean areInOrder(Node a, Node b, boolean ignoringAnnotations) { 6324660b3320d659ae17b1ec89d6d351261a507e5dFederico Tomassetti return compare(a, b, ignoringAnnotations) <= 0; 6424660b3320d659ae17b1ec89d6d351261a507e5dFederico Tomassetti } 6524660b3320d659ae17b1ec89d6d351261a507e5dFederico Tomassetti 6624660b3320d659ae17b1ec89d6d351261a507e5dFederico Tomassetti private static int compare(Node a, Node b, boolean ignoringAnnotations) { 67ad9d33b5b22f4f4d470018e41d5c33c1eaf464c8Danny van Bruggen if(a.getRange().isPresent() && !b.getRange().isPresent()) { 68ad9d33b5b22f4f4d470018e41d5c33c1eaf464c8Danny van Bruggen return -1; 69ad9d33b5b22f4f4d470018e41d5c33c1eaf464c8Danny van Bruggen } 70ad9d33b5b22f4f4d470018e41d5c33c1eaf464c8Danny van Bruggen if(!a.getRange().isPresent() && b.getRange().isPresent()) { 71ad9d33b5b22f4f4d470018e41d5c33c1eaf464c8Danny van Bruggen return 1; 72ad9d33b5b22f4f4d470018e41d5c33c1eaf464c8Danny van Bruggen } 73ad9d33b5b22f4f4d470018e41d5c33c1eaf464c8Danny van Bruggen if (!a.getRange().isPresent() && !b.getRange().isPresent()) { 74a2152a8282754017f1c2d1eb5b45cfde7e89950bDanny van Bruggen return 0; 753c7fefbf66b94c5c7b416472d416a54651b52122Danny van Bruggen } 76920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti if (ignoringAnnotations) { 774eb0569c40debb8dd96aeb72ef24ae8ff39f579bFederico Tomassetti int signLine = signum(beginLineWithoutConsideringAnnotation(a) - beginLineWithoutConsideringAnnotation(b)); 7824660b3320d659ae17b1ec89d6d351261a507e5dFederico Tomassetti if (signLine == 0) { 794eb0569c40debb8dd96aeb72ef24ae8ff39f579bFederico Tomassetti return signum(beginColumnWithoutConsideringAnnotation(a) - beginColumnWithoutConsideringAnnotation(b)); 8024660b3320d659ae17b1ec89d6d351261a507e5dFederico Tomassetti } else { 8124660b3320d659ae17b1ec89d6d351261a507e5dFederico Tomassetti return signLine; 8224660b3320d659ae17b1ec89d6d351261a507e5dFederico Tomassetti } 83920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti } 84920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti 85d679ae1e9f30f5d7cc29e510d8b7a60593f2c0fdDanny van Bruggen Position aBegin = a.getBegin().get(); 86d679ae1e9f30f5d7cc29e510d8b7a60593f2c0fdDanny van Bruggen Position bBegin = b.getBegin().get(); 87fddcb49c8fa1e47ea9a20901d5982619b63fa523matozoid 88fddcb49c8fa1e47ea9a20901d5982619b63fa523matozoid int signLine = signum(aBegin.line - bBegin.line); 8924660b3320d659ae17b1ec89d6d351261a507e5dFederico Tomassetti if (signLine == 0) { 90fddcb49c8fa1e47ea9a20901d5982619b63fa523matozoid return signum(aBegin.column - bBegin.column); 9124660b3320d659ae17b1ec89d6d351261a507e5dFederico Tomassetti } else { 9224660b3320d659ae17b1ec89d6d351261a507e5dFederico Tomassetti return signLine; 9324660b3320d659ae17b1ec89d6d351261a507e5dFederico Tomassetti } 9417229be0bf37d47628d6055ca0252d3f80724590Federico Tomassetti } 95ab8df80e3284f5b991b47ae8d3b86f5730900169Federico Tomassetti 96920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti public static AnnotationExpr getLastAnnotation(Node node) { 97482bcecc5d4726b676b208d7efb64572db718cb7matozoid if (node instanceof NodeWithAnnotations) { 98515a9392928c14a60dc9dfa42a98198a4d877534Danny van Bruggen NodeList<AnnotationExpr> annotations = NodeList.nodeList(((NodeWithAnnotations<?>) node).getAnnotations()); 99482bcecc5d4726b676b208d7efb64572db718cb7matozoid if (annotations.isEmpty()) { 100920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti return null; 101920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti } 102920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti sortByBeginPosition(annotations); 103482bcecc5d4726b676b208d7efb64572db718cb7matozoid return annotations.get(annotations.size() - 1); 104920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti } else { 105920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti return null; 106920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti } 107920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti } 108920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti 109920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti private static int beginLineWithoutConsideringAnnotation(Node node) { 1103c7fefbf66b94c5c7b416472d416a54651b52122Danny van Bruggen return beginNodeWithoutConsideringAnnotations(node).getRange().get().begin.line; 111920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti } 112920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti 113920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti 114920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti private static int beginColumnWithoutConsideringAnnotation(Node node) { 1153c7fefbf66b94c5c7b416472d416a54651b52122Danny van Bruggen return beginNodeWithoutConsideringAnnotations(node).getRange().get().begin.column; 116920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti } 117920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti 118920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti private static Node beginNodeWithoutConsideringAnnotations(Node node) { 11934898f09a47675498ea38d7494cd7b2d29136570Ross Allan if (node instanceof MethodDeclaration || node instanceof FieldDeclaration) { 120a8f6c6d62fcbdc3506f19f11a7b89307cbf4c515Danny van Bruggen NodeWithType<?, Type> casted = (NodeWithType<?, Type>) node; 121d7828ee5f27be2f10dda026372898126aeae24b7Danny van Bruggen return casted.getType(); 122920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti } else if (node instanceof ClassOrInterfaceDeclaration) { 123920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti ClassOrInterfaceDeclaration casted = (ClassOrInterfaceDeclaration) node; 12402b3c5e03c44a9373c3a9d323c3425bdffade688Danny van Bruggen return casted.getName(); 125482bcecc5d4726b676b208d7efb64572db718cb7matozoid } else { 126920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti return node; 127920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti } 128920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti } 129920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti 130482bcecc5d4726b676b208d7efb64572db718cb7matozoid public static boolean nodeContains(Node container, Node contained, boolean ignoringAnnotations) { 1313c7fefbf66b94c5c7b416472d416a54651b52122Danny van Bruggen final Range containedRange = contained.getRange().get(); 1323c7fefbf66b94c5c7b416472d416a54651b52122Danny van Bruggen final Range containerRange = container.getRange().get(); 133482bcecc5d4726b676b208d7efb64572db718cb7matozoid if (!ignoringAnnotations || PositionUtils.getLastAnnotation(container) == null) { 134515a9392928c14a60dc9dfa42a98198a4d877534Danny van Bruggen return container.containsWithin(contained); 135920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti } 136482bcecc5d4726b676b208d7efb64572db718cb7matozoid if (!container.containsWithin(contained)) { 137920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti return false; 138920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti } 139920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti // if the node is contained, but it comes immediately after the annotations, 140920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti // let's not consider it contained 141482bcecc5d4726b676b208d7efb64572db718cb7matozoid if (container instanceof NodeWithAnnotations) { 142920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti int bl = beginLineWithoutConsideringAnnotation(container); 143920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti int bc = beginColumnWithoutConsideringAnnotation(container); 144482bcecc5d4726b676b208d7efb64572db718cb7matozoid if (bl > containedRange.begin.line) return false; 145482bcecc5d4726b676b208d7efb64572db718cb7matozoid if (bl == containedRange.begin.line && bc > containedRange.begin.column) return false; 146482bcecc5d4726b676b208d7efb64572db718cb7matozoid if (containerRange.end.line < containedRange.end.line) return false; 14733299776265b9acd160a5196cb9306fd9a7085ecmatozoid // TODO < or <= ? 148482bcecc5d4726b676b208d7efb64572db718cb7matozoid return !(containerRange.end.line == containedRange.end.line && containerRange.end.column < containedRange.end.column); 149920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti } 150920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti return true; 151920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti } 152920cc1e1a13d386c73622fce28f05a8d73b1ef51Federico Tomassetti 15317229be0bf37d47628d6055ca0252d3f80724590Federico Tomassetti} 154