<commit_before>from noise import snoise2
from worldengine.world import Step
from worldengine.simulations.basic import find_threshold_f
from worldengine.simulations.hydrology import WatermapSimulation
from worldengine.simulations.irrigation import IrrigationSimulation
from worldengine.simulations.humidity import HumiditySimulation
from worldengine.simulations.temperature import TemperatureSimulation
from worldengine.simulations.permeability import PermeabilitySimulation
from worldengine.simulations.erosion import ErosionSimulation
from worldengine.simulations.precipitation import PrecipitationSimulation
from worldengine.simulations.biome import BiomeSimulation
from worldengine.common import anti_alias, get_verbose
import numpy


# ------------------
# Initial generation
# ------------------

def center_land(world):
    """Translate the map horizontally and vertically to put as much ocean as
       possible at the borders. It operates on elevation and plates map"""

    min_sum_on_y = None
    y_with_min_sum = None
    latshift = 0
    for y in range(world.height):
        sum_on_y = world.elevation['data'][y].sum()
        if min_sum_on_y is None or sum_on_y < min_sum_on_y:
            min_sum_on_y = sum_on_y
            y_with_min_sum = y
    if get_verbose():
        print("geo.center_land: height complete")

    min_sum_on_x = None
    x_with_min_sum = None
    for x in range(world.width):
        sum_on_x = world.elevation['data'].T[x].sum()
        if min_sum_on_x is None or sum_on_x < min_sum_on_x:
            min_sum_on_x = sum_on_x
            x_with_min_sum = x
    if get_verbose():
        print("geo.center_land: width complete")

    new_elevation_data = [] #TODO: this should fully use numpy
    new_plates = []
    for y in range(world.height):
        new_elevation_data.append([])
        new_plates.append([])
        src_y = (y_with_min_sum + y - latshift) % world.height
        for x in range(world.width):
            src_x = (x_with_min_sum + x) % world.width
            new_elevation_data[y].append(world.elevation['data'][src_y, src_x])
            new_plates[y].append(world.plates[src_y][src_x])
    world.elevation['data'] = numpy.array(new_elevation_data)
    world.plates = new_plates
    if get_verbose():
        print("geo.center_land: width complete")


def place_oceans_at_map_borders(world):
    """
    Lower the elevation near the border of the map
    """

    ocean_border = int(min(30, max(world.width / 5, world.height / 5)))

    def place_ocean(x, y, i):
        world.elevation['data'][y, x] = \
            (world.elevation['data'][y, x] * i) / ocean_border

    for x in range(world.width):
        for i in range(ocean_border):
            place_ocean(x, i, i)
            place_ocean(x, world.height - i - 1, i)

    for y in range(world.height):
        for i in range(ocean_border):
            place_ocean(i, y, i)
            place_ocean(world.width - i - 1, y, i)


def add_noise_to_elevation(world, seed):
    octaves = 8
    freq = 16.0 * octaves
    for y in range(world.height):
        for x in range(world.width):
            n = snoise2(x / freq * 2, y / freq * 2, octaves, base=seed)
            world.elevation['data'][y, x] += n


def fill_ocean(elevation, sea_level):#TODO: Make more use of numpy?
    height, width = elevation.shape

    ocean = numpy.zeros(elevation.shape, dtype=bool)
    to_expand = []
    for x in range(width):#handle top and bottom border of the map
        if elevation[0, x] <= sea_level:
            to_expand.append((x, 0))
        if elevation[height - 1, x] <= sea_level:
            to_expand.append((x, height - 1))
    for y in range(height):#handle left- and rightmost border of the map
        if elevation[y, 0] <= sea_level:
            to_expand.append((0, y))
        if elevation[y, width - 1] <= sea_level:
            to_expand.append((width - 1, y))
    for t in to_expand:
        tx, ty = t
        if not ocean[ty, tx]:
            ocean[ty, tx] = True
            for px, py in _around(tx, ty, width, height):
                if not ocean[py, px] and elevation[py, px] <= sea_level:
                    to_expand.append((px, py))

    return ocean


