001package jmri.jmrit.operations.setup;
002
003import java.awt.Color;
004import java.awt.JobAttributes.SidesType;
005import java.io.IOException;
006import java.util.*;
007
008import javax.swing.JComboBox;
009
010import org.jdom2.Element;
011import org.slf4j.Logger;
012import org.slf4j.LoggerFactory;
013
014import jmri.*;
015import jmri.beans.PropertyChangeSupport;
016import jmri.jmris.AbstractOperationsServer;
017import jmri.jmrit.operations.rollingstock.RollingStockLogger;
018import jmri.jmrit.operations.trains.TrainLogger;
019import jmri.jmrit.operations.trains.TrainManagerXml;
020import jmri.util.ColorUtil;
021import jmri.util.swing.JmriColorChooser;
022import jmri.web.server.WebServerPreferences;
023
024/**
025 * Operations settings.
026 *
027 * @author Daniel Boudreau Copyright (C) 2008, 2010, 2012, 2014
028 */
029public class Setup extends PropertyChangeSupport implements InstanceManagerAutoDefault, Disposable {
030
031    public static final String NONE = "";
032
033    // scale ratios from NMRA
034    private static final int Z_RATIO = 220;
035    private static final int N_RATIO = 160;
036    private static final int TT_RATIO = 120;
037    private static final int OO_RATIO = 76; // actual ratio 76.2
038    private static final int HO_RATIO = 87;
039    private static final int S_RATIO = 64;
040    private static final int O_RATIO = 48;
041    private static final int G_RATIO = 32; // NMRA #1
042
043    // initial weight in milli ounces from NMRA
044    private static final int Z_INITIAL_WEIGHT = 364; // not specified by NMRA
045    private static final int N_INITIAL_WEIGHT = 500;
046    private static final int TT_INITIAL_WEIGHT = 750;
047    private static final int HOn3_INITIAL_WEIGHT = 750;
048    private static final int OO_INITIAL_WEIGHT = 750; // not specified by NMRA
049    private static final int HO_INITIAL_WEIGHT = 1000;
050    private static final int Sn3_INITIAL_WEIGHT = 1000;
051    private static final int S_INITIAL_WEIGHT = 2000;
052    private static final int On3_INITIAL_WEIGHT = 1500;
053    private static final int O_INITIAL_WEIGHT = 5000;
054    private static final int G_INITIAL_WEIGHT = 10000; // not specified by NMRA
055
056    // additional weight in milli ounces from NMRA
057    private static final int Z_ADD_WEIGHT = 100; // not specified by NMRA
058    private static final int N_ADD_WEIGHT = 150;
059    private static final int TT_ADD_WEIGHT = 375;
060    private static final int HOn3_ADD_WEIGHT = 375;
061    private static final int OO_ADD_WEIGHT = 500; // not specified by NMRA
062    private static final int HO_ADD_WEIGHT = 500;
063    private static final int Sn3_ADD_WEIGHT = 500;
064    private static final int S_ADD_WEIGHT = 500;
065    private static final int On3_ADD_WEIGHT = 750;
066    private static final int O_ADD_WEIGHT = 1000;
067    private static final int G_ADD_WEIGHT = 2000; // not specified by NMRA
068
069    // actual weight to tons conversion ratios (based on 40' boxcar at ~80 tons)
070    private static final int Z_RATIO_TONS = 130;
071    private static final int N_RATIO_TONS = 80;
072    private static final int TT_RATIO_TONS = 36;
073    private static final int HOn3_RATIO_TONS = 20;
074    private static final int OO_RATIO_TONS = 20;
075    private static final int HO_RATIO_TONS = 20; // 20 tons per ounce
076    private static final int Sn3_RATIO_TONS = 16;
077    private static final int S_RATIO_TONS = 14;
078    private static final int On3_RATIO_TONS = 8;
079    private static final int O_RATIO_TONS = 5;
080    private static final int G_RATIO_TONS = 2;
081
082    public static final int Z_SCALE = 1;
083    public static final int N_SCALE = 2;
084    public static final int TT_SCALE = 3;
085    public static final int HOn3_SCALE = 4;
086    public static final int OO_SCALE = 5;
087    public static final int HO_SCALE = 6;
088    public static final int Sn3_SCALE = 7;
089    public static final int S_SCALE = 8;
090    public static final int On3_SCALE = 9;
091    public static final int O_SCALE = 10;
092    public static final int G_SCALE = 11; // NMRA #1
093
094    public static final int EAST = 1; // train direction serviced by this location
095    public static final int WEST = 2;
096    public static final int NORTH = 4;
097    public static final int SOUTH = 8;
098
099    public static final String EAST_DIR = Bundle.getMessage("East");
100    public static final String WEST_DIR = Bundle.getMessage("West");
101    public static final String NORTH_DIR = Bundle.getMessage("North");
102    public static final String SOUTH_DIR = Bundle.getMessage("South");
103
104    public static final String DESCRIPTIVE = Bundle.getMessage("Descriptive"); // Car types
105    public static final String AAR = Bundle.getMessage("ArrCodes"); // Car types
106
107    public static final String MONOSPACED = Bundle.getMessage("Monospaced"); // default printer font
108
109    public static final String STANDARD_FORMAT = Bundle.getMessage("StandardFormat");
110    public static final String TWO_COLUMN_FORMAT = Bundle.getMessage("TwoColumnFormat");
111    public static final String TWO_COLUMN_TRACK_FORMAT = Bundle.getMessage("TwoColumnTrackFormat");
112
113    public static final String PORTRAIT = Bundle.getMessage("Portrait");
114    public static final String LANDSCAPE = Bundle.getMessage("Landscape");
115    public static final String HALFPAGE = Bundle.getMessage("HalfPage");
116    public static final String HANDHELD = Bundle.getMessage("HandHeld");
117
118    public static final String PAGE_NORMAL = Bundle.getMessage("PageNormal");
119    public static final String PAGE_PER_TRAIN = Bundle.getMessage("PagePerTrain");
120    public static final String PAGE_PER_VISIT = Bundle.getMessage("PagePerVisit");
121
122    public static final String BUILD_REPORT_MINIMAL = "1";
123    public static final String BUILD_REPORT_NORMAL = "3";
124    public static final String BUILD_REPORT_DETAILED = "5";
125    public static final String BUILD_REPORT_VERY_DETAILED = "7";
126
127    // the following are converted to English spelling when storing to file, see KEYS below
128    public static final String ROAD = Bundle.getMessage("Road"); // the supported message format options
129    public static final String NUMBER = Bundle.getMessage("Number");
130    public static final String TYPE = Bundle.getMessage("Type");
131    public static final String MODEL = Bundle.getMessage("Model");
132    public static final String LENGTH = Bundle.getMessage("Length");
133    public static final String WEIGHT = Bundle.getMessage("Weight");
134    public static final String HP = Bundle.getMessage("HP");
135    public static final String LOAD = Bundle.getMessage("Load");
136    public static final String LOAD_TYPE = Bundle.getMessage("Load_Type");
137    public static final String COLOR = Bundle.getMessage("Color");
138    public static final String TRACK = Bundle.getMessage("Track");
139    public static final String DESTINATION = Bundle.getMessage("Destination");
140    public static final String DEST_TRACK = Bundle.getMessage("Dest&Track");
141    public static final String FINAL_DEST = Bundle.getMessage("Final_Dest");
142    public static final String FINAL_DEST_TRACK = Bundle.getMessage("FD&Track");
143    public static final String LOCATION = Bundle.getMessage("Location");
144    public static final String CONSIST = Bundle.getMessage("Consist");
145    public static final String DCC_ADDRESS = Bundle.getMessage("DCC_Address");
146    public static final String KERNEL = Bundle.getMessage("Kernel");
147    public static final String KERNEL_SIZE = Bundle.getMessage("Kernel_Size");
148    public static final String OWNER = Bundle.getMessage("Owner");
149    public static final String DIVISION = Bundle.getMessage("Division");
150    public static final String RWE = Bundle.getMessage("RWE");
151    public static final String COMMENT = Bundle.getMessage("Comment");
152    public static final String DROP_COMMENT = Bundle.getMessage("SetOut_Msg");
153    public static final String PICKUP_COMMENT = Bundle.getMessage("PickUp_Msg");
154    public static final String HAZARDOUS = Bundle.getMessage("Hazardous");
155    public static final String BLANK = " "; // blank has be a character or a space
156    public static final String TAB = Bundle.getMessage("Tab"); // used to tab out in tabular mode
157    public static final String TAB2 = Bundle.getMessage("Tab2");
158    public static final String TAB3 = Bundle.getMessage("Tab3");
159    
160    public static final String BOX = " [ ] "; // NOI18N
161
162    // these are for the utility printing when using tabs
163    public static final String NO_ROAD = "NO_ROAD"; // NOI18N
164    public static final String NO_NUMBER = "NO_NUMBER"; // NOI18N
165    public static final String NO_COLOR = "NO_COLOR"; // NOI18N
166
167    // truncated manifests
168    public static final String NO_DESTINATION = "NO_DESTINATION"; // NOI18N
169    public static final String NO_DEST_TRACK = "NO_DEST_TRACK"; // NOI18N
170    public static final String NO_LOCATION = "NO_LOCATION"; // NOI18N
171    public static final String NO_TRACK = "NO_TRACK"; // NOI18N
172
173    // Unit of Length
174    public static final String FEET = Bundle.getMessage("Feet");
175    public static final String METER = Bundle.getMessage("Meter");
176    public static final String FEET_ABV = Bundle.getMessage("FeetAbbreviation");
177    public static final String METER_ABV = Bundle.getMessage("MeterAbbreviation");
178
179    private static final String[] CAR_ATTRIBUTES = { ROAD, NUMBER, TYPE, LENGTH, WEIGHT, LOAD, LOAD_TYPE, HAZARDOUS,
180            COLOR, KERNEL, KERNEL_SIZE, OWNER, DIVISION, TRACK, LOCATION, DESTINATION, DEST_TRACK, FINAL_DEST, FINAL_DEST_TRACK,
181            COMMENT, DROP_COMMENT, PICKUP_COMMENT, RWE };
182    
183    private static final String[] ENGINE_ATTRIBUTES = {ROAD, NUMBER, TYPE, MODEL, LENGTH, WEIGHT, HP, CONSIST, OWNER,
184            TRACK, LOCATION, DESTINATION, COMMENT, DCC_ADDRESS };
185    /*
186     * The print Manifest and switch list user selectable options are stored in the
187     * xml file using the English translations.
188     */
189    private static final String[] KEYS = {"Road", "Number", "Type", "Model", "Length", "Weight", "Load", "Load_Type",
190            "HP", "Color", "Track", "Destination", "Dest&Track", "Final_Dest", "FD&Track", "Location", "Consist",
191            "DCC_Address", "Kernel", "Kernel_Size", "Owner", "Division", "RWE", "Comment", "SetOut_Msg", "PickUp_Msg",
192            "Hazardous", "Tab", "Tab2", "Tab3"};
193
194    private int scale = HO_SCALE; // Default scale
195    private int ratio = HO_RATIO;
196    private int ratioTons = HO_RATIO_TONS;
197    private int initWeight = HO_INITIAL_WEIGHT;
198    private int addWeight = HO_ADD_WEIGHT;
199    private String railroadName = NONE;
200    private int traindir = EAST + WEST + NORTH + SOUTH;
201    private int maxTrainLength = 1000; // maximum train length
202    private int maxEngineSize = 6; // maximum number of engines that can be assigned to a train
203    private double horsePowerPerTon = 1; // Horsepower per ton
204    private int carMoves = 5; // default number of moves when creating a route
205    private String carTypes = DESCRIPTIVE;
206    private String ownerName = NONE;
207    private String fontName = MONOSPACED;
208    private int manifestFontSize = 10;
209    private int buildReportFontSize = 10;
210    private String manifestOrientation = PORTRAIT;
211    private String switchListOrientation = PORTRAIT;
212    private SidesType sidesType = SidesType.ONE_SIDED;
213    private boolean printHeader = true;
214    private Color pickupEngineColor = Color.black;
215    private Color dropEngineColor = Color.black;
216    private Color pickupColor = Color.black;
217    private Color dropColor = Color.black;
218    private Color localColor = Color.black;
219    private String[] pickupEngineMessageFormat = { ROAD, NUMBER, BLANK, MODEL, BLANK, BLANK, LOCATION, COMMENT };
220    private String[] dropEngineMessageFormat = { ROAD, NUMBER, BLANK, MODEL, BLANK, BLANK, DESTINATION, COMMENT };
221    private String[] pickupManifestMessageFormat = { ROAD, NUMBER, TYPE, LENGTH, COLOR, LOAD, HAZARDOUS, LOCATION,
222            COMMENT, PICKUP_COMMENT };
223    private String[] dropManifestMessageFormat = { ROAD, NUMBER, TYPE, LENGTH, COLOR, LOAD, HAZARDOUS, DESTINATION,
224            COMMENT, DROP_COMMENT };
225    private String[] localManifestMessageFormat = { ROAD, NUMBER, TYPE, LENGTH, COLOR, LOAD, HAZARDOUS, LOCATION,
226            DESTINATION, COMMENT };
227    private String[] pickupSwitchListMessageFormat = { ROAD, NUMBER, TYPE, LENGTH, COLOR, LOAD, HAZARDOUS, LOCATION,
228            COMMENT, PICKUP_COMMENT };
229    private String[] dropSwitchListMessageFormat = { ROAD, NUMBER, TYPE, LENGTH, COLOR, LOAD, HAZARDOUS, DESTINATION,
230            COMMENT, DROP_COMMENT };
231    private String[] localSwitchListMessageFormat = { ROAD, NUMBER, TYPE, LENGTH, COLOR, LOAD, HAZARDOUS, LOCATION,
232            DESTINATION, COMMENT };
233    private String[] missingCarMessageFormat = { ROAD, NUMBER, TYPE, LENGTH, COLOR, COMMENT };
234    private String pickupEnginePrefix = BOX + Bundle.getMessage("PickUpPrefix");
235    private String dropEnginePrefix = BOX + Bundle.getMessage("SetOutPrefix");
236    private String pickupCarPrefix = BOX + Bundle.getMessage("PickUpPrefix");
237    private String dropCarPrefix = BOX + Bundle.getMessage("SetOutPrefix");
238    private String localPrefix = BOX + Bundle.getMessage("LocalCarPrefix");
239    private String switchListPickupCarPrefix = BOX + Bundle.getMessage("PickUpPrefix");
240    private String switchListDropCarPrefix = BOX + Bundle.getMessage("SetOutPrefix");
241    private String switchListLocalPrefix = BOX + Bundle.getMessage("LocalCarPrefix");
242    private String miaComment = Bundle.getMessage("misplacedCars");
243    private String hazardousMsg = "(" + Bundle.getMessage("Hazardous") + ")";
244    private String logoURL = NONE;
245    private String panelName = "Panel"; // NOI18N
246    private String buildReportLevel = BUILD_REPORT_VERY_DETAILED;
247    private String routerBuildReportLevel = BUILD_REPORT_NORMAL;
248    private int carSwitchTime = 3; // how long it takes to move a car in minutes
249    private int travelTime = 4; // how long it takes a train to move from one location to another in minutes
250    private String yearModeled = NONE; // year being modeled
251    private String lengthUnit = FEET;
252    private String lengthUnitAbv = FEET_ABV;
253    private String iconNorthColor = NONE;
254    private String iconSouthColor = NONE;
255    private String iconEastColor = NONE;
256    private String iconWestColor = NONE;
257    private String iconLocalColor = NONE;
258    private String iconTerminateColor = NONE;
259
260    private boolean tab = false; // when true, tab out manifest and switch lists
261    private int tab1CharLength = Control.max_len_string_attibute;
262    private int tab2CharLength = 6; // arbitrary lengths
263    private int tab3CharLength = 8;
264
265    private String manifestFormat = STANDARD_FORMAT;
266    private boolean manifestEditorEnabled = false; // when true use text editor to view build report
267    private boolean switchListSameManifest = true; // when true switch list format is the same as the manifest
268    private boolean manifestTruncated = false; // when true, manifest is truncated if switch list is available
269    private boolean manifestDepartureTime = false; // when true, manifest shows train's departure time
270    private boolean switchListDepartureTime = false; // when true, switch list shows train's departure time
271    private boolean switchListRouteComment = true; // when true, switch list have route location comments
272    private boolean trackSummary = true; // when true, print switch list track summary
273    private boolean groupCarMoves = false; // when true, car moves are grouped together
274    private boolean locoLast = false; // when true, loco set outs printed last
275
276    private boolean switchListRealTime = true; // when true switch list only show work for built trains
277    private boolean switchListAllTrains = true; // when true show all trains that visit the location
278    private String switchListPageFormat = PAGE_NORMAL; // how switch lists pages are printed
279
280    private boolean buildReportEditorEnabled = false; // when true use text editor to view build report
281    private boolean buildReportIndentEnabled = true; // when true use text editor to view build report
282    private boolean buildReportAlwaysPreviewEnabled = false; // when true use text editor to view build report
283
284    private boolean enableTrainIconXY = true;
285    private boolean appendTrainIcon = false; // when true, append engine number to train name
286    private String setupComment = NONE;
287
288    private boolean mainMenuEnabled = false; // when true add operations menu to main menu bar
289    private boolean closeWindowOnSave = false; // when true, close window when save button is activated
290    private boolean autoSave = true; // when true, automatically save files if modified
291    private boolean autoBackup = true; // when true, automatically backup files
292    private boolean enableValue = false; // when true show value fields for rolling stock
293    private String labelValue = Bundle.getMessage("Value");
294    private boolean enableRfid = false; // when true show RFID fields for rolling stock
295    private String labelRfid = Bundle.getMessage("RFID");
296
297    private boolean carRoutingEnabled = true; // when true enable car routing
298    private boolean carRoutingYards = true; // when true enable car routing via yard tracks
299    private boolean carRoutingStaging = false; // when true staging tracks can be used for car routing
300    private boolean forwardToYardEnabled = true; // when true forward car to yard if track is full
301    private boolean onlyActiveTrains = false; // when true only active trains are used for routing
302    private boolean checkCarDestination = false; // when true check car's track for valid destination
303
304    private boolean carLogger = false; // when true car logger is enabled
305    private boolean engineLogger = false; // when true engine logger is enabled
306    private boolean trainLogger = false; // when true train logger is enabled
307    private boolean saveTrainManifests = false; // when true save previous train manifest
308
309    private boolean aggressiveBuild = false; // when true subtract car length from track reserve length
310    private int numberPasses = 2; // the number of passes in train builder
311    private boolean allowLocalInterchangeMoves = false; // when true local C/I to C/I moves are allowed
312    private boolean allowLocalYardMoves = false; // when true local yard to yard moves are allowed
313    private boolean allowLocalSpurMoves = false; // when true local spur to spur moves are allowed
314
315    private boolean trainIntoStagingCheck = true; // staging track must accept train's rolling stock types and roads
316    private boolean trackImmediatelyAvail = false; // when true staging track is available for other trains
317    private boolean allowCarsReturnStaging = false; // allow cars on a turn to return to staging if necessary (prevent
318                                                    // build failure)
319    private boolean promptFromStaging = false; // prompt user to specify which departure staging track to use
320    private boolean promptToStaging = false; // prompt user to specify which arrival staging track to use
321    private boolean tryNormalModeStaging = true; // try normal build if route length failure using aggressive
322
323    private boolean generateCsvManifest = false; // when true generate csv manifest
324    private boolean generateCsvSwitchList = false; // when true generate csv switch list
325    private boolean enableVsdPhysicalLocations = false;
326
327    private boolean printLocationComments = false; // when true print location comments on the manifest
328    private boolean printRouteComments = false; // when true print route comments on the manifest
329    private boolean printLoadsAndEmpties = false; // when true print Loads and Empties on the manifest
330    private boolean printTrainScheduleName = false; // when true print train schedule name on manifests and switch lists
331    private boolean use12hrFormat = false; // when true use 12hr rather than 24hr format
332    private boolean printValid = true; // when true print out the valid time and date
333    private boolean sortByTrack = false; // when true manifest work is sorted by track names
334    private boolean printHeaders = false; // when true add headers to manifest and switch lists
335
336    private boolean printCabooseLoad = false; // when true print caboose load
337    private boolean printPassengerLoad = false; // when true print passenger car load
338    private boolean showTrackMoves = false; // when true show track moves in table
339
340    // property changes
341    public static final String SWITCH_LIST_CSV_PROPERTY_CHANGE = "setupSwitchListCSVChange"; // NOI18N
342    public static final String MANIFEST_CSV_PROPERTY_CHANGE = "setupManifestCSVChange"; // NOI18N
343    public static final String REAL_TIME_PROPERTY_CHANGE = "setupSwitchListRealTime"; // NOI18N
344    public static final String SHOW_TRACK_MOVES_PROPERTY_CHANGE = "setupShowTrackMoves"; // NOI18N
345    public static final String SAVE_TRAIN_MANIFEST_PROPERTY_CHANGE = "saveTrainManifestChange"; // NOI18N
346    public static final String ALLOW_CARS_TO_RETURN_PROPERTY_CHANGE = "allowCarsToReturnChange"; // NOI18N
347    public static final String TRAIN_DIRECTION_PROPERTY_CHANGE = "setupTrainDirectionChange"; // NOI18N
348    public static final String ROUTING_STAGING_PROPERTY_CHANGE = "setupRoutingStagingChange"; // NOI18N
349    public static final String TRAVEL_TIME_PROPERTY_CHANGE = "setupTravelTimeChange"; // NOI18N
350
351    public static boolean isMainMenuEnabled() {
352        InstanceManager.getDefault(OperationsSetupXml.class); // load file
353        return getDefault().mainMenuEnabled;
354    }
355
356    public static void setMainMenuEnabled(boolean enabled) {
357        getDefault().mainMenuEnabled = enabled;
358    }
359
360    public static boolean isCloseWindowOnSaveEnabled() {
361        return getDefault().closeWindowOnSave;
362    }
363
364    public static void setCloseWindowOnSaveEnabled(boolean enabled) {
365        getDefault().closeWindowOnSave = enabled;
366    }
367
368    public static boolean isAutoSaveEnabled() {
369        return getDefault().autoSave;
370    }
371
372    public static void setAutoSaveEnabled(boolean enabled) {
373        getDefault().autoSave = enabled;
374        if (enabled) {
375            AutoSave.start();
376        } else {
377            AutoSave.stop();
378        }
379    }
380
381    public static boolean isAutoBackupEnabled() {
382        return getDefault().autoBackup;
383    }
384
385    public static void setAutoBackupEnabled(boolean enabled) {
386        // Do an autoBackup only if we are changing the setting from false to
387        // true.
388        if (enabled && !getDefault().autoBackup) {
389            try {
390                new AutoBackup().autoBackup();
391            } catch (IOException ex) {
392                log.debug("Autobackup after setting AutoBackup flag true", ex);
393            }
394        }
395
396        getDefault().autoBackup = enabled;
397    }
398
399    public static boolean isValueEnabled() {
400        return getDefault().enableValue;
401    }
402
403    public static void setValueEnabled(boolean enabled) {
404        getDefault().enableValue = enabled;
405    }
406
407    public static String getValueLabel() {
408        return getDefault().labelValue;
409    }
410
411    public static void setValueLabel(String label) {
412        getDefault().labelValue = label;
413    }
414
415    public static boolean isRfidEnabled() {
416        return getDefault().enableRfid;
417    }
418
419    public static void setRfidEnabled(boolean enabled) {
420        getDefault().enableRfid = enabled;
421    }
422
423    public static String getRfidLabel() {
424        return getDefault().labelRfid;
425    }
426
427    public static void setRfidLabel(String label) {
428        getDefault().labelRfid = label;
429    }
430
431    public static boolean isCarRoutingEnabled() {
432        return getDefault().carRoutingEnabled;
433    }
434
435    public static void setCarRoutingEnabled(boolean enabled) {
436        getDefault().carRoutingEnabled = enabled;
437    }
438
439    public static boolean isCarRoutingViaYardsEnabled() {
440        return getDefault().carRoutingYards;
441    }
442
443    public static void setCarRoutingViaYardsEnabled(boolean enabled) {
444        getDefault().carRoutingYards = enabled;
445    }
446
447    public static boolean isCarRoutingViaStagingEnabled() {
448        return getDefault().carRoutingStaging;
449    }
450
451    public static void setCarRoutingViaStagingEnabled(boolean enabled) {
452        boolean old = isCarRoutingViaStagingEnabled();
453        getDefault().carRoutingStaging = enabled;
454        setDirtyAndFirePropertyChange(ROUTING_STAGING_PROPERTY_CHANGE, old, enabled);
455    }
456
457    public static boolean isForwardToYardEnabled() {
458        return getDefault().forwardToYardEnabled;
459    }
460
461    public static void setForwardToYardEnabled(boolean enabled) {
462        getDefault().forwardToYardEnabled = enabled;
463    }
464
465    public static boolean isOnlyActiveTrainsEnabled() {
466        return getDefault().onlyActiveTrains;
467    }
468
469    public static void setOnlyActiveTrainsEnabled(boolean enabled) {
470        getDefault().onlyActiveTrains = enabled;
471    }
472
473    /**
474     * When true, router checks that the car's destination is serviced by departure
475     * track. Very restrictive, not recommended.
476     * 
477     * @return true if enabled.
478     */
479    public static boolean isCheckCarDestinationEnabled() {
480        return getDefault().checkCarDestination;
481    }
482
483    public static void setCheckCarDestinationEnabled(boolean enabled) {
484        getDefault().checkCarDestination = enabled;
485    }
486
487    public static boolean isBuildAggressive() {
488        return getDefault().aggressiveBuild;
489    }
490
491    public static void setBuildAggressive(boolean enabled) {
492        getDefault().aggressiveBuild = enabled;
493    }
494
495    public static int getNumberPasses() {
496        return getDefault().numberPasses;
497    }
498
499    public static void setNumberPasses(int number) {
500        getDefault().numberPasses = number;
501    }
502
503    public static boolean isLocalInterchangeMovesEnabled() {
504        return getDefault().allowLocalInterchangeMoves;
505    }
506
507    public static void setLocalInterchangeMovesEnabled(boolean enabled) {
508        getDefault().allowLocalInterchangeMoves = enabled;
509    }
510
511    public static boolean isLocalYardMovesEnabled() {
512        return getDefault().allowLocalYardMoves;
513    }
514
515    public static void setLocalYardMovesEnabled(boolean enabled) {
516        getDefault().allowLocalYardMoves = enabled;
517    }
518
519    public static boolean isLocalSpurMovesEnabled() {
520        return getDefault().allowLocalSpurMoves;
521    }
522
523    public static void setLocalSpurMovesEnabled(boolean enabled) {
524        getDefault().allowLocalSpurMoves = enabled;
525    }
526
527    public static boolean isStagingTrainCheckEnabled() {
528        return getDefault().trainIntoStagingCheck;
529    }
530
531    /**
532     * Controls staging track selection, when true, the terminus staging track has
533     * to have the same characteristics as the train.
534     *
535     * @param enabled when true, the terminal staging track must service the same
536     *                car types, loads, etc. as the train
537     */
538    public static void setStagingTrainCheckEnabled(boolean enabled) {
539        getDefault().trainIntoStagingCheck = enabled;
540    }
541
542    public static boolean isStagingTrackImmediatelyAvail() {
543        return getDefault().trackImmediatelyAvail;
544    }
545
546    public static void setStagingTrackImmediatelyAvail(boolean enabled) {
547        getDefault().trackImmediatelyAvail = enabled;
548    }
549
550    /**
551     * allow cars to return to the same staging location if no other options
552     * (tracks) are available. Also available on a per train basis.
553     * 
554     * @return true if cars are allowed to depart and return to same staging
555     *         location
556     */
557    public static boolean isStagingAllowReturnEnabled() {
558        return getDefault().allowCarsReturnStaging;
559    }
560
561    public static void setStagingAllowReturnEnabled(boolean enabled) {
562        boolean old = getDefault().allowCarsReturnStaging;
563        getDefault().allowCarsReturnStaging = enabled;
564        setDirtyAndFirePropertyChange(ALLOW_CARS_TO_RETURN_PROPERTY_CHANGE, old, enabled);
565    }
566
567    public static boolean isStagingPromptFromEnabled() {
568        return getDefault().promptFromStaging;
569    }
570
571    public static void setStagingPromptFromEnabled(boolean enabled) {
572        getDefault().promptFromStaging = enabled;
573    }
574
575    public static boolean isStagingPromptToEnabled() {
576        return getDefault().promptToStaging;
577    }
578
579    public static void setStagingPromptToEnabled(boolean enabled) {
580        getDefault().promptToStaging = enabled;
581    }
582
583    public static boolean isStagingTryNormalBuildEnabled() {
584        return getDefault().tryNormalModeStaging;
585    }
586
587    public static void setStagingTryNormalBuildEnabled(boolean enabled) {
588        getDefault().tryNormalModeStaging = enabled;
589    }
590
591    public static boolean isGenerateCsvManifestEnabled() {
592        return getDefault().generateCsvManifest;
593    }
594
595    public static void setGenerateCsvManifestEnabled(boolean enabled) {
596        boolean old = getDefault().generateCsvManifest;
597        getDefault().generateCsvManifest = enabled;
598        if (enabled && !old) {
599            InstanceManager.getDefault(TrainManagerXml.class).createDefaultCsvManifestDirectory();
600        }
601        setDirtyAndFirePropertyChange(MANIFEST_CSV_PROPERTY_CHANGE, old, enabled);
602    }
603
604    public static boolean isGenerateCsvSwitchListEnabled() {
605        return getDefault().generateCsvSwitchList;
606    }
607
608    public static void setGenerateCsvSwitchListEnabled(boolean enabled) {
609        boolean old = getDefault().generateCsvSwitchList;
610        getDefault().generateCsvSwitchList = enabled;
611        if (enabled && !old) {
612            InstanceManager.getDefault(TrainManagerXml.class).createDefaultCsvSwitchListDirectory();
613        }
614        setDirtyAndFirePropertyChange(SWITCH_LIST_CSV_PROPERTY_CHANGE, old, enabled);
615    }
616
617    public static boolean isVsdPhysicalLocationEnabled() {
618        return getDefault().enableVsdPhysicalLocations;
619    }
620
621    public static void setVsdPhysicalLocationEnabled(boolean enabled) {
622        getDefault().enableVsdPhysicalLocations = enabled;
623    }
624
625    public static String getRailroadName() {
626        if (getDefault().railroadName.isEmpty()) {
627            return InstanceManager.getDefault(WebServerPreferences.class).getRailroadName();
628        }
629        return getDefault().railroadName;
630    }
631
632    public static void setRailroadName(String name) {
633        String old = getDefault().railroadName;
634        getDefault().railroadName = name;
635        if (old == null || !old.equals(name)) {
636            setDirtyAndFirePropertyChange("Railroad Name Change", old, name); // NOI18N
637        }
638    }
639
640    public static String getHazardousMsg() {
641        return getDefault().hazardousMsg;
642    }
643
644    public static void setHazardousMsg(String message) {
645        getDefault().hazardousMsg = message;
646    }
647
648    public static String getMiaComment() {
649        return getDefault().miaComment;
650    }
651
652    public static void setMiaComment(String comment) {
653        getDefault().miaComment = comment;
654    }
655
656    public static void setTrainDirection(int direction) {
657        int old = getDefault().traindir;
658        getDefault().traindir = direction;
659        if (old != direction) {
660            setDirtyAndFirePropertyChange(TRAIN_DIRECTION_PROPERTY_CHANGE, old, direction);
661        }
662    }
663
664    public static int getTrainDirection() {
665        return getDefault().traindir;
666    }
667
668    public static void setMaxTrainLength(int length) {
669        getDefault().maxTrainLength = length;
670    }
671
672    public static int getMaxTrainLength() {
673        return getDefault().maxTrainLength;
674    }
675
676    public static void setMaxNumberEngines(int value) {
677        getDefault().maxEngineSize = value;
678    }
679
680    public static int getMaxNumberEngines() {
681        return getDefault().maxEngineSize;
682    }
683
684    public static void setHorsePowerPerTon(double value) {
685        getDefault().horsePowerPerTon = value;
686    }
687
688    public static double getHorsePowerPerTon() {
689        return getDefault().horsePowerPerTon;
690    }
691
692    public static void setCarMoves(int moves) {
693        getDefault().carMoves = moves;
694    }
695
696    public static int getCarMoves() {
697        return getDefault().carMoves;
698    }
699
700    public static String getPanelName() {
701        return getDefault().panelName;
702    }
703
704    public static void setPanelName(String name) {
705        getDefault().panelName = name;
706    }
707
708    public static String getLengthUnit() {
709        return getDefault().lengthUnit;
710    }
711
712    /**
713     * Abbreviation unit of length
714     * 
715     * @return symbol for feet or meter
716     */
717    public static String getLengthUnitAbv() {
718        return getDefault().lengthUnitAbv;
719    }
720
721    public static void setLengthUnit(String unit) {
722        getDefault().lengthUnit = unit;
723        if (unit.equals(FEET)) {
724            getDefault().lengthUnitAbv = FEET_ABV;
725        } else {
726            getDefault().lengthUnitAbv = METER_ABV;
727        }
728    }
729
730    public static String getYearModeled() {
731        return getDefault().yearModeled;
732    }
733
734    public static void setYearModeled(String year) {
735        getDefault().yearModeled = year;
736    }
737
738    public static String getCarTypes() {
739        return getDefault().carTypes;
740    }
741
742    public static void setCarTypes(String types) {
743        getDefault().carTypes = types;
744    }
745
746    public static void setTrainIconCordEnabled(boolean enable) {
747        getDefault().enableTrainIconXY = enable;
748    }
749
750    public static boolean isTrainIconCordEnabled() {
751        return getDefault().enableTrainIconXY;
752    }
753
754    public static void setTrainIconAppendEnabled(boolean enable) {
755        getDefault().appendTrainIcon = enable;
756    }
757
758    public static boolean isTrainIconAppendEnabled() {
759        return getDefault().appendTrainIcon;
760    }
761
762    public static void setComment(String comment) {
763        getDefault().setupComment = comment;
764    }
765
766    public static String getComment() {
767        return getDefault().setupComment;
768    }
769
770    public static void setBuildReportLevel(String level) {
771        getDefault().buildReportLevel = level;
772    }
773
774    public static String getBuildReportLevel() {
775        return getDefault().buildReportLevel;
776    }
777
778    /**
779     * Sets the report level for the car router.
780     * 
781     * @param level BUILD_REPORT_NORMAL, BUILD_REPORT_DETAILED,
782     *              BUILD_REPORT_VERY_DETAILED
783     */
784    public static void setRouterBuildReportLevel(String level) {
785        getDefault().routerBuildReportLevel = level;
786    }
787
788    public static String getRouterBuildReportLevel() {
789        return getDefault().routerBuildReportLevel;
790    }
791
792    public static void setManifestEditorEnabled(boolean enable) {
793        getDefault().manifestEditorEnabled = enable;
794    }
795
796    public static boolean isManifestEditorEnabled() {
797        return getDefault().manifestEditorEnabled;
798    }
799
800    public static void setBuildReportEditorEnabled(boolean enable) {
801        getDefault().buildReportEditorEnabled = enable;
802    }
803
804    public static boolean isBuildReportEditorEnabled() {
805        return getDefault().buildReportEditorEnabled;
806    }
807
808    public static void setBuildReportIndentEnabled(boolean enable) {
809        getDefault().buildReportIndentEnabled = enable;
810    }
811
812    public static boolean isBuildReportIndentEnabled() {
813        return getDefault().buildReportIndentEnabled;
814    }
815
816    public static void setBuildReportAlwaysPreviewEnabled(boolean enable) {
817        getDefault().buildReportAlwaysPreviewEnabled = enable;
818    }
819
820    public static boolean isBuildReportAlwaysPreviewEnabled() {
821        return getDefault().buildReportAlwaysPreviewEnabled;
822    }
823
824    public static void setSwitchListFormatSameAsManifest(boolean b) {
825        getDefault().switchListSameManifest = b;
826    }
827
828    public static boolean isSwitchListFormatSameAsManifest() {
829        return getDefault().switchListSameManifest;
830    }
831
832    public static void setPrintTrackSummaryEnabled(boolean b) {
833        getDefault().trackSummary = b;
834    }
835
836    public static boolean isPrintTrackSummaryEnabled() {
837        return getDefault().trackSummary;
838    }
839
840    public static void setSwitchListRouteLocationCommentEnabled(boolean b) {
841        getDefault().switchListRouteComment = b;
842    }
843
844    public static boolean isSwitchListRouteLocationCommentEnabled() {
845        return getDefault().switchListRouteComment;
846    }
847
848    public static void setGroupCarMoves(boolean b) {
849        getDefault().groupCarMoves = b;
850    }
851
852    public static boolean isGroupCarMovesEnabled() {
853        return getDefault().groupCarMoves;
854    }
855
856    public static void setPrintLocoLast(boolean b) {
857        getDefault().locoLast = b;
858    }
859
860    public static boolean isPrintLocoLastEnabled() {
861        return getDefault().locoLast;
862    }
863
864    public static void setSwitchListRealTime(boolean b) {
865        boolean old = getDefault().switchListRealTime;
866        getDefault().switchListRealTime = b;
867        setDirtyAndFirePropertyChange(REAL_TIME_PROPERTY_CHANGE, old, b);
868    }
869
870    public static boolean isSwitchListRealTime() {
871        return getDefault().switchListRealTime;
872    }
873
874    public static void setSwitchListAllTrainsEnabled(boolean b) {
875        boolean old = getDefault().switchListAllTrains;
876        getDefault().switchListAllTrains = b;
877        setDirtyAndFirePropertyChange("Switch List All Trains", old, b); // NOI18N
878    }
879
880    /**
881     * When true switch list shows all trains visiting a location, even if the train
882     * doesn't have any work at that location. When false, switch lists only report
883     * a train if it has work at the location.
884     *
885     * @return When true show all trains visiting a location.
886     */
887    public static boolean isSwitchListAllTrainsEnabled() {
888        return getDefault().switchListAllTrains;
889    }
890
891    /**
892     * Used to determine if there's spaces or form feed between trains and locations
893     * when printing switch lists. see getSwitchListPageFormatComboBox()
894     *
895     * @param format PAGE_NORMAL, PAGE_PER_TRAIN, or PAGE_PER_VISIT
896     */
897    public static void setSwitchListPageFormat(String format) {
898        getDefault().switchListPageFormat = format;
899    }
900
901    public static String getSwitchListPageFormat() {
902        return getDefault().switchListPageFormat;
903    }
904
905    public static void setPrintTruncateManifestEnabled(boolean b) {
906        getDefault().manifestTruncated = b;
907    }
908
909    public static boolean isPrintTruncateManifestEnabled() {
910        return getDefault().manifestTruncated;
911    }
912
913    public static void setUseDepartureTimeEnabled(boolean b) {
914        getDefault().manifestDepartureTime = b;
915    }
916
917    public static boolean isUseDepartureTimeEnabled() {
918        return getDefault().manifestDepartureTime;
919    }
920
921    public static void setUseSwitchListDepartureTimeEnabled(boolean b) {
922        getDefault().switchListDepartureTime = b;
923    }
924
925    public static boolean isUseSwitchListDepartureTimeEnabled() {
926        return getDefault().switchListDepartureTime;
927    }
928
929    public static void setPrintLocationCommentsEnabled(boolean enable) {
930        getDefault().printLocationComments = enable;
931    }
932
933    public static boolean isPrintLocationCommentsEnabled() {
934        return getDefault().printLocationComments;
935    }
936
937    public static void setPrintRouteCommentsEnabled(boolean enable) {
938        getDefault().printRouteComments = enable;
939    }
940
941    public static boolean isPrintRouteCommentsEnabled() {
942        return getDefault().printRouteComments;
943    }
944
945    public static void setPrintLoadsAndEmptiesEnabled(boolean enable) {
946        getDefault().printLoadsAndEmpties = enable;
947    }
948
949    public static boolean isPrintLoadsAndEmptiesEnabled() {
950        return getDefault().printLoadsAndEmpties;
951    }
952
953    public static void setPrintTrainScheduleNameEnabled(boolean enable) {
954        getDefault().printTrainScheduleName = enable;
955    }
956
957    public static boolean isPrintTrainScheduleNameEnabled() {
958        return getDefault().printTrainScheduleName;
959    }
960
961    public static void set12hrFormatEnabled(boolean enable) {
962        getDefault().use12hrFormat = enable;
963    }
964
965    public static boolean is12hrFormatEnabled() {
966        return getDefault().use12hrFormat;
967    }
968
969    public static void setPrintValidEnabled(boolean enable) {
970        getDefault().printValid = enable;
971    }
972
973    public static boolean isPrintValidEnabled() {
974        return getDefault().printValid;
975    }
976
977    public static void setSortByTrackNameEnabled(boolean enable) {
978        getDefault().sortByTrack = enable;
979    }
980
981    /**
982     * when true manifest work is sorted by track names.
983     * 
984     * @return true if work at a location is to be sorted by track names.
985     */
986    public static boolean isSortByTrackNameEnabled() {
987        return getDefault().sortByTrack;
988    }
989
990    public static void setPrintHeadersEnabled(boolean enable) {
991        getDefault().printHeaders = enable;
992    }
993
994    public static boolean isPrintHeadersEnabled() {
995        return getDefault().printHeaders;
996    }
997
998    public static void setPrintCabooseLoadEnabled(boolean enable) {
999        getDefault().printCabooseLoad = enable;
1000    }
1001
1002    public static boolean isPrintCabooseLoadEnabled() {
1003        return getDefault().printCabooseLoad;
1004    }
1005
1006    public static void setPrintPassengerLoadEnabled(boolean enable) {
1007        getDefault().printPassengerLoad = enable;
1008    }
1009
1010    public static boolean isPrintPassengerLoadEnabled() {
1011        return getDefault().printPassengerLoad;
1012    }
1013
1014    public static void setShowTrackMovesEnabled(boolean enable) {
1015        boolean old = getDefault().showTrackMoves;
1016        getDefault().showTrackMoves = enable;
1017        setDirtyAndFirePropertyChange(SHOW_TRACK_MOVES_PROPERTY_CHANGE, old, enable);
1018    }
1019
1020    public static boolean isShowTrackMovesEnabled() {
1021        return getDefault().showTrackMoves;
1022    }
1023
1024    public static void setSwitchTime(int minutes) {
1025        getDefault().carSwitchTime = minutes;
1026    }
1027
1028    public static int getSwitchTime() {
1029        return getDefault().carSwitchTime;
1030    }
1031
1032    public static void setTravelTime(int minutes) {
1033        int old = getTravelTime();
1034        getDefault().travelTime = minutes;
1035        setDirtyAndFirePropertyChange(TRAVEL_TIME_PROPERTY_CHANGE, old, minutes);
1036    }
1037
1038    public static int getTravelTime() {
1039        return getDefault().travelTime;
1040    }
1041
1042    public static void setTrainIconColorNorth(String color) {
1043        getDefault().iconNorthColor = color;
1044    }
1045
1046    public static String getTrainIconColorNorth() {
1047        return getDefault().iconNorthColor;
1048    }
1049
1050    public static void setTrainIconColorSouth(String color) {
1051        getDefault().iconSouthColor = color;
1052    }
1053
1054    public static String getTrainIconColorSouth() {
1055        return getDefault().iconSouthColor;
1056    }
1057
1058    public static void setTrainIconColorEast(String color) {
1059        getDefault().iconEastColor = color;
1060    }
1061
1062    public static String getTrainIconColorEast() {
1063        return getDefault().iconEastColor;
1064    }
1065
1066    public static void setTrainIconColorWest(String color) {
1067        getDefault().iconWestColor = color;
1068    }
1069
1070    public static String getTrainIconColorWest() {
1071        return getDefault().iconWestColor;
1072    }
1073
1074    public static void setTrainIconColorLocal(String color) {
1075        getDefault().iconLocalColor = color;
1076    }
1077
1078    public static String getTrainIconColorLocal() {
1079        return getDefault().iconLocalColor;
1080    }
1081
1082    public static void setTrainIconColorTerminate(String color) {
1083        getDefault().iconTerminateColor = color;
1084    }
1085
1086    public static String getTrainIconColorTerminate() {
1087        return getDefault().iconTerminateColor;
1088    }
1089
1090    public static String getFontName() {
1091        return getDefault().fontName;
1092    }
1093
1094    public static void setFontName(String name) {
1095        getDefault().fontName = name;
1096    }
1097
1098    public static int getManifestFontSize() {
1099        return getDefault().manifestFontSize;
1100    }
1101
1102    public static void setManifestFontSize(int size) {
1103        getDefault().manifestFontSize = size;
1104    }
1105
1106    public static SidesType getPrintDuplexSides() {
1107        return getDefault().sidesType;
1108    }
1109
1110    public static void setPrintDuplexSides(SidesType sidesType) {
1111        getDefault().sidesType = sidesType;
1112    }
1113
1114    public static boolean isPrintPageHeaderEnabled() {
1115        return getDefault().printHeader;
1116    }
1117
1118    public static void setPrintPageHeaderEnabled(boolean enable) {
1119        getDefault().printHeader = enable;
1120    }
1121
1122    public static int getBuildReportFontSize() {
1123        return getDefault().buildReportFontSize;
1124    }
1125
1126    public static void setBuildReportFontSize(int size) {
1127        getDefault().buildReportFontSize = size;
1128    }
1129
1130    public static String getManifestOrientation() {
1131        return getDefault().manifestOrientation;
1132    }
1133
1134    public static void setManifestOrientation(String orientation) {
1135        getDefault().manifestOrientation = orientation;
1136    }
1137
1138    public static String getSwitchListOrientation() {
1139        if (isSwitchListFormatSameAsManifest()) {
1140            return getDefault().manifestOrientation;
1141        } else {
1142            return getDefault().switchListOrientation;
1143        }
1144    }
1145
1146    public static void setSwitchListOrientation(String orientation) {
1147        getDefault().switchListOrientation = orientation;
1148    }
1149
1150    public static boolean isTabEnabled() {
1151        return getDefault().tab;
1152    }
1153
1154    public static void setTabEnabled(boolean enable) {
1155        getDefault().tab = enable;
1156    }
1157
1158    public static int getTab1Length() {
1159        return getDefault().tab1CharLength;
1160    }
1161
1162    public static void setTab1length(int length) {
1163        getDefault().tab1CharLength = length;
1164    }
1165
1166    public static int getTab2Length() {
1167        return getDefault().tab2CharLength;
1168    }
1169
1170    public static void setTab2length(int length) {
1171        getDefault().tab2CharLength = length;
1172    }
1173
1174    public static int getTab3Length() {
1175        return getDefault().tab3CharLength;
1176    }
1177
1178    public static void setTab3length(int length) {
1179        getDefault().tab3CharLength = length;
1180    }
1181
1182    public static String getManifestFormat() {
1183        return getDefault().manifestFormat;
1184    }
1185
1186    /**
1187     * Sets the format for manifests
1188     * 
1189     * @param format STANDARD_FORMAT, TWO_COLUMN_FORMAT, or TWO_COLUMN_TRACK_FORMAT
1190     */
1191    public static void setManifestFormat(String format) {
1192        getDefault().manifestFormat = format;
1193    }
1194
1195    public static boolean isCarLoggerEnabled() {
1196        return getDefault().carLogger;
1197    }
1198
1199    public static void setCarLoggerEnabled(boolean enable) {
1200        getDefault().carLogger = enable;
1201        InstanceManager.getDefault(RollingStockLogger.class).enableCarLogging(enable);
1202    }
1203
1204    public static boolean isEngineLoggerEnabled() {
1205        return getDefault().engineLogger;
1206    }
1207
1208    public static void setEngineLoggerEnabled(boolean enable) {
1209        getDefault().engineLogger = enable;
1210        InstanceManager.getDefault(RollingStockLogger.class).enableEngineLogging(enable);
1211    }
1212
1213    public static boolean isTrainLoggerEnabled() {
1214        return getDefault().trainLogger;
1215    }
1216
1217    public static void setTrainLoggerEnabled(boolean enable) {
1218        getDefault().trainLogger = enable;
1219        InstanceManager.getDefault(TrainLogger.class).enableTrainLogging(enable);
1220    }
1221
1222    public static boolean isSaveTrainManifestsEnabled() {
1223        return getDefault().saveTrainManifests;
1224    }
1225
1226    public static void setSaveTrainManifestsEnabled(boolean enable) {
1227        boolean old = getDefault().saveTrainManifests;
1228        getDefault().saveTrainManifests = enable;
1229        setDirtyAndFirePropertyChange(SAVE_TRAIN_MANIFEST_PROPERTY_CHANGE, old, enable);
1230    }
1231
1232    public static String getPickupEnginePrefix() {
1233        return getDefault().pickupEnginePrefix;
1234    }
1235
1236    public static void setPickupEnginePrefix(String prefix) {
1237        getDefault().pickupEnginePrefix = prefix;
1238    }
1239
1240    public static String getDropEnginePrefix() {
1241        return getDefault().dropEnginePrefix;
1242    }
1243
1244    public static void setDropEnginePrefix(String prefix) {
1245        getDefault().dropEnginePrefix = prefix;
1246    }
1247
1248    public static String getPickupCarPrefix() {
1249        return getDefault().pickupCarPrefix;
1250    }
1251
1252    public static void setPickupCarPrefix(String prefix) {
1253        getDefault().pickupCarPrefix = prefix;
1254    }
1255
1256    public static String getDropCarPrefix() {
1257        return getDefault().dropCarPrefix;
1258    }
1259
1260    public static void setDropCarPrefix(String prefix) {
1261        getDefault().dropCarPrefix = prefix;
1262    }
1263
1264    public static String getLocalPrefix() {
1265        return getDefault().localPrefix;
1266    }
1267
1268    public static void setLocalPrefix(String prefix) {
1269        getDefault().localPrefix = prefix;
1270    }
1271
1272    public static int getManifestPrefixLength() {
1273        int maxLength = getPickupEnginePrefix().length();
1274        if (getDropEnginePrefix().length() > maxLength) {
1275            maxLength = getDropEnginePrefix().length();
1276        }
1277        if (getPickupCarPrefix().length() > maxLength) {
1278            maxLength = getPickupCarPrefix().length();
1279        }
1280        if (getDropCarPrefix().length() > maxLength) {
1281            maxLength = getDropCarPrefix().length();
1282        }
1283        if (getLocalPrefix().length() > maxLength) {
1284            maxLength = getLocalPrefix().length();
1285        }
1286        return maxLength;
1287    }
1288
1289    public static String getSwitchListPickupCarPrefix() {
1290        if (isSwitchListFormatSameAsManifest()) {
1291            return getDefault().pickupCarPrefix;
1292        } else {
1293            return getDefault().switchListPickupCarPrefix;
1294        }
1295    }
1296
1297    public static void setSwitchListPickupCarPrefix(String prefix) {
1298        getDefault().switchListPickupCarPrefix = prefix;
1299    }
1300
1301    public static String getSwitchListDropCarPrefix() {
1302        if (isSwitchListFormatSameAsManifest()) {
1303            return getDefault().dropCarPrefix;
1304        } else {
1305            return getDefault().switchListDropCarPrefix;
1306        }
1307    }
1308
1309    public static void setSwitchListDropCarPrefix(String prefix) {
1310        getDefault().switchListDropCarPrefix = prefix;
1311    }
1312
1313    public static String getSwitchListLocalPrefix() {
1314        if (isSwitchListFormatSameAsManifest()) {
1315            return getDefault().localPrefix;
1316        } else {
1317            return getDefault().switchListLocalPrefix;
1318        }
1319    }
1320
1321    public static void setSwitchListLocalPrefix(String prefix) {
1322        getDefault().switchListLocalPrefix = prefix;
1323    }
1324
1325    public static int getSwitchListPrefixLength() {
1326        int maxLength = getPickupEnginePrefix().length();
1327        if (getDropEnginePrefix().length() > maxLength) {
1328            maxLength = getDropEnginePrefix().length();
1329        }
1330        if (getSwitchListPickupCarPrefix().length() > maxLength) {
1331            maxLength = getSwitchListPickupCarPrefix().length();
1332        }
1333        if (getSwitchListDropCarPrefix().length() > maxLength) {
1334            maxLength = getSwitchListDropCarPrefix().length();
1335        }
1336        if (getSwitchListLocalPrefix().length() > maxLength) {
1337            maxLength = getSwitchListLocalPrefix().length();
1338        }
1339        return maxLength;
1340    }
1341
1342    public static String[] getEngineAttributes() {
1343        return ENGINE_ATTRIBUTES.clone();
1344    }
1345
1346    public static String[] getPickupEngineMessageFormat() {
1347        return getDefault().pickupEngineMessageFormat.clone();
1348    }
1349
1350    public static void setPickupEngineMessageFormat(String[] format) {
1351        getDefault().pickupEngineMessageFormat = format;
1352    }
1353
1354    public static String[] getDropEngineMessageFormat() {
1355        return getDefault().dropEngineMessageFormat.clone();
1356    }
1357
1358    public static void setDropEngineMessageFormat(String[] format) {
1359        getDefault().dropEngineMessageFormat = format;
1360    }
1361
1362    public static String[] getCarAttributes() {
1363        return CAR_ATTRIBUTES.clone();
1364    }
1365
1366    public static String[] getPickupManifestMessageFormat() {
1367        return getDefault().pickupManifestMessageFormat.clone();
1368    }
1369
1370    public static void setPickupManifestMessageFormat(String[] format) {
1371        getDefault().pickupManifestMessageFormat = format;
1372    }
1373
1374    public static String[] getDropManifestMessageFormat() {
1375        return getDefault().dropManifestMessageFormat.clone();
1376    }
1377
1378    public static void setDropManifestMessageFormat(String[] format) {
1379        getDefault().dropManifestMessageFormat = format;
1380    }
1381
1382    public static String[] getLocalManifestMessageFormat() {
1383        return getDefault().localManifestMessageFormat.clone();
1384    }
1385
1386    public static void setLocalManifestMessageFormat(String[] format) {
1387        getDefault().localManifestMessageFormat = format;
1388    }
1389
1390    public static String[] getMissingCarMessageFormat() {
1391        return getDefault().missingCarMessageFormat.clone();
1392    }
1393
1394    public static void setMissingCarMessageFormat(String[] format) {
1395        getDefault().missingCarMessageFormat = format;
1396    }
1397
1398    public static String[] getPickupSwitchListMessageFormat() {
1399        if (isSwitchListFormatSameAsManifest()) {
1400            return getDefault().pickupManifestMessageFormat.clone();
1401        } else {
1402            return getDefault().pickupSwitchListMessageFormat.clone();
1403        }
1404    }
1405
1406    public static void setPickupSwitchListMessageFormat(String[] format) {
1407        getDefault().pickupSwitchListMessageFormat = format;
1408    }
1409
1410    public static String[] getDropSwitchListMessageFormat() {
1411        if (isSwitchListFormatSameAsManifest()) {
1412            return getDefault().dropManifestMessageFormat.clone();
1413        } else {
1414            return getDefault().dropSwitchListMessageFormat.clone();
1415        }
1416    }
1417
1418    public static void setDropSwitchListMessageFormat(String[] format) {
1419        getDefault().dropSwitchListMessageFormat = format;
1420    }
1421
1422    public static String[] getLocalSwitchListMessageFormat() {
1423        if (isSwitchListFormatSameAsManifest()) {
1424            return getDefault().localManifestMessageFormat.clone();
1425        } else {
1426            return getDefault().localSwitchListMessageFormat.clone();
1427        }
1428    }
1429
1430    public static void setLocalSwitchListMessageFormat(String[] format) {
1431        getDefault().localSwitchListMessageFormat = format;
1432    }
1433
1434    /**
1435     * Gets the manifest format for utility cars. The car's road, number, and color
1436     * are not printed.
1437     *
1438     * @return Utility car format
1439     */
1440    public static String[] getPickupUtilityManifestMessageFormat() {
1441        return createUitlityCarMessageFormat(getPickupManifestMessageFormat());
1442    }
1443
1444    public static String[] getDropUtilityManifestMessageFormat() {
1445        return createUitlityCarMessageFormat(getDropManifestMessageFormat());
1446    }
1447
1448    public static String[] getLocalUtilityManifestMessageFormat() {
1449        return createUitlityCarMessageFormat(getLocalManifestMessageFormat());
1450    }
1451
1452    public static String[] getPickupUtilitySwitchListMessageFormat() {
1453        return createUitlityCarMessageFormat(getPickupSwitchListMessageFormat());
1454    }
1455
1456    public static String[] getDropUtilitySwitchListMessageFormat() {
1457        return createUitlityCarMessageFormat(getDropSwitchListMessageFormat());
1458    }
1459
1460    public static String[] getLocalUtilitySwitchListMessageFormat() {
1461        return createUitlityCarMessageFormat(getLocalSwitchListMessageFormat());
1462    }
1463
1464    private static String[] createUitlityCarMessageFormat(String[] format) {
1465        // remove car's road, number, color
1466        for (int i = 0; i < format.length; i++) {
1467            if (format[i].equals(ROAD)) {
1468                format[i] = NO_ROAD;
1469            } else if (format[i].equals(NUMBER)) {
1470                format[i] = NO_NUMBER;
1471            } else if (format[i].equals(COLOR)) {
1472                format[i] = NO_COLOR;
1473            }
1474        }
1475        return format;
1476    }
1477
1478    public static String[] getPickupTruncatedManifestMessageFormat() {
1479        return createTruncatedManifestMessageFormat(getPickupManifestMessageFormat());
1480    }
1481
1482    public static String[] getDropTruncatedManifestMessageFormat() {
1483        return createTruncatedManifestMessageFormat(getDropManifestMessageFormat());
1484    }
1485
1486    public static String[] createTruncatedManifestMessageFormat(String[] format) {
1487        // remove car's destination and location
1488        for (int i = 0; i < format.length; i++) {
1489            if (format[i].equals(DESTINATION)) {
1490                format[i] = NO_DESTINATION;
1491            } else if (format[i].equals(DEST_TRACK)) {
1492                format[i] = NO_DEST_TRACK;
1493            } else if (format[i].equals(LOCATION)) {
1494                format[i] = NO_LOCATION;
1495            } else if (format[i].equals(TRACK)) {
1496                format[i] = NO_TRACK;
1497            }
1498        }
1499        return format;
1500    }
1501
1502    public static String[] getPickupTwoColumnByTrackManifestMessageFormat() {
1503        return createTwoColumnByTrackPickupMessageFormat(getPickupManifestMessageFormat());
1504    }
1505
1506    public static String[] getPickupTwoColumnByTrackSwitchListMessageFormat() {
1507        return createTwoColumnByTrackPickupMessageFormat(getPickupSwitchListMessageFormat());
1508    }
1509
1510    public static String[] getPickupTwoColumnByTrackUtilityManifestMessageFormat() {
1511        return createTwoColumnByTrackPickupMessageFormat(getPickupUtilityManifestMessageFormat());
1512    }
1513
1514    public static String[] getPickupTwoColumnByTrackUtilitySwitchListMessageFormat() {
1515        return createTwoColumnByTrackPickupMessageFormat(getPickupUtilitySwitchListMessageFormat());
1516    }
1517
1518    private static String[] createTwoColumnByTrackPickupMessageFormat(String[] format) {
1519        for (int i = 0; i < format.length; i++) {
1520            if (format[i].equals(LOCATION)) {
1521                format[i] = BLANK;
1522            } else if (format[i].equals(TRACK)) {
1523                format[i] = BLANK;
1524            }
1525        }
1526        return format;
1527    }
1528
1529    public static String[] getDropTwoColumnByTrackManifestMessageFormat() {
1530        return createTwoColumnByTrackDropMessageFormat(getDropManifestMessageFormat());
1531    }
1532
1533    public static String[] getDropTwoColumnByTrackSwitchListMessageFormat() {
1534        return createTwoColumnByTrackDropMessageFormat(getDropSwitchListMessageFormat());
1535    }
1536
1537    public static String[] getDropTwoColumnByTrackUtilityManifestMessageFormat() {
1538        return createTwoColumnByTrackDropMessageFormat(getDropUtilityManifestMessageFormat());
1539    }
1540
1541    public static String[] getDropTwoColumnByTrackUtilitySwitchListMessageFormat() {
1542        return createTwoColumnByTrackDropMessageFormat(getDropUtilitySwitchListMessageFormat());
1543    }
1544
1545    private static String[] createTwoColumnByTrackDropMessageFormat(String[] format) {
1546        for (int i = 0; i < format.length; i++) {
1547            if (format[i].equals(DESTINATION)) {
1548                format[i] = BLANK;
1549            } else if (format[i].equals(TRACK)) {
1550                format[i] = BLANK;
1551            }
1552        }
1553        return format;
1554    }
1555
1556    public static String getDropEngineTextColor() {
1557        return ColorUtil.colorToColorName(getDefault().dropEngineColor);
1558    }
1559
1560    public static void setDropEngineTextColor(String color) {
1561        setDropEngineColor(ColorUtil.stringToColor(color));
1562    }
1563
1564    public static void setDropEngineColor(Color c) {
1565        getDefault().dropEngineColor = c;
1566        JmriColorChooser.addRecentColor(c);
1567    }
1568
1569    public static String getPickupEngineTextColor() {
1570        return ColorUtil.colorToColorName(getDefault().pickupEngineColor);
1571    }
1572
1573    public static void setPickupEngineTextColor(String color) {
1574        setPickupEngineColor(ColorUtil.stringToColor(color));
1575    }
1576
1577    public static void setPickupEngineColor(Color c) {
1578        getDefault().pickupEngineColor = c;
1579        JmriColorChooser.addRecentColor(c);
1580    }
1581
1582    public static String getDropTextColor() {
1583        return ColorUtil.colorToColorName(getDefault().dropColor);
1584    }
1585
1586    public static void setDropTextColor(String color) {
1587        setDropColor(ColorUtil.stringToColor(color));
1588    }
1589
1590    public static void setDropColor(Color c) {
1591        getDefault().dropColor = c;
1592        JmriColorChooser.addRecentColor(c);
1593    }
1594
1595    public static String getPickupTextColor() {
1596        return ColorUtil.colorToColorName(getDefault().pickupColor);
1597    }
1598
1599    public static void setPickupTextColor(String color) {
1600        setPickupColor(ColorUtil.stringToColor(color));
1601    }
1602
1603    public static void setPickupColor(Color c) {
1604        getDefault().pickupColor = c;
1605        JmriColorChooser.addRecentColor(c);
1606    }
1607
1608    public static String getLocalTextColor() {
1609        return ColorUtil.colorToColorName(getDefault().localColor);
1610    }
1611
1612    public static void setLocalTextColor(String color) {
1613        setLocalColor(ColorUtil.stringToColor(color));
1614    }
1615
1616    public static void setLocalColor(Color c) {
1617        getDefault().localColor = c;
1618        JmriColorChooser.addRecentColor(c);
1619    }
1620
1621    public static Color getPickupEngineColor() {
1622        return getDefault().pickupEngineColor;
1623    }
1624
1625    public static Color getDropEngineColor() {
1626        return getDefault().dropEngineColor;
1627    }
1628
1629    public static Color getPickupColor() {
1630        return getDefault().pickupColor;
1631    }
1632
1633    public static Color getDropColor() {
1634        return getDefault().dropColor;
1635    }
1636
1637    public static Color getLocalColor() {
1638        return getDefault().localColor;
1639    }
1640
1641    public static Color getColor(String colorName) {
1642        return ColorUtil.stringToColor(colorName);
1643    }
1644
1645    public static String getManifestLogoURL() {
1646        return getDefault().logoURL;
1647    }
1648
1649    public static void setManifestLogoURL(String pathName) {
1650        getDefault().logoURL = pathName;
1651    }
1652
1653    public static String getOwnerName() {
1654        return getDefault().ownerName;
1655    }
1656
1657    public static void setOwnerName(String name) {
1658        getDefault().ownerName = name;
1659    }
1660
1661    public static int getScaleRatio() {
1662        if (getDefault().scale == 0) {
1663            log.error("Scale not set");
1664        }
1665        return getDefault().ratio;
1666    }
1667
1668    public static int getScaleTonRatio() {
1669        if (getDefault().scale == 0) {
1670            log.error("Scale not set");
1671        }
1672        return getDefault().ratioTons;
1673    }
1674
1675    public static int getInitalWeight() {
1676        if (getDefault().scale == 0) {
1677            log.error("Scale not set");
1678        }
1679        return getDefault().initWeight;
1680    }
1681
1682    public static int getAddWeight() {
1683        if (getDefault().scale == 0) {
1684            log.error("Scale not set");
1685        }
1686        return getDefault().addWeight;
1687    }
1688
1689    public static int getScale() {
1690        return getDefault().scale;
1691    }
1692
1693    public static void setScale(int s) {
1694        getDefault().scale = s;
1695        switch (getDefault().scale) {
1696            case Z_SCALE:
1697                getDefault().ratio = Z_RATIO;
1698                getDefault().initWeight = Z_INITIAL_WEIGHT;
1699                getDefault().addWeight = Z_ADD_WEIGHT;
1700                getDefault().ratioTons = Z_RATIO_TONS;
1701                break;
1702            case N_SCALE:
1703                getDefault().ratio = N_RATIO;
1704                getDefault().initWeight = N_INITIAL_WEIGHT;
1705                getDefault().addWeight = N_ADD_WEIGHT;
1706                getDefault().ratioTons = N_RATIO_TONS;
1707                break;
1708            case TT_SCALE:
1709                getDefault().ratio = TT_RATIO;
1710                getDefault().initWeight = TT_INITIAL_WEIGHT;
1711                getDefault().addWeight = TT_ADD_WEIGHT;
1712                getDefault().ratioTons = TT_RATIO_TONS;
1713                break;
1714            case HOn3_SCALE:
1715                getDefault().ratio = HO_RATIO;
1716                getDefault().initWeight = HOn3_INITIAL_WEIGHT;
1717                getDefault().addWeight = HOn3_ADD_WEIGHT;
1718                getDefault().ratioTons = HOn3_RATIO_TONS;
1719                break;
1720            case OO_SCALE:
1721                getDefault().ratio = OO_RATIO;
1722                getDefault().initWeight = OO_INITIAL_WEIGHT;
1723                getDefault().addWeight = OO_ADD_WEIGHT;
1724                getDefault().ratioTons = OO_RATIO_TONS;
1725                break;
1726            case HO_SCALE:
1727                getDefault().ratio = HO_RATIO;
1728                getDefault().initWeight = HO_INITIAL_WEIGHT;
1729                getDefault().addWeight = HO_ADD_WEIGHT;
1730                getDefault().ratioTons = HO_RATIO_TONS;
1731                break;
1732            case Sn3_SCALE:
1733                getDefault().ratio = S_RATIO;
1734                getDefault().initWeight = Sn3_INITIAL_WEIGHT;
1735                getDefault().addWeight = Sn3_ADD_WEIGHT;
1736                getDefault().ratioTons = Sn3_RATIO_TONS;
1737                break;
1738            case S_SCALE:
1739                getDefault().ratio = S_RATIO;
1740                getDefault().initWeight = S_INITIAL_WEIGHT;
1741                getDefault().addWeight = S_ADD_WEIGHT;
1742                getDefault().ratioTons = S_RATIO_TONS;
1743                break;
1744            case On3_SCALE:
1745                getDefault().ratio = O_RATIO;
1746                getDefault().initWeight = On3_INITIAL_WEIGHT;
1747                getDefault().addWeight = On3_ADD_WEIGHT;
1748                getDefault().ratioTons = On3_RATIO_TONS;
1749                break;
1750            case O_SCALE:
1751                getDefault().ratio = O_RATIO;
1752                getDefault().initWeight = O_INITIAL_WEIGHT;
1753                getDefault().addWeight = O_ADD_WEIGHT;
1754                getDefault().ratioTons = O_RATIO_TONS;
1755                break;
1756            case G_SCALE:
1757                getDefault().ratio = G_RATIO;
1758                getDefault().initWeight = G_INITIAL_WEIGHT;
1759                getDefault().addWeight = G_ADD_WEIGHT;
1760                getDefault().ratioTons = G_RATIO_TONS;
1761                break;
1762            default:
1763                log.error("Unknown scale");
1764        }
1765    }
1766
1767    public static JComboBox<String> getManifestFormatComboBox() {
1768        JComboBox<String> box = new JComboBox<>();
1769        box.addItem(STANDARD_FORMAT);
1770        box.addItem(TWO_COLUMN_FORMAT);
1771        box.addItem(TWO_COLUMN_TRACK_FORMAT);
1772        return box;
1773    }
1774
1775    public static JComboBox<String> getOrientationComboBox() {
1776        JComboBox<String> box = new JComboBox<>();
1777        box.addItem(PORTRAIT);
1778        box.addItem(LANDSCAPE);
1779        box.addItem(HALFPAGE);
1780        box.addItem(HANDHELD);
1781        return box;
1782    }
1783
1784    public static JComboBox<String> getSwitchListPageFormatComboBox() {
1785        JComboBox<String> box = new JComboBox<>();
1786        box.addItem(PAGE_NORMAL);
1787        box.addItem(PAGE_PER_TRAIN);
1788        box.addItem(PAGE_PER_VISIT);
1789        return box;
1790    }
1791
1792    public static JComboBox<String> getEngineMessageComboBox() {
1793        JComboBox<String> box = new JComboBox<>();
1794        box.addItem(BLANK);
1795        for (String attribute : getEngineAttributes()) {
1796            box.addItem(attribute);
1797        }
1798        if (isTabEnabled()) {
1799            box.addItem(TAB);
1800            box.addItem(TAB2);
1801            box.addItem(TAB3);
1802        }
1803        return box;
1804    }
1805
1806    public static JComboBox<String> getCarMessageComboBox() {
1807        JComboBox<String> box = new JComboBox<>();
1808        box.addItem(BLANK);
1809        for (String attribute : getCarAttributes()) {
1810            box.addItem(attribute);
1811        }
1812        if (isTabEnabled()) {
1813            box.addItem(TAB);
1814            box.addItem(TAB2);
1815            box.addItem(TAB3);
1816        }
1817        return box;
1818    }
1819
1820    /**
1821     *
1822     * @return JComboBox loaded with the strings (North, South, East, West) showing
1823     *         the available train directions for this railroad
1824     */
1825    public static JComboBox<String> getTrainDirectionComboBox() {
1826        JComboBox<String> box = new JComboBox<>();
1827        for (String direction : getTrainDirectionList()) {
1828            box.addItem(direction);
1829        }
1830        return box;
1831    }
1832
1833    /**
1834     * Get train directions String format
1835     *
1836     * @return List of valid train directions
1837     */
1838    public static List<String> getTrainDirectionList() {
1839        List<String> directions = new ArrayList<>();
1840        if ((getDefault().traindir & EAST) == EAST) {
1841            directions.add(EAST_DIR);
1842        }
1843        if ((getDefault().traindir & WEST) == WEST) {
1844            directions.add(WEST_DIR);
1845        }
1846        if ((getDefault().traindir & NORTH) == NORTH) {
1847            directions.add(NORTH_DIR);
1848        }
1849        if ((getDefault().traindir & SOUTH) == SOUTH) {
1850            directions.add(SOUTH_DIR);
1851        }
1852        return directions;
1853    }
1854
1855    /**
1856     * Converts binary direction to String direction
1857     *
1858     * @param direction EAST, WEST, NORTH, SOUTH
1859     * @return String representation of a direction
1860     */
1861    public static String getDirectionString(int direction) {
1862        switch (direction) {
1863            case EAST:
1864                return EAST_DIR;
1865            case WEST:
1866                return WEST_DIR;
1867            case NORTH:
1868                return NORTH_DIR;
1869            case SOUTH:
1870                return SOUTH_DIR;
1871            default:
1872                return "unknown"; // NOI18N
1873        }
1874    }
1875
1876    /**
1877     * Converts binary direction to a set of String directions
1878     *
1879     * @param directions EAST, WEST, NORTH, SOUTH
1880     * @return String[] representation of a set of directions
1881     */
1882    public static String[] getDirectionStrings(int directions) {
1883        String[] dir = new String[4];
1884        int i = 0;
1885        if ((directions & EAST) == EAST) {
1886            dir[i++] = EAST_DIR;
1887        }
1888        if ((directions & WEST) == WEST) {
1889            dir[i++] = WEST_DIR;
1890        }
1891        if ((directions & NORTH) == NORTH) {
1892            dir[i++] = NORTH_DIR;
1893        }
1894        if ((directions & SOUTH) == SOUTH) {
1895            dir[i++] = SOUTH_DIR;
1896        }
1897        return dir;
1898    }
1899
1900    /**
1901     * Converts String direction to binary direction
1902     *
1903     * @param direction EAST_DIR WEST_DIR NORTH_DIR SOUTH_DIR
1904     * @return integer representation of a direction
1905     */
1906    public static int getDirectionInt(String direction) {
1907        if (direction.equals(EAST_DIR)) {
1908            return EAST;
1909        } else if (direction.equals(WEST_DIR)) {
1910            return WEST;
1911        } else if (direction.equals(NORTH_DIR)) {
1912            return NORTH;
1913        } else if (direction.equals(SOUTH_DIR)) {
1914            return SOUTH;
1915        } else {
1916            return 0; // return unknown
1917        }
1918    }
1919
1920    // must synchronize changes with operation-config.dtd
1921    public static Element store() {
1922        Element values;
1923        Element e = new Element(Xml.OPERATIONS);
1924
1925        // only store railroad name if it doesn't match the preferences railroad name
1926        if (!InstanceManager.getDefault(WebServerPreferences.class).getRailroadName().equals(getRailroadName())) {
1927            e.addContent(values = new Element(Xml.RAIL_ROAD));
1928            values.setAttribute(Xml.NAME, getRailroadName());
1929        }
1930
1931        e.addContent(values = new Element(Xml.SETUP));
1932        values.setAttribute(Xml.COMMENT, getComment());
1933
1934        e.addContent(values = new Element(Xml.SETTINGS));
1935        values.setAttribute(Xml.MAIN_MENU, isMainMenuEnabled() ? Xml.TRUE : Xml.FALSE);
1936        values.setAttribute(Xml.CLOSE_ON_SAVE, isCloseWindowOnSaveEnabled() ? Xml.TRUE : Xml.FALSE);
1937        values.setAttribute(Xml.AUTO_SAVE, isAutoSaveEnabled() ? Xml.TRUE : Xml.FALSE);
1938        values.setAttribute(Xml.AUTO_BACKUP, isAutoBackupEnabled() ? Xml.TRUE : Xml.FALSE);
1939        values.setAttribute(Xml.TRAIN_DIRECTION, Integer.toString(getTrainDirection()));
1940        values.setAttribute(Xml.TRAIN_LENGTH, Integer.toString(getMaxTrainLength()));
1941        values.setAttribute(Xml.MAX_ENGINES, Integer.toString(getMaxNumberEngines()));
1942        values.setAttribute(Xml.HPT, Double.toString(getHorsePowerPerTon()));
1943        values.setAttribute(Xml.SCALE, Integer.toString(getScale()));
1944        values.setAttribute(Xml.CAR_TYPES, getCarTypes());
1945        values.setAttribute(Xml.SWITCH_TIME, Integer.toString(getSwitchTime()));
1946        values.setAttribute(Xml.TRAVEL_TIME, Integer.toString(getTravelTime()));
1947        values.setAttribute(Xml.SHOW_VALUE, isValueEnabled() ? Xml.TRUE : Xml.FALSE);
1948        values.setAttribute(Xml.VALUE_LABEL, getValueLabel());
1949        values.setAttribute(Xml.SHOW_RFID, isRfidEnabled() ? Xml.TRUE : Xml.FALSE);
1950        values.setAttribute(Xml.RFID_LABEL, getRfidLabel());
1951        values.setAttribute(Xml.LENGTH_UNIT, getLengthUnit());
1952        values.setAttribute(Xml.YEAR_MODELED, getYearModeled());
1953
1954        e.addContent(values = new Element(Xml.PICKUP_ENG_FORMAT));
1955        storeXmlMessageFormat(values, getPickupEnginePrefix(), getPickupEngineMessageFormat());
1956
1957        e.addContent(values = new Element(Xml.DROP_ENG_FORMAT));
1958        storeXmlMessageFormat(values, getDropEnginePrefix(), getDropEngineMessageFormat());
1959
1960        e.addContent(values = new Element(Xml.PICKUP_CAR_FORMAT));
1961        storeXmlMessageFormat(values, getPickupCarPrefix(), getPickupManifestMessageFormat());
1962
1963        e.addContent(values = new Element(Xml.DROP_CAR_FORMAT));
1964        storeXmlMessageFormat(values, getDropCarPrefix(), getDropManifestMessageFormat());
1965
1966        e.addContent(values = new Element(Xml.LOCAL_FORMAT));
1967        storeXmlMessageFormat(values, getLocalPrefix(), getLocalManifestMessageFormat());
1968
1969        e.addContent(values = new Element(Xml.MISSING_CAR_FORMAT));
1970        storeXmlMessageFormat(values, NONE, getMissingCarMessageFormat());
1971
1972        e.addContent(values = new Element(Xml.SWITCH_LIST));
1973        values.setAttribute(Xml.SAME_AS_MANIFEST, isSwitchListFormatSameAsManifest() ? Xml.TRUE : Xml.FALSE);
1974        values.setAttribute(Xml.REAL_TIME, isSwitchListRealTime() ? Xml.TRUE : Xml.FALSE);
1975        values.setAttribute(Xml.ALL_TRAINS, isSwitchListAllTrainsEnabled() ? Xml.TRUE : Xml.FALSE);
1976
1977        // save switch list format
1978        String format = Xml.PAGE_NORMAL;
1979        if (getSwitchListPageFormat().equals(PAGE_PER_TRAIN)) {
1980            format = Xml.PAGE_PER_TRAIN;
1981            values.setAttribute(Xml.PAGE_MODE, Xml.TRUE); // backwards compatible for versions before 3.11
1982        } else if (getSwitchListPageFormat().equals(PAGE_PER_VISIT)) {
1983            format = Xml.PAGE_PER_VISIT;
1984        }
1985        values.setAttribute(Xml.PAGE_FORMAT, format);
1986
1987        values.setAttribute(Xml.PRINT_ROUTE_LOCATION, isSwitchListRouteLocationCommentEnabled() ? Xml.TRUE : Xml.FALSE);
1988        values.setAttribute(Xml.TRACK_SUMMARY, isPrintTrackSummaryEnabled() ? Xml.TRUE : Xml.FALSE);
1989        values.setAttribute(Xml.USE_DEPARTURE_TIME, isUseSwitchListDepartureTimeEnabled() ? Xml.TRUE : Xml.FALSE);
1990
1991        e.addContent(values = new Element(Xml.SWITCH_LIST_PICKUP_CAR_FORMAT));
1992        storeXmlMessageFormat(values, getSwitchListPickupCarPrefix(), getPickupSwitchListMessageFormat());
1993
1994        e.addContent(values = new Element(Xml.SWITCH_LIST_DROP_CAR_FORMAT));
1995        storeXmlMessageFormat(values, getSwitchListDropCarPrefix(), getDropSwitchListMessageFormat());
1996
1997        e.addContent(values = new Element(Xml.SWITCH_LIST_LOCAL_FORMAT));
1998        storeXmlMessageFormat(values, getSwitchListLocalPrefix(), getLocalSwitchListMessageFormat());
1999
2000        e.addContent(values = new Element(Xml.PANEL));
2001        values.setAttribute(Xml.NAME, getPanelName());
2002        values.setAttribute(Xml.TRAIN_ICONXY, isTrainIconCordEnabled() ? Xml.TRUE : Xml.FALSE);
2003        values.setAttribute(Xml.TRAIN_ICON_APPEND, isTrainIconAppendEnabled() ? Xml.TRUE : Xml.FALSE);
2004
2005        e.addContent(values = new Element(Xml.FONT_NAME));
2006        values.setAttribute(Xml.NAME, getFontName());
2007
2008        e.addContent(values = new Element(Xml.FONT_SIZE));
2009        values.setAttribute(Xml.SIZE, Integer.toString(getManifestFontSize()));
2010
2011        e.addContent(values = new Element(Xml.PAGE_ORIENTATION));
2012        values.setAttribute(Xml.MANIFEST, getManifestOrientation());
2013        values.setAttribute(Xml.SWITCH_LIST, getSwitchListOrientation());
2014
2015        e.addContent(values = new Element(Xml.PRINT_DUPLEX));
2016        values.setAttribute(Xml.NAME, getPrintDuplexSides().toString());
2017
2018        e.addContent(values = new Element(Xml.MANIFEST_COLORS));
2019        values.setAttribute(Xml.DROP_ENGINE_COLOR, getDropEngineTextColor());
2020        values.setAttribute(Xml.PICKUP_ENGINE_COLOR, getPickupEngineTextColor());
2021        values.setAttribute(Xml.DROP_COLOR, getDropTextColor());
2022        values.setAttribute(Xml.PICKUP_COLOR, getPickupTextColor());
2023        values.setAttribute(Xml.LOCAL_COLOR, getLocalTextColor());
2024
2025        e.addContent(values = new Element(Xml.TAB));
2026        values.setAttribute(Xml.ENABLED, isTabEnabled() ? Xml.TRUE : Xml.FALSE);
2027        values.setAttribute(Xml.LENGTH, Integer.toString(getTab1Length()));
2028        values.setAttribute(Xml.TAB2_LENGTH, Integer.toString(getTab2Length()));
2029        values.setAttribute(Xml.TAB3_LENGTH, Integer.toString(getTab3Length()));
2030
2031        e.addContent(values = new Element(Xml.MANIFEST));
2032        values.setAttribute(Xml.PRINT_LOC_COMMENTS, isPrintLocationCommentsEnabled() ? Xml.TRUE : Xml.FALSE);
2033        values.setAttribute(Xml.PRINT_ROUTE_COMMENTS, isPrintRouteCommentsEnabled() ? Xml.TRUE : Xml.FALSE);
2034        values.setAttribute(Xml.PRINT_LOADS_EMPTIES, isPrintLoadsAndEmptiesEnabled() ? Xml.TRUE : Xml.FALSE);
2035        values.setAttribute(Xml.PRINT_TRAIN_SCHEDULE, isPrintTrainScheduleNameEnabled() ? Xml.TRUE : Xml.FALSE);
2036        values.setAttribute(Xml.USE12HR_FORMAT, is12hrFormatEnabled() ? Xml.TRUE : Xml.FALSE);
2037        values.setAttribute(Xml.PRINT_VALID, isPrintValidEnabled() ? Xml.TRUE : Xml.FALSE);
2038        values.setAttribute(Xml.SORT_BY_TRACK, isSortByTrackNameEnabled() ? Xml.TRUE : Xml.FALSE);
2039        values.setAttribute(Xml.PRINT_PAGE_HEADER, isPrintPageHeaderEnabled() ? Xml.TRUE : Xml.FALSE);
2040        values.setAttribute(Xml.PRINT_HEADERS, isPrintHeadersEnabled() ? Xml.TRUE : Xml.FALSE);
2041        values.setAttribute(Xml.TRUNCATE, isPrintTruncateManifestEnabled() ? Xml.TRUE : Xml.FALSE);
2042        values.setAttribute(Xml.USE_DEPARTURE_TIME, isUseDepartureTimeEnabled() ? Xml.TRUE : Xml.FALSE);
2043        values.setAttribute(Xml.USE_EDITOR, isManifestEditorEnabled() ? Xml.TRUE : Xml.FALSE);
2044        values.setAttribute(Xml.PRINT_CABOOSE_LOAD, isPrintCabooseLoadEnabled() ? Xml.TRUE : Xml.FALSE);
2045        values.setAttribute(Xml.PRINT_PASSENGER_LOAD, isPrintPassengerLoadEnabled() ? Xml.TRUE : Xml.FALSE);
2046        values.setAttribute(Xml.GROUP_MOVES, isGroupCarMovesEnabled() ? Xml.TRUE : Xml.FALSE);
2047        values.setAttribute(Xml.PRINT_LOCO_LAST, isPrintLocoLastEnabled() ? Xml.TRUE : Xml.FALSE);
2048        values.setAttribute(Xml.HAZARDOUS_MSG, getHazardousMsg());
2049
2050        // new format June 2014
2051        e.addContent(values = new Element(Xml.MANIFEST_FORMAT));
2052
2053        // save manifest format
2054        String value = Xml.STANDARD;
2055        if (getManifestFormat().equals(TWO_COLUMN_FORMAT)) {
2056            value = Xml.TWO_COLUMN;
2057        } else if (getManifestFormat().equals(TWO_COLUMN_TRACK_FORMAT)) {
2058            value = Xml.TWO_COLUMN_TRACK;
2059        }
2060        values.setAttribute(Xml.VALUE, value);
2061
2062        if (!getManifestLogoURL().equals(NONE)) {
2063            values = new Element(Xml.MANIFEST_LOGO);
2064            values.setAttribute(Xml.NAME, getManifestLogoURL());
2065            e.addContent(values);
2066        }
2067
2068        // manifest save file options
2069        e.addContent(values = new Element(Xml.MANIFEST_FILE_OPTIONS));
2070        values.setAttribute(Xml.MANIFEST_SAVE, isSaveTrainManifestsEnabled() ? Xml.TRUE : Xml.FALSE);
2071
2072        e.addContent(values = new Element(Xml.BUILD_OPTIONS));
2073        values.setAttribute(Xml.AGGRESSIVE, isBuildAggressive() ? Xml.TRUE : Xml.FALSE);
2074        values.setAttribute(Xml.NUMBER_PASSES, Integer.toString(getNumberPasses()));
2075
2076        values.setAttribute(Xml.ALLOW_LOCAL_INTERCHANGE, isLocalInterchangeMovesEnabled() ? Xml.TRUE : Xml.FALSE);
2077        values.setAttribute(Xml.ALLOW_LOCAL_SPUR, isLocalSpurMovesEnabled() ? Xml.TRUE : Xml.FALSE);
2078        values.setAttribute(Xml.ALLOW_LOCAL_YARD, isLocalYardMovesEnabled() ? Xml.TRUE : Xml.FALSE);
2079
2080        values.setAttribute(Xml.STAGING_RESTRICTION_ENABLED, isStagingTrainCheckEnabled() ? Xml.TRUE : Xml.FALSE);
2081        values.setAttribute(Xml.STAGING_TRACK_AVAIL, isStagingTrackImmediatelyAvail() ? Xml.TRUE : Xml.FALSE);
2082        values.setAttribute(Xml.ALLOW_RETURN_STAGING, isStagingAllowReturnEnabled() ? Xml.TRUE : Xml.FALSE);
2083        values.setAttribute(Xml.PROMPT_STAGING_ENABLED, isStagingPromptFromEnabled() ? Xml.TRUE : Xml.FALSE);
2084        values.setAttribute(Xml.PROMPT_TO_STAGING_ENABLED, isStagingPromptToEnabled() ? Xml.TRUE : Xml.FALSE);
2085        values.setAttribute(Xml.STAGING_TRY_NORMAL, isStagingTryNormalBuildEnabled() ? Xml.TRUE : Xml.FALSE);
2086
2087        values.setAttribute(Xml.GENERATE_CSV_MANIFEST, isGenerateCsvManifestEnabled() ? Xml.TRUE : Xml.FALSE);
2088        values.setAttribute(Xml.GENERATE_CSV_SWITCH_LIST, isGenerateCsvSwitchListEnabled() ? Xml.TRUE : Xml.FALSE);
2089
2090        e.addContent(values = new Element(Xml.BUILD_REPORT));
2091        values.setAttribute(Xml.LEVEL, getBuildReportLevel());
2092        values.setAttribute(Xml.ROUTER_LEVEL, getRouterBuildReportLevel());
2093        values.setAttribute(Xml.USE_EDITOR, isBuildReportEditorEnabled() ? Xml.TRUE : Xml.FALSE);
2094        values.setAttribute(Xml.INDENT, isBuildReportIndentEnabled() ? Xml.TRUE : Xml.FALSE);
2095        values.setAttribute(Xml.ALWAYS_PREVIEW, isBuildReportAlwaysPreviewEnabled() ? Xml.TRUE : Xml.FALSE);
2096        values.setAttribute(Xml.FONT_SIZE, Integer.toString(getBuildReportFontSize()));
2097
2098        // new format for router options
2099        e.addContent(values = new Element(Xml.ROUTER));
2100        values.setAttribute(Xml.CAR_ROUTING_ENABLED, isCarRoutingEnabled() ? Xml.TRUE : Xml.FALSE);
2101        values.setAttribute(Xml.CAR_ROUTING_VIA_YARDS, isCarRoutingViaYardsEnabled() ? Xml.TRUE : Xml.FALSE);
2102        values.setAttribute(Xml.CAR_ROUTING_VIA_STAGING, isCarRoutingViaStagingEnabled() ? Xml.TRUE : Xml.FALSE);
2103        values.setAttribute(Xml.FORWARD_TO_YARD, isForwardToYardEnabled() ? Xml.TRUE : Xml.FALSE);
2104        values.setAttribute(Xml.ONLY_ACTIVE_TRAINS, isOnlyActiveTrainsEnabled() ? Xml.TRUE : Xml.FALSE);
2105        values.setAttribute(Xml.CHECK_CAR_DESTINATION, isCheckCarDestinationEnabled() ? Xml.TRUE : Xml.FALSE);
2106
2107        // new format for logger options
2108        e.addContent(values = new Element(Xml.LOGGER));
2109        values.setAttribute(Xml.CAR_LOGGER, isCarLoggerEnabled() ? Xml.TRUE : Xml.FALSE);
2110        values.setAttribute(Xml.ENGINE_LOGGER, isEngineLoggerEnabled() ? Xml.TRUE : Xml.FALSE);
2111        values.setAttribute(Xml.TRAIN_LOGGER, isTrainLoggerEnabled() ? Xml.TRUE : Xml.FALSE);
2112
2113        e.addContent(values = new Element(Xml.OWNER));
2114        values.setAttribute(Xml.NAME, getOwnerName());
2115
2116        e.addContent(values = new Element(Xml.ICON_COLOR));
2117        values.setAttribute(Xml.NORTH, getTrainIconColorNorth());
2118        values.setAttribute(Xml.SOUTH, getTrainIconColorSouth());
2119        values.setAttribute(Xml.EAST, getTrainIconColorEast());
2120        values.setAttribute(Xml.WEST, getTrainIconColorWest());
2121        values.setAttribute(Xml.LOCAL, getTrainIconColorLocal());
2122        values.setAttribute(Xml.TERMINATE, getTrainIconColorTerminate());
2123
2124        e.addContent(values = new Element(Xml.COMMENTS));
2125        values.setAttribute(Xml.MISPLACED_CARS, getMiaComment());
2126
2127        e.addContent(values = new Element(Xml.DISPLAY));
2128        values.setAttribute(Xml.SHOW_TRACK_MOVES, isShowTrackMovesEnabled() ? Xml.TRUE : Xml.FALSE);
2129
2130        if (isVsdPhysicalLocationEnabled()) {
2131            e.addContent(values = new Element(Xml.VSD));
2132            values.setAttribute(Xml.ENABLE_PHYSICAL_LOCATIONS, isVsdPhysicalLocationEnabled() ? Xml.TRUE : Xml.FALSE);
2133        }
2134
2135        // Save CATS setting
2136        e.addContent(values = new Element(Xml.CATS));
2137        values.setAttribute(Xml.EXACT_LOCATION_NAME,
2138                AbstractOperationsServer.isExactLoationNameEnabled() ? Xml.TRUE : Xml.FALSE);
2139        return e;
2140    }
2141
2142    private static void storeXmlMessageFormat(Element values, String prefix, String[] messageFormat) {
2143        values.setAttribute(Xml.PREFIX, prefix);
2144        StringBuilder buf = new StringBuilder();
2145        stringToTagConversion(messageFormat);
2146        for (String attibute : messageFormat) {
2147            buf.append(attibute).append(",");
2148        }
2149        values.setAttribute(Xml.SETTING, buf.toString());
2150    }
2151
2152    public static void load(Element e) {
2153        if (e.getChild(Xml.OPERATIONS) == null) {
2154            log.warn("OperationsPro settings values not found");
2155            return;
2156        }
2157        Element operations = e.getChild(Xml.OPERATIONS);
2158        org.jdom2.Attribute a;
2159
2160        if ((operations.getChild(Xml.RAIL_ROAD) != null) &&
2161                (a = operations.getChild(Xml.RAIL_ROAD).getAttribute(Xml.NAME)) != null) {
2162            String name = a.getValue();
2163            log.debug("railroadName: {}", name);
2164            // code before 4.11 "useJmriRailroadName" when using the preferences railroad
2165            // name.
2166            // here for backwards compatibility
2167            if (!name.equals(Xml.USE_JMRI_RAILROAD_NAME)) {
2168                getDefault().railroadName = name; // don't set the dirty bit
2169            }
2170        }
2171
2172        if ((operations.getChild(Xml.SETUP) != null) &&
2173                (a = operations.getChild(Xml.SETUP).getAttribute(Xml.COMMENT)) != null) {
2174            String comment = a.getValue();
2175            log.debug("setup comment: {}", comment);
2176            getDefault().setupComment = comment;
2177        }
2178
2179        if (operations.getChild(Xml.SETTINGS) != null) {
2180            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.MAIN_MENU)) != null) {
2181                String enabled = a.getValue();
2182                log.debug("mainMenu: {}", enabled);
2183                setMainMenuEnabled(enabled.equals(Xml.TRUE));
2184            }
2185            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.CLOSE_ON_SAVE)) != null) {
2186                String enabled = a.getValue();
2187                log.debug("closeOnSave: {}", enabled);
2188                setCloseWindowOnSaveEnabled(enabled.equals(Xml.TRUE));
2189            }
2190            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.TRAIN_DIRECTION)) != null) {
2191                String dir = a.getValue();
2192                log.debug("direction: {}", dir);
2193                try {
2194                    getDefault().traindir = Integer.parseInt(dir);
2195                } catch (NumberFormatException ee) {
2196                    log.error("Train direction ({}) isn't a valid number", a.getValue());
2197                }
2198            }
2199            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.TRAIN_LENGTH)) != null) {
2200                String length = a.getValue();
2201                log.debug("Max train length: {}", length);
2202                try {
2203                    setMaxTrainLength(Integer.parseInt(length));
2204                } catch (NumberFormatException ee) {
2205                    log.error("Train maximum length ({}) isn't a valid number", a.getValue());
2206                }
2207            }
2208            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.MAX_ENGINES)) != null) {
2209                String size = a.getValue();
2210                log.debug("Max number of engines: {}", size);
2211                try {
2212                    setMaxNumberEngines(Integer.parseInt(size));
2213                } catch (NumberFormatException ee) {
2214                    log.error("Maximum number of engines ({}) isn't a valid number", a.getValue());
2215                }
2216            }
2217            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.HPT)) != null) {
2218                String value = a.getValue();
2219                log.debug("HPT: {}", value);
2220                try {
2221                    setHorsePowerPerTon(Double.parseDouble(value));
2222                } catch (NumberFormatException ee) {
2223                    log.error("Train HPT ({}) isn't a valid number", a.getValue());
2224                }
2225            }
2226            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.SCALE)) != null) {
2227                String scale = a.getValue();
2228                log.debug("scale: {}", scale);
2229                try {
2230                    setScale(Integer.parseInt(scale));
2231                } catch (NumberFormatException ee) {
2232                    log.error("Scale ({}) isn't a valid number", a.getValue());
2233                }
2234            }
2235            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.CAR_TYPES)) != null) {
2236                String types = a.getValue();
2237                log.debug("CarTypes: {}", types);
2238                setCarTypes(types);
2239            }
2240            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.SWITCH_TIME)) != null) {
2241                String minutes = a.getValue();
2242                log.debug("switchTime: {}", minutes);
2243                try {
2244                    setSwitchTime(Integer.parseInt(minutes));
2245                } catch (NumberFormatException ee) {
2246                    log.error("Switch time ({}) isn't a valid number", a.getValue());
2247                }
2248            }
2249            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.TRAVEL_TIME)) != null) {
2250                String minutes = a.getValue();
2251                log.debug("travelTime: {}", minutes);
2252                try {
2253                    setTravelTime(Integer.parseInt(minutes));
2254                } catch (NumberFormatException ee) {
2255                    log.error("Travel time ({}) isn't a valid number", a.getValue());
2256                }
2257            }
2258            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.SHOW_VALUE)) != null) {
2259                String enable = a.getValue();
2260                log.debug("showValue: {}", enable);
2261                setValueEnabled(enable.equals(Xml.TRUE));
2262            }
2263            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.VALUE_LABEL)) != null) {
2264                String label = a.getValue();
2265                log.debug("valueLabel: {}", label);
2266                setValueLabel(label);
2267            }
2268            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.SHOW_RFID)) != null) {
2269                String enable = a.getValue();
2270                log.debug("showRfid: {}", enable);
2271                setRfidEnabled(enable.equals(Xml.TRUE));
2272            }
2273            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.RFID_LABEL)) != null) {
2274                String label = a.getValue();
2275                log.debug("rfidLabel: {}", label);
2276                setRfidLabel(label);
2277            }
2278            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.LENGTH_UNIT)) != null) {
2279                String unit = a.getValue();
2280                log.debug("lengthUnit: {}", unit);
2281                setLengthUnit(unit);
2282            }
2283            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.YEAR_MODELED)) != null) {
2284                String year = a.getValue();
2285                log.debug("yearModeled: {}", year);
2286                setYearModeled(year);
2287            }
2288            // next eight attributes are here for backward compatibility
2289            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.PRINT_LOC_COMMENTS)) != null) {
2290                String enable = a.getValue();
2291                log.debug("printLocComments: {}", enable);
2292                setPrintLocationCommentsEnabled(enable.equals(Xml.TRUE));
2293            }
2294            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.PRINT_ROUTE_COMMENTS)) != null) {
2295                String enable = a.getValue();
2296                log.debug("printRouteComments: {}", enable);
2297                setPrintRouteCommentsEnabled(enable.equals(Xml.TRUE));
2298            }
2299            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.PRINT_LOADS_EMPTIES)) != null) {
2300                String enable = a.getValue();
2301                log.debug("printLoadsEmpties: {}", enable);
2302                setPrintLoadsAndEmptiesEnabled(enable.equals(Xml.TRUE));
2303            }
2304            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.PRINT_TRAIN_SCHEDULE)) != null) {
2305                String enable = a.getValue();
2306                log.debug("printTrainSchedule: {}", enable);
2307                setPrintTrainScheduleNameEnabled(enable.equals(Xml.TRUE));
2308            }
2309            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.USE12HR_FORMAT)) != null) {
2310                String enable = a.getValue();
2311                log.debug("use12hrFormat: {}", enable);
2312                set12hrFormatEnabled(enable.equals(Xml.TRUE));
2313            }
2314            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.PRINT_VALID)) != null) {
2315                String enable = a.getValue();
2316                log.debug("printValid: {}", enable);
2317                setPrintValidEnabled(enable.equals(Xml.TRUE));
2318            }
2319            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.SORT_BY_TRACK)) != null) {
2320                String enable = a.getValue();
2321                log.debug("sortByTrack: {}", enable);
2322                setSortByTrackNameEnabled(enable.equals(Xml.TRUE));
2323            }
2324            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.PRINT_HEADERS)) != null) {
2325                String enable = a.getValue();
2326                log.debug("printHeaders: {}", enable);
2327                setPrintHeadersEnabled(enable.equals(Xml.TRUE));
2328            }
2329        }
2330        if (operations.getChild(Xml.PICKUP_ENG_FORMAT) != null) {
2331            if ((a = operations.getChild(Xml.PICKUP_ENG_FORMAT).getAttribute(Xml.PREFIX)) != null) {
2332                setPickupEnginePrefix(a.getValue());
2333            }
2334            if ((a = operations.getChild(Xml.PICKUP_ENG_FORMAT).getAttribute(Xml.SETTING)) != null) {
2335                String setting = a.getValue();
2336                log.debug("pickupEngFormat: {}", setting);
2337                String[] keys = setting.split(",");
2338                xmlAttributeToKeyConversion(keys);
2339                keyToStringConversion(keys);
2340                setPickupEngineMessageFormat(keys);
2341            }
2342        }
2343        if (operations.getChild(Xml.DROP_ENG_FORMAT) != null) {
2344            if ((a = operations.getChild(Xml.DROP_ENG_FORMAT).getAttribute(Xml.PREFIX)) != null) {
2345                setDropEnginePrefix(a.getValue());
2346            }
2347            if ((a = operations.getChild(Xml.DROP_ENG_FORMAT).getAttribute(Xml.SETTING)) != null) {
2348                String setting = a.getValue();
2349                log.debug("dropEngFormat: {}", setting);
2350                String[] keys = setting.split(",");
2351                xmlAttributeToKeyConversion(keys);
2352                keyToStringConversion(keys);
2353                setDropEngineMessageFormat(keys);
2354            }
2355        }
2356        if (operations.getChild(Xml.PICKUP_CAR_FORMAT) != null) {
2357            if ((a = operations.getChild(Xml.PICKUP_CAR_FORMAT).getAttribute(Xml.PREFIX)) != null) {
2358                setPickupCarPrefix(a.getValue());
2359            }
2360            if ((a = operations.getChild(Xml.PICKUP_CAR_FORMAT).getAttribute(Xml.SETTING)) != null) {
2361                String setting = a.getValue();
2362                log.debug("pickupCarFormat: {}", setting);
2363                String[] keys = setting.split(",");
2364                replaceOldFormat(keys);
2365                xmlAttributeToKeyConversion(keys);
2366                keyToStringConversion(keys);
2367                setPickupManifestMessageFormat(keys);
2368            }
2369        }
2370        if (operations.getChild(Xml.DROP_CAR_FORMAT) != null) {
2371            if ((a = operations.getChild(Xml.DROP_CAR_FORMAT).getAttribute(Xml.PREFIX)) != null) {
2372                setDropCarPrefix(a.getValue());
2373            }
2374            if ((a = operations.getChild(Xml.DROP_CAR_FORMAT).getAttribute(Xml.SETTING)) != null) {
2375                String setting = a.getValue();
2376                log.debug("dropCarFormat: {}", setting);
2377                String[] keys = setting.split(",");
2378                replaceOldFormat(keys);
2379                xmlAttributeToKeyConversion(keys);
2380                keyToStringConversion(keys);
2381                setDropManifestMessageFormat(keys);
2382            }
2383        }
2384        if (operations.getChild(Xml.LOCAL_FORMAT) != null) {
2385            if ((a = operations.getChild(Xml.LOCAL_FORMAT).getAttribute(Xml.PREFIX)) != null) {
2386                setLocalPrefix(a.getValue());
2387            }
2388            if ((a = operations.getChild(Xml.LOCAL_FORMAT).getAttribute(Xml.SETTING)) != null) {
2389                String setting = a.getValue();
2390                log.debug("localFormat: {}", setting);
2391                String[] keys = setting.split(",");
2392                replaceOldFormat(keys);
2393                xmlAttributeToKeyConversion(keys);
2394                keyToStringConversion(keys);
2395                setLocalManifestMessageFormat(keys);
2396            }
2397        }
2398        if (operations.getChild(Xml.MISSING_CAR_FORMAT) != null) {
2399            if ((a = operations.getChild(Xml.MISSING_CAR_FORMAT).getAttribute(Xml.SETTING)) != null) {
2400                String setting = a.getValue();
2401                log.debug("missingCarFormat: {}", setting);
2402                String[] keys = setting.split(",");
2403                keyToStringConversion(keys);
2404                setMissingCarMessageFormat(keys);
2405            }
2406        }
2407        if (operations.getChild(Xml.SWITCH_LIST) != null) {
2408            if ((a = operations.getChild(Xml.SWITCH_LIST).getAttribute(Xml.SAME_AS_MANIFEST)) != null) {
2409                String b = a.getValue();
2410                log.debug("sameAsManifest: {}", b);
2411                setSwitchListFormatSameAsManifest(b.equals(Xml.TRUE));
2412            }
2413            if ((a = operations.getChild(Xml.SWITCH_LIST).getAttribute(Xml.REAL_TIME)) != null) {
2414                String b = a.getValue();
2415                log.debug("realTime: {}", b);
2416                getDefault().switchListRealTime = b.equals(Xml.TRUE);
2417            }
2418            if ((a = operations.getChild(Xml.SWITCH_LIST).getAttribute(Xml.ALL_TRAINS)) != null) {
2419                String b = a.getValue();
2420                log.debug("allTrains: {}", b);
2421                getDefault().switchListAllTrains = b.equals(Xml.TRUE);
2422            }
2423            if ((a = operations.getChild(Xml.SWITCH_LIST).getAttribute(Xml.PAGE_FORMAT)) != null) {
2424                switch (a.getValue()) {
2425                    case Xml.PAGE_NORMAL:
2426                        getDefault().switchListPageFormat = PAGE_NORMAL;
2427                        break;
2428                    case Xml.PAGE_PER_TRAIN:
2429                        getDefault().switchListPageFormat = PAGE_PER_TRAIN;
2430                        break;
2431                    case Xml.PAGE_PER_VISIT:
2432                        getDefault().switchListPageFormat = PAGE_PER_VISIT;
2433                        break;
2434                    default:
2435                        log.error("Unknown switch list page format {}", a.getValue());
2436                }
2437            } // old way to save switch list page format pre 3.11
2438            else if ((a = operations.getChild(Xml.SWITCH_LIST).getAttribute(Xml.PAGE_MODE)) != null) {
2439                String b = a.getValue();
2440                log.debug("old style pageMode: {}", b);
2441                if (b.equals(Xml.TRUE)) {
2442                    getDefault().switchListPageFormat = PAGE_PER_TRAIN;
2443                }
2444            }
2445            if ((a = operations.getChild(Xml.SWITCH_LIST).getAttribute(Xml.PRINT_ROUTE_LOCATION)) != null) {
2446                String b = a.getValue();
2447                log.debug("print route location comment: {}", b);
2448                setSwitchListRouteLocationCommentEnabled(b.equals(Xml.TRUE));
2449            }
2450            if ((a = operations.getChild(Xml.SWITCH_LIST).getAttribute(Xml.TRACK_SUMMARY)) != null) {
2451                String b = a.getValue();
2452                log.debug("track summary: {}", b);
2453                setPrintTrackSummaryEnabled(b.equals(Xml.TRUE));
2454            }
2455            if ((a = operations.getChild(Xml.SWITCH_LIST).getAttribute(Xml.USE_DEPARTURE_TIME)) != null) {
2456                String b = a.getValue();
2457                log.debug("switch list departure time: {}", b);
2458                setUseSwitchListDepartureTimeEnabled(b.equals(Xml.TRUE));
2459            }
2460        }
2461        if (operations.getChild(Xml.SWITCH_LIST_PICKUP_CAR_FORMAT) != null) {
2462            if ((a = operations.getChild(Xml.SWITCH_LIST_PICKUP_CAR_FORMAT).getAttribute(Xml.PREFIX)) != null) {
2463                setSwitchListPickupCarPrefix(a.getValue());
2464            }
2465            if ((a = operations.getChild(Xml.SWITCH_LIST_PICKUP_CAR_FORMAT).getAttribute(Xml.SETTING)) != null) {
2466                String setting = a.getValue();
2467                log.debug("switchListpickupCarFormat: {}", setting);
2468                String[] keys = setting.split(",");
2469                replaceOldFormat(keys);
2470                xmlAttributeToKeyConversion(keys);
2471                keyToStringConversion(keys);
2472                setPickupSwitchListMessageFormat(keys);
2473            }
2474        }
2475        if (operations.getChild(Xml.SWITCH_LIST_DROP_CAR_FORMAT) != null) {
2476            if ((a = operations.getChild(Xml.SWITCH_LIST_DROP_CAR_FORMAT).getAttribute(Xml.PREFIX)) != null) {
2477                setSwitchListDropCarPrefix(a.getValue());
2478            }
2479            if ((a = operations.getChild(Xml.SWITCH_LIST_DROP_CAR_FORMAT).getAttribute(Xml.SETTING)) != null) {
2480                String setting = a.getValue();
2481                log.debug("switchListDropCarFormat: {}", setting);
2482                String[] keys = setting.split(",");
2483                replaceOldFormat(keys);
2484                xmlAttributeToKeyConversion(keys);
2485                keyToStringConversion(keys);
2486                setDropSwitchListMessageFormat(keys);
2487            }
2488        }
2489        if (operations.getChild(Xml.SWITCH_LIST_LOCAL_FORMAT) != null) {
2490            if ((a = operations.getChild(Xml.SWITCH_LIST_LOCAL_FORMAT).getAttribute(Xml.PREFIX)) != null) {
2491                setSwitchListLocalPrefix(a.getValue());
2492            }
2493            if ((a = operations.getChild(Xml.SWITCH_LIST_LOCAL_FORMAT).getAttribute(Xml.SETTING)) != null) {
2494                String setting = a.getValue();
2495                log.debug("switchListLocalFormat: {}", setting);
2496                String[] keys = setting.split(",");
2497                replaceOldFormat(keys);
2498                xmlAttributeToKeyConversion(keys);
2499                keyToStringConversion(keys);
2500                setLocalSwitchListMessageFormat(keys);
2501            }
2502        }
2503        if (operations.getChild(Xml.PANEL) != null) {
2504            if ((a = operations.getChild(Xml.PANEL).getAttribute(Xml.NAME)) != null) {
2505                String panel = a.getValue();
2506                log.debug("panel: {}", panel);
2507                setPanelName(panel);
2508            }
2509            if ((a = operations.getChild(Xml.PANEL).getAttribute(Xml.TRAIN_ICONXY)) != null) {
2510                String enable = a.getValue();
2511                log.debug("TrainIconXY: {}", enable);
2512                setTrainIconCordEnabled(enable.equals(Xml.TRUE));
2513            }
2514            if ((a = operations.getChild(Xml.PANEL).getAttribute(Xml.TRAIN_ICON_APPEND)) != null) {
2515                String enable = a.getValue();
2516                log.debug("TrainIconAppend: {}", enable);
2517                setTrainIconAppendEnabled(enable.equals(Xml.TRUE));
2518            }
2519        }
2520        if ((operations.getChild(Xml.FONT_NAME) != null) &&
2521                (a = operations.getChild(Xml.FONT_NAME).getAttribute(Xml.NAME)) != null) {
2522            String font = a.getValue();
2523            log.debug("fontName: {}", font);
2524            setFontName(font);
2525        }
2526        if ((operations.getChild(Xml.FONT_SIZE) != null) &&
2527                (a = operations.getChild(Xml.FONT_SIZE).getAttribute(Xml.SIZE)) != null) {
2528            String size = a.getValue();
2529            log.debug("fontsize: {}", size);
2530            try {
2531                setManifestFontSize(Integer.parseInt(size));
2532            } catch (NumberFormatException ee) {
2533                log.error("Manifest font size ({}) isn't a valid number", a.getValue());
2534            }
2535        }
2536        if ((operations.getChild(Xml.PAGE_ORIENTATION) != null)) {
2537            if ((a = operations.getChild(Xml.PAGE_ORIENTATION).getAttribute(Xml.MANIFEST)) != null) {
2538                String orientation = a.getValue();
2539                log.debug("manifestOrientation: {}", orientation);
2540                setManifestOrientation(orientation);
2541            }
2542            if ((a = operations.getChild(Xml.PAGE_ORIENTATION).getAttribute(Xml.SWITCH_LIST)) != null) {
2543                String orientation = a.getValue();
2544                log.debug("switchListOrientation: {}", orientation);
2545                setSwitchListOrientation(orientation);
2546            }
2547        }
2548        if ((operations.getChild(Xml.PRINT_DUPLEX) != null)) {
2549            if ((a = operations.getChild(Xml.PRINT_DUPLEX).getAttribute(Xml.NAME)) != null) {
2550                String sides = a.getValue();
2551                log.debug("Print duplex: {}", sides);
2552                if (sides.equals(SidesType.TWO_SIDED_LONG_EDGE.toString())) {
2553                    setPrintDuplexSides(SidesType.TWO_SIDED_LONG_EDGE);
2554                }
2555                if (sides.equals(SidesType.TWO_SIDED_SHORT_EDGE.toString())) {
2556                    setPrintDuplexSides(SidesType.TWO_SIDED_SHORT_EDGE);
2557                }
2558            }
2559        }
2560        if ((operations.getChild(Xml.MANIFEST_COLORS) != null)) {
2561            if ((a = operations.getChild(Xml.MANIFEST_COLORS).getAttribute(Xml.DROP_COLOR)) != null) {
2562                String dropColor = a.getValue();
2563                log.debug("dropColor: {}", dropColor);
2564                setDropTextColor(dropColor);
2565            }
2566            if ((a = operations.getChild(Xml.MANIFEST_COLORS).getAttribute(Xml.PICKUP_COLOR)) != null) {
2567                String pickupColor = a.getValue();
2568                log.debug("pickupColor: {}", pickupColor);
2569                setPickupTextColor(pickupColor);
2570            }
2571            if ((a = operations.getChild(Xml.MANIFEST_COLORS).getAttribute(Xml.LOCAL_COLOR)) != null) {
2572                String localColor = a.getValue();
2573                log.debug("localColor: {}", localColor);
2574                setLocalTextColor(localColor);
2575            }
2576            if ((a = operations.getChild(Xml.MANIFEST_COLORS).getAttribute(Xml.DROP_ENGINE_COLOR)) != null) {
2577                String dropColor = a.getValue();
2578                log.debug("dropEngineColor: {}", dropColor);
2579                setDropEngineTextColor(dropColor);
2580            } else {
2581                // Engine drop color didn't exist before 5.11.3
2582                setDropEngineTextColor(getDropTextColor());
2583            }
2584            if ((a = operations.getChild(Xml.MANIFEST_COLORS).getAttribute(Xml.PICKUP_ENGINE_COLOR)) != null) {
2585                String pickupColor = a.getValue();
2586                log.debug("pickupEngineColor: {}", pickupColor);
2587                setPickupEngineTextColor(pickupColor);
2588            } else {
2589                // Engine pick up color didn't exist before 5.11.3
2590                setPickupEngineTextColor(getPickupTextColor());
2591            }
2592        }
2593        if ((operations.getChild(Xml.TAB) != null)) {
2594            if ((a = operations.getChild(Xml.TAB).getAttribute(Xml.ENABLED)) != null) {
2595                String enable = a.getValue();
2596                log.debug("tab: {}", enable);
2597                setTabEnabled(enable.equals(Xml.TRUE));
2598            }
2599            if ((a = operations.getChild(Xml.TAB).getAttribute(Xml.LENGTH)) != null) {
2600                String length = a.getValue();
2601                log.debug("tab 1 length: {}", length);
2602                try {
2603                    setTab1length(Integer.parseInt(length));
2604                } catch (NumberFormatException ee) {
2605                    log.error("Tab 1 length ({}) isn't a valid number", a.getValue());
2606                }
2607            }
2608            if ((a = operations.getChild(Xml.TAB).getAttribute(Xml.TAB2_LENGTH)) != null) {
2609                String length = a.getValue();
2610                log.debug("tab 2 length: {}", length);
2611                try {
2612                    setTab2length(Integer.parseInt(length));
2613                } catch (NumberFormatException ee) {
2614                    log.error("Tab 2 length ({}) isn't a valid number", a.getValue());
2615                }
2616            }
2617            if ((a = operations.getChild(Xml.TAB).getAttribute(Xml.TAB3_LENGTH)) != null) {
2618                String length = a.getValue();
2619                log.debug("tab 3 length: {}", length);
2620                try {
2621                    setTab3length(Integer.parseInt(length));
2622                } catch (NumberFormatException ee) {
2623                    log.error("Tab 3 length ({}) isn't a valid number", a.getValue());
2624                }
2625            }
2626        }
2627        if ((operations.getChild(Xml.MANIFEST) != null)) {
2628            if ((a = operations.getChild(Xml.MANIFEST).getAttribute(Xml.PRINT_LOC_COMMENTS)) != null) {
2629                String enable = a.getValue();
2630                log.debug("manifest printLocComments: {}", enable);
2631                setPrintLocationCommentsEnabled(enable.equals(Xml.TRUE));
2632            }
2633            if ((a = operations.getChild(Xml.MANIFEST).getAttribute(Xml.PRINT_ROUTE_COMMENTS)) != null) {
2634                String enable = a.getValue();
2635                log.debug("manifest printRouteComments: {}", enable);
2636                setPrintRouteCommentsEnabled(enable.equals(Xml.TRUE));
2637            }
2638            if ((a = operations.getChild(Xml.MANIFEST).getAttribute(Xml.PRINT_LOADS_EMPTIES)) != null) {
2639                String enable = a.getValue();
2640                log.debug("manifest printLoadsEmpties: {}", enable);
2641                setPrintLoadsAndEmptiesEnabled(enable.equals(Xml.TRUE));
2642            }
2643            if ((a = operations.getChild(Xml.MANIFEST).getAttribute(Xml.PRINT_TRAIN_SCHEDULE)) != null) {
2644                String enable = a.getValue();
2645                log.debug("manifest printTrainSchedule: {}", enable);
2646                setPrintTrainScheduleNameEnabled(enable.equals(Xml.TRUE));
2647            }
2648            if ((a = operations.getChild(Xml.MANIFEST).getAttribute(Xml.USE12HR_FORMAT)) != null) {
2649                String enable = a.getValue();
2650                log.debug("manifest use12hrFormat: {}", enable);
2651                set12hrFormatEnabled(enable.equals(Xml.TRUE));
2652            }
2653            if ((a = operations.getChild(Xml.MANIFEST).getAttribute(Xml.PRINT_VALID)) != null) {
2654                String enable = a.getValue();
2655                log.debug("manifest printValid: {}", enable);
2656                setPrintValidEnabled(enable.equals(Xml.TRUE));
2657            }
2658            if ((a = operations.getChild(Xml.MANIFEST).getAttribute(Xml.SORT_BY_TRACK)) != null) {
2659                String enable = a.getValue();
2660                log.debug("manifest sortByTrack: {}", enable);
2661                setSortByTrackNameEnabled(enable.equals(Xml.TRUE));
2662            }
2663            if ((a = operations.getChild(Xml.MANIFEST).getAttribute(Xml.PRINT_PAGE_HEADER)) != null) {
2664                String enable = a.getValue();
2665                log.debug("manifest printPageHeader: {}", enable);
2666                setPrintPageHeaderEnabled(enable.equals(Xml.TRUE));
2667            }
2668            if ((a = operations.getChild(Xml.MANIFEST).getAttribute(Xml.PRINT_HEADERS)) != null) {
2669                String enable = a.getValue();
2670                log.debug("manifest print headers: {}", enable);
2671                setPrintHeadersEnabled(enable.equals(Xml.TRUE));
2672            }
2673            if ((a = operations.getChild(Xml.MANIFEST).getAttribute(Xml.TRUNCATE)) != null) {
2674                String enable = a.getValue();
2675                log.debug("manifest truncate: {}", enable);
2676                setPrintTruncateManifestEnabled(enable.equals(Xml.TRUE));
2677            }
2678            if ((a = operations.getChild(Xml.MANIFEST).getAttribute(Xml.USE_DEPARTURE_TIME)) != null) {
2679                String enable = a.getValue();
2680                log.debug("manifest use departure time: {}", enable);
2681                setUseDepartureTimeEnabled(enable.equals(Xml.TRUE));
2682            }
2683            if ((a = operations.getChild(Xml.MANIFEST).getAttribute(Xml.USE_EDITOR)) != null) {
2684                String enable = a.getValue();
2685                log.debug("manifest useEditor: {}", enable);
2686                setManifestEditorEnabled(enable.equals(Xml.TRUE));
2687            }
2688            if ((a = operations.getChild(Xml.MANIFEST).getAttribute(Xml.PRINT_CABOOSE_LOAD)) != null) {
2689                String enable = a.getValue();
2690                log.debug("manifest print caboose load: {}", enable);
2691                setPrintCabooseLoadEnabled(enable.equals(Xml.TRUE));
2692            }
2693            if ((a = operations.getChild(Xml.MANIFEST).getAttribute(Xml.PRINT_PASSENGER_LOAD)) != null) {
2694                String enable = a.getValue();
2695                log.debug("manifest print passenger load: {}", enable);
2696                setPrintPassengerLoadEnabled(enable.equals(Xml.TRUE));
2697            }
2698            if ((a = operations.getChild(Xml.MANIFEST).getAttribute(Xml.GROUP_MOVES)) != null) {
2699                String enable = a.getValue();
2700                log.debug("manifest group car moves: {}", enable);
2701                setGroupCarMoves(enable.equals(Xml.TRUE));
2702            }
2703            if ((a = operations.getChild(Xml.MANIFEST).getAttribute(Xml.PRINT_LOCO_LAST)) != null) {
2704                String enable = a.getValue();
2705                log.debug("manifest print loco last: {}", enable);
2706                setPrintLocoLast(enable.equals(Xml.TRUE));
2707            }
2708            if ((a = operations.getChild(Xml.MANIFEST).getAttribute(Xml.HAZARDOUS_MSG)) != null) {
2709                String message = a.getValue();
2710                log.debug("manifest hazardousMsg: {}", message);
2711                setHazardousMsg(message);
2712            }
2713        }
2714        if ((operations.getChild(Xml.MANIFEST_FORMAT) != null)) {
2715            if ((a = operations.getChild(Xml.MANIFEST_FORMAT).getAttribute(Xml.VALUE)) != null) {
2716                switch (a.getValue()) {
2717                    case Xml.STANDARD:
2718                        getDefault().manifestFormat = STANDARD_FORMAT;
2719                        break;
2720                    case Xml.TWO_COLUMN:
2721                        getDefault().manifestFormat = TWO_COLUMN_FORMAT;
2722                        break;
2723                    case Xml.TWO_COLUMN_TRACK:
2724                        getDefault().manifestFormat = TWO_COLUMN_TRACK_FORMAT;
2725                        break;
2726                    default:
2727                        log.debug("Unknown manifest format");
2728                }
2729            }
2730        } else if ((operations.getChild(Xml.COLUMN_FORMAT) != null)) {
2731            if ((a = operations.getChild(Xml.COLUMN_FORMAT).getAttribute(Xml.TWO_COLUMNS)) != null) {
2732                String enable = a.getValue();
2733                log.debug("two columns: {}", enable);
2734                if (enable.equals(Xml.TRUE)) {
2735                    setManifestFormat(TWO_COLUMN_FORMAT);
2736                }
2737            }
2738        }
2739        // get manifest logo
2740        if ((operations.getChild(Xml.MANIFEST_LOGO) != null)) {
2741            if ((a = operations.getChild(Xml.MANIFEST_LOGO).getAttribute(Xml.NAME)) != null) {
2742                setManifestLogoURL(a.getValue());
2743            }
2744        }
2745        // manifest file options
2746        if ((operations.getChild(Xml.MANIFEST_FILE_OPTIONS) != null)) {
2747            if ((a = operations.getChild(Xml.MANIFEST_FILE_OPTIONS).getAttribute(Xml.MANIFEST_SAVE)) != null) {
2748                String enable = a.getValue();
2749                log.debug("manifest file save option: {}", enable);
2750                getDefault().saveTrainManifests = enable.equals(Xml.TRUE);
2751            }
2752        }
2753        if ((operations.getChild(Xml.BUILD_OPTIONS) != null)) {
2754            if ((a = operations.getChild(Xml.BUILD_OPTIONS).getAttribute(Xml.AGGRESSIVE)) != null) {
2755                String enable = a.getValue();
2756                log.debug("aggressive: {}", enable);
2757                setBuildAggressive(enable.equals(Xml.TRUE));
2758            }
2759            if ((a = operations.getChild(Xml.BUILD_OPTIONS).getAttribute(Xml.NUMBER_PASSES)) != null) {
2760                String number = a.getValue();
2761                log.debug("number of passes: {}", number);
2762                try {
2763                    setNumberPasses(Integer.parseInt(number));
2764                } catch (NumberFormatException ne) {
2765                    log.debug("Number of passes isn't a number");
2766                }
2767            }
2768            if ((a = operations.getChild(Xml.BUILD_OPTIONS).getAttribute(Xml.ALLOW_LOCAL_INTERCHANGE)) != null) {
2769                String enable = a.getValue();
2770                log.debug("allowLocalInterchangeMoves: {}", enable);
2771                setLocalInterchangeMovesEnabled(enable.equals(Xml.TRUE));
2772            }
2773            if ((a = operations.getChild(Xml.BUILD_OPTIONS).getAttribute(Xml.ALLOW_LOCAL_SPUR)) != null) {
2774                String enable = a.getValue();
2775                log.debug("allowLocalSpurMoves: {}", enable);
2776                setLocalSpurMovesEnabled(enable.equals(Xml.TRUE));
2777            } else if ((a = operations.getChild(Xml.BUILD_OPTIONS).getAttribute(Xml.ALLOW_LOCAL_SIDING)) != null) {
2778                String enable = a.getValue();
2779                log.debug("allowLocalSidingMoves: {}", enable);
2780                setLocalSpurMovesEnabled(enable.equals(Xml.TRUE));
2781            }
2782            if ((a = operations.getChild(Xml.BUILD_OPTIONS).getAttribute(Xml.ALLOW_LOCAL_YARD)) != null) {
2783                String enable = a.getValue();
2784                log.debug("allowLocalYardMoves: {}", enable);
2785                setLocalYardMovesEnabled(enable.equals(Xml.TRUE));
2786            }
2787            if ((a = operations.getChild(Xml.BUILD_OPTIONS).getAttribute(Xml.STAGING_RESTRICTION_ENABLED)) != null) {
2788                String enable = a.getValue();
2789                log.debug("stagingRestrictionEnabled: {}", enable);
2790                setStagingTrainCheckEnabled(enable.equals(Xml.TRUE));
2791            }
2792            if ((a = operations.getChild(Xml.BUILD_OPTIONS).getAttribute(Xml.STAGING_TRACK_AVAIL)) != null) {
2793                String enable = a.getValue();
2794                log.debug("stagingTrackAvail: {}", enable);
2795                setStagingTrackImmediatelyAvail(enable.equals(Xml.TRUE));
2796            }
2797            if ((a = operations.getChild(Xml.BUILD_OPTIONS).getAttribute(Xml.ALLOW_RETURN_STAGING)) != null) {
2798                String enable = a.getValue();
2799                log.debug("allowReturnStaging: {}", enable);
2800                getDefault().allowCarsReturnStaging = enable.equals(Xml.TRUE);
2801            }
2802            if ((a = operations.getChild(Xml.BUILD_OPTIONS).getAttribute(Xml.PROMPT_STAGING_ENABLED)) != null) {
2803                String enable = a.getValue();
2804                log.debug("promptStagingEnabled: {}", enable);
2805                setStagingPromptFromEnabled(enable.equals(Xml.TRUE));
2806            }
2807            if ((a = operations.getChild(Xml.BUILD_OPTIONS).getAttribute(Xml.PROMPT_TO_STAGING_ENABLED)) != null) {
2808                String enable = a.getValue();
2809                log.debug("promptToStagingEnabled: {}", enable);
2810                setStagingPromptToEnabled(enable.equals(Xml.TRUE));
2811            }
2812            if ((a = operations.getChild(Xml.BUILD_OPTIONS).getAttribute(Xml.STAGING_TRY_NORMAL)) != null) {
2813                String enable = a.getValue();
2814                log.debug("stagingTryNormalEnabled: {}", enable);
2815                setStagingTryNormalBuildEnabled(enable.equals(Xml.TRUE));
2816            }
2817            if ((a = operations.getChild(Xml.BUILD_OPTIONS).getAttribute(Xml.GENERATE_CSV_MANIFEST)) != null) {
2818                String enable = a.getValue();
2819                log.debug("generateCvsManifest: {}", enable);
2820                getDefault().generateCsvManifest = enable.equals(Xml.TRUE);
2821            }
2822            if ((a = operations.getChild(Xml.BUILD_OPTIONS).getAttribute(Xml.GENERATE_CSV_SWITCH_LIST)) != null) {
2823                String enable = a.getValue();
2824                log.debug("generateCvsSwitchList: {}", enable);
2825                getDefault().generateCsvSwitchList = enable.equals(Xml.TRUE);
2826            }
2827        }
2828        if (operations.getChild(Xml.BUILD_REPORT) != null) {
2829            if ((a = operations.getChild(Xml.BUILD_REPORT).getAttribute(Xml.LEVEL)) != null) {
2830                String level = a.getValue();
2831                log.debug("buildReportLevel: {}", level);
2832                setBuildReportLevel(level);
2833            }
2834            if ((a = operations.getChild(Xml.BUILD_REPORT).getAttribute(Xml.ROUTER_LEVEL)) != null) {
2835                String level = a.getValue();
2836                log.debug("routerBuildReportLevel: {}", level);
2837                setRouterBuildReportLevel(level);
2838            }
2839            if ((a = operations.getChild(Xml.BUILD_REPORT).getAttribute(Xml.USE_EDITOR)) != null) {
2840                String enable = a.getValue();
2841                log.debug("build report useEditor: {}", enable);
2842                setBuildReportEditorEnabled(enable.equals(Xml.TRUE));
2843            }
2844            if ((a = operations.getChild(Xml.BUILD_REPORT).getAttribute(Xml.INDENT)) != null) {
2845                String enable = a.getValue();
2846                log.debug("build report indent: {}", enable);
2847                setBuildReportIndentEnabled(enable.equals(Xml.TRUE));
2848            }
2849            if ((a = operations.getChild(Xml.BUILD_REPORT).getAttribute(Xml.FONT_SIZE)) != null) {
2850                String size = a.getValue();
2851                log.debug("build font size: {}", size);
2852                try {
2853                    setBuildReportFontSize(Integer.parseInt(size));
2854                } catch (NumberFormatException ee) {
2855                    log.error("Build report font size ({}) isn't a valid number", a.getValue());
2856                }
2857            }
2858            if ((a = operations.getChild(Xml.BUILD_REPORT).getAttribute(Xml.ALWAYS_PREVIEW)) != null) {
2859                String enable = a.getValue();
2860                log.debug("build report always preview: {}", enable);
2861                setBuildReportAlwaysPreviewEnabled(enable.equals(Xml.TRUE));
2862            }
2863        }
2864
2865        if (operations.getChild(Xml.ROUTER) != null) {
2866            if ((a = operations.getChild(Xml.ROUTER).getAttribute(Xml.CAR_ROUTING_ENABLED)) != null) {
2867                String enable = a.getValue();
2868                log.debug("carRoutingEnabled: {}", enable);
2869                setCarRoutingEnabled(enable.equals(Xml.TRUE));
2870            }
2871            if ((a = operations.getChild(Xml.ROUTER).getAttribute(Xml.CAR_ROUTING_VIA_YARDS)) != null) {
2872                String enable = a.getValue();
2873                log.debug("carRoutingViaYards: {}", enable);
2874                setCarRoutingViaYardsEnabled(enable.equals(Xml.TRUE));
2875            }
2876            if ((a = operations.getChild(Xml.ROUTER).getAttribute(Xml.CAR_ROUTING_VIA_STAGING)) != null) {
2877                String enable = a.getValue();
2878                log.debug("carRoutingViaStaging: {}", enable);
2879                setCarRoutingViaStagingEnabled(enable.equals(Xml.TRUE));
2880            }
2881            if ((a = operations.getChild(Xml.ROUTER).getAttribute(Xml.FORWARD_TO_YARD)) != null) {
2882                String enable = a.getValue();
2883                log.debug("forwardToYard: {}", enable);
2884                setForwardToYardEnabled(enable.equals(Xml.TRUE));
2885            }
2886            if ((a = operations.getChild(Xml.ROUTER).getAttribute(Xml.ONLY_ACTIVE_TRAINS)) != null) {
2887                String enable = a.getValue();
2888                log.debug("onlyActiveTrains: {}", enable);
2889                setOnlyActiveTrainsEnabled(enable.equals(Xml.TRUE));
2890            }
2891            if ((a = operations.getChild(Xml.ROUTER).getAttribute(Xml.CHECK_CAR_DESTINATION)) != null) {
2892                String enable = a.getValue();
2893                log.debug("checkCarDestination: {}", enable);
2894                setCheckCarDestinationEnabled(enable.equals(Xml.TRUE));
2895            }
2896        } else if (operations.getChild(Xml.SETTINGS) != null) {
2897            // the next four items are for backwards compatibility
2898            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.CAR_ROUTING_ENABLED)) != null) {
2899                String enable = a.getValue();
2900                log.debug("carRoutingEnabled: {}", enable);
2901                setCarRoutingEnabled(enable.equals(Xml.TRUE));
2902            }
2903            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.CAR_ROUTING_VIA_YARDS)) != null) {
2904                String enable = a.getValue();
2905                log.debug("carRoutingViaYards: {}", enable);
2906                setCarRoutingViaYardsEnabled(enable.equals(Xml.TRUE));
2907            }
2908            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.CAR_ROUTING_VIA_STAGING)) != null) {
2909                String enable = a.getValue();
2910                log.debug("carRoutingViaStaging: {}", enable);
2911                setCarRoutingViaStagingEnabled(enable.equals(Xml.TRUE));
2912            }
2913            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.FORWARD_TO_YARD)) != null) {
2914                String enable = a.getValue();
2915                log.debug("forwardToYard: {}", enable);
2916                setForwardToYardEnabled(enable.equals(Xml.TRUE));
2917            }
2918        }
2919
2920        if ((operations.getChild(Xml.OWNER) != null) &&
2921                (a = operations.getChild(Xml.OWNER).getAttribute(Xml.NAME)) != null) {
2922            String owner = a.getValue();
2923            log.debug("owner: {}", owner);
2924            setOwnerName(owner);
2925        }
2926        if (operations.getChild(Xml.ICON_COLOR) != null) {
2927            if ((a = operations.getChild(Xml.ICON_COLOR).getAttribute(Xml.NORTH)) != null) {
2928                String color = a.getValue();
2929                log.debug("north color: {}", color);
2930                setTrainIconColorNorth(color);
2931            }
2932            if ((a = operations.getChild(Xml.ICON_COLOR).getAttribute(Xml.SOUTH)) != null) {
2933                String color = a.getValue();
2934                log.debug("south color: {}", color);
2935                setTrainIconColorSouth(color);
2936            }
2937            if ((a = operations.getChild(Xml.ICON_COLOR).getAttribute(Xml.EAST)) != null) {
2938                String color = a.getValue();
2939                log.debug("east color: {}", color);
2940                setTrainIconColorEast(color);
2941            }
2942            if ((a = operations.getChild(Xml.ICON_COLOR).getAttribute(Xml.WEST)) != null) {
2943                String color = a.getValue();
2944                log.debug("west color: {}", color);
2945                setTrainIconColorWest(color);
2946            }
2947            if ((a = operations.getChild(Xml.ICON_COLOR).getAttribute(Xml.LOCAL)) != null) {
2948                String color = a.getValue();
2949                log.debug("local color: {}", color);
2950                setTrainIconColorLocal(color);
2951            }
2952            if ((a = operations.getChild(Xml.ICON_COLOR).getAttribute(Xml.TERMINATE)) != null) {
2953                String color = a.getValue();
2954                log.debug("terminate color: {}", color);
2955                setTrainIconColorTerminate(color);
2956            }
2957        }
2958        if (operations.getChild(Xml.COMMENTS) != null) {
2959            if ((a = operations.getChild(Xml.COMMENTS).getAttribute(Xml.MISPLACED_CARS)) != null) {
2960                String comment = a.getValue();
2961                log.debug("Misplaced comment: {}", comment);
2962                setMiaComment(comment);
2963            }
2964        }
2965
2966        if (operations.getChild(Xml.DISPLAY) != null) {
2967            if ((a = operations.getChild(Xml.DISPLAY).getAttribute(Xml.SHOW_TRACK_MOVES)) != null) {
2968                String enable = a.getValue();
2969                log.debug("show track moves: {}", enable);
2970                getDefault().showTrackMoves = enable.equals(Xml.TRUE);
2971            }
2972        }
2973
2974        if (operations.getChild(Xml.VSD) != null) {
2975            if ((a = operations.getChild(Xml.VSD).getAttribute(Xml.ENABLE_PHYSICAL_LOCATIONS)) != null) {
2976                String enable = a.getValue();
2977                setVsdPhysicalLocationEnabled(enable.equals(Xml.TRUE));
2978            }
2979        }
2980        if (operations.getChild(Xml.CATS) != null) {
2981            if ((a = operations.getChild(Xml.CATS).getAttribute(Xml.EXACT_LOCATION_NAME)) != null) {
2982                String enable = a.getValue();
2983                AbstractOperationsServer.setExactLocationName(enable.equals(Xml.TRUE));
2984            }
2985        }
2986
2987        if (operations.getChild(Xml.SETTINGS) != null) {
2988            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.AUTO_SAVE)) != null) {
2989                String enabled = a.getValue();
2990                log.debug("autoSave: {}", enabled);
2991                setAutoSaveEnabled(enabled.equals(Xml.TRUE));
2992            }
2993            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.AUTO_BACKUP)) != null) {
2994                String enabled = a.getValue();
2995                log.debug("autoBackup: {}", enabled);
2996                setAutoBackupEnabled(enabled.equals(Xml.TRUE));
2997            }
2998        }
2999
3000        if (operations.getChild(Xml.LOGGER) != null) {
3001            if ((a = operations.getChild(Xml.LOGGER).getAttribute(Xml.CAR_LOGGER)) != null) {
3002                String enable = a.getValue();
3003                log.debug("carLogger: {}", enable);
3004                getDefault().carLogger = enable.equals(Xml.TRUE);
3005            }
3006            if ((a = operations.getChild(Xml.LOGGER).getAttribute(Xml.ENGINE_LOGGER)) != null) {
3007                String enable = a.getValue();
3008                log.debug("engineLogger: {}", enable);
3009                getDefault().engineLogger = enable.equals(Xml.TRUE);
3010            }
3011            if ((a = operations.getChild(Xml.LOGGER).getAttribute(Xml.TRAIN_LOGGER)) != null) {
3012                String enable = a.getValue();
3013                log.debug("trainLogger: {}", enable);
3014                getDefault().trainLogger = enable.equals(Xml.TRUE);
3015            }
3016        } else if (operations.getChild(Xml.SETTINGS) != null) {
3017            // for backward compatibility
3018            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.CAR_LOGGER)) != null) {
3019                String enable = a.getValue();
3020                log.debug("carLogger: {}", enable);
3021                getDefault().carLogger = enable.equals(Xml.TRUE);
3022            }
3023            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.ENGINE_LOGGER)) != null) {
3024                String enable = a.getValue();
3025                log.debug("engineLogger: {}", enable);
3026                getDefault().engineLogger = enable.equals(Xml.TRUE);
3027            }
3028            if ((a = operations.getChild(Xml.SETTINGS).getAttribute(Xml.TRAIN_LOGGER)) != null) {
3029                String enable = a.getValue();
3030                log.debug("trainLogger: {}", enable);
3031                getDefault().trainLogger = enable.equals(Xml.TRUE);
3032            }
3033        }
3034    }
3035
3036    // replace old pickup and drop message keys
3037    // Change happened from 2.11.3 to 2.11.4
3038    // 4/16/2014
3039    private static void replaceOldFormat(String[] format) {
3040        for (int i = 0; i < format.length; i++) {
3041            if (format[i].equals("Pickup Msg")) // NOI18N
3042            {
3043                format[i] = PICKUP_COMMENT;
3044            } else if (format[i].equals("Drop Msg")) // NOI18N
3045            {
3046                format[i] = DROP_COMMENT;
3047            }
3048        }
3049    }
3050
3051    /**
3052     * Converts the xml key to the proper locale text
3053     *
3054     */
3055    private static void keyToStringConversion(String[] keys) {
3056        for (int i = 0; i < keys.length; i++) {
3057            if (keys[i].equals(BLANK)) {
3058                continue;
3059            }
3060            try {
3061                keys[i] = Bundle.getMessage(keys[i]);
3062            } catch (Exception e) {
3063                log.warn("Key {}: ({}) not found", i, keys[i]);
3064            }
3065        }
3066    }
3067
3068    /*
3069     * Converts the strings into English tags for xml storage
3070     *
3071     */
3072    public static void stringToTagConversion(String[] strings) {
3073        for (int i = 0; i < strings.length; i++) {
3074            if (strings[i].equals(BLANK)) {
3075                continue;
3076            }
3077            for (String key : KEYS) {
3078                if (strings[i].equals(Bundle.getMessage(key))) {
3079                    strings[i] = Bundle.getMessage(Locale.ROOT, key);
3080                    break;
3081                }
3082            }
3083            // log.debug("Converted {} to {}", old, strings[i]);
3084        }
3085    }
3086
3087    /*
3088     * The xml attributes stored using the English translation. This converts the
3089     * attribute to the appropriate key for language conversion.
3090     */
3091    private static void xmlAttributeToKeyConversion(String[] format) {
3092        for (int i = 0; i < format.length; i++) {
3093            for (String key : KEYS) {
3094                if (format[i].equals(Bundle.getMessage(Locale.ROOT, key))) {
3095                    format[i] = key;
3096                }
3097            }
3098        }
3099    }
3100
3101    protected static void setDirtyAndFirePropertyChange(String p, Object old, Object n) {
3102        InstanceManager.getDefault(OperationsSetupXml.class).setDirty(true);
3103        getDefault().firePropertyChange(p, old, n);
3104    }
3105
3106    public static Setup getDefault() {
3107        return InstanceManager.getDefault(Setup.class);
3108    }
3109
3110    private static final Logger log = LoggerFactory.getLogger(Setup.class);
3111
3112    @Override
3113    public void dispose() {
3114        AutoSave.stop();
3115    }
3116
3117}