001package jmri.jmrit.beantable;
002
003import java.awt.event.ActionEvent;
004import java.util.Vector;
005
006import javax.swing.*;
007
008import jmri.InvokeOnGuiThread;
009import jmri.NamedBean;
010import jmri.util.swing.WrapLayout;
011
012/**
013 * Swing Action to display an Add/Edit dialong for a specific NamedBean
014 *
015 * @author Bob Jacobsen   Copyright (C) 2025
016 */
017 
018public class PropertyAddEditAction extends AbstractAction {
019
020    /**
021     * Ctor captures a reference to the bean to add/edit properties in
022     *
023     * @param bean The NamedBean that will be editied
024     */
025    public PropertyAddEditAction(NamedBean bean) {
026        thisBean = bean;
027    }
028
029    NamedBean thisBean;
030    
031    JComboBox<String> selector;
032    JTextField valueField;
033    
034    @Override
035    @InvokeOnGuiThread
036    public void actionPerformed(ActionEvent evt) {
037        // Launch a custom frame for editing
038        var frame = new JFrame("Property Add/Edit: "+thisBean.getDisplayName());
039        frame.setLayout(new WrapLayout());
040        
041        Vector<String> properties = new Vector<>(thisBean.getPropertyKeys());
042        
043        var pane1 = new JPanel();
044        frame.add(pane1);
045        pane1.add(new JLabel("Property Name: "));
046
047        selector = new JComboBox<>(properties);
048        selector.setEditable(true);
049        selector.setPrototypeDisplayValue("Reserve a long property name");
050        selector.addActionListener( (ActionEvent e1) -> selectionChanged());
051        pane1.add(selector);
052        
053        var pane2 = new JPanel();
054        frame.add(pane2);  
055        pane2.add(new JLabel("Value: "));
056        
057        valueField = new JTextField();
058        valueField.setColumns(10);
059        pane2.add(valueField);
060        
061        var setButton = new JButton("Set");
062        setButton.addActionListener( (ActionEvent e1) -> setButtonPressed());
063        frame.add(setButton);
064        
065        frame.pack();
066        frame.setVisible(true);
067    }
068    
069    // Show the value corresponding to the selected property name
070    void selectionChanged() {
071        String property = (String)selector.getSelectedItem();    
072        log.debug("Selection Changed to {}", property);
073        valueField.setText((String)thisBean.getProperty(property));
074    }
075    
076    // make the change
077    void setButtonPressed() {
078        // set the provided value for the selected property
079        log.trace("Selected index {}", selector.getSelectedIndex());
080        String property = (String)selector.getSelectedItem();
081        log.debug("Set property {} to {}", property, valueField.getText());
082        thisBean.setProperty(property, valueField.getText());
083        
084        // reload the selector box
085        Vector<String> properties = new Vector<>(thisBean.getPropertyKeys());
086        selector.setModel(new DefaultComboBoxModel<String>(properties)); 
087        selector.setEditable(true);
088        
089        // and select the entry we just made
090        selector.setSelectedItem(property);
091    }
092
093    private static final org.slf4j.Logger log = org.slf4j.LoggerFactory.getLogger(PropertyAddEditAction.class);
094}