001package jmri.jmrit.operations.trains.gui; 002 003import java.awt.*; 004import java.util.ArrayList; 005import java.util.List; 006 007import javax.swing.*; 008 009import jmri.InstanceManager; 010import jmri.jmrit.operations.*; 011import jmri.jmrit.operations.locations.Location; 012import jmri.jmrit.operations.locations.LocationManager; 013import jmri.jmrit.operations.rollingstock.RollingStock; 014import jmri.jmrit.operations.rollingstock.cars.*; 015import jmri.jmrit.operations.rollingstock.engines.*; 016import jmri.jmrit.operations.routes.*; 017import jmri.jmrit.operations.routes.gui.RouteEditFrame; 018import jmri.jmrit.operations.setup.Control; 019import jmri.jmrit.operations.setup.Setup; 020import jmri.jmrit.operations.trains.Train; 021import jmri.jmrit.operations.trains.TrainManager; 022import jmri.jmrit.operations.trains.manualtrainbuilder.gui.TrainManualBuildAction; 023import jmri.jmrit.operations.trains.tools.*; 024import jmri.jmrit.operations.trains.trainbuilder.TrainCommon; 025import jmri.util.swing.JmriJOptionPane; 026 027/** 028 * Frame for user edit of a train 029 * 030 * @author Dan Boudreau Copyright (C) 2008, 2011, 2012, 2013, 2014 031 */ 032public class TrainEditFrame extends OperationsFrame implements java.beans.PropertyChangeListener { 033 034 TrainManager trainManager = InstanceManager.getDefault(TrainManager.class); 035 RouteManager routeManager = InstanceManager.getDefault(RouteManager.class); 036 037 public Train _train = null; 038 List<JCheckBox> typeCarCheckBoxes = new ArrayList<>(); 039 List<JCheckBox> typeEngineCheckBoxes = new ArrayList<>(); 040 List<JCheckBox> locationCheckBoxes = new ArrayList<>(); 041 JPanel typeCarPanelCheckBoxes = new JPanel(); 042 JPanel typeEnginePanelCheckBoxes = new JPanel(); 043 JPanel roadAndLoadStatusPanel = new JPanel(); 044 JPanel locationPanelCheckBoxes = new JPanel(); 045 JScrollPane typeCarPane; 046 JScrollPane typeEnginePane; 047 JScrollPane locationsPane; 048 049 // labels 050 JLabel textRouteStatus = new JLabel(); 051 JLabel textModel = new JLabel(Bundle.getMessage("Model")); 052 JLabel textRoad2 = new JLabel(Bundle.getMessage("Road")); 053 JLabel textRoad3 = new JLabel(Bundle.getMessage("Road")); 054 JLabel textEngine = new JLabel(Bundle.getMessage("Engines")); 055 056 // major buttons 057 JButton editButton = new JButton(Bundle.getMessage("ButtonEdit")); // edit route 058 JButton clearButton = new JButton(Bundle.getMessage("ClearAll")); 059 JButton setButton = new JButton(Bundle.getMessage("SelectAll")); 060 JButton autoSelectButton = new JButton(Bundle.getMessage("AutoSelect")); 061 JButton resetButton = new JButton(Bundle.getMessage("ResetTrain")); 062 JButton saveTrainButton = new JButton(Bundle.getMessage("SaveTrain")); 063 JButton deleteTrainButton = new JButton(Bundle.getMessage("DeleteTrain")); 064 JButton addTrainButton = new JButton(Bundle.getMessage("AddTrain")); 065 066 // alternate buttons 067 JButton loadOptionButton = new JButton(Bundle.getMessage("AcceptAll")); 068 JButton roadOptionButton = new JButton(Bundle.getMessage("AcceptAll")); 069 070 // radio buttons 071 JRadioButton noneRadioButton = new JRadioButton(Bundle.getMessage("None")); 072 JRadioButton cabooseRadioButton = new JRadioButton(Bundle.getMessage("Caboose")); 073 JRadioButton fredRadioButton = new JRadioButton(Bundle.getMessage("FRED")); 074 ButtonGroup group = new ButtonGroup(); 075 076 // text field 077 JTextField trainNameTextField = new JTextField(Control.max_len_string_train_name); 078 JTextField trainDescriptionTextField = new JTextField(30); 079 080 // text area 081 JTextArea commentTextArea = new JTextArea(4, 70); 082 JScrollPane commentScroller = new JScrollPane(commentTextArea); 083 JColorChooser commentColorChooser = new JColorChooser(Color.black); 084 JCheckBox boldCheckBox = new JCheckBox(); 085 086 // for padding out panel 087 JLabel space0 = new JLabel(" "); // before day 088 JLabel space1 = new JLabel(" "); // between day and hour 089 JLabel space2 = new JLabel(" "); // between hour and minute 090 JLabel space3 = new JLabel(" "); // after minute 091 JLabel space4 = new JLabel(" "); // between route and edit 092 JLabel space5 = new JLabel(" "); // after edit 093 094 // combo boxes 095 JComboBox<String> dayBox = new JComboBox<>(); 096 JComboBox<String> hourBox = new JComboBox<>(); 097 JComboBox<String> minuteBox = new JComboBox<>(); 098 JComboBox<Route> routeBox = routeManager.getComboBox(); 099 JComboBox<String> roadCabooseBox = new JComboBox<>(); 100 JComboBox<String> roadEngineBox = new JComboBox<>(); 101 JComboBox<String> modelEngineBox = InstanceManager.getDefault(EngineModels.class).getComboBox(); 102 JComboBox<String> numEnginesBox = new JComboBox<>(); 103 104 JMenu toolMenu = new JMenu(Bundle.getMessage("MenuTools")); 105 106 public static final String DISPOSE = "dispose"; // NOI18N 107 108 public TrainEditFrame(Train train) { 109 super(Bundle.getMessage("TitleTrainEdit")); 110 // Set up the jtable in a Scroll Pane.. 111 locationsPane = new JScrollPane(locationPanelCheckBoxes); 112 locationsPane.setVerticalScrollBarPolicy(ScrollPaneConstants.VERTICAL_SCROLLBAR_AS_NEEDED); 113 locationsPane.setBorder(BorderFactory.createTitledBorder(Bundle.getMessage("Stops"))); 114 115 typeCarPane = new JScrollPane(typeCarPanelCheckBoxes); 116 typeCarPane.setBorder(BorderFactory.createTitledBorder(Bundle.getMessage("TypesCar"))); 117 typeCarPane.setVerticalScrollBarPolicy(ScrollPaneConstants.VERTICAL_SCROLLBAR_AS_NEEDED); 118 119 typeEnginePane = new JScrollPane(typeEnginePanelCheckBoxes); 120 typeEnginePane.setVerticalScrollBarPolicy(ScrollPaneConstants.VERTICAL_SCROLLBAR_AS_NEEDED); 121 typeEnginePane.setBorder(BorderFactory.createTitledBorder(Bundle.getMessage("TypesEngine"))); 122 123 _train = train; 124 125 getContentPane().setLayout(new BoxLayout(getContentPane(), BoxLayout.Y_AXIS)); 126 127 // Set up the panels 128 JPanel p = new JPanel(); 129 p.setLayout(new BoxLayout(p, BoxLayout.Y_AXIS)); 130 JScrollPane pPane = new JScrollPane(p); 131 pPane.setMinimumSize(new Dimension(300, 5 * trainNameTextField.getPreferredSize().height)); 132 pPane.setBorder(BorderFactory.createTitledBorder("")); 133 134 // Layout the panel by rows 135 // row 1 136 JPanel p1 = new JPanel(); 137 p1.setLayout(new BoxLayout(p1, BoxLayout.X_AXIS)); 138 // row 1a 139 JPanel pName = new JPanel(); 140 pName.setLayout(new GridBagLayout()); 141 pName.setBorder(BorderFactory.createTitledBorder(Bundle.getMessage("Name"))); 142 addItem(pName, trainNameTextField, 0, 0); 143 // row 1b 144 JPanel pDesc = new JPanel(); 145 pDesc.setLayout(new GridBagLayout()); 146 pDesc.setBorder(BorderFactory.createTitledBorder(Bundle.getMessage("Description"))); 147 trainDescriptionTextField.setToolTipText(Bundle.getMessage("TipTrainDescription")); 148 addItem(pDesc, trainDescriptionTextField, 0, 0); 149 150 p1.add(pName); 151 p1.add(pDesc); 152 153 // row 2 154 JPanel p2 = new JPanel(); 155 p2.setLayout(new BoxLayout(p2, BoxLayout.X_AXIS)); 156 // row 2a 157 JPanel pdt = new JPanel(); 158 pdt.setLayout(new GridBagLayout()); 159 pdt.setBorder(BorderFactory.createTitledBorder(Bundle.getMessage("DepartTime"))); 160 161 // build hour and minute menus 162 dayBox.setPrototypeDisplayValue("0000"); // needed for font size 9 163 hourBox.setPrototypeDisplayValue("0000"); 164 minuteBox.setPrototypeDisplayValue("0000"); 165 for (int i = 0; i < Control.numberOfDays; i++) { 166 dayBox.addItem(Integer.toString(i)); 167 } 168 for (int i = 0; i < 24; i++) { 169 if (i < 10) { 170 hourBox.addItem("0" + Integer.toString(i)); 171 } else { 172 hourBox.addItem(Integer.toString(i)); 173 } 174 } 175 for (int i = 0; i < 60; i += 1) { 176 if (i < 10) { 177 minuteBox.addItem("0" + Integer.toString(i)); 178 } else { 179 minuteBox.addItem(Integer.toString(i)); 180 } 181 } 182 183 addItem(pdt, space0, 0, 5); 184 addItem(pdt, dayBox, 1, 5); 185 addItem(pdt, space1, 2, 5); 186 addItem(pdt, hourBox, 3, 5); 187 addItem(pdt, space2, 4, 5); 188 addItem(pdt, minuteBox, 5, 5); 189 addItem(pdt, space3, 6, 5); 190 // time tips 191 dayBox.setToolTipText(Bundle.getMessage("DepartureDayTip")); 192 hourBox.setToolTipText(Bundle.getMessage("DepartureHourTip")); 193 minuteBox.setToolTipText(Bundle.getMessage("DepartureMinuteTip")); 194 195 // row 2b 196 // BUG! routeBox needs its own panel when resizing frame! 197 JPanel pr = new JPanel(); 198 pr.setLayout(new GridBagLayout()); 199 pr.setBorder(BorderFactory.createTitledBorder(Bundle.getMessage("Route"))); 200 addItem(pr, routeBox, 0, 5); 201 addItem(pr, space4, 1, 5); 202 addItem(pr, editButton, 2, 5); 203 addItem(pr, space5, 3, 5); 204 addItem(pr, textRouteStatus, 4, 5); 205 206 p2.add(pdt); 207 p2.add(pr); 208 209 p.add(p1); 210 p.add(p2); 211 212 // row 5 213 locationPanelCheckBoxes.setLayout(new GridBagLayout()); 214 215 // row 6 216 typeCarPanelCheckBoxes.setLayout(new GridBagLayout()); 217 218 // row 8 219 typeEnginePanelCheckBoxes.setLayout(new GridBagLayout()); 220 221 // status panel for roads and loads 222 roadAndLoadStatusPanel.setLayout(new BoxLayout(roadAndLoadStatusPanel, BoxLayout.X_AXIS)); 223 JPanel pRoadOption = new JPanel(); 224 pRoadOption.setBorder(BorderFactory.createTitledBorder(Bundle.getMessage("RoadOption"))); 225 pRoadOption.add(roadOptionButton); 226 roadOptionButton.addActionListener(new TrainRoadOptionsAction(this)); 227 228 JPanel pLoadOption = new JPanel(); 229 pLoadOption.setBorder(BorderFactory.createTitledBorder(Bundle.getMessage("LoadOption"))); 230 pLoadOption.add(loadOptionButton); 231 loadOptionButton.addActionListener(new TrainLoadOptionsAction(this)); 232 233 roadAndLoadStatusPanel.add(pRoadOption); 234 roadAndLoadStatusPanel.add(pLoadOption); 235 roadAndLoadStatusPanel.setVisible(false); // don't show unless there's a restriction 236 237 // row 10 238 JPanel trainReq = new JPanel(); 239 trainReq.setLayout(new GridBagLayout()); 240 trainReq.setBorder(BorderFactory.createTitledBorder(Bundle.getMessage("TrainRequires"))); 241 242 for (int i = 0; i < Setup.getMaxNumberEngines() + 1; i++) { 243 numEnginesBox.addItem(Integer.toString(i)); 244 } 245 numEnginesBox.addItem(Train.AUTO); 246 numEnginesBox.setMinimumSize(new Dimension(100, 20)); 247 numEnginesBox.setToolTipText(Bundle.getMessage("TipNumberOfLocos")); 248 addItem(trainReq, textEngine, 1, 1); 249 addItem(trainReq, numEnginesBox, 2, 1); 250 addItem(trainReq, textModel, 3, 1); 251 modelEngineBox.insertItemAt(NONE, 0); 252 modelEngineBox.setSelectedIndex(0); 253 modelEngineBox.setMinimumSize(new Dimension(120, 20)); 254 modelEngineBox.setToolTipText(Bundle.getMessage("ModelEngineTip")); 255 addItem(trainReq, modelEngineBox, 4, 1); 256 addItem(trainReq, textRoad2, 5, 1); 257 roadEngineBox.insertItemAt(NONE, 0); 258 roadEngineBox.setSelectedIndex(0); 259 roadEngineBox.setMinimumSize(new Dimension(120, 20)); 260 roadEngineBox.setToolTipText(Bundle.getMessage("RoadEngineTip")); 261 addItem(trainReq, roadEngineBox, 6, 1); 262 263 JPanel trainLastCar = new JPanel(); 264 trainLastCar.setLayout(new GridBagLayout()); 265 trainLastCar.setBorder(BorderFactory.createTitledBorder(Bundle.getMessage("TrainLastCar"))); 266 267 addItem(trainLastCar, noneRadioButton, 2, 2); 268 noneRadioButton.setToolTipText(Bundle.getMessage("TipNoCabooseOrFRED")); 269 addItem(trainLastCar, fredRadioButton, 3, 2); 270 fredRadioButton.setToolTipText(Bundle.getMessage("TipFRED")); 271 addItem(trainLastCar, cabooseRadioButton, 4, 2); 272 cabooseRadioButton.setToolTipText(Bundle.getMessage("TipCaboose")); 273 addItem(trainLastCar, textRoad3, 5, 2); 274 roadCabooseBox.setMinimumSize(new Dimension(120, 20)); 275 roadCabooseBox.setToolTipText(Bundle.getMessage("RoadCabooseTip")); 276 addItem(trainLastCar, roadCabooseBox, 6, 2); 277 group.add(noneRadioButton); 278 group.add(cabooseRadioButton); 279 group.add(fredRadioButton); 280 noneRadioButton.setSelected(true); 281 282 // row 13 comment 283 JPanel pC = new JPanel(); 284 pC.setBorder(BorderFactory.createTitledBorder(Bundle.getMessage("Comment"))); 285 pC.setLayout(new GridBagLayout()); 286 addItem(pC, commentScroller, 1, 0); 287 if (_train != null) { 288 addItem(pC, getColorChooserPanel(_train.getCommentWithColor(), commentColorChooser, boldCheckBox), 2, 0); 289 boldCheckBox.setSelected(TrainCommon.isTextBold(_train.getCommentWithColor())); 290 } else { 291 addItem(pC, getColorChooserPanel("", commentColorChooser, boldCheckBox), 2, 0); 292 } 293 294 // adjust text area width based on window size less color chooser 295 Dimension d = new Dimension(getPreferredSize().width - 100, getPreferredSize().height); 296 adjustTextAreaColumnWidth(commentScroller, commentTextArea, d); 297 298 // row 15 buttons 299 JPanel pB = new JPanel(); 300 pB.setLayout(new GridBagLayout()); 301 addItem(pB, deleteTrainButton, 0, 0); 302 addItem(pB, resetButton, 1, 0); 303 addItem(pB, addTrainButton, 2, 0); 304 addItem(pB, saveTrainButton, 3, 0); 305 306 getContentPane().add(pPane); 307 getContentPane().add(locationsPane); 308 getContentPane().add(typeCarPane); 309 getContentPane().add(typeEnginePane); 310 getContentPane().add(roadAndLoadStatusPanel); 311 getContentPane().add(trainReq); 312 getContentPane().add(trainLastCar); 313 getContentPane().add(pC); 314 getContentPane().add(pB); 315 316 // setup buttons 317 addButtonAction(editButton); 318 addButtonAction(setButton); 319 addButtonAction(clearButton); 320 addButtonAction(autoSelectButton); 321 addButtonAction(resetButton); 322 addButtonAction(deleteTrainButton); 323 addButtonAction(addTrainButton); 324 addButtonAction(saveTrainButton); 325 326 addRadioButtonAction(noneRadioButton); 327 addRadioButtonAction(cabooseRadioButton); 328 addRadioButtonAction(fredRadioButton); 329 330 // tool tips 331 resetButton.setToolTipText(Bundle.getMessage("TipTrainReset")); 332 autoSelectButton.setToolTipText(Bundle.getMessage("AutoSelectTip")); 333 commentTextArea.setToolTipText(Bundle.getMessage("TrainCommentTip")); 334 335 // build menu 336 JMenuBar menuBar = new JMenuBar(); 337 menuBar.add(toolMenu); 338 loadToolMenu(toolMenu); 339 setJMenuBar(menuBar); 340 addHelpMenu("package.jmri.jmrit.operations.Operations_TrainEdit", true); // NOI18N 341 342 if (_train != null) { 343 trainNameTextField.setText(_train.getName()); 344 trainDescriptionTextField.setText(_train.getRawDescription()); 345 routeBox.setSelectedItem(_train.getRoute()); 346 modelEngineBox.setSelectedItem(_train.getEngineModel()); 347 commentTextArea.setText(TrainCommon.isTextUserModified(_train.getCommentWithColor()) 348 ? _train.getCommentWithColor() : _train.getComment()); 349 cabooseRadioButton.setSelected(_train.isCabooseNeeded()); 350 fredRadioButton.setSelected(_train.isFredNeeded()); 351 updateDepartureTime(); 352 enableButtons(true); 353 // listen for train changes 354 _train.addPropertyChangeListener(this); 355 356 Route route = _train.getRoute(); 357 if (route != null) { 358 if (_train.getTrainDepartsRouteLocation() != null && 359 _train.getTrainDepartsRouteLocation().getLocation() != null && 360 !_train.getTrainDepartsRouteLocation().getLocation().isStaging()) 361 numEnginesBox.addItem(Train.AUTO_HPT); 362 } 363 numEnginesBox.setSelectedItem(_train.getNumberEngines()); 364 } else { 365 setTitle(Bundle.getMessage("TitleTrainAdd")); 366 enableButtons(false); 367 } 368 369 modelEngineBox.setEnabled(!numEnginesBox.getSelectedItem().equals("0")); 370 roadEngineBox.setEnabled(!numEnginesBox.getSelectedItem().equals("0")); 371 372 // load route location checkboxes 373 updateLocationCheckboxes(); 374 updateCarTypeCheckboxes(); 375 updateEngineTypeCheckboxes(); 376 updateRoadAndLoadStatus(); 377 updateCabooseRoadComboBox(); 378 updateEngineRoadComboBox(); 379 380 // setup combobox 381 addComboBoxAction(numEnginesBox); 382 addComboBoxAction(routeBox); 383 addComboBoxAction(modelEngineBox); 384 385 // get notified if combo box gets modified 386 routeManager.addPropertyChangeListener(this); 387 // get notified if car types or roads gets modified 388 InstanceManager.getDefault(CarTypes.class).addPropertyChangeListener(this); 389 InstanceManager.getDefault(CarRoads.class).addPropertyChangeListener(this); 390 InstanceManager.getDefault(EngineTypes.class).addPropertyChangeListener(this); 391 InstanceManager.getDefault(EngineModels.class).addPropertyChangeListener(this); 392 InstanceManager.getDefault(LocationManager.class).addPropertyChangeListener(this); 393 394 initMinimumSize(new Dimension(Control.panelWidth600, Control.panelHeight600)); 395 } 396 397 private void loadToolMenu(JMenu toolMenu) { 398 toolMenu.removeAll(); 399 // first 4 menu items will also close when the edit train window closes 400 toolMenu.add(new TrainEditBuildOptionsAction(this)); 401 toolMenu.add(new TrainLoadOptionsAction(this)); 402 toolMenu.add(new TrainRoadOptionsAction(this)); 403 toolMenu.add(new TrainManifestOptionAction(this)); 404 toolMenu.addSeparator(); 405 toolMenu.add(new TrainManualBuildAction(_train)); 406 toolMenu.addSeparator(); 407 toolMenu.add(new TrainCopyAction(_train)); 408 toolMenu.addSeparator(); 409 // scripts window closes when the edit train window closes 410 toolMenu.add(new TrainScriptAction(this)); 411 toolMenu.addSeparator(); 412 toolMenu.add(new TrainConductorAction(_train)); 413 toolMenu.addSeparator(); 414 toolMenu.add(new TrainByCarTypeAction(_train)); 415 toolMenu.addSeparator(); 416 toolMenu.add(new PrintTrainAction(false, _train)); 417 toolMenu.add(new PrintTrainAction(true, _train)); 418 toolMenu.add(new PrintTrainManifestAction(false, _train)); 419 toolMenu.add(new PrintTrainManifestAction(true, _train)); 420 toolMenu.add(new PrintShowCarsInTrainRouteAction(false, _train)); 421 toolMenu.add(new PrintShowCarsInTrainRouteAction(true, _train)); 422 toolMenu.add(new PrintTrainBuildReportAction(false, _train)); 423 toolMenu.add(new PrintTrainBuildReportAction(true, _train)); 424 toolMenu.add(new PrintSavedTrainManifestAction(false, _train)); 425 toolMenu.add(new PrintSavedTrainManifestAction(true, _train)); 426 toolMenu.add(new PrintSavedBuildReportAction(false, _train)); 427 toolMenu.add(new PrintSavedBuildReportAction(true, _train)); 428 } 429 430 // Save, Delete, Add, Edit, Reset, Set, Clear 431 @Override 432 public void buttonActionPerformed(java.awt.event.ActionEvent ae) { 433 Train train = trainManager.getTrainByName(trainNameTextField.getText().trim()); 434 if (ae.getSource() == saveTrainButton) { 435 log.debug("train save button activated"); 436 if (_train == null && train == null) { 437 saveNewTrain(); // this can't happen, Save button is disabled 438 } else { 439 if (train != null && train != _train) { 440 reportTrainExists(Bundle.getMessage("save")); 441 return; 442 } 443 // check to see if user supplied a route 444 if (!checkRoute() || !saveTrain()) { 445 return; 446 } 447 } 448 if (Setup.isCloseWindowOnSaveEnabled()) { 449 dispose(); 450 } 451 } 452 if (ae.getSource() == deleteTrainButton) { 453 log.debug("train delete button activated"); 454 if (train == null) { 455 return; 456 } 457 if (train.isBuilt()) { 458 JmriJOptionPane.showMessageDialog(this, 459 Bundle.getMessage("BuiltTrain"), 460 Bundle.getMessage("CanNotDeleteTrain"), JmriJOptionPane.ERROR_MESSAGE); 461 return; 462 } 463 if (!_train.reset()) { 464 JmriJOptionPane.showMessageDialog(this, 465 Bundle.getMessage("TrainIsInRoute", 466 train.getTrainTerminatesName()), 467 Bundle.getMessage("CanNotDeleteTrain"), JmriJOptionPane.ERROR_MESSAGE); 468 return; 469 } 470 if (JmriJOptionPane.showConfirmDialog(this, 471 Bundle.getMessage("deleteMsg", train.getName()), 472 Bundle.getMessage("deleteTrain"), JmriJOptionPane.YES_NO_OPTION) != JmriJOptionPane.YES_OPTION) { 473 return; 474 } 475 routeBox.setSelectedItem(null); 476 trainManager.deregister(train); 477 for (Frame frame : children) { 478 frame.dispose(); 479 } 480 _train = null; 481 enableButtons(false); 482 // save train file 483 OperationsXml.save(); 484 } 485 if (ae.getSource() == addTrainButton) { 486 if (train != null) { 487 reportTrainExists(Bundle.getMessage("add")); 488 return; 489 } 490 saveNewTrain(); 491 } 492 if (ae.getSource() == editButton) { 493 editAddRoute(); 494 } 495 if (ae.getSource() == setButton) { 496 selectCheckboxes(true); 497 } 498 if (ae.getSource() == clearButton) { 499 selectCheckboxes(false); 500 } 501 if (ae.getSource() == autoSelectButton) { 502 autoSelect(); 503 } 504 if (ae.getSource() == resetButton) { 505 if (_train != null) { 506 if (_train.checkDepartureTrack()) { 507 int results = JmriJOptionPane.showConfirmDialog(null, 508 Bundle.getMessage("StagingTrackUsed", 509 _train.getDepartureTrack().getName()), 510 Bundle.getMessage("ShouldNotResetTrain"), JmriJOptionPane.OK_CANCEL_OPTION); 511 if (results == JmriJOptionPane.OK_CANCEL_OPTION) { 512 return; 513 } 514 } 515 Train t = trainManager.getTrainBuiltAfter(train); 516 if (Setup.isBuildOnTime() && t != null) { 517 JmriJOptionPane.showMessageDialog(null, 518 Bundle.getMessage("TrainAfterBuilt", t, train), Bundle.getMessage("CanNotResetTrain"), 519 JmriJOptionPane.WARNING_MESSAGE); 520 } else if (!_train.reset()) { 521 JmriJOptionPane.showMessageDialog(this, 522 Bundle.getMessage("TrainIsInRoute", 523 _train.getTrainTerminatesName()), 524 Bundle.getMessage("CanNotResetTrain"), JmriJOptionPane.ERROR_MESSAGE); 525 } 526 } 527 } 528 } 529 530 @Override 531 public void radioButtonActionPerformed(java.awt.event.ActionEvent ae) { 532 log.debug("radio button activated"); 533 if (_train != null) { 534 if (ae.getSource() == noneRadioButton || 535 ae.getSource() == cabooseRadioButton || 536 ae.getSource() == fredRadioButton) { 537 updateCabooseRoadComboBox(); 538 } 539 } 540 } 541 542 private void saveNewTrain() { 543 if (!checkName(Bundle.getMessage("add"))) { 544 return; 545 } 546 Train train = trainManager.newTrain(trainNameTextField.getText()); 547 _train = train; 548 _train.addPropertyChangeListener(this); 549 550 // update check boxes 551 updateCarTypeCheckboxes(); 552 updateEngineTypeCheckboxes(); 553 // enable check boxes and buttons 554 enableButtons(true); 555 saveTrain(); 556 loadToolMenu(toolMenu); 557 } 558 559 private boolean saveTrain() { 560 if (!checkName(Bundle.getMessage("save"))) { 561 return false; 562 } 563 if (!checkModel() || !checkEngineRoad() || !checkCabooseRoad()) { 564 return false; 565 } 566 if (!_train.getName().equals(trainNameTextField.getText().trim()) || 567 !_train.getRawDescription().equals(trainDescriptionTextField.getText()) || 568 !_train.getCommentWithColor().equals( 569 TrainCommon.formatColorString(commentTextArea.getText(), commentColorChooser.getColor(), 570 boldCheckBox.isSelected()))) { 571 _train.setModified(true); 572 } 573 _train.setDepartureTime(dayBox.getSelectedItem().toString(), hourBox.getSelectedItem().toString(), 574 minuteBox.getSelectedItem().toString()); 575 _train.setNumberEngines((String) numEnginesBox.getSelectedItem()); 576 if (_train.getNumberEngines().equals("0")) { 577 modelEngineBox.setSelectedIndex(0); 578 roadEngineBox.setSelectedIndex(0); 579 } 580 _train.setEngineRoad((String) roadEngineBox.getSelectedItem()); 581 _train.setEngineModel((String) modelEngineBox.getSelectedItem()); 582 if (cabooseRadioButton.isSelected()) { 583 _train.setRequirements(Train.CABOOSE); 584 } 585 if (fredRadioButton.isSelected()) { 586 _train.setRequirements(Train.FRED); 587 } 588 if (noneRadioButton.isSelected()) { 589 _train.setRequirements(Train.NO_CABOOSE_OR_FRED); 590 } 591 _train.setCabooseRoad((String) roadCabooseBox.getSelectedItem()); 592 _train.setName(trainNameTextField.getText().trim()); 593 _train.setDescription(trainDescriptionTextField.getText()); 594 _train.setComment(TrainCommon.formatColorString(commentTextArea.getText(), commentColorChooser.getColor(), 595 boldCheckBox.isSelected())); 596 // save train file 597 OperationsXml.save(); 598 return true; 599 } 600 601 /** 602 * @return true if name isn't too long and is at least one character 603 */ 604 private boolean checkName(String s) { 605 String trainName = trainNameTextField.getText().trim(); 606 if (trainName.isEmpty()) { 607 log.debug("Must enter a train name"); 608 JmriJOptionPane.showMessageDialog(this, Bundle.getMessage("MustEnterName"), 609 Bundle.getMessage("CanNot", s), JmriJOptionPane.ERROR_MESSAGE); 610 return false; 611 } 612 if (trainName.length() > Control.max_len_string_train_name) { 613 JmriJOptionPane.showMessageDialog(this, 614 Bundle.getMessage("TrainNameLess", 615 Control.max_len_string_train_name + 1), 616 Bundle.getMessage("CanNot", s), JmriJOptionPane.ERROR_MESSAGE); 617 return false; 618 } 619 if (!OperationsXml.checkFileName(trainName)) { // NOI18N 620 log.error("Train name must not contain reserved characters"); 621 JmriJOptionPane.showMessageDialog(this, 622 Bundle.getMessage("NameResChar") + NEW_LINE + Bundle.getMessage("ReservedChar"), 623 Bundle.getMessage("CanNot", s), JmriJOptionPane.ERROR_MESSAGE); 624 return false; 625 } 626 627 return true; 628 } 629 630 private boolean checkModel() { 631 String model = (String) modelEngineBox.getSelectedItem(); 632 if (numEnginesBox.getSelectedItem().equals("0") || model.equals(NONE)) { 633 return true; 634 } 635 String type = InstanceManager.getDefault(EngineModels.class).getModelType(model); 636 if (!_train.isTypeNameAccepted(type)) { 637 JmriJOptionPane.showMessageDialog(this, 638 Bundle.getMessage("TrainModelService", model, type), 639 Bundle.getMessage("CanNot", Bundle.getMessage("save")), 640 JmriJOptionPane.ERROR_MESSAGE); 641 return false; 642 } 643 if (roadEngineBox.getItemCount() == 1) { 644 log.debug("No locos available that match the model selected!"); 645 JmriJOptionPane.showMessageDialog(this, 646 Bundle.getMessage("NoLocosModel", model), 647 Bundle.getMessage("TrainWillNotBuild", _train.getName()), 648 JmriJOptionPane.WARNING_MESSAGE); 649 } 650 return true; 651 } 652 653 private boolean checkEngineRoad() { 654 String road = (String) roadEngineBox.getSelectedItem(); 655 if (numEnginesBox.getSelectedItem().equals("0") || road.equals(NONE)) { 656 return true; 657 } 658 if (!road.equals(NONE) && !_train.isLocoRoadNameAccepted(road)) { 659 JmriJOptionPane.showMessageDialog(this, 660 Bundle.getMessage("TrainNotThisRoad", _train.getName(), road), 661 Bundle.getMessage("TrainWillNotBuild", _train.getName()), 662 JmriJOptionPane.WARNING_MESSAGE); 663 return false; 664 } 665 for (RollingStock rs : InstanceManager.getDefault(EngineManager.class).getList()) { 666 if (!_train.isTypeNameAccepted(rs.getTypeName())) { 667 continue; 668 } 669 if (rs.getRoadName().equals(road)) { 670 return true; 671 } 672 } 673 JmriJOptionPane.showMessageDialog(this, 674 Bundle.getMessage("NoLocoRoad", road), 675 Bundle.getMessage("TrainWillNotBuild", _train.getName()), 676 JmriJOptionPane.WARNING_MESSAGE); 677 return false; // couldn't find a loco with the selected road 678 } 679 680 private boolean checkCabooseRoad() { 681 String road = (String) roadCabooseBox.getSelectedItem(); 682 if (!road.equals(NONE) && cabooseRadioButton.isSelected() && !_train.isCabooseRoadNameAccepted(road)) { 683 JmriJOptionPane.showMessageDialog(this, 684 Bundle.getMessage("TrainNotCabooseRoad", _train.getName(), road), 685 Bundle.getMessage("TrainWillNotBuild", _train.getName()), 686 JmriJOptionPane.WARNING_MESSAGE); 687 return false; 688 } 689 return true; 690 } 691 692 private boolean checkRoute() { 693 if (_train.getRoute() == null) { 694 JmriJOptionPane.showMessageDialog(this, Bundle.getMessage("TrainNeedsRoute"), 695 Bundle.getMessage("TrainNoRoute"), 696 JmriJOptionPane.WARNING_MESSAGE); 697 return false; 698 } 699 return true; 700 701 } 702 703 private void reportTrainExists(String s) { 704 log.debug("Can not {}, train already exists", s); 705 JmriJOptionPane.showMessageDialog(this, Bundle.getMessage("TrainNameExists"), 706 Bundle.getMessage("CanNot", s), JmriJOptionPane.ERROR_MESSAGE); 707 } 708 709 private void enableButtons(boolean enabled) { 710 toolMenu.setEnabled(enabled); 711 editButton.setEnabled(enabled); 712 routeBox.setEnabled(enabled && _train != null && !_train.isBuilt()); 713 clearButton.setEnabled(enabled); 714 resetButton.setEnabled(enabled); 715 autoSelectButton.setEnabled(enabled); 716 setButton.setEnabled(enabled); 717 saveTrainButton.setEnabled(enabled); 718 deleteTrainButton.setEnabled(enabled); 719 numEnginesBox.setEnabled(enabled); 720 enableCheckboxes(enabled); 721 noneRadioButton.setEnabled(enabled); 722 fredRadioButton.setEnabled(enabled); 723 cabooseRadioButton.setEnabled(enabled); 724 roadOptionButton.setEnabled(enabled); 725 loadOptionButton.setEnabled(enabled); 726 // the inverse! 727 addTrainButton.setEnabled(!enabled); 728 } 729 730 private void selectCheckboxes(boolean enable) { 731 for (int i = 0; i < typeCarCheckBoxes.size(); i++) { 732 JCheckBox checkBox = typeCarCheckBoxes.get(i); 733 checkBox.setSelected(enable); 734 if (_train != null) { 735 _train.removePropertyChangeListener(this); 736 if (enable) { 737 _train.addTypeName(checkBox.getText()); 738 } else { 739 _train.deleteTypeName(checkBox.getText()); 740 } 741 _train.addPropertyChangeListener(this); 742 } 743 } 744 } 745 746 private void autoSelect() { 747 if (_train != null) { 748 Route route = _train.getRoute(); 749 if (route != null) { 750 typeLoop: for (String type : InstanceManager.getDefault(CarTypes.class).getNames()) { 751 for (RouteLocation rl : route.getLocationsBySequenceList()) { 752 if (rl.getMaxCarMoves() > 0 && (rl.isDropAllowed() || rl.isLocalMovesAllowed())) { 753 if (!_train.isLocationSkipped(rl) && rl.getLocation().acceptsTypeName(type)) { 754 continue typeLoop; 755 } 756 } 757 } 758 _train.deleteTypeName(type); 759 } 760 } 761 } 762 } 763 764 @Override 765 public void comboBoxActionPerformed(java.awt.event.ActionEvent ae) { 766 if (_train == null) { 767 return; 768 } 769 if (ae.getSource() == numEnginesBox) { 770 modelEngineBox.setEnabled(!numEnginesBox.getSelectedItem().equals("0")); 771 roadEngineBox.setEnabled(!numEnginesBox.getSelectedItem().equals("0")); 772 } 773 if (ae.getSource() == modelEngineBox) { 774 updateEngineRoadComboBox(); 775 } 776 if (ae.getSource() == routeBox) { 777 if (routeBox.isEnabled()) { 778 Route route = _train.getRoute(); 779 if (route != null) { 780 route.removePropertyChangeListener(this); 781 } 782 Object selected = routeBox.getSelectedItem(); 783 if (selected != null) { 784 route = (Route) selected; 785 _train.setRoute(route); 786 route.addPropertyChangeListener(this); 787 } else { 788 _train.setRoute(null); 789 } 790 updateLocationCheckboxes(); 791 updateDepartureTime(); 792 pack(); 793 repaint(); 794 } 795 } 796 } 797 798 private void enableCheckboxes(boolean enable) { 799 for (int i = 0; i < typeCarCheckBoxes.size(); i++) { 800 typeCarCheckBoxes.get(i).setEnabled(enable); 801 } 802 for (int i = 0; i < typeEngineCheckBoxes.size(); i++) { 803 typeEngineCheckBoxes.get(i).setEnabled(enable); 804 } 805 } 806 807 private void addLocationCheckBoxAction(JCheckBox b) { 808 b.addActionListener(new java.awt.event.ActionListener() { 809 @Override 810 public void actionPerformed(java.awt.event.ActionEvent e) { 811 locationCheckBoxActionPerformed(e); 812 } 813 }); 814 } 815 816 public void locationCheckBoxActionPerformed(java.awt.event.ActionEvent ae) { 817 JCheckBox b = (JCheckBox) ae.getSource(); 818 log.debug("checkbox change {}", b.getText()); 819 if (_train == null) { 820 return; 821 } 822 String id = b.getName(); 823 RouteLocation rl = _train.getRoute().getRouteLocationById(id); 824 if (b.isSelected()) { 825 _train.deleteTrainSkipsLocation(rl); 826 } else { 827 // check to see if skipped location is staging 828 if (_train.getRoute().getRouteLocationById(id).getLocation().isStaging()) { 829 int result = JmriJOptionPane.showConfirmDialog(this, 830 Bundle.getMessage("TrainRouteStaging", 831 _train.getName(), _train.getRoute().getRouteLocationById(id).getName()), 832 Bundle.getMessage("TrainRouteNotStaging"), JmriJOptionPane.OK_CANCEL_OPTION); 833 if (result != JmriJOptionPane.OK_OPTION) { 834 b.setSelected(true); 835 return; // don't skip staging 836 } 837 } 838 _train.addTrainSkipsLocation(rl); 839 } 840 } 841 842 private void updateRouteComboBox() { 843 routeBox.setEnabled(false); 844 routeManager.updateComboBox(routeBox); 845 if (_train != null) { 846 routeBox.setSelectedItem(_train.getRoute()); 847 } 848 routeBox.setEnabled(true); 849 } 850 851 private void updateCarTypeCheckboxes() { 852 typeCarCheckBoxes.clear(); 853 typeCarPanelCheckBoxes.removeAll(); 854 loadCarTypes(); 855 enableCheckboxes(_train != null); 856 typeCarPanelCheckBoxes.revalidate(); 857 repaint(); 858 } 859 860 private void loadCarTypes() { 861 int numberOfCheckboxes = getNumberOfCheckboxesPerLine(); // number per line 862 int x = 0; 863 int y = 1; // vertical position in panel 864 for (String type : InstanceManager.getDefault(CarTypes.class).getNames()) { 865 JCheckBox checkBox = new javax.swing.JCheckBox(); 866 typeCarCheckBoxes.add(checkBox); 867 checkBox.setText(type); 868 addTypeCheckBoxAction(checkBox); 869 addItemLeft(typeCarPanelCheckBoxes, checkBox, x++, y); 870 if (_train != null && _train.isTypeNameAccepted(type)) { 871 checkBox.setSelected(true); 872 } 873 if (x > numberOfCheckboxes) { 874 y++; 875 x = 0; 876 } 877 } 878 879 JPanel p = new JPanel(); 880 p.add(clearButton); 881 p.add(setButton); 882 p.add(autoSelectButton); 883 GridBagConstraints gc = new GridBagConstraints(); 884 gc.gridwidth = getNumberOfCheckboxesPerLine() + 1; 885 gc.gridy = ++y; 886 typeCarPanelCheckBoxes.add(p, gc); 887 888 } 889 890 private void updateEngineTypeCheckboxes() { 891 typeEngineCheckBoxes.clear(); 892 typeEnginePanelCheckBoxes.removeAll(); 893 loadEngineTypes(); 894 enableCheckboxes(_train != null); 895 typeEnginePanelCheckBoxes.revalidate(); 896 repaint(); 897 } 898 899 private void loadEngineTypes() { 900 int numberOfCheckboxes = getNumberOfCheckboxesPerLine(); // number per line 901 int x = 0; 902 int y = 1; 903 for (String type : InstanceManager.getDefault(EngineTypes.class).getNames()) { 904 JCheckBox checkBox = new javax.swing.JCheckBox(); 905 typeEngineCheckBoxes.add(checkBox); 906 checkBox.setText(type); 907 addTypeCheckBoxAction(checkBox); 908 addItemLeft(typeEnginePanelCheckBoxes, checkBox, x++, y); 909 if (_train != null && _train.isTypeNameAccepted(type)) { 910 checkBox.setSelected(true); 911 } 912 if (x > numberOfCheckboxes) { 913 y++; 914 x = 0; 915 } 916 } 917 } 918 919 private void updateRoadComboBoxes() { 920 updateCabooseRoadComboBox(); 921 updateEngineRoadComboBox(); 922 } 923 924 // update caboose road box based on radio selection 925 private void updateCabooseRoadComboBox() { 926 roadCabooseBox.removeAllItems(); 927 roadCabooseBox.addItem(NONE); 928 if (noneRadioButton.isSelected()) { 929 roadCabooseBox.setEnabled(false); 930 return; 931 } 932 roadCabooseBox.setEnabled(true); 933 List<String> roads; 934 if (cabooseRadioButton.isSelected()) { 935 roads = InstanceManager.getDefault(CarManager.class).getCabooseRoadNames(); 936 } else { 937 roads = InstanceManager.getDefault(CarManager.class).getFredRoadNames(); 938 } 939 for (String road : roads) { 940 roadCabooseBox.addItem(road); 941 } 942 if (_train != null) { 943 roadCabooseBox.setSelectedItem(_train.getCabooseRoad()); 944 } 945 OperationsPanel.padComboBox(roadCabooseBox); 946 } 947 948 private void updateEngineRoadComboBox() { 949 String engineModel = (String) modelEngineBox.getSelectedItem(); 950 if (engineModel == null) { 951 return; 952 } 953 InstanceManager.getDefault(EngineManager.class).updateEngineRoadComboBox(engineModel, roadEngineBox); 954 if (_train != null) { 955 roadEngineBox.setSelectedItem(_train.getEngineRoad()); 956 } 957 } 958 959 private void addTypeCheckBoxAction(JCheckBox b) { 960 b.addActionListener(new java.awt.event.ActionListener() { 961 @Override 962 public void actionPerformed(java.awt.event.ActionEvent e) { 963 typeCheckBoxActionPerformed(e); 964 } 965 }); 966 } 967 968 public void typeCheckBoxActionPerformed(java.awt.event.ActionEvent ae) { 969 JCheckBox b = (JCheckBox) ae.getSource(); 970 log.debug("checkbox change {}", b.getText()); 971 if (_train == null) { 972 return; 973 } 974 if (b.isSelected()) { 975 _train.addTypeName(b.getText()); 976 } else { 977 _train.deleteTypeName(b.getText()); 978 } 979 } 980 981 // the train's route shown as locations with checkboxes 982 private void updateLocationCheckboxes() { 983 updateRouteStatus(); 984 locationCheckBoxes.clear(); 985 locationPanelCheckBoxes.removeAll(); 986 int y = 0; // vertical position in panel 987 Route route = null; 988 if (_train != null) { 989 route = _train.getRoute(); 990 } 991 if (route != null) { 992 List<RouteLocation> routeList = route.getLocationsBySequenceList(); 993 for (RouteLocation rl : routeList) { 994 JCheckBox checkBox = new javax.swing.JCheckBox(); 995 locationCheckBoxes.add(checkBox); 996 checkBox.setText(rl.toString()); 997 checkBox.setName(rl.getId()); 998 addItemLeft(locationPanelCheckBoxes, checkBox, 0, y++); 999 Location loc = InstanceManager.getDefault(LocationManager.class).getLocationByName(rl.getName()); 1000 // does the location exist? 1001 if (loc != null) { 1002 // need to listen for name and direction changes 1003 loc.removePropertyChangeListener(this); 1004 loc.addPropertyChangeListener(this); 1005 boolean services = false; 1006 // does train direction service location? 1007 if ((rl.getTrainDirection() & loc.getTrainDirections()) != 0) { 1008 services = true; 1009 } // train must service last location or single location 1010 else if (_train.isLocalSwitcher() || rl == _train.getTrainTerminatesRouteLocation()) { 1011 services = true; 1012 } 1013 // check can drop and pick up, and moves > 0 1014 if (services && 1015 (rl.isDropAllowed() || rl.isPickUpAllowed() || rl.isLocalMovesAllowed()) && 1016 rl.getMaxCarMoves() > 0) { 1017 checkBox.setSelected(!_train.isLocationSkipped(rl)); 1018 } else { 1019 checkBox.setEnabled(false); 1020 } 1021 addLocationCheckBoxAction(checkBox); 1022 } else { 1023 checkBox.setEnabled(false); 1024 } 1025 } 1026 } 1027 locationPanelCheckBoxes.revalidate(); 1028 } 1029 1030 private void updateRouteStatus() { 1031 Route route = null; 1032 textRouteStatus.setText(NONE); // clear out previous status 1033 if (_train != null) { 1034 route = _train.getRoute(); 1035 } 1036 if (route != null) { 1037 if (!route.getStatus().equals(Route.OKAY)) { 1038 textRouteStatus.setText(route.getStatus()); 1039 textRouteStatus.setForeground(Color.RED); 1040 } 1041 } 1042 } 1043 1044 RouteEditFrame ref; 1045 1046 private void editAddRoute() { 1047 log.debug("Edit/add route"); 1048 if (ref != null) { 1049 ref.dispose(); 1050 } 1051 ref = new RouteEditFrame(); 1052 setChildFrame(ref); 1053 Route route = (Route) routeBox.getSelectedItem(); 1054 ref.initComponents(route, _train); 1055 } 1056 1057 private void updateDepartureTime() { 1058 dayBox.setSelectedItem(_train.getDepartureTimeDay()); 1059 hourBox.setSelectedItem(_train.getDepartureTimeHour()); 1060 minuteBox.setSelectedItem(_train.getDepartureTimeMinute()); 1061 // check to see if route has a departure time from the 1st location 1062 RouteLocation rl = _train.getTrainDepartsRouteLocation(); 1063 if (rl != null && !rl.getDepartureTimeHourMinutes().equals(NONE)) { 1064 dayBox.setEnabled(false); 1065 hourBox.setEnabled(false); 1066 minuteBox.setEnabled(false); 1067 } else { 1068 dayBox.setEnabled(!_train.isBuilt()); 1069 hourBox.setEnabled(!_train.isBuilt()); 1070 minuteBox.setEnabled(!_train.isBuilt()); 1071 } 1072 } 1073 1074 private void updateRoadAndLoadStatus() { 1075 if (_train != null) { 1076 // road options 1077 if (_train.getCarRoadOption().equals(Train.INCLUDE_ROADS)) { 1078 roadOptionButton.setText(Bundle.getMessage( 1079 "AcceptOnly") + " " + _train.getCarRoadNames().length + " " + Bundle.getMessage("RoadsCar")); 1080 } else if (_train.getCarRoadOption().equals(Train.EXCLUDE_ROADS)) { 1081 roadOptionButton.setText(Bundle.getMessage( 1082 "Exclude") + " " + _train.getCarRoadNames().length + " " + Bundle.getMessage("RoadsCar")); 1083 } else if (_train.getCabooseRoadOption().equals(Train.INCLUDE_ROADS)) { 1084 roadOptionButton.setText(Bundle.getMessage( 1085 "AcceptOnly") + 1086 " " + 1087 _train.getCabooseRoadNames().length + 1088 " " + 1089 Bundle.getMessage("RoadsCaboose")); 1090 } else if (_train.getCabooseRoadOption().equals(Train.EXCLUDE_ROADS)) { 1091 roadOptionButton.setText(Bundle.getMessage( 1092 "Exclude") + 1093 " " + 1094 _train.getCabooseRoadNames().length + 1095 " " + 1096 Bundle.getMessage("RoadsCaboose")); 1097 } else if (_train.getLocoRoadOption().equals(Train.INCLUDE_ROADS)) { 1098 roadOptionButton.setText(Bundle.getMessage( 1099 "AcceptOnly") + " " + _train.getLocoRoadNames().length + " " + Bundle.getMessage("RoadsLoco")); 1100 } else if (_train.getLocoRoadOption().equals(Train.EXCLUDE_ROADS)) { 1101 roadOptionButton.setText(Bundle.getMessage( 1102 "Exclude") + " " + _train.getLocoRoadNames().length + " " + Bundle.getMessage("RoadsLoco")); 1103 } else { 1104 roadOptionButton.setText(Bundle.getMessage("AcceptAll")); 1105 } 1106 // load options 1107 if (_train.getLoadOption().equals(Train.ALL_LOADS)) { 1108 loadOptionButton.setText(Bundle.getMessage("AcceptAll")); 1109 } else if (_train.getLoadOption().equals(Train.INCLUDE_LOADS)) { 1110 loadOptionButton.setText(Bundle.getMessage( 1111 "AcceptOnly") + " " + _train.getLoadNames().length + " " + Bundle.getMessage("Loads")); 1112 } else { 1113 loadOptionButton.setText(Bundle.getMessage( 1114 "Exclude") + " " + _train.getLoadNames().length + " " + Bundle.getMessage("Loads")); 1115 } 1116 if (!_train.getCarRoadOption().equals(Train.ALL_ROADS) || 1117 !_train.getCabooseRoadOption().equals(Train.ALL_ROADS) || 1118 !_train.getLocoRoadOption().equals(Train.ALL_ROADS) || 1119 !_train.getLoadOption().equals(Train.ALL_LOADS)) { 1120 roadAndLoadStatusPanel.setVisible(true); 1121 } 1122 } 1123 } 1124 1125 List<Frame> children = new ArrayList<>(); 1126 1127 public void setChildFrame(Frame frame) { 1128 if (children.contains(frame)) { 1129 return; 1130 } 1131 children.add(frame); 1132 } 1133 1134 @Override 1135 public void dispose() { 1136 InstanceManager.getDefault(LocationManager.class).removePropertyChangeListener(this); 1137 InstanceManager.getDefault(EngineTypes.class).removePropertyChangeListener(this); 1138 InstanceManager.getDefault(EngineModels.class).removePropertyChangeListener(this); 1139 InstanceManager.getDefault(CarTypes.class).removePropertyChangeListener(this); 1140 InstanceManager.getDefault(CarRoads.class).removePropertyChangeListener(this); 1141 routeManager.removePropertyChangeListener(this); 1142 for (Frame frame : children) { 1143 frame.dispose(); 1144 } 1145 if (_train != null) { 1146 _train.removePropertyChangeListener(this); 1147 Route route = _train.getRoute(); 1148 if (route != null) { 1149 for (RouteLocation rl : route.getLocationsBySequenceList()) { 1150 Location loc = rl.getLocation(); 1151 if (loc != null) { 1152 loc.removePropertyChangeListener(this); 1153 } 1154 } 1155 } 1156 } 1157 super.dispose(); 1158 } 1159 1160 @Override 1161 public void propertyChange(java.beans.PropertyChangeEvent e) { 1162 if (Control.SHOW_PROPERTY) { 1163 log.debug("Property change ({}) old: ({}) new: ({})", e.getPropertyName(), e.getOldValue(), 1164 e.getNewValue()); // NOI18N 1165 } 1166 if (e.getPropertyName().equals(CarTypes.CARTYPES_CHANGED_PROPERTY) || 1167 e.getPropertyName().equals(Train.TYPES_CHANGED_PROPERTY)) { 1168 updateCarTypeCheckboxes(); 1169 } 1170 if (e.getPropertyName().equals(EngineTypes.ENGINETYPES_CHANGED_PROPERTY)) { 1171 updateEngineTypeCheckboxes(); 1172 } 1173 if (e.getPropertyName().equals(RouteManager.LISTLENGTH_CHANGED_PROPERTY)) { 1174 updateRouteComboBox(); 1175 } 1176 if (e.getPropertyName().equals(Route.LISTCHANGE_CHANGED_PROPERTY) || 1177 e.getPropertyName().equals(LocationManager.LISTLENGTH_CHANGED_PROPERTY) || 1178 e.getPropertyName().equals(Location.NAME_CHANGED_PROPERTY) || 1179 e.getPropertyName().equals(Location.TRAIN_DIRECTION_CHANGED_PROPERTY)) { 1180 updateLocationCheckboxes(); 1181 pack(); 1182 repaint(); 1183 } 1184 if (e.getPropertyName().equals(CarRoads.CARROADS_CHANGED_PROPERTY)) { 1185 updateRoadComboBoxes(); 1186 } 1187 if (e.getPropertyName().equals(EngineModels.ENGINEMODELS_CHANGED_PROPERTY)) { 1188 InstanceManager.getDefault(EngineModels.class).updateComboBox(modelEngineBox); 1189 modelEngineBox.insertItemAt(NONE, 0); 1190 modelEngineBox.setSelectedIndex(0); 1191 if (_train != null) { 1192 modelEngineBox.setSelectedItem(_train.getEngineModel()); 1193 } 1194 } 1195 if (e.getPropertyName().equals(Train.DEPARTURETIME_CHANGED_PROPERTY)) { 1196 updateDepartureTime(); 1197 } 1198 if (e.getPropertyName().equals(Train.TRAIN_ROUTE_CHANGED_PROPERTY) && _train != null) { 1199 routeBox.setSelectedItem(_train.getRoute()); 1200 } 1201 if (e.getPropertyName().equals(Route.ROUTE_STATUS_CHANGED_PROPERTY)) { 1202 updateDepartureTime(); 1203 enableButtons(_train != null); 1204 updateRouteStatus(); 1205 } 1206 if (e.getPropertyName().equals(Train.ROADS_CHANGED_PROPERTY) || 1207 e.getPropertyName().equals(Train.LOADS_CHANGED_PROPERTY)) { 1208 updateRoadAndLoadStatus(); 1209 } 1210 } 1211 1212 private static final org.slf4j.Logger log = org.slf4j.LoggerFactory.getLogger(TrainEditFrame.class); 1213}