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    
017    package org.jetbrains.jet.lang.psi;
018    
019    import com.intellij.lang.ASTNode;
020    import com.intellij.navigation.ItemPresentation;
021    import com.intellij.navigation.ItemPresentationProviders;
022    import org.jetbrains.annotations.NotNull;
023    import org.jetbrains.annotations.Nullable;
024    import org.jetbrains.jet.lang.psi.stubs.PsiJetParameterStub;
025    import org.jetbrains.jet.lang.psi.stubs.elements.JetStubElementTypes;
026    import org.jetbrains.jet.lang.psi.typeRefHelpers.TypeRefHelpersPackage;
027    import org.jetbrains.jet.lexer.JetTokens;
028    
029    import java.util.Collections;
030    import java.util.List;
031    
032    public class JetParameter extends JetNamedDeclarationStub<PsiJetParameterStub> implements JetCallableDeclaration {
033    
034        public JetParameter(@NotNull ASTNode node) {
035            super(node);
036        }
037    
038        public JetParameter(@NotNull PsiJetParameterStub stub) {
039            super(stub, JetStubElementTypes.VALUE_PARAMETER);
040        }
041    
042        @Override
043        public <R, D> R accept(@NotNull JetVisitor<R, D> visitor, D data) {
044            return visitor.visitParameter(this, data);
045        }
046    
047        @Override
048        @Nullable
049        public JetTypeReference getTypeReference() {
050            return getStubOrPsiChild(JetStubElementTypes.TYPE_REFERENCE);
051        }
052    
053        @Override
054        @Nullable
055        public JetTypeReference setTypeReference(@Nullable JetTypeReference typeRef) {
056            return TypeRefHelpersPackage.setTypeReference(this, getNameIdentifier(), typeRef);
057        }
058    
059        public boolean hasDefaultValue() {
060            PsiJetParameterStub stub = getStub();
061            if (stub != null) {
062                return stub.hasDefaultValue();
063            }
064            return getDefaultValue() != null;
065        }
066    
067        @Nullable
068        public JetExpression getDefaultValue() {
069            PsiJetParameterStub stub = getStub();
070            if (stub != null && !stub.hasDefaultValue()) {
071                return null;
072            }
073            boolean passedEQ = false;
074            ASTNode child = getNode().getFirstChildNode();
075            while (child != null) {
076                if (child.getElementType() == JetTokens.EQ) passedEQ = true;
077                if (passedEQ && child.getPsi() instanceof JetExpression) {
078                    return (JetExpression) child.getPsi();
079                }
080                child = child.getTreeNext();
081            }
082    
083            return null;
084        }
085    
086        public boolean isMutable() {
087            PsiJetParameterStub stub = getStub();
088            if (stub != null) {
089                return stub.isMutable();
090            }
091    
092            return findChildByType(JetTokens.VAR_KEYWORD) != null;
093        }
094    
095        public boolean isVarArg() {
096            JetModifierList modifierList = getModifierList();
097            return modifierList != null && modifierList.hasModifier(JetTokens.VARARG_KEYWORD);
098        }
099    
100        public boolean hasValOrVarNode() {
101            PsiJetParameterStub stub = getStub();
102            if (stub != null) {
103                return stub.hasValOrValNode();
104            }
105            return getValOrVarNode() != null;
106        }
107    
108        @Nullable
109        public ASTNode getValOrVarNode() {
110            PsiJetParameterStub stub = getStub();
111            if (stub != null && !stub.hasValOrValNode()) {
112                return null;
113            }
114            ASTNode val = getNode().findChildByType(JetTokens.VAL_KEYWORD);
115            if (val != null) return val;
116    
117            return getNode().findChildByType(JetTokens.VAR_KEYWORD);
118        }
119    
120        @Override
121        public ItemPresentation getPresentation() {
122            return ItemPresentationProviders.getItemPresentation(this);
123        }
124    
125        public boolean isLoopParameter() {
126            return getParent() instanceof JetForExpression;
127        }
128    
129        @Nullable
130        @Override
131        public JetParameterList getValueParameterList() {
132            return null;
133        }
134    
135        @Nullable
136        @Override
137        public JetTypeReference getReceiverTypeReference() {
138            return null;
139        }
140    
141        @NotNull
142        @Override
143        public List<JetTypeConstraint> getTypeConstraints() {
144            return Collections.emptyList();
145        }
146    
147        @NotNull
148        @Override
149        public List<JetTypeParameter> getTypeParameters() {
150            return Collections.emptyList();
151        }
152    }