import numpy as np

from PreCourlis.lib.mascaret.mascaret_file import Section


# Check that sediment layers do not cross eachother
def check_section(section: Section) -> np.array:
    result = np.empty(shape=(section.nlayers + 1, section.z.size), dtype=bool)

    # Check zfond, which is outside of the layer_elev list
    if section.nlayers > 0:
        result[0] = section.z >= section.layers_elev[0]
    else:
        result[0] = section.z == section.z

    # Then check the layers with the previous and next layer
    # (the layers order is given by the user = order in layers list)
    for i in range(section.nlayers):
        current_values = section.layers_elev[i]

        if i == 0:
            previous_values = section.z
        else:
            previous_values = section.layers_elev[i - 1]

        if i == (section.nlayers - 1):
            next_values = current_values
        else:
            next_values = section.layers_elev[i + 1]

        result[i + 1] = np.logical_and(
            previous_values >= current_values, current_values >= next_values
        )

    return result


def move_up_invalid_points_from_section(section: Section):
    if section.nlayers == 0:
        return

    for layer_pos in reversed(range(1, section.nlayers)):
        for elevation_pos in range(section.layers_elev[0].size):
            if (
                section.layers_elev[layer_pos][elevation_pos]
                > section.layers_elev[layer_pos - 1][elevation_pos]
            ):
                section.layers_elev[layer_pos - 1][elevation_pos] = section.layers_elev[
                    layer_pos
                ][elevation_pos]

    for elevation_pos in range(section.layers_elev[0].size):
        if section.layers_elev[0][elevation_pos] > section.z[elevation_pos]:
            section.z[elevation_pos] = section.layers_elev[0][elevation_pos]


def move_down_invalid_points_from_section(section: Section):
    if section.nlayers == 0:
        return

    for layer_pos in range(section.nlayers):
        for elevation_pos in range(section.layers_elev[0].size):
            if layer_pos == 0:
                if (
                    section.z[elevation_pos]
                    < section.layers_elev[layer_pos][elevation_pos]
                ):
                    section.layers_elev[layer_pos][elevation_pos] = section.z[
                        elevation_pos
                    ]
            else:
                if (
                    section.layers_elev[layer_pos - 1][elevation_pos]
                    < section.layers_elev[layer_pos][elevation_pos]
                ):
                    section.layers_elev[layer_pos][elevation_pos] = section.layers_elev[
                        layer_pos - 1
                    ][elevation_pos]
