<commit_before>/*
 * Copyright 2012 <NAME> (mjuhasz)
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *    http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package bdsup2sub.core;

import bdsup2sub.tools.Props;
import bdsup2sub.utils.FilenameUtils;
import bdsup2sub.utils.PlatformUtils;
import bdsup2sub.utils.SubtitleUtils;

import javax.swing.*;
import java.awt.*;
import java.io.File;
import java.util.*;
import java.util.List;


public final class Configuration {

    public static final Color OK_BACKGROUND = UIManager.getColor("TextField.background");
    public static final Color WARN_BACKGROUND = new Color(0xffffffc0);
    public static final Color ERROR_BACKGROUND = new Color(0xffe1acac);

    public static final boolean CONVERT_RESOLUTION_BY_DEFAULT = false;
    public static final boolean CONVERT_FRAMERATE_BY_DEFAULT = false;
    public static final int DEFAULT_PTS_DELAY = 0;
    public static final boolean FIX_SHORT_FRAMES_BY_DEFAULT = false;
    public static final int DEFAULT_MIN_DISPLAY_TIME_PTS = 90 * 500;
    public static final boolean APPLY_FREE_SCALE_BY_DEFAULT = false;
    public static final double DEFAULT_FREE_SCALE_FACTOR_X = 1.0;
    public static final double DEFAULT_FREE_SCALE_FACTOR_Y = 1.0;
    public static final double MIN_FREE_SCALE_FACTOR = 0.5;
    public static final double MAX_FREE_SCALE_FACTOR = 2.0;
    public static final double DEFAULT_SOURCE_FRAMERATE = Framerate.FPS_23_976.getValue();  //TODO: dumb default
    public static final double DEFAULT_TARGET_FRAMERATE = Framerate.PAL.getValue(); //TODO: dumb default
    public static final Resolution DEFAULT_TARGET_RESOLUTION = Resolution.PAL; //TODO: dumb default
    public static final int DEFAULT_ALPHA_CROP_THRESHOLD = 14;
    public static final int DEFAULT_ALPHA_THRESHOLD = 80;
    public static final int DEFAULT_LUMINANCE_MED_HIGH_THRESHOLD = 210;
    public static final int DEFAULT_LUMINANCE_LOW_MED_THRESHOLD = 160;
    public static final int DEFAULT_MOVE_Y_OFFSET = 10;
    public static final int DEFAULT_MOVE_X_OFFSET = 10;
    public static final int DEFAULT_CROP_LINE_COUNT = 0;
    //Two equal captions are merged of they are closer than 200ms (0.2*90000 = 18000)
    public static final int DEFAULT_MERGE_PTS_DIFF = 18000;
    public static final OutputMode DEFAULT_OUTPUT_MODE = OutputMode.VOBSUB;

    private boolean convertResolution = CONVERT_RESOLUTION_BY_DEFAULT;
    private boolean convertFPS = CONVERT_FRAMERATE_BY_DEFAULT;
    private int delayPTS = DEFAULT_PTS_DELAY;
    private boolean cliMode = true;
    private boolean fixShortFrames = FIX_SHORT_FRAMES_BY_DEFAULT;
    private int minTimePTS = DEFAULT_MIN_DISPLAY_TIME_PTS;
    private boolean applyFreeScale = APPLY_FREE_SCALE_BY_DEFAULT;
    private double freeScaleFactorX = DEFAULT_FREE_SCALE_FACTOR_X;
    private double freeScaleFactorY = DEFAULT_FREE_SCALE_FACTOR_Y;
    private double fpsSrc = DEFAULT_SOURCE_FRAMERATE;
    private double fpsTrg = DEFAULT_TARGET_FRAMERATE;
    private boolean fpsSrcCertain;
    private Resolution outputResolution = DEFAULT_TARGET_RESOLUTION;
    private int languageIdx;
    private boolean exportForced;

    private int cropOffsetY = DEFAULT_CROP_LINE_COUNT;
    private ForcedFlagState forceAll = ForcedFlagState.KEEP;
    private boolean swapCrCb;
    private CaptionMoveModeX moveModeX = CaptionMoveModeX.KEEP_POSITION;
    private CaptionMoveModeY moveModeY = CaptionMoveModeY.KEEP_POSITION;
    private int moveOffsetX = DEFAULT_MOVE_X_OFFSET;
    private int moveOffsetY = DEFAULT_MOVE_Y_OFFSET;
    private boolean moveCaptions;
    /** Factor to calculate height of one cinemascope bar from screen height */
    private double cineBarFactor = 5.0/42;
    private StreamID currentStreamID = StreamID.UNKNOWN;
    private boolean keepFps;

    private static final int RECENT_FILE_COUNT = 5;
    private static final String CONFIG_FILE = "bdsup2sup.ini";
    private static final Configuration INSTANCE = new Configuration();
    private final String configFilePath;
    private List<String> recentFiles;
    private int[] luminanceThreshold = {DEFAULT_LUMINANCE_MED_HIGH_THRESHOLD, DEFAULT_LUMINANCE_LOW_MED_THRESHOLD};
    private int alphaThreshold = DEFAULT_ALPHA_THRESHOLD;

    private Props props;

    private Configuration() {
        configFilePath = workOutConfigFilePath();
        props = new Props();
    }

    public void load() {
        readConfigFile();
        loadConfig();
    }

    private void readConfigFile() {
        props.clear();
        props.setHeader(Constants.APP_NAME + " " + Constants.APP_VERSION + " settings - don't modify manually");
        props.load(configFilePath);
    }

    private void loadConfig() {
        loadRecentFiles();

        convertResolution = loadConvertResolution();
        outputResolution = loadOutputResolution();
        convertFPS = loadConvertFPS();
        fpsSrc = loadFpsSrc();
        fpsTrg = loadFpsTrg();
        delayPTS = loadDelayPTS();
        fixShortFrames = loadFixShortFrames();
        minTimePTS = loadMinTimePTS();
        applyFreeScale = loadApplyFreeScale();
        freeScaleFactorX = loadFreeScaleFactorX();
        freeScaleFactorY = loadFreeScaleFactorY();
    }

    public void storeConfig() {
        if (!cliMode) {
            props.save(configFilePath);
        }
    }

    private void loadRecentFiles() {
        recentFiles = new ArrayList<String>();
        int i = 0;
        String filename;
        while (i < RECENT_FILE_COUNT && (filename = props.get("recent_" + i, "")).length() > 0) {
            if (new File(filename).exists()) {
                recentFiles.add(filename);
            }
            i++;
        }
    }

    public static Configuration getInstance() {
        return INSTANCE;
    }

    private String workOutConfigFilePath() {
        if (PlatformUtils.isLinux()) {
            String xdgConfigHome = System.getenv("XDG_CONFIG_HOME");
            File configFileDir = new File((xdgConfigHome != null ? xdgConfigHome : System.getProperty("user.home") + "/.config") + "/bdsup2sub");
            if (!configFileDir.exists()) {
                configFileDir.mkdir();
            }
            return configFileDir + "/" + CONFIG_FILE;
        } else {
            String relPathToClassFile = Configuration.class.getName().replace('.','/') + ".class";
            String absPathToClassFile = Configuration.class.getClassLoader().getResource(relPathToClassFile).getPath();

            int pos = absPathToClassFile.toLowerCase().indexOf(relPathToClassFile.toLowerCase());
            String configFileDir = absPathToClassFile.substring(0, pos);

            if (configFileDir.startsWith("file:")) {
                configFileDir = configFileDir.substring("file:".length());
            }

            configFileDir = FilenameUtils.separatorsToUnix(configFileDir);
            pos = configFileDir.lastIndexOf(".jar");
            if (pos != -1) {
                pos = configFileDir.substring(0, pos).lastIndexOf('/');
                if (pos != -1) {
                    configFileDir = configFileDir.substring(0, pos + 1);
                }
            }
            return configFileDir + CONFIG_FILE;
        }
    }
    
    public boolean isCliMode() {
        return cliMode;
    }

    public void setCliMode(boolean cliMode) {
        this.cliMode = cliMode;
    }
