# Path: dipplanner/settings.py
# __VERSION__ = None
# FRESH_WATER_DENSITY = 1.0  #: water density kg/l
# SEA_WATER_DENSITY = 1.03  #: water density kg/l
# ABSOLUTE_MAX_PPO2 = 2.0  #: in bar
# ABSOLUTE_MIN_PPO2 = 0.16  #: in bar
# ABSOLUTE_MAX_TANK_PRESSURE = 300  #: in bar
# ABSOLUTE_MAX_TANK_SIZE = 2 * 20  #: in liter
# SURFACE_TEMP = 37
# HE_NARCOTIC_VALUE = 0.23  #: helium narcotic value
# N2_NARCOTIC_VALUE = 1.0  #: nitrogen narcotic value
# O2_NARCOTIC_VALUE = 1.0  #: oxygen narcotic value
# AR_NARCOTIC_VALUE = 2.33  #: argon narcotic value
# DEFAULT_AIR_FH2 = 0.0  #: fraction of HE in standard AIR
# DEFAULT_AIR_FN2 = 0.7808  #: fraction of N2 in standard AIR
# DEFAULT_AIR_FO2 = 0.2095  #: fraction of O2 in standard AIR
# DEFAULT_AIR_FAR = 0.00934  #: fraction of AR (argon) in standard AIR
# DEFAULT_AIR_F_INNERT_GAS = DEFAULT_AIR_FH2 + DEFAULT_AIR_FN2 + DEFAULT_AIR_FAR
# STOP_DEPTH_INCREMENT = 3  #: in meter
# LAST_STOP_DEPTH = 3  #: in meter : last stop before surfacing
# STOP_TIME_INCREMENT = 1  #: in second
# FORCE_ALL_STOPS = True
# AMBIANT_PRESSURE_SEA_LEVEL = 1.01325  #: surface pressure (in bar)
# METHOD_FOR_DEPTH_CALCULATION = 'complex'  #: either simple (/10) or complex
# TRAVEL_SWITCH = 'late'  #: "late" or "early"
# FLIGHT_ALTITUDE = 2450
# TEMPLATE = "default-color.tpl"  #: template should be in templates/ directory
# DECO_MODEL = "ZHL16c"  #: ZHL16c or ZHL16b or ZHL16a
# BUHLMANN_VALUES = "1a"  #: 1a (4 mins for 1st comp) or 1b (5 mins)
# WATER_DENSITY = SEA_WATER_DENSITY  #: water density kg/l
# AMBIANT_PRESSURE_SURFACE = AMBIANT_PRESSURE_SEA_LEVEL
# DEFAULT_MAX_PPO2 = 1.6  #: in bar
# DEFAULT_MIN_PPO2 = 0.16  #: in bar
# DEFAULT_MAX_END = 30  #: in meter
# DIVE_CONSUMPTION_RATE = 20.0 / 60  #: liter/s
# DECO_CONSUMPTION_RATE = 17.0 / 60  #: liter/s
# DESCENT_RATE = 20 / 60   #: m/s
# ASCENT_RATE = 10 / 60   #: m/s
# DECO_ASCENT_RATE = 3 / 60   #: m/s
# RUN_TIME = True
# USE_OC_DECO = True  #: if True, use enabled gases of decomp in oc or bailout
# GF_LOW = 0.30  #: % between 0.0 and 1.0
# GF_HIGH = 0.80  #: % between 0.0 and 1.0
# MULTILEVEL_MODE = False
# AUTOMATIC_TANK_REFILL = True  #: automatic refill of tanks between dives
# 
# Path: dipplanner/dipp_exception.py
# class DipplannerException(Exception):
#     """Base exception class for dipplanner."""
# 
#     def __init__(self, description):
#         """Init of DipplannerException.
# 
#         :param str description: text describing the error
#         """
#         super().__init__()
#         self.logger = logging.getLogger(self.__class__.__name__)
#         self.description = description
# 
#     def __str__(self):
#         """String representing the object.
# 
#         :returns: a string describing the Exception
#         :rtype: str
#         """
#         return ''.join(self.description)
# 
# Path: dipplanner/tools.py
# def pressure_to_depth(pressure, method=None):
#     """Calculate depth based on given pressure.
# 
#     depending of choosen mehod (complex or not), the calculation is done
#     either * 10 or using water density and g.
# 
#     :param float pressure: pressure in bar
#     :param str method: 'complex' for complex method, any other string for
#                        simple method.
# 
#     :returns: depth in meter
#     :rtype: float
#     """
#     if method is None:
#         method = settings.METHOD_FOR_DEPTH_CALCULATION
#     if method == 'complex':
#         g = 9.81
#         return pressure / (settings.WATER_DENSITY * 1E3 * g * 1E-5)
#     else:
#         return pressure * 10
# 
# def depth_to_pressure(depth, method=None):
#     """Calculate pressure based on given depth.
# 
#     depending of choosen mehod (complex or not), the calculation is done
#     either /10 or using water density and g.
# 
#     :param float depth: in meter
#     :param str method: 'complex' for complex method, any other string for
#                        simple method.
# 
#     :returns: depth pressure in bar
#     :rtype: float
#     """
#     if method is None:
#         method = settings.METHOD_FOR_DEPTH_CALCULATION
#     if method == 'complex':
#         g = 9.81
#         return settings.WATER_DENSITY * 1E3 * g * float(depth) * 1E-5
#     else:
#         return depth / 10


