package org.openstreetmap.josm.plugins.UnitScale;

import static org.openstreetmap.josm.tools.I18n.tr;

import java.util.Map;
import org.openstreetmap.josm.data.SystemOfMeasurement;
import org.openstreetmap.josm.gui.layer.Layer;
import org.openstreetmap.josm.gui.MainApplication;

public class UnitScaleCommon {
    public static double currentScale = 1;

    public static void allSystemPut(String key, SystemOfMeasurement system) {
        SystemOfMeasurement.ALL_SYSTEMS.put(key, system);
    }

    public static void allSystemRemove(String key) {
        SystemOfMeasurement.ALL_SYSTEMS.remove(key);
    }
    
    public static SystemOfMeasurement allSystemGet(String key) {
        return SystemOfMeasurement.ALL_SYSTEMS.get(key);
    }

    public static SystemOfMeasurement scaleSingle(SystemOfMeasurement system, double ratio) {
        if (ratio > 0) {
            return new SystemOfMeasurement(system.getName(),
                system.aValue * ratio,
                system.aName,
                system.bValue * ratio,
                system.bName,
                system.speedName,
                system.speedValue * ratio);
        }
        return system;
    }

    public static void scaleAll(double ratio) {
        for (Map.Entry<String, SystemOfMeasurement> entry : SystemOfMeasurement.ALL_SYSTEMS.entrySet()) {
            allSystemPut(entry.getKey(), scaleSingle(entry.getValue(), ratio));
        }
        currentScale *= ratio;
    }
    
    public static void scaleToAbsolute(double scale) {
        if (scale > 0) {
            scaleAll(scale / currentScale);
        }
    }
    
    public static void resetScale() {
        // this has floating point rounding errors at a certain point
        // best to have a backup map
        scaleToAbsolute(1);
    }
    
    public static void scaleToMeasure(double measure, boolean absolute, boolean radius) {
        double sc;
        double Re = 6378.1; // Earth radius (at equator according to astronomical standards)

        if (absolute) {
            if (radius) {
                sc = (measure / Re) / (Math.PI * 2);
            } else {
                sc = measure / (Re * Math.PI * 2);
            }
        } else {
            if (radius) {
                sc = measure / (Math.PI * 2);
            } else {
                sc = measure;
            }
        }

        scaleToAbsolute(sc);
    }
    
    public static void autoSaveToLayer(double ratio) {
        if (MainApplication.getLayerManager().getEditLayer() != null) {
            MainApplication.getLayerManager().getEditLayer().data.setScale(ratio);
        }
    }
}