<commit_msg>Store the configuration in the user's home on Mac and Windows.<commit_after>/*
 * Copyright 2012 <NAME> (mjuhasz)
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *    http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package bdsup2sub.core;

import bdsup2sub.tools.Props;
import bdsup2sub.utils.FilenameUtils;
import bdsup2sub.utils.PlatformUtils;
import bdsup2sub.utils.SubtitleUtils;

import javax.swing.*;
import java.awt.*;
import java.io.File;
import java.util.*;
import java.util.List;


public final class Configuration {

    public static final Color OK_BACKGROUND = UIManager.getColor("TextField.background");
    public static final Color WARN_BACKGROUND = new Color(0xffffffc0);
    public static final Color ERROR_BACKGROUND = new Color(0xffe1acac);

    public static final boolean CONVERT_RESOLUTION_BY_DEFAULT = false;
    public static final boolean CONVERT_FRAMERATE_BY_DEFAULT = false;
    public static final int DEFAULT_PTS_DELAY = 0;
    public static final boolean FIX_SHORT_FRAMES_BY_DEFAULT = false;
    public static final int DEFAULT_MIN_DISPLAY_TIME_PTS = 90 * 500;
    public static final boolean APPLY_FREE_SCALE_BY_DEFAULT = false;
    public static final double DEFAULT_FREE_SCALE_FACTOR_X = 1.0;
    public static final double DEFAULT_FREE_SCALE_FACTOR_Y = 1.0;
    public static final double MIN_FREE_SCALE_FACTOR = 0.5;
    public static final double MAX_FREE_SCALE_FACTOR = 2.0;
    public static final double DEFAULT_SOURCE_FRAMERATE = Framerate.FPS_23_976.getValue();  //TODO: dumb default
    public static final double DEFAULT_TARGET_FRAMERATE = Framerate.PAL.getValue(); //TODO: dumb default
    public static final Resolution DEFAULT_TARGET_RESOLUTION = Resolution.PAL; //TODO: dumb default
    public static final int DEFAULT_ALPHA_CROP_THRESHOLD = 14;
    public static final int DEFAULT_ALPHA_THRESHOLD = 80;
    public static final int DEFAULT_LUMINANCE_MED_HIGH_THRESHOLD = 210;
    public static final int DEFAULT_LUMINANCE_LOW_MED_THRESHOLD = 160;
    public static final int DEFAULT_MOVE_Y_OFFSET = 10;
    public static final int DEFAULT_MOVE_X_OFFSET = 10;
    public static final int DEFAULT_CROP_LINE_COUNT = 0;
    //Two equal captions are merged of they are closer than 200ms (0.2*90000 = 18000)
    public static final int DEFAULT_MERGE_PTS_DIFF = 18000;
    public static final OutputMode DEFAULT_OUTPUT_MODE = OutputMode.VOBSUB;

