// how do i create an entity? // large row: // beat finds empty row // we public static GraphicEntity1 New(GridRect rect, Board1 board) { var ge = new GameObject().AddComponent <GraphicEntity1>(); ge.Initialize(rect, board); return(ge); }
/// <summary> /// Gets the average score a brain gets over a number of boards /// </summary> /// <returns></returns> private double AverageScore(Brain brain, int runs) { double minScore = 999999999; double avgTime = 0; double prevScore = 0; double avgTurns = 0; for (int i = 0; i < runs; i++) { NewBoard(i); while (Board1.Progress1Tick()) { RunBrain(Board1, brain); } prevScore += CalculateScore(Board1); minScore = Math.Min(CalculateScore(Board1), minScore); avgTime += Board1.Tick; avgTurns += Board1.Turns; } avgTime /= runs; avgTurns /= runs; Console.WriteLine(minScore); Console.WriteLine(avgTime); Console.WriteLine(avgTurns); return(prevScore / runs); }
/** * <summary>Generates new brains, the size of the brain is determined by height * width</summary> * <param name="hlHeight">determines thd width of the hidden layer</param> * <param name="hlWidth">determines the height of the hidden layers</param> */ private void ModeGenerateNewBrains(int hlWidth, int hlHeight) { NewBoard(); DrawFieldRectangles(); NewBrain(hlWidth, hlHeight); while (savedFilesCount < savedFilesMax) { RedrawField(); bool gameOver = true; for (int i = 0; i < 1000; i++) { if (Board1.Progress1Tick()) { RunBrain(); gameOver = false; } else { gameOver = true; break; } } if (!gameOver) { continue; } Board1.GameOver = true; //gameover double score = CalculateScore(); if (score > ScoreTreshold) { try { string filename = "SnakeBrainFile" + Math.Floor(score).ToString() + "-" + DateTime.Now.Ticks.ToString() + ".dat"; FileStream SnakeBrainFile = new FileStream(filename, FileMode.OpenOrCreate, FileAccess.Write); Formatter.Serialize(SnakeBrainFile, SnakeBrain); SnakeBrainFile.Close(); savedFilesCount++; //MessageBox.Show("Saved snakebrain as " + filename); } catch (Exception err) { MessageBox.Show("Error saving snake brain."); MessageBox.Show(err.Message); } //MessageBox.Show("You crashed into your own tail and died or you ran out of time, your final score was " + string.Format("{0:N2}", score) + "\n\nGrow more quickly and grow larger to gain a larger score"); } NewBoard(); NewBrain(hlWidth, hlHeight); } MessageBox.Show("End of program, " + savedFilesCount.ToString() + " brain files generated.\nReview the executables' folder to see the brain files"); Restart(); }
public void Initialize(GridRect rect, Board1 board) { //Debug.Log($"Creating GraphicEntity: {rect}"); this.board = board; this.rect = rect; board.LockTiles(rect, this); var rectParams = board.GridRectToRectParams(rect); animatable = NoteFactory.CreateRect(rectParams); }
private void DemoAICycle() { RedrawField(); if (Board1.Progress1Tick()) { RunBrain(); } else {//gameOver NewBoard(); } }
private void DemoAICycle() { RedrawField(); if (Board1.Progress1Tick()) { RunBrain(Board1, SnakeBrain); } else {//gameOver Counter++; NewBoard(Counter); } }
IEnumerator SetupAndLaunch() { yield return(null); var gap = 0.309f; //var gap = 0.1f; var sideLength = CameraHelper.Height / ((1 + gap) * rows + gap); cols = (int)(CameraHelper.Width / ((1 + gap) * sideLength)); board = new Board1(cols, rows, sideLength, gap * sideLength); //Debug.Log($"Creating {rows} rows, {cols} cols"); boardRect = new GridRect(0, 0, cols, rows); StartVisualization(); }
/// <summary> /// runs the main brain a few times after mutating it and returns its average score /// </summary> /// <param name="mutateMagnitude">The magnitude by which mutations can happen</param> /// <param name="iterations">The number of times the snake plays the game before returning the average score.</param> /// <param name="mutateNRR">Determines how much mutation magnitude distrubution conforms to a normal distribution.</param> /// <returns>the average score</returns> private double ModeTrainAI(double mutateMagnitude = .1, int mutateNRR = 4, int iterations = 100, int mutationChance = 5) { SnakeBrain.Mutate(mutateMagnitude, mutateNRR, mutationChance); double averageScore = 0; for (int i = 0; i < iterations; i++) { NewBoard(i); while (Board1.Progress1Tick()) { RunBrain(); } averageScore += CalculateScore(); } return(averageScore / iterations); }
void Start() { var gap = 0f; var sideLength = CameraHelper.Height / ((1 + gap) * rows + gap); cols = (int)(CameraHelper.Width / ((1 + gap) * sideLength)); board = new Board1(cols, rows, sideLength, gap * sideLength); boardRect = new GridRect(0, 0, cols, rows); width = cols; height = rows; //CreateTiles(); /*var sideLength = CameraHelper.Height / (1.414f * rows + 0.414f); * cols = (int)(CameraHelper.Width / (1.414f * sideLength)); * board = new Board1(cols, rows, sideLength, 0.414f * sideLength); */ //OSCHandler.Instance.Init(); StartCoroutine(SetupAndLaunch()); }
/// <summary> /// runs the main brain a few times after mutating it and returns its average score /// </summary> /// <param name="mutateMagnitude">The magnitude by which mutations can happen</param> /// <param name="iterations">The number of times the snake plays the game before returning the average score.</param> /// <param name="mutateNRR">Determines how much mutation magnitude distrubution conforms to a normal distribution.</param> /// <param name="randomly">Whether or not to use deterministic brain changes</param> /// <param name="incrementor">if non-random then this must should increment by 1 each call</param> /// <returns>the average score</returns> private double ModeTrainAI(double mutateMagnitude = .1, int mutateNRR = 4, int iterations = 100, int nrOfMutations = 2, bool randomly = false, int incrementor = 0) { if (randomly) { SnakeBrain.Mutate(mutateMagnitude, mutateNRR, nrOfMutations); } double averageScore = 0; for (int i = 0; i < iterations; i++) { NewBoard(i); while (Board1.Progress1Tick()) { RunBrain(Board1, SnakeBrain); } averageScore += CalculateScore(Board1); } return(averageScore / iterations); }
public static bool operator !=(Board Board1, Board Board2) { if (Board1.IsValid() == false || Board2.IsValid() == false) { return(false); } if (Board1.Street != Board2.Street) { return(true); } if (Board1.Mask != Board2.Mask) { return(true); } return(false); }
void Start() { board = FindObjectOfType <Board1>(); findMatches = FindObjectOfType <FindMatches>(); }
IEnumerator SetupAndLaunch() { yield return(null); /* * if (Display.displays.Count() > 1) { * Screen.SetResolution(Screen.width, Screen.height, false); * * //var secondary = Display.displays[1]; * //PlayerPrefs.SetInt("UnitySelectMonitor", 0); * //Screen.SetResolution(secondary.systemWidth, secondary.systemHeight, true); * }// else { * // PlayerPrefs.SetInt("UnitySelectMonitor", 0); * //} */ //Screen.SetResolution(Screen.width, Screen.height, false); /* Store the current screen resolution * int screenWidth = Screen.width; * int screenHeight = Screen.height; * // Setting this PlayerPrefs is what actually changes the monitor to display on * // Set the resolution low for a frame * Screen.SetResolution(800, 600, isFullScreen); * * yield return null; // Wait a frame * // Set the previous resolution * Screen.SetResolution(screenWidth, screenHeight, isFullScreen); * * while (!Screen.fullScreen) { * yield return null; // Wait a frame * } * * if (Display.displays.Count() > 1) { * var second = Display.displays[0]; * Screen.SetResolution(second.systemWidth, second.systemHeight, true); * } * * //Screen.SetResolution(Screen.currentResolution.width, Screen.currentResolution.height, true); * //Screen.SetResolution(1920, 1200, true); * yield return null; // Wait a frame * yield return null; // Wait a frame * yield return null; // Wait a frame * */ var gap = 0.309f; //var gap = 0.1f; var sideLength = CameraHelper.Height / ((1 + gap) * rows + gap); cols = (int)(CameraHelper.Width / ((1 + gap) * sideLength)); board = new Board1(cols, rows, sideLength, gap * sideLength); //Debug.Log($"Creating {rows} rows, {cols} cols"); boardRect = new GridRect(0, 0, cols, rows); blues = new Color[9]; blues[0] = blue.WithAlpha(0); blues[1] = blue.WithAlpha(0.125f); blues[2] = blue.WithAlpha(0.125f * 2); blues[3] = blue.WithAlpha(0.125f * 3); blues[4] = blue.WithAlpha(0.125f * 4); blues[5] = blue.WithAlpha(0.125f * 5); blues[6] = blue.WithAlpha(0.125f * 6); blues[7] = blue.WithAlpha(0.125f * 7); blues[8] = blue; oranges = new Color[9]; oranges[0] = orange.WithAlpha(0); oranges[1] = orange.WithAlpha(0.125f); oranges[2] = orange.WithAlpha(0.125f * 2); oranges[3] = orange.WithAlpha(0.125f * 3); oranges[4] = orange.WithAlpha(0.125f * 4); oranges[5] = orange.WithAlpha(0.125f * 5); oranges[6] = orange.WithAlpha(0.125f * 6); oranges[7] = orange.WithAlpha(0.125f * 7); oranges[8] = orange; //StartCoroutine(Run()); //StartCoroutine(Run2()); //AddRow(); //StartCoroutine(Run()); StartVisualization(); }
private void ModeTrainAIButton_Click(object sender, RoutedEventArgs e) { if (!double.TryParse(ModeTrainAIDegreeBox.Text, out double degree)) { MessageBox.Show("Invalid interval value, please input a double (aka. decimal) value"); return; } if (!int.TryParse(ModeTrainAIIterationsBox.Text, out int iterations)) { MessageBox.Show("Invalid iterations value, please input an integer"); return; } if (!int.TryParse(ModeTrainAIMutationChanceBox.Text, out int mutationChance)) { MessageBox.Show("Invalid mutation chance value, please input an integer"); return; } mutationChance = 100 / mutationChance; if (!int.TryParse(ModeTrainAINRRBox.Text, out int nrr)) { MessageBox.Show("Invalid NRR value, please input an integer"); return; } if (!double.TryParse(ModeTrainAITresholdBox.Text, out double treshold)) { MessageBox.Show("Invalid treshold value, please input a double"); return; } OpenFileDialog dlg = new OpenFileDialog { DefaultExt = ".dat", Filter = "Data Files (*.dat)|*.dat" }; bool?result = dlg.ShowDialog(); if (result != true) { MessageBox.Show("Couldn't recover file path"); return; } if (!File.Exists(dlg.FileName)) { MessageBox.Show("Couldn't find that file"); return; } try { FileStream SnakeBrainInstanceFromFile = new FileStream(dlg.FileName, FileMode.Open, FileAccess.Read); SnakeBrain = (Brain)Formatter.Deserialize(SnakeBrainInstanceFromFile); SnakeBrainInstanceFromFile.Close(); } catch (Exception err) { MessageBox.Show("Could not load selected snake brain file for this demo"); MessageBox.Show(err.Message); return; } int len = MainGrid.Children.Count; for (int i = 0; i < len; i++) { MainGrid.Children.RemoveAt(0); } NewBoard(); DrawFieldRectangles(); Brain prevBrain = DeepCopy(SnakeBrain); double prevScore = 0; for (int i = 0; i < iterations; i++) { NewBoard(); while (Board1.Progress1Tick()) { RunBrain(); } prevScore += CalculateScore(); } prevScore /= iterations; MinScore = prevScore * 0.75; int count = 1000000000; while (--count > 0) { double score = ModeTrainAI(degree, nrr, iterations, mutationChance); if (score / treshold > prevScore && score > MinScore) { if (score * .75 > MinScore) { MinScore = score * .75; try { string filename = "TrainedSnakeBrainFile" + Math.Floor(score).ToString() + "-" + SnakeBrain.HiddenLayerWidth + "-" + SnakeBrain.HiddenLayerHeight + "-" + iterations.ToString() + "-" + DateTime.Now.Ticks.ToString() + ".dat"; FileStream SnakeBrainFile = new FileStream(filename, FileMode.OpenOrCreate, FileAccess.Write); Formatter.Serialize(SnakeBrainFile, SnakeBrain); SnakeBrainFile.Close(); savedFilesCount++; } catch (Exception err) { MessageBox.Show("Error saving snake brain."); MessageBox.Show(err.Message); } } prevScore = score; prevBrain = DeepCopy(SnakeBrain); } else { SnakeBrain = DeepCopy(prevBrain); } if (savedFilesCount > savedFilesMax) { break; } } }
private void RunBrain() { double[] tailDistances = new double[4] { Board1.WidthHeight - 1, Board1.WidthHeight - 1, Board1.WidthHeight - 1, Board1.WidthHeight - 1 }; for (int i = 0; i < Board1.TailLength; i++) { if (Board1.TailY[i] == Board1.SnakeHeadY) { tailDistances[0] = Math.Min(tailDistances[0], Board1.DistanceLeft(Board1.SnakeHeadX, Board1.TailX[i])); tailDistances[2] = Math.Min(tailDistances[2], Board1.DistanceRight(Board1.SnakeHeadX, Board1.TailX[i])); } if (Board1.TailX[i] == Board1.SnakeHeadX) { tailDistances[1] = Math.Min(tailDistances[1], Board1.DistanceUp(Board1.SnakeHeadY, Board1.TailY[i])); tailDistances[3] = Math.Min(tailDistances[3], Board1.DistanceDown(Board1.SnakeHeadY, Board1.TailY[i])); } } int[] foodDistances = new int[4] { Board1.DistanceLeft(Board1.SnakeHeadX, Board1.FoodX), Board1.DistanceUp(Board1.SnakeHeadY, Board1.FoodY), Board1.DistanceRight(Board1.SnakeHeadX, Board1.FoodX), Board1.DistanceDown(Board1.SnakeHeadY, Board1.FoodY) }; int k = (int)Board1.SnakeDirection; int horizontalDistance; int verticalDistance; if (foodDistances[k] > foodDistances[(k + 2) % 4]) { verticalDistance = -foodDistances[(k + 2) % 4]; } else { verticalDistance = foodDistances[k]; } if (foodDistances[(k + 1) % 4] > foodDistances[(k + 3) % 4]) { horizontalDistance = -foodDistances[(k + 3) % 4]; } else { horizontalDistance = foodDistances[(k + 1) % 4]; } double[] perceptronsValues = new double[4] { //a bearing value to the next food piece relative to the current snake heading. //vertical goes into the x argument to make sure that a dead ahead food direction leads to a value of 0 Math.Atan2(horizontalDistance, verticalDistance), //whether or not a tail piece is ahead of, to the left of or to the right of the snake head tailDistances[k], tailDistances[(k + 3) % 4], tailDistances[(k + 1) % 4], }; //calculate what the brain "thinks" that it should do double[] brainThoughts = SnakeBrain.InputToOutput(perceptronsValues); double maxvalue = brainThoughts.Max(); for (int i = 0; i < 3; i++) { if (maxvalue == brainThoughts[i]) { if (i == 1) { Board1.ChangeDirection(Board.Direction.right); } else if (i == 2) { Board1.ChangeDirection(Board.Direction.left); } } } }
void Start() { board = FindObjectOfType <Board1>(); }