You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
// Create an orthogonal maze 30x20Mazemaze=newOrthogonalMaze(30,20);// Generate it using Prim's algorithmMazeGeneratorgenerator=newPrimGeneration(maze);generator.Generate();// Export the maze to SVG fileMazeSvgExporterBuilder.For(maze).AddBackground(SvgColor.White).AddWallsAsSinglePath().Build().ExportToFile("orthogonal-maze.svg");
Maze with a solution
// Create an orthogonal maze 30x20Mazemaze=newOrthogonalMaze(30,20);// Specify entry and exit of the maze.// You can also do it after maze generationMazeEdgeentry=maze.GetOuterWalls().First();// First outer wallMazeEdgeexit=maze.GetOuterWalls().Last();// Last outer wall// Add a pathmaze.Paths.Add(new(maze,entry,exit));// Generate maze using Hunt and Kill algorithmMazeGeneratorgenerator=newHuntAndKillGeneration(maze);generator.Generate();// Create a maze exporterMazeSvgExporterBuilder.For(maze).WithPadding(5f).IncludeMetadata()// This will write a description about the maze in SVG-file..AddBackground(SvgColor.White).AddWallsAsSinglePath().AddSolutions().Build().ExportToFile("orthogonal-maze-with-solution.svg");
Maze with multiple solutions
// Create an orthogonal maze 25x25GridMaze2Dmaze=newOrthogonalMaze(25,25);// For any GridMaze2D you can use [row, column] indexer.// For mazes with custom cells structure or with an inner room// it can return null, but in our case it will never return null.MazeCellnorthCell=maze[0,maze.Columns/2]!;MazeCellsouthCell=maze[maze.Rows-1,maze.Columns/2]!;MazeCellwestCell=maze[maze.Rows/2,0]!;MazeCelleastCell=maze[maze.Rows/2,maze.Columns-1]!;// We have entry/exits cells. Now we need to find outer walls// to specify entries and exits.// We can use 'MazeCell' property 'DirectedNeighbors' for this purpose.MazeEdgenorthWall=new(northCell,northCell.DirectedNeighbors[OrthogonalMaze.North]!);MazeEdgesouthWall=new(southCell,southCell.DirectedNeighbors[OrthogonalMaze.South]!);MazeEdgewestWall=new(westCell,westCell.DirectedNeighbors[OrthogonalMaze.West]!);MazeEdgeeastWall=new(eastCell,eastCell.DirectedNeighbors[OrthogonalMaze.East]!);// When creating maze edges for paths make sure that second cell is always outer.// Add pathsmaze.Paths.Add(new(maze,northWall,westWall));// N-Wmaze.Paths.Add(new(maze,northWall,eastWall));// N-Emaze.Paths.Add(new(maze,southWall,westWall));// S-Wmaze.Paths.Add(new(maze,southWall,eastWall));// S-E// Generate maze using Randomized Depth-first search algorithmMazeGeneratorgenerator=newDFSGeneration(maze);// Additonaly remove some dead ends from the maze using MazeBraidergenerator.PostProcessors.Add(newMazeBraider(0.5f));generator.Generate();// Group for pathsSvgGrouppathsGroup=new(){Fill=SvgFill.None,// This setting is strongly recommendedStrokeWidth=3f,StrokeOpacity=0.6f};// Different colors for solutionsSvgFill[]solutionsFills=[SvgColor.Orange,SvgColor.Magenta,SvgColor.Green,SvgColor.Blue];// Create a maze exporter(it doesn't need to be closed or disposed)MazeSvgExporterBuilder.For(maze).WithPadding(5f).IncludeMetadata().AddBackground(SvgColor.White).AddWallsAsSinglePath().AddSolutions(pathsGroup, i =>newSvgPath(){Stroke=solutionsFills[i]}).Build().ExportToFile("orthogonal-maze-with-multiple-solutions.svg");
Circular (theta) maze
// Create a Theta maze with radius 18, inner radius 3 and 40 cells on each circleMazemaze=newThetaMaze(18,3,40);// Specify entry and exit of the maze.// You can also do it after maze generationMazeEdgeentry=maze.GetOuterWalls().First();// First outer wallMazeEdgeexit=maze.GetOuterWalls().Last();// Last outer wallmaze.Paths.Add(new(maze,entry,exit));// Selection method for a cell.// It's a newest cell with 50% probability, or a random cellstaticintNewestOrRandom(System.Randomrnd,intn)=>rnd.Next(2)==0?n-1:rnd.Next(n);// Generate it using Growing tree algorithmMazeGeneratorgenerator=newGrowingTreeGeneration(maze,NewestOrRandom);generator.Generate();// Specify gradient stopsvarstops=newSvgStop[2]{new(0f,SvgColor.FromHexCode("#ff0000")),new(1f,SvgColor.FromHexCode("#ffa600")),};// Create a radial gradientSvgGradientradialGradient=newSvgRadialGradient(){Id="wallsGradient",// Each gradient should have an IdStops=stops,GradientUnits=SvgGradientUnits.UserSpaceOnUse,Cx=newSvgLength(50f,SvgLengthUnit.Percentage),Cy=newSvgLength(50f,SvgLengthUnit.Percentage),R=newSvgLength(50f,SvgLengthUnit.Percentage),};MazeSvgExporterBuilder.For(maze).WithPadding(2.5f).AddWallsAsSinglePath(newSvgPath(){Stroke=radialGradient,StrokeWidth=5f,Fill=SvgFill.None,StrokeLinecap=SvgLinecap.Round,StrokeLinejoin=SvgLinejoin.Round}).Build().ExportToFile("theta-maze.svg");
Graph representation
// Create a Hexagonal Sigma MazeMazemaze=newSigmaMaze(15);// Generate it using Aldous Broder's algorithmMazeGeneratorgenerator=newAldousBroderGeneration(maze);generator.Generate();// Order matters here, so we should add edges before nodesMazeSvgExporterBuilder.For(maze).AddBackground(SvgColor.White).AddPassagesGraphEdges().AddAllNodes().Build().ExportToFile("sigma-maze-as-graph.svg");
Binary tree representation
// Create an Orthogonal Maze 10x10Mazemaze=newOrthogonalMaze(10,10);// Generate it using Binary tree algorithm.// Note that you can use it only for orthogonal mazes.MazeGeneratorgenerator=newBinaryTreeGeneration(maze);generator.Generate();// Create a maze exporterMazeSvgExporterexporter=MazeSvgExporterBuilder.For(maze).AddBackground(SvgColor.White).AddPassagesGraphEdges().AddAllNodes().Build();floatcX=exporter.Width/2f,cY=exporter.Height/2f;// Define custom SvgRootSvgRootroot=new(){// Rotate the maze to display it as binary tree.// Note that in some applications or browsers this transform// will have no effectTransform=$"translate({cX.ToInvariantString()}, {cY.ToInvariantString()}) rotate(225)"};// Export the mazeexporter.ExportToFile("binary-tree-maze.svg",root);
Stylized graph maze
// You can use here any type of mazeMazemaze=newUpsilonMaze(20,20);MazeGeneratorgenerator=newWilsonGeneration(maze);generator.Generate();// Predicate for a dead end which has at least one outer neighborboolIsEdgeDeadEnd(MazeCellcell){returncell.TryFindNeighbor(c =>c.IsMazePart,out_)&&maze.IsDeadEnd(cell);}// Find dead end at the beginning which will be our entryMazeCellentry=maze.Cells.First(IsEdgeDeadEnd);// Find dead end at the end which will be our exitMazeCellexit=maze.Cells.Last(IsEdgeDeadEnd);// Other dead endsvardeadEnds=fromcinmaze.FindDeadEnds()wherec!=entry&&c!=exitselectc;// Create a path for displaying a solutionMazeEdgeentryEdge=new(entry,entry.DirectedNeighbors.First(c =>c.IsNotNullAndOuter())!);MazeEdgeexitEdge=new(exit,exit.DirectedNeighbors.First(c =>c.IsNotNullAndOuter())!);maze.Paths.Add(new(maze,entryEdge,exitEdge));// NodesSvgPolygonentryTriangle=new(){Id="entry",Points=[new(0f,-7.5f),new(7.5f,7.5f),new(-7.5f,7.5f)],Fill=SvgColor.Green};SvgPolygonexitTriangle=new(){Id="exit",Points=[new(0f,7.5f),new(7.5f,-7.5f),new(-7.5f,-7.5f)],Fill=SvgColor.Red};SvgCircledeadEndCircle=new(){Id="deadEnd",R=4.5f,Fill=SvgColor.Blue,};// EdgesSvgPathedgesPath=new(){Fill=SvgFill.None,StrokeWidth=5f,StrokeLinecap=SvgLinecap.Round,StrokeLinejoin=SvgLinejoin.Round};// SolutionSvgGroupsolutionsGroup=new(){Fill=SvgFill.None,Stroke=SvgColor.Orange,StrokeWidth=edgesPath.StrokeWidth,StrokeDasharray=[10f]};// Custom styleSvgRootroot=new(){Style="stroke: black; stroke-width: 2.5"};MazeSvgExporterBuilder.For(maze).IncludeMetadata().AddBackground(SvgColor.White).AddPassagesGraphEdges(edgesPath,false).AddSolutions(solutionsGroup,intersectOuterCells:false).AddNode(entry,entryTriangle).AddNode(exit,exitTriangle).AddNodes(deadEnds,deadEndCircle).Build().ExportToFile("lines-maze.svg",root);
Rainbow triangular maze
// Triangular maze with inner triangular roomGridMaze2Dmaze=newDeltaMaze(30,10);// Add entry and exit using cells coordinates.// Note that coordinates here are [row, column] and not [x, y]MazeEdgeentry=new(maze[11,27]!,maze[11,27]!.DirectedNeighbors[DeltaMaze.East]!);MazeEdgeexit=new(maze[29,30]!,maze[29,30]!.DirectedNeighbors[DeltaMaze.South]!);maze.Paths.Add(new(maze,entry,exit));// Use Kruskal's algorithm for generationMazeGeneratorgenerator=newKruskalGeneration(maze);generator.Generate();// Specify radient stopsvarstops=newSvgStop[7]{new(0f/6f,SvgColor.FromHexCode("#e81416")),// Rednew(1f/6f,SvgColor.FromHexCode("#ffa500")),// Orangenew(2f/6f,SvgColor.FromHexCode("#faeb36")),// Yellownew(3f/6f,SvgColor.FromHexCode("#79c314")),// Greennew(4f/6f,SvgColor.FromHexCode("#487de7")),// Bluenew(5f/6f,SvgColor.FromHexCode("#4b369d")),// Indigonew(6f/6f,SvgColor.FromHexCode("#70369d"))// Violet};// Create a linear gradientSvgGradientrainbowGradient=newSvgLinearGradient(){Id="rainbowGradient",// Each gradient should have an IdStops=stops,GradientUnits=SvgGradientUnits.UserSpaceOnUse,X1=newSvgLength(0f,SvgLengthUnit.Percentage),Y1=newSvgLength(0f,SvgLengthUnit.Percentage),X2=newSvgLength(100f,SvgLengthUnit.Percentage),Y2=newSvgLength(0f,SvgLengthUnit.Percentage)};MazeSvgExporterBuilder.For(maze).WithPadding(5f).AddBackground(SvgColor.Black).AddWallsAsSinglePath(new(){Fill=SvgFill.None,Stroke=rainbowGradient,},wallsWidth:2f).Build().ExportToFile("triangular-rainbow-maze.svg");
Generation animation
// Create an orthogonal maze 10x10Mazemaze=newOrthogonalMaze(10,10);// Create a generatorMazeGeneratorgenerator=newDFSGeneration(maze);// Create a maze exportervarexporter=MazeSvgExporterBuilder.For(maze).AddBackground(SvgColor.White).AddUnvisitedCells(generator,newSvgGroup(){Fill=SvgColor.Black,Stroke=SvgColor.Black}).AddHighlightedCells(generator,newSvgGroup(){Fill=SvgColor.Gray,Stroke=SvgColor.Gray}).AddSelectedCell(generator,newSvgGroup(){Fill=SvgColor.Red,Stroke=SvgColor.Red}).AddWallsAsSinglePath().Build();inti=0;foreach(Mazeframeingenerator.GenerateStepByStep()){// Export the maze generation framestringpath=$"{i++:000}.svg";awaitexporter.ExportToFileAsync(path);}
Generation animation (Origin Shift)
// Create an orthogonal maze 5x5Mazemaze=newOrthogonalMaze(5,5);// Parameters that simulate author's original approachOriginShiftParams@params=new(){GenerateUntilAllCellsAreVisited=false,MaxIterations=250,NeighborSelector=newUnweightedNeighborSelector()};// Create a generatorOriginShiftGenerationoriginShiftGenerator=new(maze,@params);// Marker for directed edges arrowSvgMarkerarrowMarker=new(){Id="directedEdgeArrow",// ID is mandatory for SvgMarker to workOrient=SvgMarkerOrient.Auto,MarkerWidth=3f,MarkerHeight=4f,RefX=4.5f,RefY=1.5f,Shape=newSvgPath(){D="M0,0 V3 L2.5,1.5 Z",Fill=SvgColor.Black,Stroke=SvgFill.None}};// Group for edgesSvgGroupedgesGroup=new(){Fill=SvgFill.None,Stroke=SvgColor.Black,StrokeWidth=2f};// Path used for each edgeSvgPathedgePath=new(){MarkerEnd=arrowMarker};// Group for nodesSvgGroupnodesGroup=new(){Id="nodes"};// Circle for nodesSvgCirclenodeCircle=new(){Id="node",Fill=SvgColor.White,Stroke=SvgColor.Black,StrokeWidth=2f,R=5f};// Circle for an "origin"SvgCircleoriginCircle=new(){Id="origin",Fill=SvgColor.Red,Stroke=SvgColor.Black,StrokeWidth=2f,R=5f};varexporter=MazeSvgExporterBuilder.For(maze).AddBackground(SvgColor.White).AddDirectedEdges(originShiftGenerator.DirectedMaze.DirectedEdges,edgesGroup,edgePath).AddAllNodes(nodeCircle,nodesGroup).AddSelectedNode(originShiftGenerator,originCircle).Build();inti=0;foreach(MazeframeinoriginShiftGenerator.GenerateStepByStep()){// Export the maze generation framestringpath=$"{i++:000}.svg";awaitexporter.ExportToFileAsync(path);}