1 /*******************************************************************************
2  * Copyright (c) 2000, 2011 IBM Corporation and others.
3  *
4  * This program and the accompanying materials
5  * are made available under the terms of the Eclipse Public License 2.0
6  * which accompanies this distribution, and is available at
7  * https://www.eclipse.org/legal/epl-2.0/
8  *
9  * SPDX-License-Identifier: EPL-2.0
10  *
11  * Contributors:
12  *     IBM Corporation - initial API and implementation
13  *******************************************************************************/
14 package org.eclipse.jdt.ui.actions;
15 
16 import java.io.CharConversionException;
17 
18 import org.eclipse.jface.dialogs.MessageDialog;
19 import org.eclipse.jface.viewers.IStructuredSelection;
20 
21 import org.eclipse.jface.text.ITextSelection;
22 
23 import org.eclipse.ui.IWorkbenchSite;
24 import org.eclipse.ui.PlatformUI;
25 
26 import org.eclipse.jdt.core.IType;
27 import org.eclipse.jdt.core.JavaModelException;
28 
29 import org.eclipse.jdt.internal.corext.refactoring.RefactoringAvailabilityTester;
30 import org.eclipse.jdt.internal.corext.refactoring.RefactoringExecutionStarter;
31 import org.eclipse.jdt.internal.corext.util.JavaModelUtil;
32 
33 import org.eclipse.jdt.internal.ui.IJavaHelpContextIds;
34 import org.eclipse.jdt.internal.ui.JavaPlugin;
35 import org.eclipse.jdt.internal.ui.actions.ActionUtil;
36 import org.eclipse.jdt.internal.ui.actions.SelectionConverter;
37 import org.eclipse.jdt.internal.ui.javaeditor.JavaEditor;
38 import org.eclipse.jdt.internal.ui.javaeditor.JavaTextSelection;
39 import org.eclipse.jdt.internal.ui.refactoring.RefactoringMessages;
40 import org.eclipse.jdt.internal.ui.refactoring.actions.RefactoringActions;
41 import org.eclipse.jdt.internal.ui.util.ExceptionHandler;
42 
43 /**
44  * Extract a new interface from a class and tries to use the interface instead
45  * of the concrete class where possible.
46  * <p>
47  * This class may be instantiated; it is not intended to be subclassed.
48  * </p>
49  *
50  * @since 2.1
51  *
52  * @noextend This class is not intended to be subclassed by clients.
53  */
54 public class ExtractInterfaceAction extends SelectionDispatchAction {
55 
56 	private JavaEditor fEditor;
57 
58 	/**
59 	 * Note: This constructor is for internal use only. Clients should not call this constructor.
60 	 * @param editor the java editor
61 	 *
62 	 * @noreference This constructor is not intended to be referenced by clients.
63 	 */
ExtractInterfaceAction(JavaEditor editor)64 	public ExtractInterfaceAction(JavaEditor editor) {
65 		this(editor.getEditorSite());
66 		fEditor= editor;
67 		setEnabled(SelectionConverter.canOperateOn(fEditor));
68 	}
69 
70 	/**
71 	 * Creates a new <code>ExtractInterfaceAction</code>. The action requires
72 	 * that the selection provided by the site's selection provider is of type <code>
73 	 * org.eclipse.jface.viewers.IStructuredSelection</code>.
74 	 *
75 	 * @param site the site providing context information for this action
76 	 */
ExtractInterfaceAction(IWorkbenchSite site)77 	public ExtractInterfaceAction(IWorkbenchSite site) {
78 		super(site);
79 		setText(RefactoringMessages.ExtractInterfaceAction_Extract_Interface);
80 		PlatformUI.getWorkbench().getHelpSystem().setHelp(this, IJavaHelpContextIds.EXTRACT_INTERFACE_ACTION);
81 	}
82 
83 	//---- structured selection -------------------------------------------
84 
85 	/*
86 	 * @see SelectionDispatchAction#selectionChanged(IStructuredSelection)
87 	 */
88 	@Override
selectionChanged(IStructuredSelection selection)89 	public void selectionChanged(IStructuredSelection selection) {
90 		try {
91 			setEnabled(RefactoringAvailabilityTester.isExtractInterfaceAvailable(selection));
92 		} catch (JavaModelException e) {
93 			// http://bugs.eclipse.org/bugs/show_bug.cgi?id=19253
94 			if (!(e.getException() instanceof CharConversionException) && JavaModelUtil.isExceptionToBeLogged(e))
95 				JavaPlugin.log(e);
96 			setEnabled(false);//no UI - happens on selection changes
97 		}
98 	}
99 
100 	/*
101 	 * @see SelectionDispatchAction#run(IStructuredSelection)
102 	 */
103 	@Override
run(IStructuredSelection selection)104 	public void run(IStructuredSelection selection) {
105 		try {
106 			if (RefactoringAvailabilityTester.isExtractInterfaceAvailable(selection)) {
107 				IType singleSelectedType= RefactoringAvailabilityTester.getSingleSelectedType(selection);
108 				if (! ActionUtil.isEditable(getShell(), singleSelectedType))
109 					return;
110 				RefactoringExecutionStarter.startExtractInterfaceRefactoring(singleSelectedType, getShell());
111 			}
112 		} catch (JavaModelException e) {
113 			ExceptionHandler.handle(e, RefactoringMessages.OpenRefactoringWizardAction_refactoring, RefactoringMessages.OpenRefactoringWizardAction_exception);
114 		}
115 	}
116 
117     /*
118      * @see SelectionDispatchAction#selectionChanged(ITextSelection)
119      */
120 	@Override
selectionChanged(ITextSelection selection)121 	public void selectionChanged(ITextSelection selection) {
122 		setEnabled(true);
123 	}
124 
125 	/**
126 	 * Note: This method is for internal use only. Clients should not call this method.
127 	 * @param selection the Java text selection (internal type)
128 	 *
129 	 * @noreference This method is not intended to be referenced by clients.
130 	 */
131 	@Override
selectionChanged(JavaTextSelection selection)132 	public void selectionChanged(JavaTextSelection selection) {
133 		try {
134 			setEnabled(RefactoringAvailabilityTester.isExtractInterfaceAvailable(selection));
135 		} catch (JavaModelException e) {
136 			setEnabled(false);
137 		}
138 	}
139 
140 	/*
141      * @see SelectionDispatchAction#run(ITextSelection)
142      */
143 	@Override
run(ITextSelection selection)144 	public void run(ITextSelection selection) {
145 		try {
146 			if (!ActionUtil.isEditable(fEditor))
147 				return;
148 			IType type= RefactoringActions.getEnclosingOrPrimaryType(fEditor);
149 			if (RefactoringAvailabilityTester.isExtractInterfaceAvailable(type)) {
150 				RefactoringExecutionStarter.startExtractInterfaceRefactoring(type, getShell());
151 			} else {
152 				String unavailable= RefactoringMessages.ExtractInterfaceAction_To_activate;
153 				MessageDialog.openInformation(getShell(), RefactoringMessages.OpenRefactoringWizardAction_unavailable, unavailable);
154 			}
155 		} catch (JavaModelException e) {
156 			ExceptionHandler.handle(e, RefactoringMessages.OpenRefactoringWizardAction_refactoring, RefactoringMessages.OpenRefactoringWizardAction_exception);
157 		}
158 	}
159 }
160