001package jmri.jmrit.operations.rollingstock.cars.tools;
002
003import java.util.ArrayList;
004import java.util.List;
005
006import javax.swing.JTable;
007
008import edu.umd.cs.findbugs.annotations.SuppressFBWarnings;
009import jmri.jmrit.operations.rollingstock.cars.*;
010import jmri.jmrit.operations.rollingstock.cars.gui.CarSetFrame;
011import jmri.jmrit.operations.rollingstock.cars.gui.CarsTableModel;
012import jmri.util.swing.JmriJOptionPane;
013
014/**
015 * Frame for user to place a group of cars on the layout
016 *
017 * @author Dan Boudreau Copyright (C) 2011, 2013, 2023
018 */
019public class CarsSetFrame extends CarSetFrame {
020
021    CarsTableModel _carsTableModel;
022    JTable _carsTable;
023
024    public CarsSetFrame() {
025        super();
026    }
027
028    // Ignore checkbox states
029    private static boolean ignoreStatusCheckBoxSelected = true;
030    private static boolean ignoreLocationCheckBoxSelected = true;
031    private static boolean ignoreDivisionCheckBoxSelected = true;
032    private static boolean ignoreRWECheckBoxSelected = true;
033    private static boolean ignoreRWLCheckBoxSelected = true;
034    private static boolean ignoreLoadCheckBoxSelected = true;
035    private static boolean ignoreKernelCheckBoxSelected = true;
036    private static boolean ignoreDestinationCheckBoxSelected = true;
037    private static boolean ignoreFinalDestinationCheckBoxSelected = true;
038    private static boolean ignoreTrainCheckBoxSelected = true;
039
040    public void initComponents(JTable carsTable) {
041        _carsTable = carsTable;
042        _carsTableModel = (CarsTableModel) carsTable.getModel();
043
044        super.initComponents("package.jmri.jmrit.operations.Operations_SetCars");
045
046        setTitle(Bundle.getMessage("TitleSetCars"));
047        // modify Save button text to "Apply";
048        saveButton.setText(Bundle.getMessage("ButtonApply"));
049
050        // show ignore checkboxes
051        ignoreStatusCheckBox.setVisible(true);
052        ignoreLocationCheckBox.setVisible(true);
053        ignoreDivisionCheckBox.setVisible(true);
054        ignoreRWECheckBox.setVisible(true);
055        ignoreRWLCheckBox.setVisible(true);
056        ignoreLoadCheckBox.setVisible(true);
057        ignoreKernelCheckBox.setVisible(true);
058        ignoreDestinationCheckBox.setVisible(true);
059        ignoreFinalDestinationCheckBox.setVisible(true);
060        ignoreTrainCheckBox.setVisible(true);
061        ignoreAllButton.setVisible(true);
062
063        // set the last state
064        ignoreStatusCheckBox.setSelected(ignoreStatusCheckBoxSelected);
065        ignoreLocationCheckBox.setSelected(ignoreLocationCheckBoxSelected);
066        ignoreDivisionCheckBox.setSelected(ignoreDivisionCheckBoxSelected);
067        ignoreRWECheckBox.setSelected(ignoreRWECheckBoxSelected);
068        ignoreRWLCheckBox.setSelected(ignoreRWLCheckBoxSelected);
069        ignoreLoadCheckBox.setSelected(ignoreLoadCheckBoxSelected);
070        ignoreKernelCheckBox.setSelected(ignoreKernelCheckBoxSelected);
071        ignoreDestinationCheckBox.setSelected(ignoreDestinationCheckBoxSelected);
072        ignoreFinalDestinationCheckBox.setSelected(ignoreFinalDestinationCheckBoxSelected);
073        ignoreTrainCheckBox.setSelected(ignoreTrainCheckBoxSelected);
074
075        // first car in the list becomes the master
076        int rows[] = _carsTable.getSelectedRows();
077        if (rows.length > 0) {
078            Car car = _carsTableModel.getCarAtIndex(_carsTable.convertRowIndexToModel(rows[0]));
079            super.load(car);
080        } else {
081            enableComponents(true);
082            showMessageDialogWarning();
083        }
084    }
085
086    @Override
087    public void buttonActionPerformed(java.awt.event.ActionEvent ae) {
088        super.buttonActionPerformed(ae);
089        if (ae.getSource() == ignoreAllButton) {
090            ignoreAll(toggle);
091        }
092    }
093
094    boolean toggle = false;
095
096    protected void ignoreAll(boolean b) {
097        ignoreStatusCheckBox.setSelected(!locationUnknownCheckBox.isSelected() & b);
098        ignoreLocationCheckBox.setSelected(b);
099        ignoreDivisionCheckBox.setSelected(b);
100        ignoreRWECheckBox.setSelected(b);
101        ignoreRWLCheckBox.setSelected(b);
102        ignoreLoadCheckBox.setSelected(b);
103        ignoreKernelCheckBox.setSelected(b);
104        ignoreDestinationCheckBox.setSelected(b);
105        ignoreFinalDestinationCheckBox.setSelected(b);
106        ignoreTrainCheckBox.setSelected(b);
107        enableComponents(!locationUnknownCheckBox.isSelected());
108        toggle = !b;
109    }
110
111    @Override
112    @SuppressFBWarnings(value = "ST_WRITE_TO_STATIC_FROM_INSTANCE_METHOD", justification = "GUI ease of use")
113    protected boolean save() {
114        // save ignore states
115        ignoreStatusCheckBoxSelected = ignoreStatusCheckBox.isSelected();
116        ignoreLocationCheckBoxSelected = ignoreLocationCheckBox.isSelected();
117        ignoreDivisionCheckBoxSelected = ignoreDivisionCheckBox.isSelected();
118        ignoreRWECheckBoxSelected = ignoreRWECheckBox.isSelected();
119        ignoreRWLCheckBoxSelected = ignoreRWLCheckBox.isSelected();
120        ignoreLoadCheckBoxSelected = ignoreLoadCheckBox.isSelected();
121        ignoreKernelCheckBoxSelected = ignoreKernelCheckBox.isSelected();
122        ignoreDestinationCheckBoxSelected = ignoreKernelCheckBox.isSelected();
123        ignoreFinalDestinationCheckBoxSelected = ignoreFinalDestinationCheckBox.isSelected();
124        ignoreTrainCheckBoxSelected = ignoreTrainCheckBox.isSelected();
125
126        // need to get selected cars before they are modified their location in the table can change
127        List<Car> cars = new ArrayList<Car>();
128        int rows[] = _carsTable.getSelectedRows();
129        for (int row : rows) {
130            Car car = _carsTableModel.getCarAtIndex(_carsTable.convertRowIndexToModel(row));
131            log.debug("Adding selected car {} to change list", car.toString());
132            cars.add(car);
133        }
134        if (rows.length == 0) {
135            showMessageDialogWarning();
136            return false;
137        } else if (cars.get(0) != _car) {
138            log.debug("Default car isn't the first one selected");
139            if (JmriJOptionPane.showConfirmDialog(this, Bundle
140                    .getMessage("doYouWantToChange", cars.get(0).toString()), Bundle
141                    .getMessage("changeDefaultCar"), JmriJOptionPane.YES_NO_OPTION) == JmriJOptionPane.YES_OPTION) {
142                super.load(cars.get(0)); // new default car
143                return false; // done, don't modify any of the cars selected
144            }
145        }
146
147        // don't ask for to change cars in a kernel when giving a selected group of cars a new kernel name
148        askKernelChange = false;
149        
150        // determine if all cars in every kernel are selected
151        for (Car car : cars) {
152            if (car.getKernel() != null) {
153                for (Car c : car.getKernel().getCars()) {
154                    if (!cars.contains(c)) {
155                        askKernelChange = true; // not all selected
156                        break;
157                    }
158                }
159            }
160        }
161
162        for (Car car : cars) {
163            if (!super.change(car)) {
164                return false;
165            } else if (car.getKernel() != null && !ignoreKernelCheckBox.isSelected()) {
166                askKernelChange = false; // changing kernel name
167            }
168        }
169        return false; // all good, but don't close window
170    }
171    
172    private void showMessageDialogWarning() {
173        JmriJOptionPane.showMessageDialog(this, Bundle.getMessage("selectCars"), Bundle
174                .getMessage("carNoneSelected"), JmriJOptionPane.WARNING_MESSAGE);
175    }
176
177    private static final org.slf4j.Logger log = org.slf4j.LoggerFactory.getLogger(CarsSetFrame.class);
178}