blob: 389c4a7916c24144aad0302f599034a8b12249f4 [file] [log] [blame]
package com.intellij.structuralsearch.impl.matcher.handlers;
import com.intellij.dupLocator.equivalence.EquivalenceDescriptor;
import com.intellij.dupLocator.iterators.NodeIterator;
import com.intellij.dupLocator.util.DuplocatorUtil;
import com.intellij.dupLocator.util.NodeFilter;
import com.intellij.psi.PsiElement;
import com.intellij.structuralsearch.impl.matcher.MatchContext;
import com.intellij.structuralsearch.impl.matcher.filters.LexicalNodesFilter;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
/**
* @author Eugene.Kudelevsky
*/
public class SkippingHandler extends MatchingHandler implements DelegatingHandler {
private final MatchingHandler myDelegate;
public SkippingHandler(@NotNull MatchingHandler delegate) {
myDelegate = delegate;
}
public boolean match(PsiElement patternNode, PsiElement matchedNode, final MatchContext matchContext) {
if (patternNode == null || matchedNode == null || matchedNode.getClass() == patternNode.getClass()) {
return myDelegate.match(patternNode, matchedNode, matchContext);
}
/*if (patternNode != null && matchedNode != null && patternNode.getClass() == matchedNode.getClass()) {
//return myDelegate.match(patternNode, matchedNode, matchContext);
}*/
PsiElement newPatternNode = skipNodeIfNeccessary(patternNode);
matchedNode = skipNodeIfNeccessary(matchedNode);
if (newPatternNode != patternNode) {
return matchContext.getPattern().getHandler(newPatternNode).match(newPatternNode, matchedNode, matchContext);
}
return myDelegate.match(patternNode, matchedNode, matchContext);
}
@Override
public boolean canMatch(PsiElement patternNode, PsiElement matchedNode) {
return myDelegate.canMatch(patternNode, matchedNode);
}
@Override
public boolean matchSequentially(final NodeIterator nodes, final NodeIterator nodes2, final MatchContext context) {
return myDelegate.matchSequentially(nodes, nodes2, context);
}
public boolean match(PsiElement patternNode,
PsiElement matchedNode,
final int start,
final int end,
final MatchContext context) {
if (patternNode == null || matchedNode == null || patternNode.getClass() == matchedNode.getClass()) {
return myDelegate.match(patternNode, matchedNode, start, end, context);
}
PsiElement newPatternNode = skipNodeIfNeccessary(patternNode);
matchedNode = skipNodeIfNeccessary(matchedNode);
if (newPatternNode != patternNode) {
return context.getPattern().getHandler(newPatternNode).match(newPatternNode, matchedNode, start, end, context);
}
return myDelegate.match(patternNode, matchedNode, start, end, context);
}
protected boolean isMatchSequentiallySucceeded(final NodeIterator nodes2) {
return myDelegate.isMatchSequentiallySucceeded(nodes2);
}
@Override
public boolean shouldAdvanceTheMatchFor(PsiElement patternElement, PsiElement matchedElement) {
return true;
}
public MatchingHandler getDelegate() {
return myDelegate;
}
@Nullable
public static PsiElement getOnlyNonWhitespaceChild(PsiElement element) {
PsiElement onlyChild = null;
for (PsiElement child = element.getFirstChild(); child != null; child = child.getNextSibling()) {
if (DuplocatorUtil.isIgnoredNode(element) || child.getTextLength() == 0) {
continue;
}
if (onlyChild != null) {
return null;
}
onlyChild = child;
}
return onlyChild;
}
@Nullable
public static PsiElement skipNodeIfNeccessary(PsiElement element) {
return skipNodeIfNeccessary(element, null, null);
}
@Nullable
public static PsiElement skipNodeIfNeccessary(PsiElement element, EquivalenceDescriptor descriptor, NodeFilter filter) {
return DuplocatorUtil.skipNodeIfNeccessary(element, descriptor, filter != null ? filter : LexicalNodesFilter.getInstance());
}
}