mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
IDEA-202744 Implement browse button inside combo boxes.
This commit is contained in:
@@ -15,6 +15,7 @@
|
||||
*/
|
||||
package com.intellij.execution.ui;
|
||||
|
||||
import com.intellij.openapi.ui.ComboBox;
|
||||
import com.intellij.openapi.ui.TextComponentAccessor;
|
||||
import com.intellij.openapi.util.io.FileUtil;
|
||||
import com.intellij.ui.SortedComboBoxModel;
|
||||
@@ -22,17 +23,13 @@ import com.intellij.ui.components.JBTextField;
|
||||
import com.intellij.util.ui.StatusText;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import javax.swing.*;
|
||||
import javax.swing.plaf.basic.BasicComboBoxEditor;
|
||||
import java.awt.*;
|
||||
import java.awt.event.FocusEvent;
|
||||
import java.awt.event.FocusListener;
|
||||
|
||||
/**
|
||||
* @author nik
|
||||
*/
|
||||
class JreComboboxEditor extends BasicComboBoxEditor {
|
||||
public static final TextComponentAccessor<JComboBox> TEXT_COMPONENT_ACCESSOR = new JreComboBoxTextComponentAccessor();
|
||||
public static final TextComponentAccessor<ComboBox<JrePathEditor.JreComboBoxItem>> TEXT_COMPONENT_ACCESSOR = new JreComboBoxTextComponentAccessor();
|
||||
private final SortedComboBoxModel<JrePathEditor.JreComboBoxItem> myComboBoxModel;
|
||||
|
||||
JreComboboxEditor(SortedComboBoxModel<JrePathEditor.JreComboBoxItem> comboBoxModel) {
|
||||
@@ -55,30 +52,6 @@ class JreComboboxEditor extends BasicComboBoxEditor {
|
||||
return new JrePathEditor.CustomJreItem(FileUtil.toSystemIndependentName(text));
|
||||
}
|
||||
|
||||
@Override
|
||||
protected JTextField createEditorComponent() {
|
||||
JBTextField field = new JBTextField();
|
||||
field.setBorder(null);
|
||||
field.addFocusListener(new FocusListener() {
|
||||
@Override public void focusGained(FocusEvent e) {
|
||||
update(e);
|
||||
}
|
||||
@Override public void focusLost(FocusEvent e) {
|
||||
update(e);
|
||||
}
|
||||
|
||||
private void update(FocusEvent e) {
|
||||
Component c = e.getComponent().getParent();
|
||||
if (c != null) {
|
||||
c.revalidate();
|
||||
c.repaint();
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
return field;
|
||||
}
|
||||
|
||||
public StatusText getEmptyText() {
|
||||
return getEditorComponent().getEmptyText();
|
||||
}
|
||||
@@ -88,15 +61,15 @@ class JreComboboxEditor extends BasicComboBoxEditor {
|
||||
return (JBTextField)super.getEditorComponent();
|
||||
}
|
||||
|
||||
private static class JreComboBoxTextComponentAccessor implements TextComponentAccessor<JComboBox> {
|
||||
private static class JreComboBoxTextComponentAccessor implements TextComponentAccessor<ComboBox<JrePathEditor.JreComboBoxItem>> {
|
||||
@Override
|
||||
public String getText(JComboBox component) {
|
||||
public String getText(ComboBox<JrePathEditor.JreComboBoxItem> component) {
|
||||
Object item = component.getEditor().getItem();
|
||||
return item != null ? ((JrePathEditor.JreComboBoxItem)item).getPresentableText() : "";
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setText(JComboBox component, @NotNull String text) {
|
||||
public void setText(ComboBox<JrePathEditor.JreComboBoxItem> component, @NotNull String text) {
|
||||
component.getEditor().setItem(new JrePathEditor.CustomJreItem(FileUtil.toSystemIndependentName(text)));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -7,6 +7,7 @@ import com.intellij.ide.util.BrowseFilesListener;
|
||||
import com.intellij.openapi.projectRoots.ProjectJdkTable;
|
||||
import com.intellij.openapi.projectRoots.Sdk;
|
||||
import com.intellij.openapi.roots.ui.OrderEntryAppearanceService;
|
||||
import com.intellij.openapi.ui.BrowseFolderRunnable;
|
||||
import com.intellij.openapi.ui.ComboBox;
|
||||
import com.intellij.openapi.ui.LabeledComponent;
|
||||
import com.intellij.openapi.util.Comparing;
|
||||
@@ -14,6 +15,8 @@ import com.intellij.openapi.util.SystemInfo;
|
||||
import com.intellij.openapi.util.io.FileUtil;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.ui.*;
|
||||
import com.intellij.ui.components.JBTextField;
|
||||
import com.intellij.ui.components.fields.ExtendableTextField;
|
||||
import com.intellij.util.ui.JBUI;
|
||||
import com.intellij.util.ui.StatusText;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
@@ -22,6 +25,8 @@ import org.jetbrains.annotations.Nullable;
|
||||
import javax.swing.*;
|
||||
import java.awt.*;
|
||||
import java.awt.event.ActionListener;
|
||||
import java.awt.event.FocusEvent;
|
||||
import java.awt.event.FocusListener;
|
||||
import java.io.File;
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
@@ -29,7 +34,7 @@ import java.util.Set;
|
||||
/**
|
||||
* @author nik
|
||||
*/
|
||||
public class JrePathEditor extends LabeledComponent<ComboboxWithBrowseButton> implements PanelWithAnchor {
|
||||
public class JrePathEditor extends LabeledComponent<ComboBox> implements PanelWithAnchor {
|
||||
private static final String DEFAULT_JRE_TEXT = "Default";
|
||||
private final JreComboboxEditor myComboboxEditor;
|
||||
private final DefaultJreItem myDefaultJreItem;
|
||||
@@ -101,20 +106,47 @@ public class JrePathEditor extends LabeledComponent<ComboboxWithBrowseButton> im
|
||||
}
|
||||
}
|
||||
});
|
||||
myComboboxEditor = new JreComboboxEditor(myComboBoxModel);
|
||||
myComboboxEditor.getEditorComponent().setTextToTriggerEmptyTextStatus(DEFAULT_JRE_TEXT);
|
||||
|
||||
Runnable action = new BrowseFolderRunnable<>(ExecutionBundle.message("run.configuration.select.alternate.jre.label"),
|
||||
ExecutionBundle.message("run.configuration.select.jre.dir.label"),
|
||||
null,
|
||||
BrowseFilesListener.SINGLE_DIRECTORY_DESCRIPTOR,
|
||||
comboBox,
|
||||
JreComboboxEditor.TEXT_COMPONENT_ACCESSOR);
|
||||
|
||||
myComboboxEditor = new JreComboboxEditor(myComboBoxModel) {
|
||||
@Override
|
||||
protected JTextField createEditorComponent() {
|
||||
JBTextField field = ExtendableTextField.createBrowsableField(action, null);
|
||||
field.setBorder(null);
|
||||
field.addFocusListener(new FocusListener() {
|
||||
@Override public void focusGained(FocusEvent e) {
|
||||
update(e);
|
||||
}
|
||||
@Override public void focusLost(FocusEvent e) {
|
||||
update(e);
|
||||
}
|
||||
|
||||
private void update(FocusEvent e) {
|
||||
Component c = e.getComponent().getParent();
|
||||
if (c != null) {
|
||||
c.revalidate();
|
||||
c.repaint();
|
||||
}
|
||||
}
|
||||
});
|
||||
field.setTextToTriggerEmptyTextStatus(DEFAULT_JRE_TEXT);
|
||||
|
||||
return field;
|
||||
}
|
||||
|
||||
};
|
||||
comboBox.setEditor(myComboboxEditor);
|
||||
InsertPathAction.addTo(myComboboxEditor.getEditorComponent());
|
||||
|
||||
ComboboxWithBrowseButton pathField = new ComboboxWithBrowseButton(comboBox);
|
||||
pathField.addBrowseFolderListener(ExecutionBundle.message("run.configuration.select.alternate.jre.label"),
|
||||
ExecutionBundle.message("run.configuration.select.jre.dir.label"),
|
||||
null, BrowseFilesListener.SINGLE_DIRECTORY_DESCRIPTOR,
|
||||
JreComboboxEditor.TEXT_COMPONENT_ACCESSOR);
|
||||
|
||||
setLabelLocation(BorderLayout.WEST);
|
||||
setText(ExecutionBundle.message("run.configuration.jre.label"));
|
||||
setComponent(pathField);
|
||||
setComponent(comboBox);
|
||||
|
||||
updateUI();
|
||||
}
|
||||
@@ -133,7 +165,7 @@ public class JrePathEditor extends LabeledComponent<ComboboxWithBrowseButton> im
|
||||
}
|
||||
|
||||
private JreComboBoxItem getSelectedJre() {
|
||||
return (JreComboBoxItem)getComponent().getComboBox().getEditor().getItem();
|
||||
return (JreComboBoxItem)getComponent().getEditor().getItem();
|
||||
}
|
||||
|
||||
public void setDefaultJreSelector(DefaultJreSelector defaultJreSelector) {
|
||||
@@ -150,7 +182,7 @@ public class JrePathEditor extends LabeledComponent<ComboboxWithBrowseButton> im
|
||||
toSelect = alternative;
|
||||
}
|
||||
}
|
||||
getComponent().getChildComponent().setSelectedItem(toSelect);
|
||||
getComponent().setSelectedItem(toSelect);
|
||||
updateDefaultJrePresentation();
|
||||
}
|
||||
|
||||
@@ -174,7 +206,7 @@ public class JrePathEditor extends LabeledComponent<ComboboxWithBrowseButton> im
|
||||
}
|
||||
|
||||
public void addActionListener(ActionListener listener) {
|
||||
getComponent().getComboBox().addActionListener(listener);
|
||||
getComponent().addActionListener(listener);
|
||||
}
|
||||
|
||||
interface JreComboBoxItem {
|
||||
|
||||
+1
-2
@@ -172,11 +172,10 @@ public class ExternalProjectPathField extends ComponentWithBrowseButton<External
|
||||
result.stopHere();
|
||||
}
|
||||
};
|
||||
EditorTextField result = provider.createEditor(project, false, editor -> {
|
||||
EditorTextField result = provider.createEditor(project, true, editor -> {
|
||||
collapseIfPossible(editor, externalSystemId, project);
|
||||
editor.getSettings().setShowIntentionBulb(false);
|
||||
});
|
||||
result.setBorder(UIUtil.getTextFieldBorder());
|
||||
result.setOneLineMode(true);
|
||||
result.setOpaque(true);
|
||||
result.setBackground(UIUtil.getTextFieldBackground());
|
||||
|
||||
@@ -104,7 +104,7 @@ public class CommonProgramParametersPanel extends JPanel implements PanelWithAnc
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent e) {
|
||||
List<String> macros = new ArrayList<>();
|
||||
ComboBoxModel<String> model = myWorkingDirectoryComboBox.getChildComponent().getModel();
|
||||
ComboBoxModel<String> model = myWorkingDirectoryComboBox.getModel();
|
||||
for (int i = 0; i < model.getSize(); ++i) {
|
||||
macros.add(model.getElementAt(i));
|
||||
}
|
||||
@@ -150,7 +150,7 @@ public class CommonProgramParametersPanel extends JPanel implements PanelWithAnc
|
||||
}
|
||||
|
||||
public void addWorkingDirectoryListener(Consumer<? super String> onTextChange) {
|
||||
myWorkingDirectoryComboBox.getChildComponent().addActionListener(event -> onTextChange.accept(myWorkingDirectoryComboBox.getText()));
|
||||
myWorkingDirectoryComboBox.addActionListener(event -> onTextChange.accept(myWorkingDirectoryComboBox.getText()));
|
||||
}
|
||||
|
||||
public void setWorkingDirectory(String dir) {
|
||||
|
||||
+27
-23
@@ -21,29 +21,30 @@ import com.intellij.openapi.fileChooser.FileChooserDescriptor;
|
||||
import com.intellij.openapi.fileChooser.FileChooserFactory;
|
||||
import com.intellij.openapi.module.Module;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.ui.BrowseFolderRunnable;
|
||||
import com.intellij.openapi.ui.ComboBox;
|
||||
import com.intellij.openapi.ui.ComponentWithBrowseButton;
|
||||
import com.intellij.openapi.ui.TextComponentAccessor;
|
||||
import com.intellij.ui.TextAccessor;
|
||||
import com.intellij.ui.components.fields.ExtendableTextField;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.awt.Component;
|
||||
import javax.swing.plaf.basic.BasicComboBoxEditor;
|
||||
import java.awt.*;
|
||||
|
||||
public class MacroComboBoxWithBrowseButton extends ComponentWithBrowseButton<ComboBox<String>> implements TextAccessor {
|
||||
public class MacroComboBoxWithBrowseButton extends ComboBox<String> implements TextAccessor {
|
||||
private Module module;
|
||||
private boolean always;
|
||||
|
||||
public MacroComboBoxWithBrowseButton(FileChooserDescriptor descriptor, Project project) {
|
||||
super(new ComboBox<>(new MacroComboBoxModel()), null);
|
||||
super(new MacroComboBoxModel());
|
||||
|
||||
ComboBox<String> combobox = getChildComponent();
|
||||
combobox.setEditable(true);
|
||||
setEditable(true);
|
||||
descriptor.withShowHiddenFiles(true);
|
||||
addActionListener(new BrowseFolderActionListener<ComboBox<String>>(null, null, this, project, descriptor, accessor) {
|
||||
|
||||
Runnable action = new BrowseFolderRunnable<ComboBox<String>>(null, null, project, descriptor, this, accessor) {
|
||||
private Module getModule() {
|
||||
Module module = MacroComboBoxWithBrowseButton.this.module;
|
||||
if (module == null) module = myFileChooserDescriptor.getUserData(LangDataKeys.MODULE_CONTEXT);
|
||||
if (module == null) module = myFileChooserDescriptor.getUserData(LangDataKeys.MODULE);
|
||||
return module;
|
||||
@@ -69,29 +70,32 @@ public class MacroComboBoxWithBrowseButton extends ComponentWithBrowseButton<Com
|
||||
|
||||
return super.expandPath(path);
|
||||
}
|
||||
});
|
||||
ComboBoxEditor editor = combobox.getEditor();
|
||||
if (editor != null) {
|
||||
Component component = editor.getEditorComponent();
|
||||
if (component instanceof JTextField) {
|
||||
FileChooserFactory.getInstance().installFileCompletion((JTextField)component, descriptor, true, null);
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
private MacroComboBoxModel getModel() {
|
||||
ComboBoxModel<String> model = getChildComponent().getModel();
|
||||
return model instanceof MacroComboBoxModel ? (MacroComboBoxModel)model : null;
|
||||
ComboBoxEditor editor = new BasicComboBoxEditor() {
|
||||
@Override
|
||||
protected JTextField createEditorComponent() {
|
||||
JTextField editor = ExtendableTextField.createBrowsableField(action, project);
|
||||
editor.setBorder(null);
|
||||
return editor;
|
||||
}
|
||||
};
|
||||
setEditor(editor);
|
||||
|
||||
Component component = editor.getEditorComponent();
|
||||
if (component instanceof JTextField) {
|
||||
FileChooserFactory.getInstance().installFileCompletion((JTextField)component, descriptor, true, null);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getText() {
|
||||
return accessor.getText(getChildComponent());
|
||||
return accessor.getText(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setText(String text) {
|
||||
accessor.setText(getChildComponent(), text != null ? text : "");
|
||||
accessor.setText(this, text != null ? text : "");
|
||||
}
|
||||
|
||||
public void setModule(Module module) {
|
||||
@@ -105,7 +109,7 @@ public class MacroComboBoxWithBrowseButton extends ComponentWithBrowseButton<Com
|
||||
}
|
||||
|
||||
private void configure() {
|
||||
MacroComboBoxModel model = getModel();
|
||||
MacroComboBoxModel model = (MacroComboBoxModel)getModel();
|
||||
if (model != null) model.useModuleDir(always || module != null);
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,109 @@
|
||||
// Copyright 2000-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
|
||||
package com.intellij.openapi.ui;
|
||||
|
||||
import com.intellij.openapi.fileChooser.FileChooser;
|
||||
import com.intellij.openapi.fileChooser.FileChooserDescriptor;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.util.io.FileUtil;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.openapi.vfs.LocalFileSystem;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import org.jetbrains.annotations.ApiStatus;
|
||||
import org.jetbrains.annotations.Nls;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
|
||||
@ApiStatus.Experimental
|
||||
public class BrowseFolderRunnable<T extends JComponent> implements Runnable {
|
||||
private final String myTitle;
|
||||
private final String myDescription;
|
||||
protected final TextComponentAccessor<? super T> myAccessor;
|
||||
protected final FileChooserDescriptor myFileChooserDescriptor;
|
||||
|
||||
protected T myTextComponent;
|
||||
private Project myProject;
|
||||
|
||||
public BrowseFolderRunnable(@Nullable @Nls(capitalization = Nls.Capitalization.Title) String title,
|
||||
@Nullable @Nls(capitalization = Nls.Capitalization.Sentence) String description,
|
||||
@Nullable Project project,
|
||||
FileChooserDescriptor fileChooserDescriptor,
|
||||
@Nullable T component,
|
||||
TextComponentAccessor<? super T> accessor) {
|
||||
if (fileChooserDescriptor != null && fileChooserDescriptor.isChooseMultiple()) {
|
||||
//LOG.error("multiple selection not supported");
|
||||
fileChooserDescriptor = new FileChooserDescriptor(fileChooserDescriptor) {
|
||||
@Override
|
||||
public boolean isChooseMultiple() {
|
||||
return false;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
myTitle = title;
|
||||
myDescription = description;
|
||||
myTextComponent = component;
|
||||
myProject = project;
|
||||
myFileChooserDescriptor = fileChooserDescriptor;
|
||||
myAccessor = accessor;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
protected Project getProject() {
|
||||
return myProject;
|
||||
}
|
||||
|
||||
protected void setProject(@Nullable Project project) {
|
||||
myProject = project;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
FileChooserDescriptor fileChooserDescriptor = myFileChooserDescriptor;
|
||||
if (myTitle != null || myDescription != null) {
|
||||
fileChooserDescriptor = (FileChooserDescriptor)myFileChooserDescriptor.clone();
|
||||
if (myTitle != null) {
|
||||
fileChooserDescriptor.setTitle(myTitle);
|
||||
}
|
||||
if (myDescription != null) {
|
||||
fileChooserDescriptor.setDescription(myDescription);
|
||||
}
|
||||
}
|
||||
|
||||
FileChooser.chooseFile(fileChooserDescriptor, getProject(), myTextComponent, getInitialFile(),
|
||||
vf -> myAccessor.setText(myTextComponent, chosenFileToResultingText(vf)));
|
||||
}
|
||||
|
||||
@Nullable
|
||||
protected VirtualFile getInitialFile() {
|
||||
String directoryName = myAccessor.getText(myTextComponent).trim();
|
||||
if (StringUtil.isEmptyOrSpaces(directoryName)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
directoryName = FileUtil.toSystemIndependentName(directoryName);
|
||||
VirtualFile path = LocalFileSystem.getInstance().findFileByPath(expandPath(directoryName));
|
||||
while (path == null && directoryName.length() > 0) {
|
||||
int pos = directoryName.lastIndexOf('/');
|
||||
if (pos <= 0) break;
|
||||
directoryName = directoryName.substring(0, pos);
|
||||
path = LocalFileSystem.getInstance().findFileByPath(directoryName);
|
||||
}
|
||||
return path;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
protected String expandPath(@NotNull String path) {
|
||||
return path;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
protected String chosenFileToResultingText(@NotNull VirtualFile chosenFile) {
|
||||
return chosenFile.getPresentableUrl();
|
||||
}
|
||||
|
||||
protected String getComponentText() {
|
||||
return myAccessor.getText(myTextComponent).trim();
|
||||
}
|
||||
}
|
||||
@@ -9,16 +9,12 @@ import com.intellij.openapi.actionSystem.ShortcutSet;
|
||||
import com.intellij.openapi.application.ApplicationManager;
|
||||
import com.intellij.openapi.application.Experiments;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.fileChooser.FileChooser;
|
||||
import com.intellij.openapi.fileChooser.FileChooserDescriptor;
|
||||
import com.intellij.openapi.keymap.KeymapUtil;
|
||||
import com.intellij.openapi.project.DumbAwareAction;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.util.IconLoader;
|
||||
import com.intellij.openapi.util.SystemInfo;
|
||||
import com.intellij.openapi.util.io.FileUtil;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.openapi.vfs.LocalFileSystem;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.openapi.wm.IdeFocusManager;
|
||||
import com.intellij.ui.GuiUtils;
|
||||
@@ -219,97 +215,23 @@ public class ComponentWithBrowseButton<Comp extends JComponent> extends JPanel i
|
||||
}
|
||||
}
|
||||
|
||||
public static class BrowseFolderActionListener<T extends JComponent> implements ActionListener {
|
||||
private final String myTitle;
|
||||
private final String myDescription;
|
||||
protected ComponentWithBrowseButton<T> myTextComponent;
|
||||
private final TextComponentAccessor<? super T> myAccessor;
|
||||
private Project myProject;
|
||||
protected final FileChooserDescriptor myFileChooserDescriptor;
|
||||
|
||||
public static class BrowseFolderActionListener<T extends JComponent> extends BrowseFolderRunnable <T> implements ActionListener {
|
||||
public BrowseFolderActionListener(@Nullable @Nls(capitalization = Nls.Capitalization.Title) String title,
|
||||
@Nullable @Nls(capitalization = Nls.Capitalization.Sentence) String description,
|
||||
ComponentWithBrowseButton<T> textField,
|
||||
@Nullable ComponentWithBrowseButton<T> textField,
|
||||
@Nullable Project project,
|
||||
FileChooserDescriptor fileChooserDescriptor,
|
||||
TextComponentAccessor<? super T> accessor) {
|
||||
if (fileChooserDescriptor != null && fileChooserDescriptor.isChooseMultiple()) {
|
||||
LOG.error("multiple selection not supported");
|
||||
fileChooserDescriptor = new FileChooserDescriptor(fileChooserDescriptor) {
|
||||
@Override
|
||||
public boolean isChooseMultiple() {
|
||||
return false;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
myTitle = title;
|
||||
myDescription = description;
|
||||
myTextComponent = textField;
|
||||
myProject = project;
|
||||
myFileChooserDescriptor = fileChooserDescriptor;
|
||||
myAccessor = accessor;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
protected Project getProject() {
|
||||
return myProject;
|
||||
}
|
||||
|
||||
protected void setProject(@Nullable Project project) {
|
||||
myProject = project;
|
||||
super(title, description, project, fileChooserDescriptor, textField != null ? textField.getChildComponent() : null, accessor);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent e) {
|
||||
FileChooserDescriptor fileChooserDescriptor = myFileChooserDescriptor;
|
||||
if (myTitle != null || myDescription != null) {
|
||||
fileChooserDescriptor = (FileChooserDescriptor)myFileChooserDescriptor.clone();
|
||||
if (myTitle != null) {
|
||||
fileChooserDescriptor.setTitle(myTitle);
|
||||
}
|
||||
if (myDescription != null) {
|
||||
fileChooserDescriptor.setDescription(myDescription);
|
||||
}
|
||||
}
|
||||
|
||||
FileChooser.chooseFile(fileChooserDescriptor, getProject(), myTextComponent, getInitialFile(), this::onFileChosen);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
protected VirtualFile getInitialFile() {
|
||||
String directoryName = getComponentText();
|
||||
if (StringUtil.isEmptyOrSpaces(directoryName)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
directoryName = FileUtil.toSystemIndependentName(directoryName);
|
||||
VirtualFile path = LocalFileSystem.getInstance().findFileByPath(expandPath(directoryName));
|
||||
while (path == null && directoryName.length() > 0) {
|
||||
int pos = directoryName.lastIndexOf('/');
|
||||
if (pos <= 0) break;
|
||||
directoryName = directoryName.substring(0, pos);
|
||||
path = LocalFileSystem.getInstance().findFileByPath(directoryName);
|
||||
}
|
||||
return path;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
protected String expandPath(@NotNull String path) {
|
||||
return path;
|
||||
}
|
||||
|
||||
protected String getComponentText() {
|
||||
return myAccessor.getText(myTextComponent.getChildComponent()).trim();
|
||||
}
|
||||
|
||||
@NotNull
|
||||
protected String chosenFileToResultingText(@NotNull VirtualFile chosenFile) {
|
||||
return chosenFile.getPresentableUrl();
|
||||
run();
|
||||
}
|
||||
|
||||
protected void onFileChosen(@NotNull VirtualFile chosenFile) {
|
||||
myAccessor.setText(myTextComponent.getChildComponent(), chosenFileToResultingText(chosenFile));
|
||||
myAccessor.setText(myTextComponent, chosenFileToResultingText(chosenFile));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -32,7 +32,7 @@ public class TextBrowseFolderListener extends ComponentWithBrowseButton.BrowseFo
|
||||
}
|
||||
|
||||
void setOwnerComponent(@NotNull TextFieldWithBrowseButton component) {
|
||||
myTextComponent = component;
|
||||
myTextComponent = component.getChildComponent();
|
||||
}
|
||||
|
||||
FileChooserDescriptor getFileChooserDescriptor() {
|
||||
|
||||
@@ -99,6 +99,7 @@ public class JBTextField extends JTextField implements ComponentWithEmptyText, T
|
||||
|
||||
Rectangle rect = new Rectangle(getSize());
|
||||
JBInsets.removeFrom(rect, getInsets());
|
||||
JBInsets.removeFrom(rect, getMargin());
|
||||
((Graphics2D)g).fill(rect);
|
||||
|
||||
g.setColor(getForeground());
|
||||
|
||||
@@ -1,12 +1,23 @@
|
||||
// Copyright 2000-2018 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
|
||||
package com.intellij.ui.components.fields;
|
||||
|
||||
import com.intellij.icons.AllIcons;
|
||||
import com.intellij.openapi.Disposable;
|
||||
import com.intellij.openapi.actionSystem.AnActionEvent;
|
||||
import com.intellij.openapi.actionSystem.CustomShortcutSet;
|
||||
import com.intellij.openapi.keymap.KeymapUtil;
|
||||
import com.intellij.openapi.project.DumbAwareAction;
|
||||
import com.intellij.ui.UIBundle;
|
||||
import com.intellij.ui.components.JBTextField;
|
||||
import org.jetbrains.annotations.ApiStatus;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
import javax.swing.border.Border;
|
||||
import javax.swing.plaf.TextUI;
|
||||
import java.awt.event.InputEvent;
|
||||
import java.awt.event.KeyEvent;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
@@ -103,4 +114,26 @@ public class ExtendableTextField extends JBTextField implements ExtendableTextCo
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ApiStatus.Experimental
|
||||
public static ExtendableTextField createBrowsableField(@NotNull Runnable action, @Nullable Disposable parentDisposable) {
|
||||
ExtendableTextField field = new ExtendableTextField();
|
||||
|
||||
KeyStroke keyStroke = KeyStroke.getKeyStroke(KeyEvent.VK_ENTER, InputEvent.SHIFT_DOWN_MASK);
|
||||
String tooltip = UIBundle.message("component.with.browse.button.browse.button.tooltip.text") +
|
||||
" (" + KeymapUtil.getKeystrokeText(keyStroke) + ")";
|
||||
|
||||
ExtendableTextComponent.Extension browseExtension =
|
||||
ExtendableTextComponent.Extension.create(AllIcons.General.OpenDisk, AllIcons.General.OpenDiskHover, tooltip, action);
|
||||
|
||||
new DumbAwareAction() {
|
||||
@Override
|
||||
public void actionPerformed(@NotNull AnActionEvent e) {
|
||||
action.run();
|
||||
}
|
||||
}.registerCustomShortcutSet(new CustomShortcutSet(keyStroke), field, parentDisposable);
|
||||
field.addExtension(browseExtension);
|
||||
|
||||
return field;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -238,7 +238,7 @@ fun <T : JComponent> installFileCompletionAndBrowseDialog(project: Project?,
|
||||
super.onFileChosen(chosenFile)
|
||||
}
|
||||
else {
|
||||
textComponentAccessor.setText(myTextComponent.childComponent, fileChosen(chosenFile))
|
||||
textComponentAccessor.setText(myTextComponent, fileChosen(chosenFile))
|
||||
}
|
||||
}
|
||||
})
|
||||
|
||||
@@ -13,12 +13,12 @@ import com.intellij.lang.ant.config.impl.TargetChooserDialog;
|
||||
import com.intellij.openapi.options.SettingsEditor;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.ui.LabeledComponent;
|
||||
import com.intellij.openapi.ui.TextFieldWithBrowseButton;
|
||||
import com.intellij.openapi.util.InvalidDataException;
|
||||
import com.intellij.openapi.util.JDOMExternalizable;
|
||||
import com.intellij.openapi.util.WriteExternalException;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.ui.components.fields.ExtendableTextField;
|
||||
import com.intellij.util.containers.ContainerUtil;
|
||||
import com.intellij.util.ui.ColumnInfo;
|
||||
import com.intellij.util.ui.ListTableModel;
|
||||
@@ -28,8 +28,6 @@ import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.awt.*;
|
||||
import java.awt.event.ActionEvent;
|
||||
import java.awt.event.ActionListener;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
@@ -171,27 +169,24 @@ public final class AntRunConfiguration extends LocatableConfigurationBase implem
|
||||
private String myFileUrl = null;
|
||||
private String myTargetName = null;
|
||||
|
||||
private final JTextField myTextField = new JTextField();
|
||||
private ExtendableTextField myTextField;
|
||||
private final PropertiesTable myPropTable = new PropertiesTable();
|
||||
|
||||
private final ActionListener myActionListener = new ActionListener() {
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent e) {
|
||||
AntBuildTarget buildTarget = getTarget();
|
||||
final TargetChooserDialog dlg = new TargetChooserDialog(getProject(), buildTarget);
|
||||
if (dlg.showAndGet()) {
|
||||
myFileUrl = null;
|
||||
myTargetName = null;
|
||||
buildTarget = dlg.getSelectedTarget();
|
||||
if (buildTarget != null) {
|
||||
final VirtualFile vFile = buildTarget.getModel().getBuildFile().getVirtualFile();
|
||||
if (vFile != null) {
|
||||
myFileUrl = vFile.getUrl();
|
||||
myTargetName = buildTarget.getName();
|
||||
}
|
||||
private final Runnable myAction = () -> {
|
||||
AntBuildTarget buildTarget = getTarget();
|
||||
final TargetChooserDialog dlg = new TargetChooserDialog(getProject(), buildTarget);
|
||||
if (dlg.showAndGet()) {
|
||||
myFileUrl = null;
|
||||
myTargetName = null;
|
||||
buildTarget = dlg.getSelectedTarget();
|
||||
if (buildTarget != null) {
|
||||
final VirtualFile vFile = buildTarget.getModel().getBuildFile().getVirtualFile();
|
||||
if (vFile != null) {
|
||||
myFileUrl = vFile.getUrl();
|
||||
myTargetName = buildTarget.getName();
|
||||
}
|
||||
updateUI();
|
||||
}
|
||||
updateUI();
|
||||
}
|
||||
};
|
||||
|
||||
@@ -224,9 +219,10 @@ public final class AntRunConfiguration extends LocatableConfigurationBase implem
|
||||
@NotNull
|
||||
@Override
|
||||
protected JComponent createEditor() {
|
||||
myTextField.setEditable(false);
|
||||
myTextField = ExtendableTextField.createBrowsableField(myAction, this);
|
||||
|
||||
final JPanel panel = new JPanel(new BorderLayout());
|
||||
panel.add(LabeledComponent.create(new TextFieldWithBrowseButton(myTextField, myActionListener), "Target name", BorderLayout.WEST), BorderLayout.NORTH);
|
||||
panel.add(LabeledComponent.create(myTextField, "Target name", BorderLayout.WEST), BorderLayout.NORTH);
|
||||
|
||||
final LabeledComponent<JComponent> tableComponent = LabeledComponent.create(myPropTable.getComponent(), "Ant Properties");
|
||||
tableComponent.setBorder(BorderFactory.createEmptyBorder(10, 0, 0, 0));
|
||||
|
||||
Reference in New Issue
Block a user