intial source from ttp://www.sf.net/projects/wdte
[phpeclipse.git] / archive / net.sourceforge.phpeclipse.css.ui / src / net / sourceforge / phpeclipse / css / ui / internal / editor / UncommentAction.java
1 /*
2  * Copyright (c) 2003-2004 Christopher Lenz and others.
3  * All rights reserved. This program and the accompanying materials 
4  * are made available under the terms of the Common Public License v1.0
5  * which accompanies this distribution, and is available at
6  * http://www.eclipse.org/legal/cpl-v10.html
7  * 
8  * Contributors:
9  *     Christopher Lenz - initial API and implementation
10  * 
11  * $Id: UncommentAction.java,v 1.1 2004-09-02 18:11:50 jsurfer Exp $
12  */
13
14 package net.sourceforge.phpeclipse.css.ui.internal.editor;
15
16 import java.util.ResourceBundle;
17
18 import net.sourceforge.phpeclipse.css.ui.internal.text.CssPartitionScanner;
19
20 import org.eclipse.jface.text.BadLocationException;
21 import org.eclipse.jface.text.IDocument;
22 import org.eclipse.jface.text.IRewriteTarget;
23 import org.eclipse.jface.text.ITextSelection;
24 import org.eclipse.jface.text.ITypedRegion;
25 import org.eclipse.jface.viewers.ISelection;
26 import org.eclipse.jface.viewers.ISelectionProvider;
27 import org.eclipse.ui.IEditorInput;
28 import org.eclipse.ui.texteditor.IDocumentProvider;
29 import org.eclipse.ui.texteditor.ITextEditor;
30 import org.eclipse.ui.texteditor.ITextEditorExtension2;
31 import org.eclipse.ui.texteditor.TextEditorAction;
32
33 /**
34  * (Heavily inspired by the RemoveBlockComment class in JDT-UI)
35  */
36 public class UncommentAction extends TextEditorAction {
37
38         // Constructors ------------------------------------------------------------
39
40         /**
41          * Creates a new instance.
42          * 
43          * @param bundle the resource bundle
44          * @param prefix a prefix to be prepended to the various resource keys
45          *        (described in <code>ResourceAction</code> constructor), or 
46          *        <code>null</code> if none
47          * @param editor the text editor
48          */
49         public UncommentAction(ResourceBundle bundle, String prefix,
50                 ITextEditor editor) {
51                 super(bundle, prefix, editor);
52         }
53         
54         // TextEditorAction Implementation -----------------------------------------
55
56         /**
57          * @see org.eclipse.jface.action.Action#run()
58          */
59         public void run() {
60                 if (!isEnabled()) {
61                         return;
62                 }
63                 ITextEditor editor = getTextEditor();
64                 if ((editor == null) || !ensureEditable(editor)) {
65                         return;
66                 }
67                 ITextSelection selection = getCurrentSelection();
68                 if (!isValidSelection(selection)) {
69                         return;
70                 }
71                 IDocumentProvider docProvider = editor.getDocumentProvider();
72                 IEditorInput input = editor.getEditorInput();
73                 if (docProvider == null || input == null) {
74                         return;
75                 }
76                 IDocument document = docProvider.getDocument(input);
77                 if (document == null) {
78                         return;
79                 }
80                 IRewriteTarget target = (IRewriteTarget)
81                         editor.getAdapter(IRewriteTarget.class);
82                 if (target != null) {
83                         target.beginCompoundChange();
84                 }
85                 try {
86                         ITypedRegion region = getBlockCommentRegion(document, selection);
87                         if (region != null) {
88                                 int offset = region.getOffset();
89                                 document.replace(offset, 2, ""); //$NON-NLS-1$
90                                 document.replace(offset + region.getLength() - 4, 2,
91                                         ""); //$NON-NLS-1$
92                         }
93                 } catch (BadLocationException e) {
94                         // ignore
95                 } finally {
96                         if (target != null) {
97                                 target.endCompoundChange();
98                         }
99                 }
100         }
101         
102         // Private Methods ---------------------------------------------------------
103
104         /**
105          * Ensures that the editor is modifyable. If the editor is an instance of
106          * <code>ITextEditorExtension2</code>, its 
107          * <code>validateEditorInputState</code> method is called, otherwise, the 
108          * result of <code>isEditable</code> is returned.
109          * 
110          * @param editor the editor to be checked
111          * @return <code>true</code> if the editor is editable, <code>false</code> 
112          *         otherwise
113          */
114         private boolean ensureEditable(ITextEditor editor) {
115                 if (editor instanceof ITextEditorExtension2) {
116                         ITextEditorExtension2 extension = (ITextEditorExtension2) editor;
117                         return extension.validateEditorInputState();
118                 }
119                 return editor.isEditable();
120         }
121
122         /**
123          * Returns the block comment typed region enclosing the position at the end 
124          * of <code>selection</code> or <code>null</code> if there is no block 
125          * comment at this position.
126          * 
127          * @param selection the caret position (the end of the selection is taken as
128          *        the position)
129          * @return the block comment region at the selection's end, or 
130          *         <code>null</code>
131          */
132         private ITypedRegion getBlockCommentRegion(IDocument document,
133                 ITextSelection selection) {
134                 try {
135                         ITypedRegion region = document.getPartition(
136                                 selection.getOffset() + selection.getLength());
137                         if (CssPartitionScanner.CSS_COMMENT.equals(region.getType())) {
138                                 return region;
139                         }
140                 } catch (BadLocationException e) {
141                         // ignore
142                 }
143                 return null;
144         }
145
146         /**
147          * Returns the editor's selection, or <code>null</code> if no selection can 
148          * be obtained or the editor is <code>null</code>.
149          * 
150          * @return the selection of the action's editor, or <code>null</code>
151          */
152         private ITextSelection getCurrentSelection() {
153                 ITextEditor editor = getTextEditor();
154                 if (editor != null) {
155                         ISelectionProvider provider = editor.getSelectionProvider();
156                         if (provider != null) {
157                                 ISelection selection = provider.getSelection();
158                                 if (selection instanceof ITextSelection) {
159                                         return (ITextSelection) selection;
160                                 }
161                         }
162                 }
163                 return null;
164         }
165
166         /**
167          * Checks whether given selection is valid, i.e. neither <code>null</code> 
168          * or empty.
169          * 
170          * @param selection the selection to check
171          * @return <code>true</code> if the selection is valid, <code>false</code> 
172          *         otherwise
173          */
174         private boolean isValidSelection(ITextSelection selection) {
175                 if (selection != null) {
176                         return (!selection.isEmpty() && (selection.getLength() > 0));
177                 }
178                 return false;
179         }
180
181 }