import logging
import math
import re
from dipplanner import settings
from dipplanner.dipp_exception import DipplannerException
from dipplanner.tools import pressure_to_depth, depth_to_pressure
# 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 <http://www.gnu.org/licenses/gpl.html>
#
# This module is part of dipplanner, a Dive planning Tool written in python
"""Tank Class.

.. note:: in MVPlan, this class was the 'Gas' class
"""

# local imports


class InvalidGas(DipplannerException):
    """Gas informations provided for the Tank are invalid."""

    def __init__(self, description):
        """Init of the Exception.

        :param str description: text describing the error
        """
        super().__init__(description)
        self.logger.error(
            "Raising an exception: InvalidGas ! (%s)", description)



# Path: dipplanner/settings.py
# __VERSION__ = None
# FRESH_WATER_DENSITY = 1.0  #: water density kg/l
# SEA_WATER_DENSITY = 1.03  #: water density kg/l
# ABSOLUTE_MAX_PPO2 = 2.0  #: in bar
# ABSOLUTE_MIN_PPO2 = 0.16  #: in bar
# ABSOLUTE_MAX_TANK_PRESSURE = 300  #: in bar
# ABSOLUTE_MAX_TANK_SIZE = 2 * 20  #: in liter
# SURFACE_TEMP = 37
# HE_NARCOTIC_VALUE = 0.23  #: helium narcotic value
# N2_NARCOTIC_VALUE = 1.0  #: nitrogen narcotic value
# O2_NARCOTIC_VALUE = 1.0  #: oxygen narcotic value
# AR_NARCOTIC_VALUE = 2.33  #: argon narcotic value
# DEFAULT_AIR_FH2 = 0.0  #: fraction of HE in standard AIR
# DEFAULT_AIR_FN2 = 0.7808  #: fraction of N2 in standard AIR
# DEFAULT_AIR_FO2 = 0.2095  #: fraction of O2 in standard AIR
# DEFAULT_AIR_FAR = 0.00934  #: fraction of AR (argon) in standard AIR
# DEFAULT_AIR_F_INNERT_GAS = DEFAULT_AIR_FH2 + DEFAULT_AIR_FN2 + DEFAULT_AIR_FAR
# STOP_DEPTH_INCREMENT = 3  #: in meter
# LAST_STOP_DEPTH = 3  #: in meter : last stop before surfacing
# STOP_TIME_INCREMENT = 1  #: in second
# FORCE_ALL_STOPS = True
# AMBIANT_PRESSURE_SEA_LEVEL = 1.01325  #: surface pressure (in bar)
# METHOD_FOR_DEPTH_CALCULATION = 'complex'  #: either simple (/10) or complex
# TRAVEL_SWITCH = 'late'  #: "late" or "early"
# FLIGHT_ALTITUDE = 2450
# TEMPLATE = "default-color.tpl"  #: template should be in templates/ directory
# DECO_MODEL = "ZHL16c"  #: ZHL16c or ZHL16b or ZHL16a
# BUHLMANN_VALUES = "1a"  #: 1a (4 mins for 1st comp) or 1b (5 mins)
# WATER_DENSITY = SEA_WATER_DENSITY  #: water density kg/l
# AMBIANT_PRESSURE_SURFACE = AMBIANT_PRESSURE_SEA_LEVEL
# DEFAULT_MAX_PPO2 = 1.6  #: in bar
# DEFAULT_MIN_PPO2 = 0.16  #: in bar
# DEFAULT_MAX_END = 30  #: in meter
# DIVE_CONSUMPTION_RATE = 20.0 / 60  #: liter/s
# DECO_CONSUMPTION_RATE = 17.0 / 60  #: liter/s
# DESCENT_RATE = 20 / 60   #: m/s
# ASCENT_RATE = 10 / 60   #: m/s
# DECO_ASCENT_RATE = 3 / 60   #: m/s
# RUN_TIME = True
# USE_OC_DECO = True  #: if True, use enabled gases of decomp in oc or bailout
# GF_LOW = 0.30  #: % between 0.0 and 1.0
# GF_HIGH = 0.80  #: % between 0.0 and 1.0
# MULTILEVEL_MODE = False
# AUTOMATIC_TANK_REFILL = True  #: automatic refill of tanks between dives
# 
# Path: dipplanner/dipp_exception.py
# class DipplannerException(Exception):
#     """Base exception class for dipplanner."""
# 
#     def __init__(self, description):
#         """Init of DipplannerException.
# 
#         :param str description: text describing the error
#         """
#         super().__init__()
#         self.logger = logging.getLogger(self.__class__.__name__)
#         self.description = description
# 
#     def __str__(self):
#         """String representing the object.
# 
#         :returns: a string describing the Exception
#         :rtype: str
#         """
#         return ''.join(self.description)
# 
# Path: dipplanner/tools.py
# def pressure_to_depth(pressure, method=None):
#     """Calculate depth based on given pressure.
# 
#     depending of choosen mehod (complex or not), the calculation is done
#     either * 10 or using water density and g.
# 
#     :param float pressure: pressure in bar
#     :param str method: 'complex' for complex method, any other string for
#                        simple method.
# 
#     :returns: depth in meter
#     :rtype: float
#     """
#     if method is None:
#         method = settings.METHOD_FOR_DEPTH_CALCULATION
#     if method == 'complex':
#         g = 9.81
#         return pressure / (settings.WATER_DENSITY * 1E3 * g * 1E-5)
#     else:
#         return pressure * 10
# 
# def depth_to_pressure(depth, method=None):
#     """Calculate pressure based on given depth.
# 
#     depending of choosen mehod (complex or not), the calculation is done
#     either /10 or using water density and g.
# 
#     :param float depth: in meter
#     :param str method: 'complex' for complex method, any other string for
#                        simple method.
# 
#     :returns: depth pressure in bar
#     :rtype: float
#     """
#     if method is None:
#         method = settings.METHOD_FOR_DEPTH_CALCULATION
#     if method == 'complex':
#         g = 9.81
#         return settings.WATER_DENSITY * 1E3 * g * float(depth) * 1E-5
#     else:
#         return depth / 10


# Path: dipplanner/tank.py
import logging
import math
import re
from dipplanner import settings
from dipplanner.dipp_exception import DipplannerException
from dipplanner.tools import pressure_to_depth, depth_to_pressure

# 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 <http://www.gnu.org/licenses/gpl.html>
#
# This module is part of dipplanner, a Dive planning Tool written in python
"""Tank Class.

.. note:: in MVPlan, this class was the 'Gas' class
"""

# local imports


class InvalidGas(DipplannerException):
    """Gas informations provided for the Tank are invalid."""

    def __init__(self, description):
        """Init of the Exception.

        :param str description: text describing the error
        """
        super().__init__(description)
        self.logger.error(
            "Raising an exception: InvalidGas ! (%s)", description)



class InvalidTank(DipplannerException):