2 * Copyright 2000-2009 JetBrains s.r.o.
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
16 package com
.intellij
.codeInsight
.daemon
.quickFix
;
18 import com
.intellij
.codeInsight
.CodeInsightUtil
;
19 import com
.intellij
.codeInsight
.daemon
.QuickFixBundle
;
20 import com
.intellij
.codeInsight
.daemon
.impl
.quickfix
.EmptyExpression
;
21 import com
.intellij
.codeInsight
.generation
.ClassMember
;
22 import com
.intellij
.codeInsight
.generation
.GenerateFieldOrPropertyHandler
;
23 import com
.intellij
.codeInsight
.generation
.GenerateMembersUtil
;
24 import com
.intellij
.codeInsight
.generation
.GenerationInfo
;
25 import com
.intellij
.codeInsight
.intention
.IntentionAction
;
26 import com
.intellij
.codeInsight
.template
.*;
27 import com
.intellij
.codeInspection
.LocalQuickFix
;
28 import com
.intellij
.codeInspection
.ProblemDescriptor
;
29 import com
.intellij
.openapi
.application
.Result
;
30 import com
.intellij
.openapi
.command
.WriteCommandAction
;
31 import com
.intellij
.openapi
.diagnostic
.Logger
;
32 import com
.intellij
.openapi
.editor
.Editor
;
33 import com
.intellij
.openapi
.project
.Project
;
34 import com
.intellij
.psi
.*;
35 import com
.intellij
.psi
.util
.PropertyMemberType
;
36 import com
.intellij
.psi
.util
.PropertyUtil
;
37 import com
.intellij
.util
.IncorrectOperationException
;
38 import org
.jetbrains
.annotations
.NonNls
;
39 import org
.jetbrains
.annotations
.NotNull
;
41 import java
.util
.List
;
46 public class CreateFieldOrPropertyFix
implements IntentionAction
, LocalQuickFix
{
47 private static final Logger LOG
= Logger
.getInstance("com.intellij.codeInsight.daemon.quickFix.CreateFieldOrPropertyFix");
49 private final PsiClass myClass
;
50 private final String myName
;
51 private final PsiType myType
;
52 private final PropertyMemberType myMemberType
;
53 private final PsiAnnotation
[] myAnnotations
;
55 public CreateFieldOrPropertyFix(final PsiClass aClass
, final String name
, final PsiType type
, final PropertyMemberType memberType
, final PsiAnnotation
[] annotations
) {
59 myMemberType
= memberType
;
60 myAnnotations
= annotations
;
64 public String
getText() {
65 return QuickFixBundle
.message(myMemberType
== PropertyMemberType
.FIELD ?
"create.field.text":"create.property.text", myName
);
69 public String
getName() {
74 public String
getFamilyName() {
78 public void applyFix(@NotNull final Project project
, @NotNull ProblemDescriptor descriptor
) {
79 applyFixInner(project
);
82 public boolean isAvailable(@NotNull Project project
, Editor editor
, PsiFile file
) {
86 public void invoke(@NotNull Project project
, Editor editor
, PsiFile file
) {
87 applyFixInner(project
);
90 private void applyFixInner(final Project project
) {
91 final PsiFile file
= myClass
.getContainingFile();
92 final Editor editor
= CodeInsightUtil
.positionCursor(project
, myClass
.getContainingFile(), myClass
.getLBrace());
94 new WriteCommandAction(project
, file
) {
95 protected void run(Result result
) throws Throwable
{
96 generateMembers(project
, editor
, file
);
100 protected boolean isGlobalUndoAction() {
101 return true; // todo check
107 private void generateMembers(final Project project
, final Editor editor
, final PsiFile file
) {
109 List
<?
extends GenerationInfo
> prototypes
= new GenerateFieldOrPropertyHandler(myName
, myType
, myMemberType
, myAnnotations
).generateMemberPrototypes(myClass
, ClassMember
.EMPTY_ARRAY
);
110 prototypes
= GenerateMembersUtil
.insertMembersAtOffset(myClass
.getContainingFile(), editor
.getCaretModel().getOffset(), prototypes
);
111 if (prototypes
.isEmpty()) return;
112 final PsiElement scope
= prototypes
.get(0).getPsiMember().getContext();
113 assert scope
!= null;
114 final Expression expression
= new EmptyExpression() {
115 public com
.intellij
.codeInsight
.template
.Result
calculateResult(final ExpressionContext context
) {
116 return new TextResult(myType
.getCanonicalText());
119 final TemplateBuilderImpl builder
= new TemplateBuilderImpl(scope
);
120 boolean first
= true;
121 @NonNls final String TYPE_NAME_VAR
= "TYPE_NAME_VAR";
122 for (GenerationInfo prototype
: prototypes
) {
123 final PsiTypeElement typeElement
= PropertyUtil
.getPropertyTypeElement(prototype
.getPsiMember());
126 builder
.replaceElement(typeElement
, TYPE_NAME_VAR
, expression
, true);
129 builder
.replaceElement(typeElement
, TYPE_NAME_VAR
, TYPE_NAME_VAR
, false);
132 PsiDocumentManager
.getInstance(project
).doPostponedOperationsAndUnblockDocument(editor
.getDocument());
133 editor
.getCaretModel().moveToOffset(scope
.getTextRange().getStartOffset());
134 TemplateManager
.getInstance(project
).startTemplate(editor
, builder
.buildInlineTemplate());
136 catch (IncorrectOperationException e
) {
141 public boolean startInWriteAction() {