/* Preferences.h
Copyright (c) 2014 by Michael Zahniser

Endless Sky is free software: you can redistribute it and/or modify it under the
terms of the GNU General Public License as published by the Free Software
Foundation, either version 3 of the License, or (at your option) any later version.

Endless Sky 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.

You should have received a copy of the GNU General Public License along with
this program. If not, see <https://www.gnu.org/licenses/>.
*/

#pragma once

#include <cstdint>
#include <string>
#include <vector>

enum class Alignment;



class Preferences {
public:
	enum class VSync : int_fast8_t {
		off = 0,
		on,
		adaptive,
	};

	enum class CameraAccel : int_fast8_t {
		OFF = 0,
		ON,
		REVERSED,
	};

	enum class DateFormat : int_fast8_t {
		DMY = 0, ///< Day-first format. (Sat, 4 Oct 1941)
		MDY,     ///< Month-first format. (Sat, Oct 4, 1941)
		YMD      ///< All-numeric ISO 8601. (1941-10-04)
	};

	enum class NotificationSetting : int_fast8_t {
		OFF = 0,
		MESSAGE,
		BOTH
	};

	enum class OverlayState : int_fast8_t {
		OFF = 0,
		ON,
		DAMAGED,
		DISABLED,
		ON_HIT,
	};

	enum class OverlayType : int_fast8_t {
		ALL = 0,
		FLAGSHIP,
		ESCORT,
		ENEMY,
		NEUTRAL
	};

	enum class TurretOverlays : int_fast8_t {
		OFF = 0,
		ALWAYS_ON,
		BLINDSPOTS_ONLY
	};

	enum class AutoAim : int_fast8_t {
		OFF = 0,
		ALWAYS_ON,
		WHEN_FIRING
	};

	enum class AutoFire : int_fast8_t {
		OFF = 0,
		ON,
		GUNS_ONLY,
		TURRETS_ONLY
	};

	enum class BoardingPriority : int_fast8_t {
		PROXIMITY = 0,
		VALUE,
		MIXED
	};

	enum class FlotsamCollection : int_fast8_t {
		OFF = 0,
		ON,
		FLAGSHIP,
		ESCORT
	};

	enum class BackgroundParallax : int {
		OFF = 0,
		FANCY,
		FAST
	};

	enum class ExtendedJumpEffects : int {
		OFF = 0,
		MEDIUM,
		HEAVY
	};

	enum class AlertIndicator : int_fast8_t {
		NONE = 0,
		AUDIO,
		VISUAL,
		BOTH
	};

	enum class MinimapDisplay : int_fast8_t {
		OFF = 0,
		WHEN_JUMPING,
		ALWAYS_ON
	};

	enum class FlagshipSpacePriority : int_fast8_t {
		NONE = 0,
		PASSENGERS,
		CARGO,
		BOTH
	};

	enum class LargeGraphicsReduction : int_fast8_t {
		OFF,
		LARGEST_ONLY,
		ALL
	};

	enum class HighlightShips : int_fast8_t {
		OFF,
		FLAGSHIP,
		OWNED_SHIPS,
		ALL
	};

	enum class TributeConfirmation : int_fast8_t {
		OFF = 0,
		FRIENDLY_ONLY,
		ALWAYS
	};

	enum class AmmoRefill : int_fast8_t {
		NEVER = 0,
		ASK,
		WHEN_FREE,
		ALWAYS
	};

#ifdef _WIN32
	enum class TitleBarTheme : int_fast8_t {
		DEFAULT,
		LIGHT,
		DARK
	};

	enum class WindowRounding : int_fast8_t {
		DEFAULT,
		OFF,
		LARGE,
		SMALL
	};
#endif


public:
	static void Load();
	static void Save();

	static bool Has(const std::string &name);
	static void Set(const std::string &name, bool on = true);

	/// Toggle the ammo usage preferences, cycling between "never," "frugally," and "always."
	static void ToggleAmmoUsage();
	static std::string AmmoUsage();

	/// Date format preferences.
	static void ToggleDateFormat();
	static DateFormat GetDateFormat();
	static const std::string &DateFormatSetting();

	// Notification preferences.
	static void ToggleNotificationSetting();
	static NotificationSetting GetNotificationSetting();
	static const std::string &NotificationSettingString();

	// Scroll speed preference.
	static int ScrollSpeed();
	static void SetScrollSpeed(int speed);

