001/* 002 * Copyright 2010-2013 JetBrains s.r.o. 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 */ 016 017package org.jetbrains.jet.lang.psi; 018 019import com.intellij.lang.ASTNode; 020import com.intellij.psi.PsiElement; 021import com.intellij.psi.PsiReference; 022import com.intellij.psi.PsiReferenceService; 023import com.intellij.psi.impl.source.resolve.reference.ReferenceProvidersRegistry; 024import com.intellij.psi.tree.IElementType; 025import com.intellij.psi.tree.TokenSet; 026import org.jetbrains.annotations.NotNull; 027import org.jetbrains.annotations.Nullable; 028import org.jetbrains.jet.lang.parsing.JetExpressionParsing; 029import org.jetbrains.jet.lang.resolve.name.Name; 030import org.jetbrains.jet.lexer.JetTokens; 031 032import static org.jetbrains.jet.lexer.JetTokens.*; 033 034public class JetSimpleNameExpression extends JetReferenceExpression { 035 public static final TokenSet REFERENCE_TOKENS = TokenSet.orSet(LABELS, TokenSet.create(IDENTIFIER, FIELD_IDENTIFIER, THIS_KEYWORD, SUPER_KEYWORD)); 036 037 public JetSimpleNameExpression(@NotNull ASTNode node) { 038 super(node); 039 } 040 041 /** 042 * null if it's not a code expression 043 * @return receiver expression 044 */ 045 @Nullable 046 public JetExpression getReceiverExpression() { 047 PsiElement parent = getParent(); 048 if (parent instanceof JetQualifiedExpression && !isImportDirectiveExpression()) { 049 JetExpression receiverExpression = ((JetQualifiedExpression) parent).getReceiverExpression(); 050 // Name expression can't be receiver for itself 051 if (receiverExpression != this) { 052 return receiverExpression; 053 } 054 } 055 else if (parent instanceof JetCallExpression) { 056 //This is in case `a().b()` 057 JetCallExpression callExpression = (JetCallExpression) parent; 058 parent = callExpression.getParent(); 059 if (parent instanceof JetQualifiedExpression) { 060 JetQualifiedExpression qualifiedExpression = (JetQualifiedExpression) parent; 061 return qualifiedExpression.getReceiverExpression(); 062 } 063 } 064 065 return null; 066 } 067 068 public boolean isImportDirectiveExpression() { 069 PsiElement parent = getParent(); 070 if (parent == null) return false; 071 else return parent instanceof JetImportDirective || 072 parent.getParent() instanceof JetImportDirective; 073 } 074 075 @NotNull 076 public String getReferencedName() { 077 String text = getReferencedNameElement().getNode().getText(); 078 return JetPsiUtil.unquoteIdentifierOrFieldReference(text); 079 } 080 081 @NotNull 082 public Name getReferencedNameAsName() { 083 String name = getReferencedName(); 084 return Name.identifierNoValidate(name); 085 } 086 087 @NotNull 088 public PsiElement getReferencedNameElement() { 089 PsiElement element = findChildByType(REFERENCE_TOKENS); 090 if (element == null) { 091 element = findChildByType(JetExpressionParsing.ALL_OPERATIONS); 092 } 093 094 if (element != null) { 095 return element; 096 } 097 098 return this; 099 } 100 101 @Nullable 102 public PsiElement getIdentifier() { 103 return findChildByType(JetTokens.IDENTIFIER); 104 } 105 106 @Nullable @IfNotParsed 107 public IElementType getReferencedNameElementType() { 108 return getReferencedNameElement().getNode().getElementType(); 109 } 110 111 @NotNull 112 @Override 113 public PsiReference[] getReferences() { 114 return ReferenceProvidersRegistry.getReferencesFromProviders(this, PsiReferenceService.Hints.NO_HINTS); 115 } 116 117 @Nullable 118 @Override 119 public PsiReference getReference() { 120 PsiReference[] references = getReferences(); 121 if (references.length == 1) return references[0]; 122 else return null; 123 } 124 125 @Override 126 public void accept(@NotNull JetVisitorVoid visitor) { 127 visitor.visitSimpleNameExpression(this); 128 } 129 130 @Override 131 public <R, D> R accept(@NotNull JetVisitor<R, D> visitor, D data) { 132 return visitor.visitSimpleNameExpression(this, data); 133 } 134}