Subversion Repositories mkgmap

Rev

Rev 4656 | Blame | Compare with Previous | Last modification | View Log | RSS feed

/*
 * Copyright (C) 2006 Steve Ratcliffe
 *
 *  This program is free software; you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License version 2 as
 *  published by the Free Software Foundation.
 *
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU General Public License for more details.
 *
 *
 * Author: Steve Ratcliffe
 * Create date: 16-Dec-2006
 */

package uk.me.parabola.mkgmap.main;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.nio.file.Files;

import uk.me.parabola.imgfmt.FileExistsException;
import uk.me.parabola.imgfmt.FileNotWritableException;
import uk.me.parabola.imgfmt.FileSystemParam;
import uk.me.parabola.imgfmt.FormatException;
import uk.me.parabola.imgfmt.MapFailedException;
import uk.me.parabola.imgfmt.app.map.Map;
import uk.me.parabola.imgfmt.app.srt.Sort;
import uk.me.parabola.log.Logger;
import uk.me.parabola.mkgmap.CommandArgs;
import uk.me.parabola.mkgmap.build.MapBuilder;
import uk.me.parabola.mkgmap.combiners.OverviewBuilder;
import uk.me.parabola.mkgmap.general.LoadableMapDataSource;
import uk.me.parabola.mkgmap.reader.MapReader;

/**
 * Main routine for the command line map-making utility.
 *
 * @author Steve Ratcliffe
 */

public class MapMaker implements MapProcessor {
        private static final Logger log = Logger.getLogger(MapMaker.class);
        private Sort sort;
        private final boolean createOverviewFiles;

        public MapMaker(boolean createOverviewFiles) {
                this.createOverviewFiles = createOverviewFiles;
        }

        public String makeMap(CommandArgs args, String filename) {
                if (new File(filename).isDirectory()) {
                        Logger.defaultLogger.error("Need a single file, not a directory: " + filename);
                        return filename;
                }
                try {
                        LoadableMapDataSource src = loadFromFile(args, filename);
                        sort = args.getSort();
                        if (createOverviewFiles){
                                if (src.overviewMapLevels() != null){
                                        makeMap(args, src, OverviewBuilder.OVERVIEW_PREFIX);
                                } else {
                                        String fname = OverviewBuilder.getOverviewImgName(args.getMapname());
                                       
                                        File f = new File(args.getOutputDir(), fname);
                                        tryRemove(f);
                                }
                        }
                        return makeMap(args, src, "");
                } catch (FormatException e) {
                        Logger.defaultLogger.error("Bad file format: " + filename, e);
                        return filename;
                } catch (FileNotFoundException e) {
                        Logger.defaultLogger.error("Could not open file: " + filename);
                        return filename;
                }
        }

        private static void tryRemove(File f) {
                if (f.exists() && f.isFile()) {
                        try {
                                Files.delete(f.toPath());
                                log.warn("removed " + f);
                        } catch (IOException e) {
                                log.warn("removing " + f + "failed with " + e.getMessage());
                        }
                }
        }

        /**
         * Make a map from the given map data source.
         *
         * @param args User supplied arguments.
         * @param src The data source to load.
         * @param mapNamePrefix prefix for output file (e.g. ovm_ for overview map component files)
         * @return The output filename for the map.
         */

        private String makeMap(CommandArgs args, LoadableMapDataSource src, String mapNamePrefix) {

                if (src.getBounds().isEmpty())
                        return null;

                FileSystemParam params = new FileSystemParam();
                params.setBlockSize(args.getBlockSize());
                params.setMapDescription(args.getDescription());
                log.info("Started making", args.getMapname(), "(" + args.getDescription() + ")");
                try {
                        Map map = Map.createMap(mapNamePrefix + args.getMapname(), args.getOutputDir(), params, args.getMapname(), sort, false);
                        setOptions(map, args);

                        MapBuilder builder = new MapBuilder(OverviewBuilder.OVERVIEW_PREFIX.equals(mapNamePrefix), false);
                        builder.config(args.getProperties());
                        builder.makeMap(map, src);

                        // Collect information on map complete.
                        String outName = map.getFilename();
                        log.info("finished making map", outName, "closing");
                        map.close();
                        return outName;
                } catch (FileExistsException e) {
                        Logger.defaultLogger.error(e.getMessage());
                        throw new MapFailedException("File exists already", e);
                } catch (FileNotWritableException e) {
                        Logger.defaultLogger.error(e.getMessage());
                        throw new MapFailedException("Could not create or write to file", e);
                }
                catch (MapFailedException e) {
                        Logger.defaultLogger.error(e.getMessage()); // make sure the filename is logged
                        throw e;
                }
        }

        /**
         * Set options from the command line.
         *
         * @param map The map to modify.
         * @param args The command line arguments.
         */

        private static void setOptions(Map map, CommandArgs args) {
                map.config(args.getProperties());

                String s = args.getCharset();
                if (s != null)
                        map.setLabelCharset(s, args.isForceUpper());

                Sort sort = args.getSort();
                map.setSort(sort);
        }

        /**
         * Load up from the file.  It is not necessary for the map reader to completely
         * read the whole file in at once, it could pull in map-features as needed.
         *
         * @param args The user supplied parameters.
         * @param name The filename or resource name to be read.
         * @return A LoadableMapDataSource that will be used to construct the map.
         * @throws FileNotFoundException For non existing files.
         * @throws FormatException When the file format is not valid.
         */

        private static LoadableMapDataSource loadFromFile(CommandArgs args, String name) throws FileNotFoundException {
                LoadableMapDataSource src = MapReader.createMapReader(name);
                src.config(args.getProperties());
                log.info("Started loading", name);
                src.load(name, !args.getProperties().getProperty("transparent", false));
                log.info("Finished loading", name);
                return src;
        }
}