001package jmri.jmrit.logixng.expressions.swing;
002
003import java.awt.*;
004import java.util.ArrayList;
005import java.util.List;
006
007import javax.annotation.CheckForNull;
008import javax.annotation.Nonnull;
009import javax.swing.*;
010
011import jmri.InstanceManager;
012import jmri.jmrit.logixng.*;
013import jmri.jmrit.logixng.Module;
014import jmri.jmrit.logixng.Module.ParameterData;
015import jmri.jmrit.logixng.Module.ReturnValueType;
016import jmri.jmrit.logixng.SymbolTable.InitialValueType;
017import jmri.jmrit.logixng.expressions.DigitalCallModule;
018import jmri.jmrit.logixng.tools.swing.CallModuleParameterTableModel;
019import jmri.util.swing.JComboBoxUtil;
020
021/**
022 * Configures an ModuleDigitalExpression object with a Swing JPanel.
023 *
024 * @author Daniel Bergqvist Copyright 2021
025 */
026public class DigitalCallModuleSwing extends AbstractDigitalExpressionSwing {
027
028    private JComboBox<ModuleItem> _moduleComboBox;
029    private CallModuleParameterTableModel _moduleParametersTableModel;
030
031    @Override
032    protected void createPanel(@CheckForNull Base object, @Nonnull JPanel buttonPanel) {
033        if ((object != null) && (! (object instanceof DigitalCallModule))) {
034            throw new IllegalArgumentException("object is not a Module: " + object.getClass().getName());
035        }
036        DigitalCallModule callModule = (DigitalCallModule)object;
037
038        panel = new JPanel();
039
040        panel.setLayout(new BoxLayout(panel, BoxLayout.Y_AXIS));
041
042        JPanel beanPanel = new JPanel();
043        beanPanel.add(new JLabel("Module:"));
044        _moduleComboBox = new JComboBox<>();
045        _moduleComboBox.addItem(new ModuleItem(null));
046        for (Module m : InstanceManager.getDefault(ModuleManager.class).getNamedBeanSet()) {
047//            System.out.format("Root socket type: %s%n", m.getRootSocketType().getName());
048            if ("DefaultFemaleDigitalExpressionSocket".equals(m.getRootSocketType().getName())) {
049                ModuleItem mi = new ModuleItem(m);
050                _moduleComboBox.addItem(mi);
051                if ((callModule != null)
052                        && (callModule.getSelectNamedBean().getNamedBean() != null)
053                        && (callModule.getSelectNamedBean().getNamedBean().getBean() == m)) {
054                    _moduleComboBox.setSelectedItem(mi);
055                }
056            }
057        }
058        JComboBoxUtil.setupComboBoxMaxRows(_moduleComboBox);
059        beanPanel.add(_moduleComboBox);
060        panel.add(beanPanel);
061
062        Module module = null;
063        List<ParameterData> parameterData;
064        if (callModule != null) {
065            if (callModule.getSelectNamedBean().getNamedBean() != null) {
066                module = callModule.getSelectNamedBean().getNamedBean().getBean();
067            }
068            parameterData = callModule.getParameterData();
069        } else {
070            parameterData = new ArrayList<>();
071        }
072        JTable table = new JTable();
073        _moduleParametersTableModel = new CallModuleParameterTableModel(module, parameterData);
074        table.setModel(_moduleParametersTableModel);
075        table.setDefaultRenderer(InitialValueType.class,
076                new CallModuleParameterTableModel.TypeCellRenderer());
077        table.setDefaultEditor(InitialValueType.class,
078                new CallModuleParameterTableModel.InitialValueCellEditor());
079        table.setDefaultRenderer(ReturnValueType.class,
080                new CallModuleParameterTableModel.TypeCellRenderer());
081        table.setDefaultEditor(ReturnValueType.class,
082                new CallModuleParameterTableModel.ReturnValueCellEditor());
083        _moduleParametersTableModel.setColumnsForComboBoxes(table);
084        JScrollPane scrollpane = new JScrollPane(table);
085        scrollpane.setPreferredSize(new Dimension(400, 200));
086        panel.add(scrollpane);
087    }
088
089    /** {@inheritDoc} */
090    @Override
091    public boolean validate(@Nonnull List<String> errorMessages) {
092        return true;
093    }
094
095    /** {@inheritDoc} */
096    @Override
097    public MaleSocket createNewObject(@Nonnull String systemName, @CheckForNull String userName) {
098        DigitalCallModule action = new DigitalCallModule(systemName, userName);
099        updateObject(action);
100        return InstanceManager.getDefault(DigitalExpressionManager.class).registerExpression(action);
101    }
102
103    /** {@inheritDoc} */
104    @Override
105    public void updateObject(@Nonnull Base object) {
106        if (! (object instanceof DigitalCallModule)) {
107            throw new IllegalArgumentException("object is not a Module: " + object.getClass().getName());
108        }
109        DigitalCallModule callModule = (DigitalCallModule)object;
110
111        ModuleItem mi = _moduleComboBox.getItemAt(_moduleComboBox.getSelectedIndex());
112        if (mi._module != null) {
113            callModule.getSelectNamedBean().setNamedBean(mi._module);
114            callModule.getParameterData().clear();
115            callModule.getParameterData().addAll(_moduleParametersTableModel.getParameters());
116        }
117        else {
118            callModule.getSelectNamedBean().removeNamedBean();
119        }
120    }
121
122    /** {@inheritDoc} */
123    @Override
124    public String toString() {
125        return Bundle.getMessage("DigitalCallModule_Short");
126    }
127
128    @Override
129    public void dispose() {
130    }
131
132
133    private static class ModuleItem {
134
135        private final Module _module;
136
137        public ModuleItem(Module m) {
138            _module = m;
139        }
140
141        @Override
142        public String toString() {
143            if (_module == null) return "";
144            else return _module.getDisplayName();
145        }
146    }
147
148}