001package jmri.jmrit.operations.routes.tools;
002
003import java.awt.Frame;
004import java.io.IOException;
005import java.util.List;
006
007import org.slf4j.Logger;
008import org.slf4j.LoggerFactory;
009
010import jmri.InstanceManager;
011import jmri.jmrit.operations.routes.*;
012import jmri.jmrit.operations.setup.Control;
013import jmri.jmrit.operations.setup.Setup;
014import jmri.jmrit.operations.trains.trainbuilder.TrainCommon;
015import jmri.util.davidflanagan.HardcopyWriter;
016
017/**
018 * Prints a summary of a route or all routes.
019 * <p>
020 * This uses the older style printing, for compatibility with Java 1.1.8 in
021 * Macintosh MRJ
022 *
023 * @author Bob Jacobsen Copyright (C) 2003
024 * @author Dennis Miller Copyright (C) 2005
025 * @author Daniel Boudreau Copyright (C) 2009, 2012, 2023
026 */
027public class PrintRoutes {
028
029    static final String NEW_LINE = "\n"; // NOI18N
030    static final String TAB = "\t"; // NOI18N
031    static final String SPACE = " ";
032    private static final char FORM_FEED = '\f';
033
034    private static final int MAX_NAME_LENGTH = Control.max_len_string_location_name;
035
036    boolean _isPreview;
037
038    /**
039     * Prints or previews a summary of all routes
040     * 
041     * @param isPreview true if print preview
042     */
043    public PrintRoutes(boolean isPreview) {
044        _isPreview = isPreview;
045        printRoutes();
046    }
047
048    /**
049     * Prints or previews a summary of a route
050     * 
051     * @param isPreview true if print preview
052     * @param route     The route to be printed
053     */
054    public PrintRoutes(boolean isPreview, Route route) {
055        _isPreview = isPreview;
056        printRoute(route);
057    }
058
059    private void printRoutes() {
060        // obtain a HardcopyWriter to do this
061        try (HardcopyWriter writer = new HardcopyWriter(new Frame(), Bundle.getMessage("TitleRoutesTable"), null, null,
062                Control.reportFontSize, .5 * 72, .5 * 72, .5 * 72, .5 * 72, _isPreview, "", false, true, null, null)) {
063
064            writer.write(SPACE); // prevents exception when using Preview and no routes
065            List<Route> routes = InstanceManager.getDefault(RouteManager.class).getRoutesByNameList();
066            for (int i = 0; i < routes.size(); i++) {
067                Route route = routes.get(i);
068                writer.write(route.getName() + NEW_LINE);
069                printRoute(writer, route);
070                if (i != routes.size() - 1) {
071                    writer.write(FORM_FEED);
072                }
073            }
074        } catch (HardcopyWriter.PrintCanceledException ex) {
075            log.debug("Print canceled");
076        } catch (IOException e1) {
077            log.error("Exception in print routes: {}", e1.getLocalizedMessage());
078        }
079    }
080
081    private void printRoute(Route route) {
082        if (route == null) {
083            return;
084        }
085        // obtain a HardcopyWriter to do this
086        try (HardcopyWriter writer = new HardcopyWriter(new Frame(), Bundle.getMessage("TitleRoute", route.getName()),
087                null, null, Control.reportFontSize, .5 * 72, .5 * 72, .5 * 72, .5 * 72, _isPreview, "", false, true,
088                null, null)) {
089
090            printRoute(writer, route);
091        } catch (HardcopyWriter.PrintCanceledException ex) {
092            log.debug("Print canceled");
093        } catch (IOException e1) {
094            log.error("Exception in print routes: {}", e1.getLocalizedMessage());
095        }
096    }
097
098    private void printRoute(HardcopyWriter writer, Route route) throws IOException {
099        writer.write(route.getComment() + NEW_LINE);
100        if (!route.getComment().isBlank()) {
101            writer.write(NEW_LINE);
102        }
103
104        writer.write(getPrintHeader1());
105
106        List<RouteLocation> routeList = route.getLocationsBySequenceList();
107        for (RouteLocation rl : routeList) {
108            String s = padAndTruncate(rl.getName(), MAX_NAME_LENGTH) +
109                    rl.getTrainDirectionString() +
110                    TAB +
111                    padAndTruncate(Integer.toString(rl.getMaxCarMoves()), 4) +
112                    padAndTruncate(rl.isPickUpAllowed() ? Bundle.getMessage("yes") : Bundle.getMessage("no"), 6) +
113                    padAndTruncate(rl.isDropAllowed() ? Bundle.getMessage("yes") : Bundle.getMessage("no"), 6) +
114                    (rl.isLocalMovesAllowed() ? Bundle.getMessage("yes") : Bundle.getMessage("no")) +
115                    TAB +
116                    (rl.getWait() + Setup.getTravelTime()) +
117                    TAB +
118                    rl.getMaxTrainLength() +
119                    TAB +
120                    rl.getGrade() +
121                    TAB +
122                    padAndTruncate(Integer.toString(rl.getTrainIconX()), 5) +
123                    rl.getTrainIconY() +
124                    NEW_LINE;
125            writer.write(s);
126        }
127
128        writer.write(getPrintHeader2());
129
130        for (RouteLocation rl : routeList) {
131            String s = padAndTruncate(rl.getName(),
132                    MAX_NAME_LENGTH) + padAndTruncate(rl.getFormatedDepartureTime(), 12) + rl.getComment() + NEW_LINE;
133            writer.write(s);
134        }
135    }
136
137    private String getPrintHeader1() {
138        String s = Bundle.getMessage("Location") +
139                TAB +
140                "    " +
141                Bundle.getMessage("Direction") +
142                SPACE +
143                Bundle.getMessage("MaxMoves") +
144                SPACE +
145                Bundle.getMessage("Pull?") +
146                SPACE +
147                Bundle.getMessage("Drop?") +
148                SPACE +
149                Bundle.getMessage("Local?") +
150                SPACE +
151                Bundle.getMessage("Travel") +
152                TAB +
153                Bundle.getMessage("Length") +
154                TAB +
155                Bundle.getMessage("Grade") +
156                TAB +
157                Bundle.getMessage("X") +
158                "    " +
159                Bundle.getMessage("Y") +
160                NEW_LINE;
161        return s;
162    }
163
164    private String getPrintHeader2() {
165        String s = NEW_LINE +
166                Bundle.getMessage("Location") +
167                TAB +
168                SPACE +
169                SPACE +
170                SPACE +
171                SPACE +
172                SPACE +
173                Bundle.getMessage("DepartTime") +
174                SPACE +
175                SPACE +
176                Bundle.getMessage("Comment") +
177                NEW_LINE;
178        return s;
179    }
180
181    private String padAndTruncate(String string, int fieldSize) {
182        return TrainCommon.padAndTruncate(string, fieldSize);
183    }
184
185    private final static Logger log = LoggerFactory.getLogger(PrintRoutes.class);
186}