	static int TooltipActivation();
	static void SetTooltipActivation(int steps);

	static double ViewZoom();
	static bool ZoomViewIn();
	static bool ZoomViewOut();
	static double MinViewZoom();
	static double MaxViewZoom();
	static const std::vector<double> &Zooms();

	static void ToggleScreenMode();
	static const std::string &ScreenModeSetting();

	/// VSync setting, either "on", "off", or "adaptive".
	static bool ToggleVSync();
	static VSync VSyncState();
	static const std::string &VSyncSetting();

	static void ToggleCameraAcceleration();
	static CameraAccel CameraAcceleration();
	static const std::string &CameraAccelerationSetting();

	static void CycleStatusOverlays(OverlayType type);
	static OverlayState StatusOverlaysState(OverlayType type);
	static const std::string &StatusOverlaysSetting(OverlayType type);

	/// Turret overlays setting, either "off", "always on", or "blindspots only".
	static void ToggleTurretOverlays();
	static TurretOverlays GetTurretOverlays();
	static const std::string &TurretOverlaysSetting();

	/// Highlight ships setting, either "off", "flagship", "owned ships", or "all".
	static void ToggleHighlightShips();
	static HighlightShips GetHighlightShips();
	static const std::string &HighlightShipsSetting();

	/// Auto aim setting, either "off", "always on", or "when firing".
	static void ToggleAutoAim();
	static AutoAim GetAutoAim();
	static const std::string &AutoAimSetting();

	/// Auto fire setting, either "off", "on", "guns only", or "turrets only".
	static void ToggleAutoFire();
	static AutoFire GetAutoFire();
	static const std::string &AutoFireSetting();

	/// Background parallax setting, either "fast", "fancy", or "off".
	static void ToggleParallax();
	static BackgroundParallax GetBackgroundParallax();
	static const std::string &ParallaxSetting();

	/// Extended jump effects setting, either "off", "medium", or "heavy".
	static void ToggleExtendedJumpEffects();
	static ExtendedJumpEffects GetExtendedJumpEffects();
	static const std::string &ExtendedJumpEffectsSetting();

	/// Boarding target setting, either "proximity", "value" or "mixed".
	static void ToggleBoarding();
	static BoardingPriority GetBoardingPriority();
	static const std::string &BoardingSetting();

	/// Flotsam setting, either "off", "on", "flagship only", or "escorts only".
	static void ToggleFlotsam();
	static FlotsamCollection GetFlotsamCollection();
	static const std::string &FlotsamSetting();

	/// Red alert siren and symbol.
	static void ToggleAlert();
	static AlertIndicator GetAlertIndicator();
	static const std::string &AlertSetting();
	static bool PlayAudioAlert();
	static bool DisplayVisualAlert();
	static bool DoAlertHelper(AlertIndicator toDo);

	/// Minimap display settings.
	static void ToggleMinimapDisplay();
	static MinimapDisplay GetMinimapDisplay();
	static const std::string &MinimapSetting();

	/// Flagship space priority setting.
	static void ToggleFlagshipSpacePriority();
	static FlagshipSpacePriority GetFlagshipSpacePriority();
	static const std::string &FlagshipSpacePrioritySetting();

	/// Large graphics reduction setting.
	static void ToggleLargeGraphicsReduction();
	static LargeGraphicsReduction GetLargeGraphicsReduction();
	static const std::string &LargeGraphicsReductionSetting();

	/// Tribute confirmation dialog setting.
	static void ToggleTributeConfirmation();
	static TributeConfirmation GetTributeConfirmation();
	static const std::string &TributeConfirmationSetting();

	/// Outfitter ammo refill confirmation setting.
	static void ToggleAmmoRefill();
	static AmmoRefill GetAmmoRefill();
	static const std::string &AmmoRefillSetting();

	/// Text alignment override setting.
	static void ToggleTextAlignment();
	static Alignment GetTextAlignment();
	static const std::string &TextAlignmentSetting();

	static void ToggleBlockScreenSaver();

	static int GetPreviousSaveCount();

#ifdef _WIN32
	static void ToggleTitleBarTheme();
	static TitleBarTheme GetTitleBarTheme();
	static const std::string &TitleBarThemeSetting();

	static void ToggleWindowRounding();
	static WindowRounding GetWindowRounding();
	static const std::string &WindowRoundingSetting();
#endif
};
