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.
17 package com.intellij.refactoring.copy;
19 import com.intellij.ide.util.DirectoryUtil;
20 import com.intellij.openapi.application.ApplicationManager;
21 import com.intellij.openapi.command.CommandProcessor;
22 import com.intellij.openapi.fileChooser.FileChooserDescriptorFactory;
23 import com.intellij.openapi.help.HelpManager;
24 import com.intellij.openapi.project.Project;
25 import com.intellij.openapi.ui.DialogWrapper;
26 import com.intellij.openapi.ui.Messages;
27 import com.intellij.openapi.ui.impl.DialogWrapperPeerImpl;
28 import com.intellij.psi.PsiDirectory;
29 import com.intellij.psi.PsiElement;
30 import com.intellij.psi.PsiFile;
31 import com.intellij.psi.PsiManager;
32 import com.intellij.refactoring.RefactoringBundle;
33 import com.intellij.ui.*;
34 import com.intellij.util.IncorrectOperationException;
35 import org.jetbrains.annotations.NonNls;
38 import javax.swing.event.DocumentEvent;
39 import javax.swing.event.DocumentListener;
43 class CopyFilesOrDirectoriesDialog extends DialogWrapper{
44 private JLabel myInformationLabel;
45 private EditorComboWithBrowseButton myTargetDirectoryField;
46 private JTextField myNewNameField;
47 private final Project myProject;
48 private final boolean myShowDirectoryField;
49 private final boolean myShowNewNameField;
51 private PsiDirectory myTargetDirectory;
52 @NonNls private static final String RECENT_KEYS = "CopyFile.RECENT_KEYS";
54 public CopyFilesOrDirectoriesDialog(PsiElement[] elements, PsiDirectory defaultTargetDirectory, Project project, boolean doClone) {
57 myShowDirectoryField = !doClone;
58 myShowNewNameField = elements.length == 1;
60 if (doClone && elements.length != 1) {
61 throw new IllegalArgumentException("wrong number of elements to clone: " + elements.length);
65 RefactoringBundle.message("copy.files.clone.title") :
66 RefactoringBundle.message("copy.files.copy.title"));
69 if (elements.length == 1) {
71 if (elements[0] instanceof PsiFile) {
72 PsiFile file = (PsiFile)elements[0];
74 RefactoringBundle.message("copy.files.clone.file.0", file.getVirtualFile().getPresentableUrl()) :
75 RefactoringBundle.message("copy.files.copy.file.0", file.getVirtualFile().getPresentableUrl());
76 final String fileName = file.getName();
77 myNewNameField.setText(fileName);
78 final int dotIdx = fileName.lastIndexOf(".");
80 myNewNameField.select(0, dotIdx);
81 myNewNameField.putClientProperty(DialogWrapperPeerImpl.HAVE_INITIAL_SELECTION, true);
85 PsiDirectory directory = (PsiDirectory)elements[0];
87 RefactoringBundle.message("copy.files.clone.directory.0", directory.getVirtualFile().getPresentableUrl()) :
88 RefactoringBundle.message("copy.files.copy.directory.0", directory.getVirtualFile().getPresentableUrl());
89 myNewNameField.setText(directory.getName());
91 myInformationLabel.setText(text);
94 setMultipleElementCopyLabel(elements);
97 if (myShowDirectoryField) {
98 myTargetDirectoryField.prependItem(defaultTargetDirectory == null ? "" : defaultTargetDirectory.getVirtualFile().getPresentableUrl());
103 private void setMultipleElementCopyLabel(PsiElement[] elements) {
104 boolean allFiles = true;
105 boolean allDirectories = true;
106 for (PsiElement element : elements) {
107 if (element instanceof PsiDirectory) {
111 allDirectories = false;
115 myInformationLabel.setText(RefactoringBundle.message("copy.files.copy.specified.files.label"));
117 else if (allDirectories) {
118 myInformationLabel.setText(RefactoringBundle.message("copy.files.copy.specified.directories.label"));
121 myInformationLabel.setText(RefactoringBundle.message("copy.files.copy.specified.mixed.label"));
125 protected Action[] createActions(){
126 return new Action[]{getOKAction(),getCancelAction(),getHelpAction()};
129 public JComponent getPreferredFocusedComponent() {
130 return myShowNewNameField ? myNewNameField : myTargetDirectoryField.getChildComponent();
133 protected JComponent createCenterPanel() {
134 return new JPanel(new BorderLayout());
137 protected JComponent createNorthPanel() {
138 JPanel panel = new JPanel(new GridBagLayout());
140 myInformationLabel = new JLabel();
142 panel.add(myInformationLabel, new GridBagConstraints(0,0,2,1,1,0,GridBagConstraints.WEST,GridBagConstraints.HORIZONTAL,new Insets(4,8,4,8),0,0));
144 DocumentListener documentListener = new DocumentAdapter() {
145 public void textChanged(DocumentEvent event) {
149 if (myShowNewNameField) {
150 myNewNameField = new JTextField();
151 Dimension size = myNewNameField.getPreferredSize();
152 FontMetrics fontMetrics = myNewNameField.getFontMetrics(myNewNameField.getFont());
153 size.width = fontMetrics.charWidth('a') * 60;
154 myNewNameField.setPreferredSize(size);
156 panel.add(new JLabel(RefactoringBundle.message("copy.files.new.name.label")), new GridBagConstraints(0,1,1,1,0,0,GridBagConstraints.WEST,GridBagConstraints.HORIZONTAL,new Insets(4,8,4,8),0,0));
158 panel.add(myNewNameField, new GridBagConstraints(1,1,1,1,1,0,GridBagConstraints.WEST,GridBagConstraints.HORIZONTAL,new Insets(4,0,4,8),0,0));
160 myNewNameField.getDocument().addDocumentListener(documentListener);
163 if (myShowDirectoryField) {
164 panel.add(new JLabel(RefactoringBundle.message("copy.files.to.directory.label")), new GridBagConstraints(0,2,1,1,0,0,GridBagConstraints.WEST,GridBagConstraints.HORIZONTAL,new Insets(4,8,4,8),0,0));
166 myTargetDirectoryField = new EditorComboWithBrowseButton(null, "", myProject,
168 myTargetDirectoryField.addBrowseFolderListener(RefactoringBundle.message("select.target.directory"),
169 RefactoringBundle.message("the.file.will.be.copied.to.this.directory"),
170 myProject, FileChooserDescriptorFactory.createSingleFolderDescriptor(),
171 EditorComboBox.COMPONENT_ACCESSOR);
172 myTargetDirectoryField.setTextFieldPreferredWidth(60);
173 panel.add(myTargetDirectoryField, new GridBagConstraints(1,2,1,1,1,0,GridBagConstraints.WEST,GridBagConstraints.HORIZONTAL,new Insets(4,0,4,8),0,0));
175 myTargetDirectoryField.getChildComponent().getDocument().addDocumentListener(new com.intellij.openapi.editor.event.DocumentAdapter() {
177 public void documentChanged(com.intellij.openapi.editor.event.DocumentEvent e) {
186 public PsiDirectory getTargetDirectory() {
187 return myTargetDirectory;
190 public String getNewName() {
191 return myNewNameField != null ? myNewNameField.getText().trim() : null;
194 protected void doOKAction(){
195 if (myShowNewNameField) {
196 String newName = getNewName();
198 if (newName.length() == 0) {
199 Messages.showMessageDialog(myProject, RefactoringBundle.message("no.new.name.specified"), RefactoringBundle.message("error.title"), Messages.getErrorIcon());
204 if (myShowDirectoryField) {
205 final String targetDirectoryName = myTargetDirectoryField.getText();
207 if (targetDirectoryName.length() == 0) {
208 Messages.showMessageDialog(myProject, RefactoringBundle.message("no.target.directory.specified"), RefactoringBundle.message("error.title"), Messages.getErrorIcon());
212 RecentsManager.getInstance(myProject).registerRecentEntry(RECENT_KEYS, targetDirectoryName);
214 CommandProcessor.getInstance().executeCommand(myProject, new Runnable() {
216 ApplicationManager.getApplication().runWriteAction(new Runnable() {
219 myTargetDirectory = DirectoryUtil.mkdirs(PsiManager.getInstance(myProject), targetDirectoryName.replace(File.separatorChar, '/'));
221 catch (IncorrectOperationException e) {
226 }, RefactoringBundle.message("create.directory"), null);
228 if (myTargetDirectory == null) {
229 Messages.showMessageDialog(myProject, RefactoringBundle.message("cannot.create.directory"), RefactoringBundle.message("error.title"), Messages.getErrorIcon());
237 private void validateOKButton() {
238 if (myShowDirectoryField) {
239 if (myTargetDirectoryField.getText().length() == 0) {
240 setOKActionEnabled(false);
244 if (myShowNewNameField) {
245 if (getNewName().length() == 0) {
246 setOKActionEnabled(false);
250 setOKActionEnabled(true);
253 protected void doHelpAction() {
254 HelpManager.getInstance().invokeHelp("refactoring.copyClass");