package com.rthoni.intellij.codefromds.ui.dialogs; import com.intellij.database.model.DasObject; import com.intellij.database.model.DasTable; import com.intellij.database.psi.DbDataSource; import com.intellij.database.psi.DbPsiFacade; import com.intellij.database.util.DasUtil; import com.intellij.openapi.actionSystem.ActionManager; import com.intellij.openapi.fileChooser.FileChooserDescriptorFactory; import com.intellij.openapi.project.Project; import com.intellij.openapi.project.ProjectManager; import com.intellij.openapi.ui.DialogWrapper; import com.intellij.openapi.ui.TextFieldWithBrowseButton; import com.intellij.openapi.ui.ValidationInfo; import com.intellij.ui.ColoredListCellRenderer; import com.intellij.ui.JBColor; import com.intellij.ui.components.JBList; import com.rthoni.intellij.codefromds.dbo.ColumnSelection; import com.rthoni.intellij.codefromds.dbo.DataSourceSelection; import com.rthoni.intellij.codefromds.dbo.GenerateOptions; import com.rthoni.intellij.codefromds.dbo.TableSelection; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; import javax.swing.*; import javax.swing.event.DocumentEvent; import javax.swing.event.DocumentListener; import javax.swing.event.ListSelectionListener; import java.awt.event.ActionListener; import java.io.File; import java.util.Arrays; import java.util.Collection; import java.util.List; import java.util.Vector; import java.util.stream.Collectors; /** * Created by robin on 11/14/16. */ public class GenerateDialog extends DialogWrapper { private JPanel _panel; private JBList _listDatasources; private JBList _listTables; private JBList _listColumns; private TextFieldWithBrowseButton _textModels; private TextFieldWithBrowseButton _textDataSOurceTemplate; private TextFieldWithBrowseButton _textModelsTemplate; private TextFieldWithBrowseButton _textConfigPath; private GenerateOptions _options; public GenerateDialog(@Nullable Project project) { super(project); setTitle("Code FROM data source"); showSource(null); init(); } public GenerateOptions getOptions() { return _options; } public void setOptions(GenerateOptions options) { _options = options; if (_options != null) { showSource(_options.getSelection()); Project project = _options.getSelection().getSource().getProject(); setupTextField(_textModels, project); setupTextField(_textDataSOurceTemplate, project); setupTextField(_textModelsTemplate, project); setupTextField(_textConfigPath, project); _textModels.setText(_options.getModelsPath()); _textDataSOurceTemplate.setText(_options.getDataSourceTemplatePath()); _textModelsTemplate.setText(_options.getModelsTemplatePath()); _textConfigPath.setText(_options.getConfigPath()); } else { showSource(null); setupTextField(_textModels, null); setupTextField(_textDataSOurceTemplate, null); setupTextField(_textModelsTemplate, null); setupTextField(_textConfigPath, null); _textModels.setText(""); _textDataSOurceTemplate.setText(""); _textModelsTemplate.setText(""); _textConfigPath.setText(""); } } @Nullable @Override protected ValidationInfo doValidate() { ValidationInfo info = null; File modelDir = _options == null ? null : new File(_options.getModelsPath()); if (_options == null) { info = new ValidationInfo("No Data Source Selected", _listDatasources); } else if (!modelDir.exists() || !modelDir.isDirectory()) { info = new ValidationInfo("Bad Model Folder", _textModels.getTextField()); } return info; } @Nullable @Override protected JComponent createCenterPanel() { ProjectManager pm = ProjectManager.getInstance(); Project[] projects = pm.getOpenProjects(); List dataSources = Arrays.stream(projects).map(project -> DbPsiFacade.getInstance(project).getDataSources()).flatMap(Collection::stream).collect(Collectors.toList()); _listDatasources.setListData(dataSources.stream().map(DasObject::getName).toArray(String[]::new)); _listDatasources.addListSelectionListener(e -> { if (!e.getValueIsAdjusting()) { int index = _listDatasources.getSelectedIndex(); if (index == -1) { setOptions(null); } else { setOptions(new GenerateOptions(dataSources.get(index))); } } }); _listTables.addListSelectionListener(e -> { if (!e.getValueIsAdjusting()) { int index = _listTables.getSelectedIndex(); if (index == -1) { showTable(null); } else { showTable(_options.getSelection().getTables().get(index)); } } }); _textModels.getTextField().getDocument().addDocumentListener(new DocumentListener() { @Override public void insertUpdate(DocumentEvent e) { changed(); } @Override public void removeUpdate(DocumentEvent e) { changed(); } @Override public void changedUpdate(DocumentEvent e) { changed(); } public void changed() { _options.setModelsPath(_textModels.getText()); } }); _listTables.setCellRenderer(new ColoredListCellRenderer() { @Override protected void customizeCellRenderer(@NotNull JList jList, Object o, int i, boolean b, boolean b1) { TableSelection tableSelection = _options.getSelection().getTables().get(i); if (tableSelection.hasAll()) { setBackground(JBColor.GREEN); } else if (tableSelection.hasNone()) { setBackground(JBColor.RED); } else { setBackground(JBColor.ORANGE); } append(tableSelection.getTable().getName()); } }); if (dataSources.size() > 0) { _listDatasources.setSelectedIndices(new int[]{0}); } return _panel; } private void setupTextField(TextFieldWithBrowseButton field, Project project) { for (ActionListener l : field.getButton().getActionListeners()) { field.getButton().removeActionListener(l); } field.addBrowseFolderListener("Choose Models Destination Folder", "Choose folder", project, FileChooserDescriptorFactory.createSingleFolderDescriptor()); } private void showSource(DataSourceSelection source) { if (source != null) { List tables = source.getTables().stream().map(t -> t.getTable().getName()).collect(Collectors.toList()); _listTables.setListData(tables.toArray(new String[tables.size()])); if (tables.size() > 0) { showTable(source.getTables().get(0)); } else { showTable(null); } } else { _listTables.setListData(new String[]{}); showTable(null); } } private int[] getSelectedIndices(final TableSelection table) { List columns = table.getColumns(); List indices = new Vector<>(); for (int i = 0; i < columns.size(); ++i) { if (columns.get(i).isSelected()) { indices.add(i); } } return indices.stream().mapToInt(Integer::intValue).toArray(); } private void updateSelection(final TableSelection table) { List columns = table.getColumns(); for (int i = 0; i < columns.size(); ++i) { columns.get(i).setSelected(_listColumns.isSelectedIndex(i)); } } private void showTable(TableSelection table) { for (ListSelectionListener e : _listColumns.getListSelectionListeners()) { _listColumns.removeListSelectionListener(e); } if (table != null) { _listColumns.setListData(table.getColumns().stream().map(c -> c.getColumn().getName()).toArray(String[]::new)); int[] indices = getSelectedIndices(table); _listColumns.setSelectedIndices(indices); _listColumns.addListSelectionListener(e -> { if (!e.getValueIsAdjusting()) { _listTables.updateUI(); updateSelection(table); } }); } else { _listColumns.setListData(new String[]{}); } } }