def initialize_ocean_and_thresholds(world, ocean_level=1.0):
    """
    Calculate the ocean, the sea depth and the elevation thresholds
    :param world: a world having elevation but not thresholds
    :param ocean_level: the elevation representing the ocean level
    :return: nothing, the world will be changed
    """
    e = world.elevation['data']
    ocean = fill_ocean(e, ocean_level)
    hl = find_threshold_f(e, 0.10)
    ml = find_threshold_f(e, 0.03)
    e_th = [('sea', ocean_level),
            ('plain', hl),
            ('hill', ml),
            ('mountain', None)]
    harmonize_ocean(ocean, e, ocean_level)
    world.set_ocean(ocean)
    world.set_elevation(e, e_th)
    world.sea_depth = sea_depth(world, ocean_level)


def harmonize_ocean(ocean, elevation, ocean_level):
    """
    The goal of this function is to make the ocean floor less noisy.
    The underwater erosion should cause the ocean floor to be more uniform
    """
    height, width = elevation.shape

    shallow_sea = ocean_level * 0.85
    midpoint = shallow_sea / 2.0

    for y in range(height):
        for x in range(width):
            e = elevation[y, x]
            if ocean[y, x] and e < shallow_sea:
                if e < midpoint:
                    e = midpoint - ((midpoint - e) / 5.0)
                else:
                    e = midpoint + ((e - midpoint) / 5.0)
                elevation[y, x] = e

# ----
# Misc
# ----

def sea_depth(world, sea_level):
    sea_depth = sea_level - world.elevation['data']<commit_msg>added comment about numpy in harmonize_ocean<commit_after>from noise import snoise2
from worldengine.world import Step
from worldengine.simulations.basic import find_threshold_f
from worldengine.simulations.hydrology import WatermapSimulation
from worldengine.simulations.irrigation import IrrigationSimulation
from worldengine.simulations.humidity import HumiditySimulation
from worldengine.simulations.temperature import TemperatureSimulation
from worldengine.simulations.permeability import PermeabilitySimulation
from worldengine.simulations.erosion import ErosionSimulation
from worldengine.simulations.precipitation import PrecipitationSimulation
from worldengine.simulations.biome import BiomeSimulation
from worldengine.common import anti_alias, get_verbose
import numpy


# ------------------
# Initial generation
# ------------------

def center_land(world):
    """Translate the map horizontally and vertically to put as much ocean as
       possible at the borders. It operates on elevation and plates map"""

    min_sum_on_y = None
    y_with_min_sum = None
    latshift = 0
    for y in range(world.height):
        sum_on_y = world.elevation['data'][y].sum()
        if min_sum_on_y is None or sum_on_y < min_sum_on_y:
            min_sum_on_y = sum_on_y
            y_with_min_sum = y
    if get_verbose():
        print("geo.center_land: height complete")

    min_sum_on_x = None
    x_with_min_sum = None
    for x in range(world.width):
        sum_on_x = world.elevation['data'].T[x].sum()
        if min_sum_on_x is None or sum_on_x < min_sum_on_x:
            min_sum_on_x = sum_on_x
            x_with_min_sum = x
    if get_verbose():
        print("geo.center_land: width complete")

    new_elevation_data = [] #TODO: this should fully use numpy
    new_plates = []
    for y in range(world.height):
        new_elevation_data.append([])
        new_plates.append([])
        src_y = (y_with_min_sum + y - latshift) % world.height
        for x in range(world.width):
            src_x = (x_with_min_sum + x) % world.width
            new_elevation_data[y].append(world.elevation['data'][src_y, src_x])
            new_plates[y].append(world.plates[src_y][src_x])
    world.elevation['data'] = numpy.array(new_elevation_data)
    world.plates = new_plates
    if get_verbose():
        print("geo.center_land: width complete")


