454 lines
13 KiB
C#
454 lines
13 KiB
C#
using Godot;
|
|
using System;
|
|
using Godot.Collections;
|
|
|
|
public partial class World : Node2D
|
|
{
|
|
public enum GeneratorAlgorithm
|
|
{
|
|
Random,
|
|
Simple,
|
|
Complex
|
|
}
|
|
|
|
|
|
Vector2I _darkGras = new Vector2I(0, 0);
|
|
Vector2I _brightGras = new Vector2I(1, 0);
|
|
Vector2I _flower = new Vector2I(2, 0);
|
|
TileMapLayer _tileMapLayer;
|
|
|
|
Vector2 _screenSize;
|
|
float _worldWidth;
|
|
float _worldHeight;
|
|
private Vector2I _tileSize;
|
|
private Timer _generationTimeout;
|
|
|
|
[Export] public GeneratorAlgorithm Algorithm = GeneratorAlgorithm.Random;
|
|
|
|
private void GenerateGrid()
|
|
{
|
|
Dictionary grid = new Dictionary();
|
|
for (int x = 0; x < _worldHeight; x++)
|
|
{
|
|
for (int y = 0; y < _worldWidth; y++)
|
|
{
|
|
// grid[new Vector2(x, y)] = null;
|
|
}
|
|
}
|
|
}
|
|
|
|
private Vector2 gridToWorld(Vector2 pos) => pos * _tileSize.X;
|
|
// private Vector2 worldToGrid(Vector2 pos) => Godot.Mathf.Floor(pos / _tileSize.X);
|
|
|
|
public override void _Ready()
|
|
{
|
|
GD.Print("World Node Ready");
|
|
|
|
GD.Print("Getting Screen Size");
|
|
_screenSize = GetViewportRect().Size;
|
|
GD.Print("Setting World Size");
|
|
_worldWidth = _screenSize.X;
|
|
_worldHeight = _screenSize.Y;
|
|
|
|
GD.Print("Getting Tilemap Layer and Setting Tile Size");
|
|
_tileMapLayer = GetNode<TileMapLayer>("TileMapLayer");
|
|
_tileSize = _tileMapLayer.TileSet.TileSize;
|
|
|
|
GD.Print("Getting Timer");
|
|
_generationTimeout = GetNode<Timer>("GenerationTimeout");
|
|
|
|
// Grid generation
|
|
GD.Print("Setting Grid Properties");
|
|
Node2D grid = GetNode<Node2D>("Grid");
|
|
grid.Set("width", _worldHeight / _tileSize.X);
|
|
grid.Set("height", _worldHeight / _tileSize.Y);
|
|
grid.Set("cell_size", _tileSize);
|
|
GD.Print("Calling generateGrid");
|
|
grid.Call("generateGrid");
|
|
|
|
GD.Print("Randomizing Seed");
|
|
GD.Randomize();
|
|
|
|
// World generation
|
|
GD.Print("Generating World");
|
|
if (_generationTimeout.IsNodeReady())
|
|
GenerateWorld();
|
|
}
|
|
|
|
// public override void _Process(double delta)
|
|
// {
|
|
// GD.Print(algorithm);
|
|
//
|
|
// }
|
|
|
|
private void GenerateWorld()
|
|
{
|
|
try
|
|
{
|
|
if (_generationTimeout.IsStopped())
|
|
{
|
|
switch (Algorithm)
|
|
{
|
|
case GeneratorAlgorithm.Random:
|
|
GenerateWorldRandom();
|
|
break;
|
|
case GeneratorAlgorithm.Simple:
|
|
GenerateWorldSimplexNoise();
|
|
break;
|
|
case GeneratorAlgorithm.Complex:
|
|
GenerateWorldComplex();
|
|
break;
|
|
default:
|
|
break;
|
|
}
|
|
}
|
|
|
|
_generationTimeout.Start();
|
|
}
|
|
catch (Exception e)
|
|
{
|
|
GD.PrintErr(e);
|
|
}
|
|
}
|
|
|
|
private void GenerateWorldRandom()
|
|
{
|
|
for (int y = 0; y < _worldHeight; y++)
|
|
{
|
|
for (int x = 0; x < _worldWidth; x++)
|
|
{
|
|
float rnd = GD.Randf();
|
|
|
|
if (rnd < .7f)
|
|
_tileMapLayer.SetCell(new Vector2I(x, y), 0, _darkGras);
|
|
else if (rnd < .9f)
|
|
_tileMapLayer.SetCell(new Vector2I(x, y), 0, _brightGras);
|
|
else
|
|
_tileMapLayer.SetCell(new Vector2I(x, y), 0, _flower);
|
|
}
|
|
}
|
|
}
|
|
|
|
private void GenerateWorldSimplexNoise()
|
|
{
|
|
var noise = new FastNoiseLite();
|
|
|
|
noise.Seed = GD.RandRange(int.MinValue, int.MaxValue);
|
|
noise.FractalOctaves = 2;
|
|
|
|
for (int y = 0; y < _worldHeight; y++)
|
|
{
|
|
for (int x = 0; x < _worldWidth; x++)
|
|
{
|
|
var rnd = noise.GetNoise2D(x, y);
|
|
|
|
// var xRnd = noise.GetNoise1D(x);
|
|
// var yRnd = noise.GetNoise1D(y);
|
|
|
|
if (rnd < .3f)
|
|
_tileMapLayer.SetCell(new Vector2I(x, y), 0, _darkGras);
|
|
else if (rnd < .6f)
|
|
_tileMapLayer.SetCell(new Vector2I(x, y), 0, _brightGras);
|
|
else
|
|
_tileMapLayer.SetCell(new Vector2I(x, y), 0, _flower);
|
|
|
|
|
|
// if (yRnd < .3f)
|
|
// tileMapLayer.SetCell(new Vector2I(x, y), 0, darkGras);
|
|
// else if (xRnd < .6f)
|
|
// tileMapLayer.SetCell(new Vector2I(x, y), 0, brightGras);
|
|
// else
|
|
// tileMapLayer.SetCell(new Vector2I(x, y), 0, flower);
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
[ExportGroup("General")]
|
|
[Export]
|
|
public FastNoiseLite.NoiseTypeEnum NoiseType
|
|
{
|
|
get => _noiseType;
|
|
set
|
|
{
|
|
_noiseType = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
[Export] public int NoiseSeed
|
|
{
|
|
get => _noiseSeed;
|
|
set
|
|
{
|
|
_noiseSeed = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
[Export] public Vector3 NoiseOffset
|
|
{
|
|
get => _noiseOffset;
|
|
set
|
|
{
|
|
_noiseOffset = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
[ExportGroup("Perlin and Simplex")]
|
|
[Export] public float NoiseFrequency
|
|
{
|
|
get => _noiseFrequency;
|
|
set
|
|
{
|
|
_noiseFrequency = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
[Export] public FastNoiseLite.FractalTypeEnum NoiseFractalType
|
|
{
|
|
get => _noiseFractalType;
|
|
set
|
|
{
|
|
_noiseFractalType = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
[Export] public int NoiseFractalOctaves
|
|
{
|
|
get => _noiseFractalOctaves;
|
|
set
|
|
{
|
|
_noiseFractalOctaves = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
|
|
[Export] public float NoiseFractalLacunarity
|
|
{
|
|
get => _noiseFractalLacunarity;
|
|
set
|
|
{
|
|
_noiseFractalLacunarity = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
|
|
[Export] public float NoiseFractalGain
|
|
{
|
|
get => _noiseFractalGain;
|
|
set
|
|
{
|
|
_noiseFractalGain = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
|
|
[Export] public float NoiseFractalWeightedStrength
|
|
{
|
|
get => _noiseFractalWeightedStrength;
|
|
set
|
|
{
|
|
_noiseFractalWeightedStrength = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
|
|
[Export] public float NoiseFractalPingPongStrength
|
|
{
|
|
get => _noiseFractalPingPongStrength;
|
|
set
|
|
{
|
|
_noiseFractalPingPongStrength = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
|
|
[ExportGroup("Cellular")]
|
|
[Export] public float NoiseCellularJitter
|
|
{
|
|
get => _noiseCellularJitter;
|
|
set
|
|
{
|
|
_noiseCellularJitter = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
|
|
[Export]
|
|
public FastNoiseLite.CellularDistanceFunctionEnum NoiseCellularDistanceFunction
|
|
{
|
|
get => _noiseCellularDistanceFunction;
|
|
set
|
|
{
|
|
_noiseCellularDistanceFunction = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
|
|
[Export] public FastNoiseLite.CellularReturnTypeEnum NoiseCellularReturnType
|
|
{
|
|
get => _noiseCellularReturnType;
|
|
set
|
|
{
|
|
_noiseCellularReturnType = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
|
|
[ExportGroup("Domain Warp")]
|
|
[Export] public bool NoiseDomainWarpEnabled
|
|
{
|
|
get => _noiseDomainWarpEnabled;
|
|
set
|
|
{
|
|
_noiseDomainWarpEnabled = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
|
|
[Export] public FastNoiseLite.DomainWarpTypeEnum NoiseDomainWarpType
|
|
{
|
|
get => _noiseDomainWarpType;
|
|
set
|
|
{
|
|
_noiseDomainWarpType = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
|
|
[Export] public float NoiseDomainWarpAmplitude
|
|
{
|
|
get => _noiseDomainWarpAmplitude;
|
|
set
|
|
{
|
|
_noiseDomainWarpAmplitude = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
|
|
[Export] public float NoiseDomainWarpFrequency
|
|
{
|
|
get => _noiseDomainWarpFrequency;
|
|
set
|
|
{
|
|
_noiseDomainWarpFrequency = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
|
|
[Export] public FastNoiseLite.DomainWarpFractalTypeEnum NoiseDomainWarpFractalType
|
|
{
|
|
get => _noiseDomainWarpFractalType;
|
|
set
|
|
{
|
|
_noiseDomainWarpFractalType = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
|
|
[Export] public int NoiseDomainWarpFractalOctaves
|
|
{
|
|
get => _noiseDomainWarpFractalOctaves;
|
|
set
|
|
{
|
|
_noiseDomainWarpFractalOctaves = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
|
|
[Export] public float NoiseDomainWarpFractalLacunarity
|
|
{
|
|
get => _noiseDomainWarpFractalLacunarity;
|
|
set
|
|
{
|
|
_noiseDomainWarpFractalLacunarity = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
|
|
[Export] public float NoiseDomainWarpFractalGain
|
|
{
|
|
get => _noiseDomainWarpFractalGain;
|
|
set
|
|
{
|
|
_noiseDomainWarpFractalGain = value;
|
|
GenerateWorld();
|
|
}
|
|
}
|
|
|
|
// General
|
|
private int _noiseSeed;
|
|
private FastNoiseLite.NoiseTypeEnum _noiseType;
|
|
|
|
// Simplex and Perlin
|
|
private float _noiseFrequency = 0.01f;
|
|
private Vector3 _noiseOffset = new(0.0f, 0.0f, 0.0f);
|
|
private FastNoiseLite.FractalTypeEnum _noiseFractalType = FastNoiseLite.FractalTypeEnum.Fbm;
|
|
private int _noiseFractalOctaves = 5;
|
|
private float _noiseFractalLacunarity = 2.0f;
|
|
private float _noiseFractalGain = 0.5f;
|
|
private float _noiseFractalWeightedStrength = 0.0f;
|
|
private float _noiseFractalPingPongStrength = 2.0f;
|
|
|
|
// Cellular
|
|
private float _noiseCellularJitter = 1.0f;
|
|
private FastNoiseLite.CellularDistanceFunctionEnum _noiseCellularDistanceFunction;
|
|
private FastNoiseLite.CellularReturnTypeEnum _noiseCellularReturnType = FastNoiseLite.CellularReturnTypeEnum.Distance;
|
|
|
|
// Domain Warp
|
|
private bool _noiseDomainWarpEnabled = false;
|
|
private FastNoiseLite.DomainWarpTypeEnum _noiseDomainWarpType = FastNoiseLite.DomainWarpTypeEnum.SimplexReduced;
|
|
private float _noiseDomainWarpAmplitude = 30.0f;
|
|
private float _noiseDomainWarpFrequency = 0.05f;
|
|
private FastNoiseLite.DomainWarpFractalTypeEnum _noiseDomainWarpFractalType =
|
|
FastNoiseLite.DomainWarpFractalTypeEnum.Progressive;
|
|
private int _noiseDomainWarpFractalOctaves = 5;
|
|
private float _noiseDomainWarpFractalLacunarity = 6.0f;
|
|
private float _noiseDomainWarpFractalGain = 0.5f;
|
|
|
|
private void GenerateWorldComplex()
|
|
{
|
|
var noise = new FastNoiseLite();
|
|
if (NoiseSeed == 0)
|
|
noise.Seed = GD.RandRange(int.MinValue, int.MaxValue);
|
|
else
|
|
noise.Seed = NoiseSeed;
|
|
GD.Print(noise.Seed);
|
|
|
|
noise.NoiseType = _noiseType;
|
|
noise.Frequency = _noiseFrequency;
|
|
noise.Offset = _noiseOffset;
|
|
noise.FractalType = _noiseFractalType;
|
|
noise.FractalOctaves = _noiseFractalOctaves;
|
|
noise.FractalLacunarity = _noiseFractalLacunarity;
|
|
noise.FractalGain = _noiseFractalGain;
|
|
noise.FractalWeightedStrength = _noiseFractalWeightedStrength;
|
|
noise.FractalPingPongStrength = _noiseFractalPingPongStrength;
|
|
noise.CellularJitter = _noiseCellularJitter;
|
|
noise.CellularReturnType = _noiseCellularReturnType;
|
|
noise.DomainWarpEnabled = _noiseDomainWarpEnabled;
|
|
noise.DomainWarpType = _noiseDomainWarpType;
|
|
noise.DomainWarpAmplitude = _noiseDomainWarpAmplitude;
|
|
noise.DomainWarpFrequency = _noiseDomainWarpFrequency;
|
|
noise.DomainWarpFractalType = _noiseDomainWarpFractalType;
|
|
noise.DomainWarpFractalOctaves = _noiseDomainWarpFractalOctaves;
|
|
noise.DomainWarpFractalLacunarity = _noiseDomainWarpFractalLacunarity;
|
|
noise.DomainWarpFractalGain = _noiseDomainWarpFractalGain;
|
|
|
|
|
|
|
|
for (int y = 0; y < _worldHeight; y++)
|
|
{
|
|
for (int x = 0; x < _worldWidth; x++)
|
|
{
|
|
var rnd = noise.GetNoise2D(x, y);
|
|
|
|
if (rnd < .3f)
|
|
_tileMapLayer.SetCell(new Vector2I(x, y), 0, _darkGras);
|
|
else if (rnd < .6f)
|
|
_tileMapLayer.SetCell(new Vector2I(x, y), 0, _brightGras);
|
|
else
|
|
_tileMapLayer.SetCell(new Vector2I(x, y), 0, _flower);
|
|
}
|
|
}
|
|
}
|
|
} |