public void TestMaskWithOverlapping() { var a = new int[, ] { { 1, 0 }, { 0, 1 }, }; var model = OverlappingModel.Create(a, 2, false, 8); var mask = new bool[4 * 5]; for (var x = 0; x < 5; x++) { for (var y = 0; y < 4; y++) { if (x == 2 || x == 3) { mask[x + y * 5] = false; } else { mask[x + y * 5] = true; } } } var topology = new GridTopology(5, 4, false).WithMask(mask); var propagator = new TilePropagator(model, topology); propagator.Select(0, 0, 0, new Tile(1)); propagator.Select(4, 0, 0, new Tile(0)); propagator.Run(); Assert.AreEqual(Resolution.Decided, propagator.Status); }
/// <summary>Creates an <c>AdjacencyRule</c> for the overlapping model</summary> public static RuleData buildRule(PatternStorage patterns, ref Map source) { var rule = new RuleData(); int nPatterns = patterns.len; rule.nPatterns = nPatterns; { // do not count symmetric combinations int nCombinations = (nPatterns + 1) * (nPatterns) / 2; rule.cache = new Grid2D <bool>(4, nCombinations); } for (int from = 0; from < nPatterns; from++) { for (int to = from; to < nPatterns; to++) { for (int d = 0; d < 4; d++) { var dir = (Dir4)d; bool canOverlap = OverlappingModel.testCompatibility(from, dir, to, patterns, source); rule.cache.add(canOverlap); } } } return(rule); }
static void F() { Utils.ClearLogConsole(); // Random.InitState(Time.tim); bool finished = false; OverlappingModel model = null; var name = "Dungeon"; // var name = "Flowers"; for (int i = 0; i < 1 && !finished; i++) { // model = new OverlappingModel(name, 3, 48, 48, true, true, 2, -4); model = new OverlappingModel(name, 3, 48, 48, true, true, 8, 0); finished = model.Run(42, 0);//(int) (DateTime.Now.Millisecond), 0); } Debug.Log("Finished: " + finished); if (finished) { var t = model.Graphics(); File.WriteAllBytes($"Assets\\{name}-result.png", t.EncodeToPNG()); } AssetDatabase.Refresh(); // AssetDatabase.CreateAsset(t, ""); }
public TileModel GetModel(DirectionSet directions, ITopoArray <Tile>[] samples, TileRotation tileRotation) { var modelConfig = Config.Model ?? new Adjacent(); TileModel tileModel; if (modelConfig is Overlapping overlapping) { var model = new OverlappingModel(overlapping.NX, overlapping.NY, overlapping.NZ); foreach (var sample in samples) { model.AddSample(sample, tileRotation); } tileModel = model; } else if (modelConfig is Adjacent adjacent) { var model = new AdjacentModel(directions); foreach (var sample in samples) { model.AddSample(sample, tileRotation); } tileModel = model; } else { throw new ConfigurationException($"Unrecognized model type {modelConfig.GetType()}"); } SetupAdjacencies(tileModel, tileRotation); SetupTiles(tileModel, tileRotation); return(tileModel); }
public static Model create(ref Map source, int N, Vec2i outputSize) { var patterns = RuleData.extractEveryPattern(ref source, N, PatternUtil.variations); var rule = OverlappingModel.buildRule(patterns, ref source); return(new Model(outputSize, patterns, rule)); }
static void Main() { Random random = new Random(); var xdoc = new XmlDocument(); xdoc.Load("samples.xml"); int counter = 1; foreach (XmlNode xnode in xdoc.FirstChild.ChildNodes) { if (xnode.Name == "#comment") { continue; } Model model; string name = xnode.Get <string>("name"); Console.WriteLine($"< {name}"); if (xnode.Name == "overlapping") { model = new OverlappingModel(name, xnode.Get("N", 2), xnode.Get("width", 48), xnode.Get("height", 48), xnode.Get("periodicInput", true), xnode.Get("periodic", false), xnode.Get("symmetry", 8), xnode.Get("ground", 0)); } else if (xnode.Name == "simpletiled") { model = new SimpleTiledModel(name, xnode.Get <string>("subset"), xnode.Get("width", 10), xnode.Get("height", 10), xnode.Get("periodic", false), xnode.Get("black", false)); } else { continue; } for (int i = 0; i < xnode.Get("screenshots", 2); i++) { for (int k = 0; k < 10; k++) { Console.Write("> "); int seed = random.Next(); bool finished = model.Run(seed, xnode.Get("limit", 0)); if (finished) { Console.WriteLine("DONE"); model.Graphics().Save($"{counter} {name} {i}.png"); break; } else { Console.WriteLine("CONTRADICTION"); } } } counter++; } }
static void Main() { Random random = new Random(); XDocument xdoc = XDocument.Load("samples.xml"); int counter = 1; foreach (XElement xelem in xdoc.Root.Elements("overlapping", "simpletiled")) { Model model; string name = xelem.Get <string>("name"); Console.WriteLine($"< {name}"); if (xelem.Name == "overlapping") { model = new OverlappingModel(name, xelem.Get("N", 2), xelem.Get("width", 48), xelem.Get("height", 48), xelem.Get("periodicInput", true), xelem.Get("periodic", false), xelem.Get("symmetry", 8), xelem.Get("ground", 0)); } else if (xelem.Name == "simpletiled") { model = new SimpleTiledModel(name, xelem.Get <string>("subset"), xelem.Get("width", 10), xelem.Get("height", 10), xelem.Get("periodic", false), xelem.Get("black", false)); } else { continue; } for (int i = 0; i < xelem.Get("screenshots", 2); i++) { for (int k = 0; k < 10; k++) { Console.Write("> "); int seed = random.Next(); bool finished = model.Run(seed, xelem.Get("limit", 0)); if (finished) { Console.WriteLine("DONE"); model.Graphics().Save($"{counter} {name} {i}.png"); if (model is SimpleTiledModel && xelem.Get("textOutput", false)) { System.IO.File.WriteAllText($"{counter} {name} {i}.txt", (model as SimpleTiledModel).TextOutput()); } break; } else { Console.WriteLine("CONTRADICTION"); } } } counter++; } }
public void Draw() { if (output == null) { Debug.Log("output was null"); Generate(); Draw(); } if (group == null) { Debug.Log("group was null"); return; } undrawn = false; try{ for (int y = 0; y < depth; y++) { for (int x = 0; x < width; x++) { if (rendering[x, y] == null) { int v = (int)model.Sample(x, y); if (v != 99 && v < training.tiles.Length) { Vector3 pos = new Vector3(x * gridsize, y * gridsize, 0f); int rot = (int)training.RS[v]; GameObject fab = training.tiles[v] as GameObject; if (fab != null) { GameObject tile = (GameObject)Instantiate(fab, new Vector3(), Quaternion.identity); Vector3 fscale = tile.transform.localScale; tile.transform.parent = group; tile.transform.localPosition = pos; BlockMover bm = tile.GetComponent <BlockMover>(); if (bm != null) { tile.transform.localPosition += bm.dist; } tile.transform.localEulerAngles = new Vector3(0, 0, 360 - (rot * 90)); tile.transform.localScale = fscale; rendering[x, y] = tile; } } else { undrawn = true; } } } } } catch (IndexOutOfRangeException e) { model = null; return; } }
public static WfcOverlap create(ref Map source, int N, Vec2i outputSize) { if (N < 2) { throw new System.ArgumentException($"given N = {N}; it must be bigger than one"); } var model = OverlappingModel.create(ref source, N, outputSize); var state = new State(outputSize.x, outputSize.y, model.patterns, ref model.rule); return(new WfcOverlap(model, state, N)); }
public void Generate() { if (training == null) { Debug.Log("Can't Generate: no designated Training component"); } if (IsPrefabRef(training.gameObject)) { GameObject o = CreatePrefab(training.gameObject, new Vector3(0, 99999f, 0f), Quaternion.identity); training = o.GetComponent <Training>(); } if (training.sample == null) { training.Compile(); } if (output == null) { Transform ot = transform.Find("output-overlap"); if (ot != null) { output = ot.gameObject; } } if (output == null) { output = new GameObject("output-overlap"); output.transform.parent = transform; output.transform.position = this.gameObject.transform.position; output.transform.rotation = this.gameObject.transform.rotation; } for (int i = 0; i < output.transform.childCount; i++) { GameObject go = output.transform.GetChild(i).gameObject; if (Application.isPlaying) { Destroy(go); } else { DestroyImmediate(go); } } group = new GameObject(training.gameObject.name).transform; group.parent = output.transform; group.position = output.transform.position; group.rotation = output.transform.rotation; group.localScale = new Vector3(1f, 1f, 1f); rendering = new GameObject[width, depth]; model = new OverlappingModel(training.sample, N, width, depth, periodicInput, periodicOutput, symmetry, foundation, xloc, zloc); undrawn = true; Run(); }
public override void Generate() { if (training == null) { Debug.Log("Can't Generate: no designated Training component"); } if (training.sample == null) { training.Compile(); } outputTilemap = GetComponent <Tilemap>(); tilesRendering = new TileBase[width, depth]; model = new OverlappingModel(training.sample, N, width, depth, periodicInput, periodicOutput, symmetry, foundation); undrawn = true; }
public TileModel BuildModel() { TileModel model = null; switch (Type) { case ModelType.Adjacent: model = new AdjacentModel(); break; case ModelType.Overlapping: model = new OverlappingModel(3); break; } return(model); }
public static void DoTheDance() { Random random = new Random(); var xdoc = new XmlDocument(); xdoc.Load("mapGen.xml"); int counter = 1; foreach (XmlNode xnode in xdoc.FirstChild.ChildNodes) { if (xnode.Name == "#comment") continue; Model model; string name = xnode.Get<string>("name"); Console.WriteLine($"< {name}"); if (xnode.Name == "overlapping") model = new OverlappingModel(name, xnode.Get("N", 2), xnode.Get("width", 48), xnode.Get("height", 48), xnode.Get("periodicInput", true), xnode.Get("periodic", false), xnode.Get("symmetry", 8), xnode.Get("ground", 0)); else if (xnode.Name == "simpletiled") model = new SimpleTiledModel(name, xnode.Get<string>("subset"), xnode.Get("width", 10), xnode.Get("height", 10), xnode.Get("periodic", false), xnode.Get("black", false)); else continue; for (int i = 0; i < xnode.Get("screenshots", 2); i++) { for (int k = 0; k < 10; k++) { Console.Write("> "); int seed = random.Next(); bool finished = model.Run(seed, xnode.Get("limit", 0)); if (finished) { Console.WriteLine("DONE"); model.Graphics().Save($"{counter} {name} {i}.png"); if (model is SimpleTiledModel && xnode.Get("textOutput", false)) System.IO.File.WriteAllText($"{counter} {name} {i}.txt", (model as SimpleTiledModel).TextOutput()); break; } else Console.WriteLine("CONTRADICTION"); } } counter++; } Otter.Util.Log("EGG"); }
public TileModel GetModel(DirectionSet directions, SampleSet sampleSet, TileRotation tileRotation) { var samples = sampleSet.Samples; var modelConfig = Config.Model ?? new Adjacent(); TileModel tileModel; if (modelConfig is Overlapping overlapping) { var model = new OverlappingModel(overlapping.NX, overlapping.NY, overlapping.NZ); foreach (var sample in samples) { model.AddSample(sample, tileRotation); } tileModel = model; } else if (modelConfig is Adjacent adjacent) { var model = new AdjacentModel(directions); foreach (var sample in samples) { model.AddSample(sample, tileRotation); } tileModel = model; } else { throw new ConfigurationException($"Unrecognized model type {modelConfig.GetType()}"); } var autoAdjacencies = Config.AutoAdjacency ? AdjacencyUtils.GetAutoAdjacencies(sampleSet, tileRotation, Config.AutoAdjacencyTolerance) : new AdjacentModel.Adjacency[0]; var manualAdjacencies = GetManualAdjacencies(sampleSet.Directions, tileRotation); SetupAdjacencies(tileModel, tileRotation, autoAdjacencies.Concat(manualAdjacencies).ToList()); SetupTiles(tileModel, tileRotation); return(tileModel); }
public void TestToTopArray() { var a = new int[, ] { { 1, 0 }, { 0, 1 }, }; var model = OverlappingModel.Create(a, 2, false, 8); var propagator = new TilePropagator(model, new GridTopology(4, 4, false)); propagator.Select(0, 0, 0, new Tile(1)); var status = propagator.Run(); Assert.AreEqual(Resolution.Decided, status); var result = propagator.ToValueArray <int>().ToArray2d(); Assert.AreEqual(4, result.GetLength(0)); Assert.AreEqual(4, result.GetLength(1)); Assert.AreEqual(1, result[0, 0]); Assert.AreEqual(1, result[3, 3]); }
private static TileModel GetModel(DeBroglieConfig config, Directions directions, ITopoArray <Tile>[] samples, TileRotation tileRotation) { var modelConfig = config.Model ?? new Adjacent(); if (modelConfig is Overlapping overlapping) { var model = new OverlappingModel(overlapping.NX, overlapping.NY, overlapping.NZ); foreach (var sample in samples) { model.AddSample(sample, config.RotationalSymmetry, config.ReflectionalSymmetry, tileRotation); } return(model); } else if (modelConfig is Adjacent adjacent) { var model = new AdjacentModel(directions); foreach (var sample in samples) { model.AddSample(sample, config.RotationalSymmetry, config.ReflectionalSymmetry, tileRotation); } return(model); } throw new System.Exception($"Unrecognized model type {modelConfig.GetType()}"); }
public void Draw(bool staircase = false) { if (output == null) { return; } if (group == null) { return; } undrawn = false; try { for (int z = 0; z < 1; z++) { for (int y = 0; y < depth; y++) { for (int x = 0; x < width; x++) { if (rendering[x, y, z] == null) { int v = (int)model.Sample(x, y); if (v != 99 && v < training.tiles.Length) { Vector3 pos = new Vector3(x * gridsize, y * gridsize, z * gridsize); int rot = (int)training.RS[v]; GameObject fab = training.tiles[v] as GameObject; if (fab != null) { GameObject tile = (GameObject)Instantiate(fab, new Vector3(), Quaternion.identity); Vector3 fscale = tile.transform.localScale; tile.transform.parent = group; tile.transform.localPosition = pos; tile.transform.localEulerAngles = new Vector3(0, 0, 360 - (rot * 90)); //----mark rotation !---- tile.transform.localScale = fscale; rendering[x, y, z] = tile; if (staircase && x % 3 == 0 && y % 5 == 0) { DrawStaircase(tile); } } } else { undrawn = true; } } } } } } catch (IndexOutOfRangeException e) { Debug.Log(e); model = null; return; } //---------Sorting and delete plateforms---------- for (int z = 0; z < 1; z++) { for (int y = 0; y < depth; y++) { for (int x = 0; x < width; x++) { if (rendering[x, y, z] != null) { //Debug.Log(rendering[x, y, z].name.Replace("(Clone)", "") + " | " + repMur.name); //------ if (rendering[x, y, z].name.Replace("(Clone)", "") == repMur.name) { //--the following deletes the 'flying room' if it is one-- bool flying = true; //--------------- does the room have a path to it? we suppose it has not and whenever a path is found, int v = (int)model.Sample(x, y); //--- switch flying to false, we then delete the room is flying hasn't been changed by the algorythm Vector3 pos = new Vector3(x * gridsize, y * gridsize, z * gridsize); int rot = (int)training.RS[v]; pos = rendering[x, y, 0].transform.position; //pos.x += 1; GameObject currentObj = null; //-> = renderingxyz transform.gameobject while (currentObj == null) { Collider[] hitColliders = Physics.OverlapSphere(rendering[x, y, 0].transform.position, 1f); if (hitColliders.Length != 0) { for (int i = 0; i < hitColliders.Length; i++) { if (hitColliders[i].gameObject.name != null) { currentObj = hitColliders[i].gameObject; if (currentObj.name.Replace("(Clone)", "") == repMur5.name || currentObj.name.Replace("(Clone)", "") == repMur6.name) { flying = false; //Debug.Log("+1 not flying house"); } } } } //-----faire une chenille qui est "periodic output frendly"------ } } if (rendering[x, y, z].name == "cube3(Clone)" || rendering[x, y, z].name == "cube2(Clone)") { Collider[] hitColliders = Physics.OverlapSphere(rendering[x, y, z].transform.position, 1.0f); if (hitColliders.Length != 0) { for (int i = 0; i < hitColliders.Length; i++) { if (hitColliders[i].name == "cube1(Clone)") { hitColliders[i].name = "porte"; } } } } } } } } }
static void Main() { int stageCount = 25; Stopwatch sw = Stopwatch.StartNew(); String timeStamp = ""; // DateTime.Now.ToString("yyyyMMddHHmmssffff"); Random random = new Random(); XDocument xdoc = XDocument.Load("samples.xml"); using (StreamWriter w = File.CreateText("answer.txt")) { w.WriteLine(stageCount.ToString()); } int counter = 1; foreach (XElement xelem in xdoc.Root.Elements("overlapping", "simpletiled")) { Model model; string name = xelem.Get <string>("name"); Console.WriteLine($"< {name}"); if (xelem.Name == "overlapping") { model = new OverlappingModel(name, xelem.Get("N", 2), xelem.Get("width", 48), xelem.Get("height", 48), xelem.Get("periodicInput", true), xelem.Get("periodic", false), xelem.Get("symmetry", 8), xelem.Get("ground", 0)); } else if (xelem.Name == "simpletiled") { model = new SimpleTiledModel(timeStamp, name, xelem.Get <string>("subset"), xelem.Get("width", 10), xelem.Get("height", 10), xelem.Get("periodic", false), xelem.Get("black", false)); } else { continue; } for (int i = 0; i < xelem.Get("screenshots", stageCount); i++) { for (int k = 0; k < 10; k++) { Console.Write("> "); int seed = random.Next(); bool finished = model.Run(seed, xelem.Get("limit", 0)); if (finished) { Console.WriteLine("DONE"); //model.Graphics().Save($"{counter} {name} {i}.png"); //model.Graphics().Save("image/" + i + ".png"); string outputFileName = "image/" + i + ".png"; using (MemoryStream memory = new MemoryStream()) { using (FileStream fs = new FileStream(outputFileName, FileMode.Create, FileAccess.ReadWrite)) { model.Graphics().Save(memory, ImageFormat.Png); byte[] bytes = memory.ToArray(); fs.Write(bytes, 0, bytes.Length); } } if (model is SimpleTiledModel && xelem.Get("textOutput", false)) { System.IO.File.WriteAllText($"{counter} {name} {i}.txt", (model as SimpleTiledModel).TextOutput()); } break; } else { Console.WriteLine("CONTRADICTION"); } } } counter++; } Console.WriteLine($"time = {sw.ElapsedMilliseconds}"); }
public void TestPathConstraint() { var a = new int[, ] { { 0, 0, 0, 1, 0, 0 }, { 0, 0, 0, 1, 0, 0 }, { 0, 0, 0, 1, 0, 0 }, { 1, 1, 1, 1, 0, 0 }, { 0, 0, 0, 0, 0, 0 }, { 0, 0, 0, 0, 0, 0 } }; var seed = Environment.TickCount; var r = new Random(seed); Console.WriteLine("Seed {0}", seed); var model = OverlappingModel.Create(a, 3, false, 8); var propagator = new TilePropagator(model, new Topology(10, 10, false), true, constraints: new[] { new PathConstraint(new HashSet <Tile> { new Tile(1) }, new [] { new Point(0, 0), new Point(9, 9) }) }, random: r); var status = propagator.Run(); Assert.AreEqual(Resolution.Decided, status); var result = propagator.ToValueArray <int>().ToArray2d(); // Write out result for debugging for (var y = 0; y < 10; y++) { for (var x = 0; x < 10; x++) { Console.Write(result[x, y]); } Console.WriteLine(); } // Simple flood fill algorithm to determine we have in fact got a path var stack = new Stack <ValueTuple <int, int> >(); var visited = new bool[10, 10]; stack.Push((0, 0)); while (stack.TryPop(out var current)) { var(x, y) = current; if (x < 0 || x >= 10 || y < 0 || y >= 10) { continue; } if (visited[x, y]) { continue; } visited[x, y] = true; if (result[x, y] == 1) { if (x == 9 && y == 9) { return; } stack.Push((x + 1, y)); stack.Push((x - 1, y)); stack.Push((x, y + 1)); stack.Push((x, y - 1)); } } Assert.Fail(); }
public void TestLoopConstraint() { var a = new int[, ] { { 0, 0, 0, 1, 0, 0 }, { 0, 0, 0, 1, 0, 0 }, { 0, 0, 0, 1, 0, 0 }, { 1, 1, 1, 1, 0, 0 }, { 0, 0, 0, 0, 0, 0 }, { 0, 0, 0, 0, 0, 0 } }; var seed = Environment.TickCount; // TODO: This seed shows that this constraint can fail occasionally //seed = -1847040250; var r = new Random(seed); System.Console.WriteLine("Seed {0}", seed); var model = OverlappingModel.Create(a, 3, false, 8); var constraint = new LoopConstraint { PathSpec = new PathSpec { Tiles = new HashSet <Tile> { new Tile(1) }, } }; var topology = new GridTopology(10, 10, false); var propagator = new TilePropagator(model, topology, new TilePropagatorOptions { BacktrackType = BacktrackType.Backtrack, Constraints = new[] { constraint }, RandomDouble = r.NextDouble }); var status = propagator.Run(); Assert.AreEqual(Resolution.Decided, status); var result = propagator.ToValueArray <int>().ToArray2d(); // Write out result for debugging for (var y = 0; y < topology.Height; y++) { for (var x = 0; x < topology.Width; x++) { System.Console.Write(result[x, y]); } System.Console.WriteLine(); } // Every cell should have exactly 2 neighbours for (var y = 0; y < topology.Height; y++) { for (var x = 0; x < topology.Width; x++) { if (result[x, y] == 1) { var n = 0; if (x > 0) { n += result[x - 1, y]; } if (x < topology.Width - 1) { n += result[x + 1, y]; } if (y > 0) { n += result[x, y - 1]; } if (y < topology.Height - 1) { n += result[x, y + 1]; } Assert.AreEqual(2, n, $"At {x},{y}"); } } } }
static void Main() { Stopwatch sw = Stopwatch.StartNew(); Random random = new Random(); XDocument xdoc = XDocument.Load("samples.xml"); int masterCounter = 0; foreach (XElement xelem in xdoc.Root.Elements("overlapping", "simpletiled")) { var screenshotCount = xelem.Get("screenshots", 10); for (int i = 0; i < screenshotCount; i++) { Parallel.For(0, attempts, (k) => { Model model; string name = xelem.Get <string>("name"); Console.WriteLine($"< {name}"); if (xelem.Name == "overlapping") { model = new OverlappingModel(name, xelem.Get("N", 2), xelem.Get("width", 48), xelem.Get("height", 48), xelem.Get("periodicInput", true), xelem.Get("periodic", false), xelem.Get("symmetry", 8), xelem.Get("ground", 0)); } else if (xelem.Name == "simpletiled") { model = new SimpleTiledModel(name, xelem.Get <string>("subset"), xelem.Get("width", 10), xelem.Get("height", 10), xelem.Get("periodic", false), xelem.Get("black", false)); } else { return; } while (masterCounter < screenshotCount) { Console.Write("> "); int seed = random.Next(); bool finished = model.Run(seed, xelem.Get("limit", 0)); if (finished) { Console.WriteLine("DONE"); var counter = Interlocked.Exchange(ref masterCounter, masterCounter + 1); model.Graphics().Save($"{counter} {name} {i}.png"); if (model is SimpleTiledModel && xelem.Get("textOutput", false)) { System.IO.File.WriteAllText($"{counter} {name} {i}.txt", (model as SimpleTiledModel).TextOutput()); } return; } else { //Console.WriteLine( $"CONTRADICTION Completed {model.CompletedNodes}" ); } } }); } } Console.WriteLine($"time = {sw.ElapsedMilliseconds}"); }
public void TestConnectedConstraintWithEdged() { var a = new int[, ] { { 0, 0, 0, 1, 0, 0 }, { 0, 0, 0, 1, 0, 0 }, { 0, 0, 0, 1, 0, 0 }, { 1, 1, 1, 1, 0, 0 }, { 0, 0, 0, 0, 0, 0 }, { 0, 0, 0, 0, 0, 0 } }; var allDirections = DirectionSet.Cartesian2d.ToHashSet(); var exits = new Dictionary <Tile, ISet <Direction> >() { { new Tile(1), allDirections }, }; var seed = Environment.TickCount; var r = new Random(seed); Console.WriteLine("Seed {0}", seed); var model = OverlappingModel.Create(a, 3, false, 8); var constraint = new ConnectedConstraint { PathSpec = new EdgedPathSpec { Exits = exits, RelevantCells = new[] { new Point(0, 0), new Point(9, 9) }, } }; var propagator = new TilePropagator(model, new GridTopology(10, 10, false), new TilePropagatorOptions { BackTrackDepth = -1, Constraints = new[] { constraint }, RandomDouble = r.NextDouble }); var status = propagator.Run(); Assert.AreEqual(Resolution.Decided, status); var result = propagator.ToValueArray <int>().ToArray2d(); // Write out result for debugging for (var y = 0; y < 10; y++) { for (var x = 0; x < 10; x++) { Console.Write(result[x, y]); } Console.WriteLine(); } // Simple flood fill algorithm to determine we have in fact got a path var stack = new Stack <ValueTuple <int, int> >(); var visited = new bool[10, 10]; stack.Push((0, 0)); while (stack.TryPop(out var current)) { var(x, y) = current; if (x < 0 || x >= 10 || y < 0 || y >= 10) { continue; } if (visited[x, y]) { continue; } visited[x, y] = true; if (result[x, y] == 1) { if (x == 9 && y == 9) { return; } stack.Push((x + 1, y)); stack.Push((x - 1, y)); stack.Push((x, y + 1)); stack.Push((x, y - 1)); } } Assert.Fail(); }
public void TestAcyclicConstraint() { var a = new int[, ] { { 0, 0, 0, 1, 0, 0 }, { 0, 0, 0, 1, 0, 0 }, { 0, 0, 0, 1, 0, 0 }, { 1, 1, 1, 1, 0, 0 }, { 0, 1, 0, 0, 0, 0 }, { 0, 1, 0, 0, 0, 0 } }; var seed = Environment.TickCount; var r = new Random(seed); Console.WriteLine("Seed {0}", seed); var model = OverlappingModel.Create(a, 3, false, 8); var topology = new GridTopology(10, 10, false); /* * var pathSpec = new PathSpec * { * Tiles = new HashSet<Tile> { new Tile(1) }, * }; */ var pathSpec = new EdgedPathSpec { Exits = new Dictionary <Tile, ISet <Direction> > { { new Tile(1), topology.Directions.ToHashSet() } }, }; var constraint = new AcyclicConstraint { PathSpec = pathSpec, }; var propagator = new TilePropagator(model, topology, new TilePropagatorOptions { BackTrackDepth = -1, Constraints = new[] { constraint }, RandomDouble = r.NextDouble }); var status = propagator.Run(); Assert.AreEqual(Resolution.Decided, status); var result = propagator.ToValueArray <int>().ToArray2d(); // Write out result for debugging for (var y = 0; y < topology.Height; y++) { for (var x = 0; x < topology.Width; x++) { Console.Write(result[x, y]); } Console.WriteLine(); } var visited = new bool[topology.Width, topology.Height]; for (var y = 0; y < topology.Height; y++) { for (var x = 0; x < topology.Width; x++) { if (result[x, y] != 1) { continue; } if (visited[x, y]) { continue; } void Visit(int x2, int y2, int dir) { if (x2 < 0 || x2 >= topology.Width || y2 < 0 || y2 >= topology.Height) { return; } if (result[x2, y2] != 1) { return; } if (visited[x2, y2]) { Assert.Fail(); } visited[x2, y2] = true; if (dir != 0) { Visit(x2 - 1, y2, 2); } if (dir != 2) { Visit(x2 + 1, y2, 0); } if (dir != 1) { Visit(x2, y2 - 1, 3); } if (dir != 3) { Visit(x2, y2 + 1, 1); } } Visit(x, y, -1); } } }
static void Main() { Stopwatch sw = Stopwatch.StartNew(); Random random = new Random(); XDocument xdoc = XDocument.Load("samples.xml"); foreach (XElement xelem in xdoc.Root.Elements("overlapping", "simpletiled")) { Model model; string name = xelem.Get <string>("name"); Console.WriteLine($"< {name}"); bool isOverlapping = xelem.Name == "overlapping"; int size = xelem.Get("size", isOverlapping ? 48 : 24); int width = xelem.Get("width", size); int height = xelem.Get("height", size); bool periodic = xelem.Get("periodic", false); string heuristicString = xelem.Get <string>("heuristic"); var heuristic = heuristicString == "Scanline" ? Model.Heuristic.Scanline : (heuristicString == "MRV" ? Model.Heuristic.MRV : Model.Heuristic.Entropy); if (isOverlapping) { int N = xelem.Get("N", 3); bool periodicInput = xelem.Get("periodicInput", true); int symmetry = xelem.Get("symmetry", 8); int ground = xelem.Get("ground", 0); model = new OverlappingModel(name, N, width, height, periodicInput, periodic, symmetry, ground, heuristic); } else { string subset = xelem.Get <string>("subset"); bool blackBackground = xelem.Get("blackBackground", false); model = new SimpleTiledModel(name, subset, width, height, periodic, blackBackground, heuristic); } for (int i = 0; i < xelem.Get("screenshots", 2); i++) { for (int k = 0; k < 10; k++) { Console.Write("> "); int seed = random.Next(); bool success = model.Run(seed, xelem.Get("limit", -1)); if (success) { Console.WriteLine("DONE"); model.Graphics().Save($"{name} {seed}.png"); if (model is SimpleTiledModel stmodel && xelem.Get("textOutput", false)) { System.IO.File.WriteAllText($"{name} {seed}.txt", stmodel.TextOutput()); } break; } else { Console.WriteLine("CONTRADICTION"); } } } } Console.WriteLine($"time = {sw.ElapsedMilliseconds}"); }
static void Main() { #if (VERSIONING) Console.WriteLine("Version number: {0}", Versioning.VersionNumber); #else Console.WriteLine("There seems to be no versioning available."); #endif Stopwatch sw = Stopwatch.StartNew(); Random random = new Random(); XDocument xdoc = XDocument.Load("samples.xml"); int counter = 1; foreach (XElement xelem in xdoc.Root.Elements("overlapping", "simpletiled")) { Model model; string name = xelem.Get <string>("name"); Log($"Now processing picture <{name}>"); if (xelem.Name == "overlapping") { model = new OverlappingModel( name, xelem.Get("N", 2), xelem.Get("width", 48), xelem.Get("height", 48), xelem.Get("periodicInput", true), xelem.Get("periodic", false), xelem.Get("symmetry", 8), xelem.Get("ground", 0)); Log("\tProcessing as overlapping model"); } else if (xelem.Name == "simpletiled") { model = new SimpleTiledModel( name, xelem.Get <string>("subset"), xelem.Get("width", 10), xelem.Get("height", 10), xelem.Get("periodic", false), xelem.Get("black", false)); Log("\tProcessing as simpletiled model"); } else { Log("\tDid not find a valid model. Moving on to the next picture.."); continue; } for (int i = 0; i < xelem.Get("screenshots", 2); i++) { for (int k = 0; k < 10; k++) { int seed = random.Next(); Log($"\tFor process #{i+1} the random seed is {seed}"); bool finished = model.Run(seed, xelem.Get("limit", 0)); if (finished) { Log("\t-->SUCCESS<--"); model.Graphics().Save($"{counter} {name} {i}.png"); Log($"\tSaving result with name {counter} {name} {i}.png"); if (model is SimpleTiledModel && xelem.Get("textOutput", false)) { System.IO.File.WriteAllText($"{counter} {name} {i}.txt", (model as SimpleTiledModel).TextOutput()); } break; } else { Log("\t-->CONTRADICTION<--"); continue; } } } counter++; } Log($"time = {sw.ElapsedMilliseconds}"); Console.ReadLine(); }
// called once on creation private void Start() { // retrieve the output dimenions width = PlayerPrefs.GetInt("ppWidth"); height = PlayerPrefs.GetInt("ppHeight"); System.Random random = new System.Random(); // create the model Model model; model = new OverlappingModel(inputName, N, width, height, periodicInput, periodicOutput, symmetry); // iterate 10 times for (int i = 0; i < 10; i++) { // run the algorithm with a random seed and return whether or not it completed int seed = random.Next(); bool finished = model.Run(seed); // if the algorithm completed if (finished) { // get the output image Texture2D texture2D = model.Graphics(); //set the size of the dungeon array dungeon = new int[texture2D.width, texture2D.height]; // iterate through the dungeon while mapping the image to it for (int column = 0; column < dungeon.GetLength(0); column++) { for (int row = 0; row < dungeon.GetLength(1); row++) { // decide on whether the tile is a wall or not based on the greyscale value of the pixel float tempValue = texture2D.GetPixel(column, row).grayscale; if (tempValue < 0.51f) { dungeon[column, row] = 0; } else { dungeon[column, row] = 1; } } } // this block of code is just adding a border of walls around the generated dungeon int borderSize = 5; int[,] borderedDungeon = new int[width + borderSize * 2, height + borderSize * 2]; // iterate through the 2d array. GetLength(0) returns the width of the array for (int column = 0; column < borderedDungeon.GetLength(0); column++) { // GetLength(1) returns the height of the array for (int row = 0; row < borderedDungeon.GetLength(1); row++) { // putting the original array into the bordered one if (column >= borderSize && column < width + borderSize && row >= borderSize && row < height + borderSize) { borderedDungeon[column, row] = dungeon[column - borderSize, row - borderSize]; } else // add the border { borderedDungeon[column, row] = 1; } } } // create a MeshGenerator and generate a mesh based on the 2d array MeshGenerator gen = GetComponent <MeshGenerator>(); gen.GenerateMesh(borderedDungeon, 1); // pass the dungeon to be exported as a csv file FindObjectOfType <GameManager>().ExportDungeonData(borderedDungeon); // prints the output image inside unity Sprite sprite = Sprite.Create(texture2D, new Rect(0, 0, texture2D.width, texture2D.height), Vector2.zero); GameObject gameObject = new GameObject($"{name}"); SpriteRenderer spriteRenderer = gameObject.AddComponent <SpriteRenderer>(); spriteRenderer.sprite = sprite; break; } } }
static void Main() { Stopwatch sw = Stopwatch.StartNew(); System.Random random = new System.Random(42); XDocument xdoc = XDocument.Load("C:\\Users\\theor\\Downloads\\WaveFunctionCollapse-master\\samples.xml"); int counter = 1; var xElements = xdoc.Root.Elements("overlapping", "simpletiled"); var count = xElements.Count(); foreach (XElement xelem in xElements) { Model model; string name = xelem.Get <string>("name"); EditorUtility.DisplayProgressBar("Generating", name, counter / (float)count); Debug.Log($"< {name}"); if (xelem.Name == "overlapping") { model = new OverlappingModel(name, xelem.Get("N", 2), xelem.Get("width", 48), xelem.Get("height", 48), xelem.Get("periodicInput", true), xelem.Get("periodic", false), xelem.Get("symmetry", 8), xelem.Get("ground", 0)); } // else if (xelem.Name == "simpletiled") // model = new SimpleTiledModel(name, xelem.Get<string>("subset"), // xelem.Get("width", 10), xelem.Get("height", 10), xelem.Get("periodic", false), xelem.Get("black", false)); else { continue; } int a = 0; for (int i = 0; i < xelem.Get("screenshots", 2); i++) { for (int k = 0; k < 10; k++) { Console.Write("> "); int seed = random.Next(); bool finished = model.Run(++a, xelem.Get("limit", 0)); if (finished) { Debug.Log("DONE"); var t = model.Graphics(); File.WriteAllBytes($"Assets\\Output\\{counter} {name} {i}.png", t.EncodeToPNG()); // if (model is SimpleTiledModel && xelem.Get("textOutput", false)) // System.IO.File.WriteAllText($"output\\{counter} {name} {i}.txt", (model as SimpleTiledModel).TextOutput()); break; } else { Debug.Log("CONTRADICTION"); } } } counter++; } EditorUtility.ClearProgressBar(); Console.WriteLine($"time = {sw.ElapsedMilliseconds}"); AssetDatabase.Refresh(); }