def place_oceans_at_map_borders(world):
    """
    Lower the elevation near the border of the map
    """

    ocean_border = int(min(30, max(world.width / 5, world.height / 5)))

    def place_ocean(x, y, i):
        world.elevation['data'][y, x] = \
            (world.elevation['data'][y, x] * i) / ocean_border

    for x in range(world.width):
        for i in range(ocean_border):
            place_ocean(x, i, i)
            place_ocean(x, world.height - i - 1, i)

    for y in range(world.height):
        for i in range(ocean_border):
            place_ocean(i, y, i)
            place_ocean(world.width - i - 1, y, i)


def add_noise_to_elevation(world, seed):
    octaves = 8
    freq = 16.0 * octaves
    for y in range(world.height):
        for x in range(world.width):
            n = snoise2(x / freq * 2, y / freq * 2, octaves, base=seed)
            world.elevation['data'][y, x] += n


def fill_ocean(elevation, sea_level):#TODO: Make more use of numpy?
    height, width = elevation.shape

    ocean = numpy.zeros(elevation.shape, dtype=bool)
    to_expand = []
    for x in range(width):#handle top and bottom border of the map
        if elevation[0, x] <= sea_level:
            to_expand.append((x, 0))
        if elevation[height - 1, x] <= sea_level:
            to_expand.append((x, height - 1))
    for y in range(height):#handle left- and rightmost border of the map
        if elevation[y, 0] <= sea_level:
            to_expand.append((0, y))
        if elevation[y, width - 1] <= sea_level:
            to_expand.append((width - 1, y))
    for t in to_expand:
        tx, ty = t
        if not ocean[ty, tx]:
            ocean[ty, tx] = True
            for px, py in _around(tx, ty, width, height):
                if not ocean[py, px] and elevation[py, px] <= sea_level:
                    to_expand.append((px, py))

    return ocean


def initialize_ocean_and_thresholds(world, ocean_level=1.0):
    """
    Calculate the ocean, the sea depth and the elevation thresholds
    :param world: a world having elevation but not thresholds
    :param ocean_level: the elevation representing the ocean level
    :return: nothing, the world will be changed
    """
    e = world.elevation['data']
    ocean = fill_ocean(e, ocean_level)
    hl = find_threshold_f(e, 0.10)
    ml = find_threshold_f(e, 0.03)
    e_th = [('sea', ocean_level),
            ('plain', hl),
            ('hill', ml),
            ('mountain', None)]
    harmonize_ocean(ocean, e, ocean_level)
    world.set_ocean(ocean)
    world.set_elevation(e, e_th)
    world.sea_depth = sea_depth(world, ocean_level)


def harmonize_ocean(ocean, elevation, ocean_level):
    """
    The goal of this function is to make the ocean floor less noisy.
    The underwater erosion should cause the ocean floor to be more uniform
    """
    height, width = elevation.shape

    shallow_sea = ocean_level * 0.85
    midpoint = shallow_sea / 2.0

    for y in range(height):
        for x in range(width):
            e = elevation[y, x]
            if ocean[y, x] and e < shallow_sea:
                # TODO: use numpy to avoid the loop
                if e < midpoint:
                    e = midpoint - ((midpoint - e) / 5.0)
                else:
                    e = midpoint + ((e - midpoint) / 5.0)
                elevation[y, x] = e

# ----
# Misc
# ----

def sea_depth(world, sea_level):
    sea_depth = sea_level - world.elevation['data']
{'fraction_non_alphanumeric': 0.10758668636482141, 'fraction_numerical': 0.006952289910489268, 'mean_word_length': 2.543103448275862, 'pattern_counts': {'":': 0, '<': 21, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, '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': '783065', 'n_tokens_mistral': 3830, 'n_tokens_neox': 3632, 'n_words': 1015}