    private boolean convertResolution = CONVERT_RESOLUTION_BY_DEFAULT;
    private boolean convertFPS = CONVERT_FRAMERATE_BY_DEFAULT;
    private int delayPTS = DEFAULT_PTS_DELAY;
    private boolean cliMode = true;
    private boolean fixShortFrames = FIX_SHORT_FRAMES_BY_DEFAULT;
    private int minTimePTS = DEFAULT_MIN_DISPLAY_TIME_PTS;
    private boolean applyFreeScale = APPLY_FREE_SCALE_BY_DEFAULT;
    private double freeScaleFactorX = DEFAULT_FREE_SCALE_FACTOR_X;
    private double freeScaleFactorY = DEFAULT_FREE_SCALE_FACTOR_Y;
    private double fpsSrc = DEFAULT_SOURCE_FRAMERATE;
    private double fpsTrg = DEFAULT_TARGET_FRAMERATE;
    private boolean fpsSrcCertain;
    private Resolution outputResolution = DEFAULT_TARGET_RESOLUTION;
    private int languageIdx;
    private boolean exportForced;

    private int cropOffsetY = DEFAULT_CROP_LINE_COUNT;
    private ForcedFlagState forceAll = ForcedFlagState.KEEP;
    private boolean swapCrCb;
    private CaptionMoveModeX moveModeX = CaptionMoveModeX.KEEP_POSITION;
    private CaptionMoveModeY moveModeY = CaptionMoveModeY.KEEP_POSITION;
    private int moveOffsetX = DEFAULT_MOVE_X_OFFSET;
    private int moveOffsetY = DEFAULT_MOVE_Y_OFFSET;
    private boolean moveCaptions;
    /** Factor to calculate height of one cinemascope bar from screen height */
    private double cineBarFactor = 5.0/42;
    private StreamID currentStreamID = StreamID.UNKNOWN;
    private boolean keepFps;

    private static final int RECENT_FILE_COUNT = 5;
    private static final String CONFIG_FILE = "bdsup2sup.ini";
    private static final Configuration INSTANCE = new Configuration();
    private final String configFilePath;
    private List<String> recentFiles;
    private int[] luminanceThreshold = {DEFAULT_LUMINANCE_MED_HIGH_THRESHOLD, DEFAULT_LUMINANCE_LOW_MED_THRESHOLD};
    private int alphaThreshold = DEFAULT_ALPHA_THRESHOLD;

    private Props props;

    private Configuration() {
        configFilePath = workOutConfigFilePath();
        props = new Props();
    }

    public void load() {
        readConfigFile();
        loadConfig();
    }

    private void readConfigFile() {
        props.clear();
        props.setHeader(Constants.APP_NAME + " " + Constants.APP_VERSION + " settings - don't modify manually");
        props.load(configFilePath);
    }

    private void loadConfig() {
        loadRecentFiles();

        convertResolution = loadConvertResolution();
        outputResolution = loadOutputResolution();
        convertFPS = loadConvertFPS();
        fpsSrc = loadFpsSrc();
        fpsTrg = loadFpsTrg();
        delayPTS = loadDelayPTS();
        fixShortFrames = loadFixShortFrames();
        minTimePTS = loadMinTimePTS();
        applyFreeScale = loadApplyFreeScale();
        freeScaleFactorX = loadFreeScaleFactorX();
        freeScaleFactorY = loadFreeScaleFactorY();
    }

    public void storeConfig() {
        if (!cliMode) {
            props.save(configFilePath);
        }
    }

    private void loadRecentFiles() {
        recentFiles = new ArrayList<String>();
        int i = 0;
        String filename;
        while (i < RECENT_FILE_COUNT && (filename = props.get("recent_" + i, "")).length() > 0) {
            if (new File(filename).exists()) {
                recentFiles.add(filename);
            }
            i++;
        }
    }

    public static Configuration getInstance() {
        return INSTANCE;
    }

    private String workOutConfigFilePath() {
        if (PlatformUtils.isLinux()) {
            String xdgConfigHome = System.getenv("XDG_CONFIG_HOME");
            File configFileDir = new File((xdgConfigHome != null ? xdgConfigHome : System.getProperty("user.home") + "/.config") + "/bdsup2sub");
            if (!configFileDir.exists()) {
                configFileDir.mkdir();
            }
            return configFileDir + "/" + CONFIG_FILE;
        } else if (PlatformUtils.isMac()) {
            File configFileDir = new File(System.getProperty("user.home") + "/Library/Application Support/bdsup2sub");
            if (!configFileDir.exists()) {
                configFileDir.mkdir();
            }
            return configFileDir + "/" + CONFIG_FILE;
        } else {
            File configFileDir = new File(System.getProperty("user.home") + "/bdsup2sub");
            if (!configFileDir.exists()) {
                configFileDir.mkdir();
            }
            return configFileDir + "/" + CONFIG_FILE;
        }
    }
    
    public boolean isCliMode() {
        return cliMode;
    }

    public void setCliMode(boolean cliMode) {
        this.cliMode = cliMode;
    }

{'fraction_non_alphanumeric': 0.07789914317483158, 'fraction_numerical': 0.010988292236248283, 'mean_word_length': 3.2709497206703912, 'pattern_counts': {'":': 0, '<': 11, '<?xml version=': 0, '>': 11, 'https://': 0, 'lorem ipsum': 0, 'www.': 2, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '6015345', 'n_tokens_mistral': 4525, 'n_tokens_neox': 4328, 'n_words': 1172}