public void DrawField2(Tetromino tetromino) { for (int x = 0; x < _playingField.GetLength(0); x++) { for (int y = 0; y < _playingField.GetLength(1); y++) { Console.SetCursorPosition(x + 2, y + 2); Console.ForegroundColor = _colorsForeground[_playingField[x, y]]; Console.Write(_sprites[_playingField[x, y]]); for (var tx = 0; tx < 4; tx++) { for (var ty = 0; ty < 4; ty++) { if (tetromino.X + tx == x && tetromino.Y + ty == y && tetromino.Shape[tetromino.Rotate(tx, ty, tetromino.Rotation)] != '.') { Console.SetCursorPosition(x + 2, y + 2); Console.ForegroundColor = tetromino.Color; Console.Write(_sprites[tetromino.Sprite]); } } } } } }
public void ResetField(Tetromino tetromino) { for (int px = 0; px < 4; px++) { for (int py = 0; py < 4; py++) { if (tetromino.Shape[tetromino.Rotate(px, py, tetromino.Rotation)] != '.') { _map[(tetromino.X + px), (tetromino.Y + py)] = 'B'; _mapColor[(tetromino.X + px), (tetromino.Y + py)] = ConsoleColor.Gray; } } } }
public async void UpdateFieldAsync(Tetromino tetromino) { for (int px = 0; px < 4; px++) { for (int py = 0; py < 4; py++) { if (tetromino.Shape[tetromino.Rotate(px, py, tetromino.Rotation)] != '.') { _playingField[(tetromino.X + px), (tetromino.Y + py)] = tetromino.Sprite; _mapColor[(tetromino.X + px), (tetromino.Y + py)] = tetromino.Color; } } } }
protected Tetromino RotateTetromino(Tetromino t) { Tetromino rotated = t.Rotate(); EraseTetromino(t); //旋转后可能与其他块有重叠,故略微挪动以找到空位 foreach (Direction direction in Enum.GetValues(typeof(Direction))) { if (IsEmpty(rotated.Move(direction))) { DrawTetromino(rotated, false); return(rotated); } } DrawTetromino(t, false); return(Tetromino.Zero); }
protected override void Update(GameTime gameTime) { // Exit check if (GamePad.GetState(PlayerIndex.One).Buttons.Back == ButtonState.Pressed || Keyboard.GetState().IsKeyDown(Keys.Escape)) { Exit(); } if (GameOver || GameWon) { playerShouldRemove = true; if (Keyboard.GetState().IsKeyDown(Keys.Enter)) { playerShouldRemove = false; player.position.X = 100; player.position.Y = 700; player.velocity = Vector2.Zero; // Restart the game Score = 0; Lines = 0; // Reset the queue of next tetromino nextTetrominos = new Queue <char>(); nextTetrominos.Enqueue(GetRandomCharacter(CHARLIST, new Random())); // Reset the board gameBoard.Reset(); GameOver = false; GameWon = false; } return; } // Tetromino generation if (currentTetromino == null || !currentTetromino.IsFalling) { currentTetromino = GenerateNewTetromino(nextTetrominos.Dequeue()); nextTetrominos.Enqueue(GetRandomCharacter(CHARLIST, randomGenerator)); // Reset the nextBlockBoards nextBlockBoards.Reset(); // add a tetromino in the board new Tetromino(nextBlockBoards, 2, 1, nextTetrominos.ElementAt(0), BlockTextures[nextTetrominos.ElementAt(0)]); } // Apply gravity if (gameTime.TotalGameTime.TotalMilliseconds - lastGravityEffectTime > 1000 / Speed) { currentTetromino?.MoveTo(currentTetromino.X, currentTetromino.Y - 1); lastGravityEffectTime = gameTime.TotalGameTime.TotalMilliseconds; } // Check for last action / update bool actionIsAllowed = false; if (gameTime.TotalGameTime.TotalMilliseconds - lastActionTime > ActionDelay) { actionIsAllowed = true; } if (actionIsAllowed) { // ----------------------------------------- // Movement // ----------------------------------------- if (Keyboard.GetState().IsKeyDown(Keys.Left)) { currentTetromino?.MoveTo(currentTetromino.X - 1, currentTetromino.Y); lastActionTime = gameTime.TotalGameTime.TotalMilliseconds; } if (Keyboard.GetState().IsKeyDown(Keys.Right)) { currentTetromino?.MoveTo(currentTetromino.X + 1, currentTetromino.Y); lastActionTime = gameTime.TotalGameTime.TotalMilliseconds; } if (Keyboard.GetState().IsKeyDown(Keys.Down)) { currentTetromino?.MoveTo(currentTetromino.X, currentTetromino.Y - 1); lastActionTime = gameTime.TotalGameTime.TotalMilliseconds; } // ----------------------------------------- // Rotation // ----------------------------------------- if (Keyboard.GetState().IsKeyDown(Keys.Up)) { currentTetromino?.Rotate(1); // clock wise rotation lastActionTime = gameTime.TotalGameTime.TotalMilliseconds; } } currentTetromino?.Update(gameTime); // Row check if (currentTetromino != null && !currentTetromino.IsFalling) { // If the tetromino is outside if (currentTetromino.Y >= 22) { GameOver = true; } // Get the row to remove int rowCleared = gameBoard.ClearRow(); if (rowCleared > 0) { // Increase Score Score += (Level + 1) * 100 * (int)Math.Pow(2, rowCleared); // Update Lines Lines += rowCleared; } } // player movement if (Keyboard.GetState().IsKeyDown(Keys.D)) { temptVelocity.X = speed; nextPosition = new Vector2(player.position.X + temptVelocity.X, player.position.Y); if (player.IsColliding(nextPosition, gameBoard) == false && player.position.X < 538) { player.velocity.X = temptVelocity.X; } else if (player.IsColliding(nextPosition, gameBoard) == true) { player.position.X = 250 + gameBoard.Blocks[player.collideBlock].X * 32 - 32; player.velocity.X = 0; } } else if (Keyboard.GetState().IsKeyDown(Keys.A)) { temptVelocity.X = -speed; nextPosition = new Vector2(player.position.X + temptVelocity.X, player.position.Y); // Console.WriteLine(player.IsColliding(nextPosition, gameBoard)); if (player.IsColliding(nextPosition, gameBoard) == false && player.position.X > 250) { player.velocity.X = temptVelocity.X; } else if (player.IsColliding(nextPosition, gameBoard) == true) { player.position.X = 250 + gameBoard.Blocks[player.collideBlock].X * 32 + 32; player.velocity.X = 0; } } else { player.velocity.X = 0; } player.position.X += player.velocity.X; if (Keyboard.GetState().IsKeyDown(Keys.W)) { nextPosition = new Vector2(player.position.X, player.position.Y - jumpStrength); if (player.IsColliding(nextPosition, gameBoard) == false && hasJumped == false) { player.position.Y -= jumpStrength; player.velocity.Y = -5f; hasJumped = true; } else if (player.IsColliding(nextPosition, gameBoard) == true) { player.position.Y = 200 + (24 - gameBoard.Blocks[player.collideBlock].Y) * 32; player.velocity.Y = 0; if (belongToCurrent(gameBoard.Blocks[player.collideBlock]) && currentTetromino.IsFalling == true) { GameOver = true; } } } temptVelocity.Y = player.velocity.Y + gravity; nextPosition = new Vector2(player.position.X, player.position.Y + temptVelocity.Y); // Console.WriteLine(nextPosition); if (player.IsColliding(nextPosition, gameBoard) == false) { player.velocity.Y = temptVelocity.Y; } else if (player.IsColliding(nextPosition, gameBoard) == true && player.velocity.Y < 0) { player.position.Y = 200 + (24 - gameBoard.Blocks[player.collideBlock].Y) * 32; player.velocity.Y = 0; if (belongToCurrent(gameBoard.Blocks[player.collideBlock]) && currentTetromino.IsFalling == true) { GameOver = true; } } else if (player.IsColliding(nextPosition, gameBoard) == true && player.velocity.Y > 0) { hasJumped = false; player.position.Y = 200 + (24 - gameBoard.Blocks[player.collideBlock].Y) * 32 - 64; player.velocity.Y = 0; } player.position.Y += player.velocity.Y; if (Math.Ceiling(player.position.Y + player.texture.Height + player.velocity.Y) >= 968) { hasJumped = false; player.position.Y = 936; } if (player.TopColliding(player.position.X, player.position.Y, gameBoard) == true) { if (belongToCurrent(gameBoard.Blocks[player.collideIndex]) && currentTetromino.IsFalling == true) { GameOver = true; } } else if (player.position.X > 570 && player.position.X < 666 && player.position.Y > 690 && player.position.Y < 790) { GameWon = true; player.position.Y = 760; hasJumped = false; } base.Update(gameTime); }
public static void Rotate(Tetromino tetromino, Brush[,] fieldMatrix, MoveContext context) { RemoveTetrominoFromFieldMatrix(tetromino, fieldMatrix); tetromino.Rotate(context); UpdateField(tetromino, fieldMatrix); }
static void RotateTetromino() { ClearTetromino(); _currentTetromino.Rotate(); DrawTetromino(); }
protected override void Update(GameTime gameTime) { MouseState mouseState = Mouse.GetState(); KeyboardState keyboardState = Keyboard.GetState(); if (ButtonIntersects(ref mouseState, buttonStart) || ButtonIntersects(ref mouseState, buttonExit) || ButtonIntersects(ref mouseState, buttonResume) || ButtonIntersects(ref mouseState, buttonRestart)) { buttonOutline.Enable(spriteBatch); } else { buttonOutline.Disable(spriteBatch); } if (buttonStart.BoundingBox.Contains(mouseState.Position)) { buttonOutline.Position.Y = 360 * 3 / 2; } if (buttonExit.BoundingBox.Contains(mouseState.Position)) { buttonOutline.Position.Y = 440 * 3 / 2; } if (buttonResume.BoundingBox.Contains(mouseState.Position)) { buttonOutline.Position.Y = 360 * 3 / 2; } if (buttonRestart.BoundingBox.Contains(mouseState.Position)) { buttonOutline.Position.Y = 520 * 3 / 2; } switch (GameState) { case STATE_MENU: buttonResume.Disable(spriteBatch); buttonRestart.Disable(spriteBatch); if (Clicked(ref mouseState, buttonStart)) { GameState = STATE_PLAYING; startTime = gameTime.TotalGameTime.TotalSeconds; } if (Clicked(ref mouseState, buttonExit)) { Exit(); } break; case STATE_PLAYING: buttonStart.Disable(spriteBatch); buttonExit.Disable(spriteBatch); buttonResume.Disable(spriteBatch); buttonRestart.Disable(spriteBatch); if (keyboardState.IsKeyDown(Keys.P)) { GameState = STATE_PAUSED; endTime = gameTime.TotalGameTime.TotalSeconds; timeInterval = endTime - startTime; totalTime += timeInterval; } break; case STATE_PAUSED: buttonResume.Enable(spriteBatch); buttonExit.Enable(spriteBatch); buttonRestart.Enable(spriteBatch); if (Clicked(ref mouseState, buttonRestart)) { GameState = STATE_PLAYING; Restart = true; totalTime = 0; startTime = gameTime.TotalGameTime.TotalSeconds; timeCount = false; } if (Clicked(ref mouseState, buttonResume)) { GameState = STATE_PLAYING; startTime = gameTime.TotalGameTime.TotalSeconds; } if (Clicked(ref mouseState, buttonExit)) { Exit(); } break; case STATE_GAMEOVER: buttonRestart.Enable(spriteBatch); buttonExit.Enable(spriteBatch); if (timeCount == false) { endTime = gameTime.TotalGameTime.TotalSeconds; timeInterval = endTime - startTime; totalTime += timeInterval; timeCount = true; } if (Clicked(ref mouseState, buttonRestart)) { GameState = STATE_PLAYING; Restart = true; totalTime = 0; startTime = gameTime.TotalGameTime.TotalSeconds; timeCount = false; } if (Clicked(ref mouseState, buttonExit)) { Exit(); } break; case STATE_GAMEWON: buttonRestart.Enable(spriteBatch); buttonExit.Enable(spriteBatch); { endTime = gameTime.TotalGameTime.TotalSeconds; timeInterval = endTime - startTime; totalTime += timeInterval; timeCount = true; } if (Clicked(ref mouseState, buttonRestart)) { GameState = STATE_PLAYING; Restart = true; totalTime = 0; startTime = gameTime.TotalGameTime.TotalSeconds; timeCount = false; } if (Clicked(ref mouseState, buttonExit)) { Exit(); } break; default: break; } if (GameState == STATE_PLAYING) { if (Restart == true) { player.position = position1; player.velocity = Vector2.Zero; endHeight = 500; Lines = 0; gameBoard.Reset(); currentTetromino?.MoveTo(currentTetromino.Xghost, currentTetromino.Yghost); nextBlockBoards[0].Reset(); nextBlockBoards[1].Reset(); nextTetrominos = new Queue <char>(); for (int k = 0; k < 2; k++) { nextTetrominos.Enqueue(GetRandomCharacter(CHARLIST, new Random())); } hasJumped = false; outOfStart = false; Restart = false; lastActionTime = 0; lastGravityEffectTime = 0; lastSkipTime = 0; skip = 0; dieTime = 0; winTime = 0; player.sprite.PlayAnimation(idleAnimation); } // Tetromino generation if ((currentTetromino == null || !currentTetromino.IsFalling) && outOfStart == true) { currentTetromino = GenerateNewTetromino(nextTetrominos.Dequeue()); nextTetrominos.Enqueue(GetRandomCharacter(CHARLIST, randomGenerator)); // Reset the nextBlockBoards for (int k = 0; k < 2; k++) { nextBlockBoards[k].Reset(); // add a tetromino in the board new Tetromino(nextBlockBoards[k], 2, 1, nextTetrominos.ElementAt(k), BlockTextures[nextTetrominos.ElementAt(k)]); } } // Apply gravity if (gameTime.TotalGameTime.TotalMilliseconds - lastGravityEffectTime > 1000 / FallSpeed) { currentTetromino?.MoveTo(currentTetromino.X, currentTetromino.Y - 1); lastGravityEffectTime = gameTime.TotalGameTime.TotalMilliseconds; } // Check for last action / update bool actionIsAllowed = false; if (gameTime.TotalGameTime.TotalMilliseconds - lastActionTime > ActionDelay) { actionIsAllowed = true; } if (actionIsAllowed) { // ----------------------------------------- // Movement // ----------------------------------------- if (Keyboard.GetState().IsKeyDown(Keys.Left)) { currentTetromino?.MoveTo(currentTetromino.X - 1, currentTetromino.Y); lastActionTime = gameTime.TotalGameTime.TotalMilliseconds; } if (Keyboard.GetState().IsKeyDown(Keys.Right)) { currentTetromino?.MoveTo(currentTetromino.X + 1, currentTetromino.Y); lastActionTime = gameTime.TotalGameTime.TotalMilliseconds; } if (Keyboard.GetState().IsKeyDown(Keys.Down)) { currentTetromino?.MoveTo(currentTetromino.X, currentTetromino.Y - 1); lastActionTime = gameTime.TotalGameTime.TotalMilliseconds; } // ----------------------------------------- // Rotation // ----------------------------------------- if (Keyboard.GetState().IsKeyDown(Keys.Up)) { currentTetromino?.Rotate(1); // clock wise rotation lastActionTime = gameTime.TotalGameTime.TotalMilliseconds; } } currentTetromino?.Update(gameTime); // Row check if (currentTetromino != null && !currentTetromino.IsFalling) { // If the tetromino is outside if (currentTetromino.Y >= 18) { GameState = STATE_GAMEOVER; } // Get the row to remove int rowCleared = gameBoard.ClearRow(); if (rowCleared > 0) { // Update Lines Lines += rowCleared; // decrease end goal endHeight += 64 * 3 / 2 * rowCleared; skip--; if (skip <= 0) { skip = 0; } if (endHeight >= (640 - 160) * 3 / 2) { endHeight = (640 - 160) * 3 / 2; } } } if (Keyboard.GetState().IsKeyDown(Keys.Space)) { if (gameTime.TotalGameTime.TotalMilliseconds - lastSkipTime > ActionDelay && skip < 3) { nextTetrominos.Dequeue(); nextTetrominos.Enqueue(GetRandomCharacter(CHARLIST, randomGenerator)); for (int k = 0; k < 2; k++) { nextBlockBoards[k].Reset(); // add a tetromino in the board new Tetromino(nextBlockBoards[k], 2, 1, nextTetrominos.ElementAt(k), BlockTextures[nextTetrominos.ElementAt(k)]); } skip++; lastSkipTime = gameTime.TotalGameTime.TotalMilliseconds; } } // player movement if (Keyboard.GetState().IsKeyDown(Keys.D) && player.sprite.Animation != dieAnimation) { temptVelocity.X = speed; nextPosition = new Vector2(player.position.X + temptVelocity.X, player.position.Y); if (player.IsColliding(nextPosition, gameBoard) == false) { player.velocity.X = temptVelocity.X; } else if (player.IsColliding(nextPosition, gameBoard) == true) { player.position.X = (320 + gameBoard.Blocks[player.collideBlock].X * 32 - 32) * 3 / 2; player.velocity.X = 0; } player.sprite.PlayAnimation(runAnimation); } else if (Keyboard.GetState().IsKeyDown(Keys.A) && player.sprite.Animation != dieAnimation) { temptVelocity.X = -speed; nextPosition = new Vector2(player.position.X + temptVelocity.X, player.position.Y); // Console.WriteLine(player.IsColliding(nextPosition, gameBoard)); if (player.IsColliding(nextPosition, gameBoard) == false) { player.velocity.X = temptVelocity.X; } else if (player.IsColliding(nextPosition, gameBoard) == true) { player.position.X = (320 + gameBoard.Blocks[player.collideBlock].X * 32 + 32) * 3 / 2; player.velocity.X = 0; } player.sprite.PlayAnimation(runAnimation); } else if (player.sprite.Animation != dieAnimation) { player.velocity.X = 0; player.sprite.PlayAnimation(idleAnimation); } player.position.X += player.velocity.X; if (player.position.X >= 320 * 3 / 2) { outOfStart = true; } if (Keyboard.GetState().IsKeyDown(Keys.W) && player.sprite.Animation != dieAnimation) { nextPosition = new Vector2(player.position.X, player.position.Y - jumpStrength); // Console.WriteLine("{0},{1},{2}",player.IsColliding(nextPosition, gameBoard), hasJumped, nextPosition); if (player.IsColliding(nextPosition, gameBoard) == false && hasJumped == false) { if (nextPosition.Y <= 0) { player.position.Y = 0; player.velocity.Y = -8f; hasJumped = true; } else { player.position.Y -= jumpStrength; player.velocity.Y = -8f; hasJumped = true; } player.sprite.PlayAnimation(jumpAnimation); } else if (player.IsColliding(nextPosition, gameBoard) == true && hasJumped == false) { player.position.Y = (20 - gameBoard.Blocks[player.collideBlock].Y) * 32 * 3 / 2; player.sprite.PlayAnimation(jumpAnimation); player.velocity.Y = 0; hasJumped = true; if (belongToCurrent(gameBoard.Blocks[player.collideBlock]) && currentTetromino.IsFalling == true) { player.sprite.PlayAnimation(dieAnimation); dieTime = gameTime.TotalGameTime.TotalMilliseconds; } } } temptVelocity.Y = player.velocity.Y + gravity; nextPosition = new Vector2(player.position.X, player.position.Y + temptVelocity.Y); // Console.WriteLine(nextPosition); if (player.IsColliding(nextPosition, gameBoard) == false) { player.velocity.Y = temptVelocity.Y; } else if (player.IsColliding(nextPosition, gameBoard) == true && player.velocity.Y < 0) { player.position.Y = (20 - gameBoard.Blocks[player.collideBlock].Y) * 32 * 3 / 2; player.velocity.Y = 0; } else if (player.IsColliding(nextPosition, gameBoard) == true && player.velocity.Y > 0) { hasJumped = false; player.position.Y = (20 - gameBoard.Blocks[player.collideBlock].Y - 2) * 32 * 3 / 2; player.velocity.Y = 0; player.sprite.PlayAnimation(idleAnimation); } player.position.Y += player.velocity.Y; if (player.position.Y + 32 * 3 / 2 <= endHeight) { if (player.position.X >= (1120 - 320 - 32) * 3 / 2) { player.position.X = (1120 - 320 - 32) * 3 / 2; player.velocity.X = 0; } else if (player.position.X <= 320 * 3 / 2) { player.position.X = 320 * 3 / 2; player.velocity.X = 0; } } if (endHeight + 160 * 3 / 2 <= (640 - 160) * 3 / 2) { if (player.position.Y >= endHeight + 160 * 3 / 2 && player.position.Y + 32 * 3 / 2 <= (640 - 160) * 3 / 2) { if (player.position.X >= (1120 - 320 - 32) * 3 / 2) { player.position.X = (1120 - 320 - 32) * 3 / 2; player.velocity.X = 0; } else if (player.position.X <= 320 * 3 / 2) { player.position.X = 320 * 3 / 2; player.velocity.X = 0; } } else if (player.position.Y >= (640 - 160) * 3 / 2) { if (player.position.X >= (1120 - 320 - 32) * 3 / 2) { player.position.X = (1120 - 320 - 32) * 3 / 2; player.velocity.X = 0; } else if (player.position.X <= 160 * 3 / 2 && outOfStart == false) { player.position.X = 160 * 3 / 2; player.velocity.X = 0; } else if (player.position.X <= 320 * 3 / 2 && outOfStart == true) { player.position.X = 320 * 3 / 2; player.velocity.X = 0; } } } else if (endHeight + 160 * 3 / 2 > (640 - 160) * 3 / 2) { if (player.position.Y + 32 * 3 / 2 <= (640 - 160) * 3 / 2 && player.position.Y >= endHeight) { if (player.position.X >= (1120 - 160 - 32) * 3 / 2) { player.position.X = (1120 - 160 - 32) * 3 / 2; player.velocity.X = 0; } else if (player.position.X <= 320 * 3 / 2) { player.position.X = 320 * 3 / 2; player.velocity.X = 0; } } else if (player.position.Y + 32 * 3 / 2 < (640 - 160) * 3 / 2 && player.position.Y >= endHeight + 160 * 3 / 2) { if (player.position.X >= (1120 - 160 - 32) * 3 / 2) { player.position.X = (1120 - 160 - 32) * 3 / 2; player.velocity.X = 0; } else if (player.position.X <= 160 * 3 / 2 && outOfStart == false) { player.position.X = 160 * 3 / 2; player.velocity.X = 0; } else if (player.position.X <= 320 * 3 / 2 && outOfStart == true) { player.position.X = 320 * 3 / 2; player.velocity.X = 0; } } else if (player.position.Y >= endHeight + 160 * 3 / 2) { if (player.position.X >= (1120 - 320 - 32) * 3 / 2) { player.position.X = (1120 - 320 - 32) * 3 / 2; player.velocity.X = 0; } else if (player.position.X <= 160 * 3 / 2 && outOfStart == false) { player.position.X = 160 * 3 / 2; player.velocity.X = 0; } else if (player.position.X <= 320 * 3 / 2 && outOfStart == true) { player.position.X = 320 * 3 / 2; player.velocity.X = 0; } } } if (player.position.Y + player.velocity.Y >= (640 - 32) * 3 / 2) { hasJumped = false; player.position.Y = (640 - 32) * 3 / 2; player.velocity.Y = 0; } if (player.TopColliding(player.position.X, player.position.Y, gameBoard) == true) { if (belongToCurrent(gameBoard.Blocks[player.collideIndex]) && currentTetromino.IsFalling == true) { player.sprite.PlayAnimation(dieAnimation); dieTime = gameTime.TotalGameTime.TotalMilliseconds; } } if (player.position.X > (320 + 480) * 3 / 2 && player.position.X < (320 + 480 + 160) * 3 / 2 && player.position.Y > endHeight && player.position.Y < endHeight + (160 - 32) * 3 / 2) { GameState = STATE_GAMEWON; } if (player.sprite.Animation == dieAnimation && gameTime.TotalGameTime.TotalMilliseconds - dieTime > 300) { GameState = STATE_GAMEOVER; } } if (GameState == STATE_PAUSED) { player.velocity = Vector2.Zero; } Console.WriteLine(player.sprite.Animation); Console.WriteLine(dieTime); Console.WriteLine(gameTime.TotalGameTime.TotalMilliseconds); base.Update(gameTime); }
protected override void Update(GameTime gameTime) { player.Update(gameTime); // Exit check if (GamePad.GetState(PlayerIndex.One).Buttons.Back == ButtonState.Pressed || Keyboard.GetState().IsKeyDown(Keys.Escape)) { Exit(); } if (GameOver) { if (Keyboard.GetState().IsKeyDown(Keys.Enter)) { // Restart the game Score = 0; Lines = 0; // Reset the queue of next tetromino nextTetrominos = new Queue <char>(); nextTetrominos.Enqueue(GetRandomCharacter(CHARLIST, new Random())); // Reset the board gameBoard.Reset(); GameOver = false; } return; } // Tetromino generation if (currentTetromino == null || !currentTetromino.IsFalling) { currentTetromino = GenerateNewTetromino(nextTetrominos.Dequeue()); nextTetrominos.Enqueue(GetRandomCharacter(CHARLIST, randomGenerator)); // Reset the nextBlockBoards nextBlockBoards.Reset(); // add a tetromino in the board new Tetromino(nextBlockBoards, 2, 1, nextTetrominos.ElementAt(0), BlockTextures[nextTetrominos.ElementAt(0)]); } // Apply gravity if (gameTime.TotalGameTime.TotalMilliseconds - lastGravityEffectTime > 1000 / Speed) { currentTetromino?.MoveTo(currentTetromino.X, currentTetromino.Y - 1); lastGravityEffectTime = gameTime.TotalGameTime.TotalMilliseconds; } // Check for last action / update bool actionIsAllowed = false; if (gameTime.TotalGameTime.TotalMilliseconds - lastActionTime > ActionDelay) { actionIsAllowed = true; } if (actionIsAllowed) { // ----------------------------------------- // Movement // ----------------------------------------- if (Keyboard.GetState().IsKeyDown(Keys.Left)) { currentTetromino?.MoveTo(currentTetromino.X - 1, currentTetromino.Y); lastActionTime = gameTime.TotalGameTime.TotalMilliseconds; } if (Keyboard.GetState().IsKeyDown(Keys.Right)) { currentTetromino?.MoveTo(currentTetromino.X + 1, currentTetromino.Y); lastActionTime = gameTime.TotalGameTime.TotalMilliseconds; } if (Keyboard.GetState().IsKeyDown(Keys.Down)) { currentTetromino?.MoveTo(currentTetromino.X, currentTetromino.Y - 1); lastActionTime = gameTime.TotalGameTime.TotalMilliseconds; } // ----------------------------------------- // Rotation // ----------------------------------------- if (Keyboard.GetState().IsKeyDown(Keys.Up)) { currentTetromino?.Rotate(1); lastActionTime = gameTime.TotalGameTime.TotalMilliseconds; } // ----------------------------------------- // Teleportation to ghost position // ----------------------------------------- if (Keyboard.GetState().IsKeyDown(Keys.Space)) // clock wise rotation { currentTetromino?.MoveTo(currentTetromino.Xghost, currentTetromino.Yghost); if (currentTetromino != null) { currentTetromino.IsFalling = false; } lastActionTime = gameTime.TotalGameTime.TotalMilliseconds; } } // currentTetromino?.Update(gameTime); // Row check if (currentTetromino != null && !currentTetromino.IsFalling) { // If the tetromino is outside if (currentTetromino.Y >= 20) { GameOver = true; } // Get the row to remove int rowCleared = gameBoard.ClearRow(); if (rowCleared > 0) { // Increase Score Score += (Level + 1) * 100 * (int)Math.Pow(2, rowCleared); // Update Lines Lines += rowCleared; } } base.Update(gameTime); }
void Rotate() { Cell[] fallingCells = GetFallingCells(); current.Rotate(fallingCells, matrix); }
private void GameLoop() { Field field = new Field(); Tetromino tetromino = new Tetromino(); field.UpdateField(tetromino); //tetromino.UpdatePositionInField(field); bool forceDown = true; var speedCount = 0; int speed = 20; int pieceCount = 0; List <int> lines = new List <int>(); while (!_isGameOver) { Thread.Sleep(50); speedCount++; forceDown = (speedCount == speed); bool[] keys = new bool[4]; for (int i = 0; i < 4; i++) // R L D Z { keys[i] = (0x8000 & GetAsyncKeyState((char)("\x27\x25\x28Z"[i]))) != 0; } tetromino.X += (keys[0] && tetromino.WillFitAtDestination(tetromino.X + _speed, tetromino.Y, tetromino.Rotation, field)) ? _speed : 0; tetromino.X -= (keys[1] && tetromino.WillFitAtDestination(tetromino.X - _speed, tetromino.Y, tetromino.Rotation, field)) ? _speed : 0; tetromino.Y += (keys[2] && tetromino.WillFitAtDestination(tetromino.X, tetromino.Y + _speed, tetromino.Rotation, field)) ? _speed : 0; if (keys[3]) { tetromino.Rotation += (_rotateHold && tetromino.WillFitAtDestination(tetromino.X, tetromino.Y, tetromino.Rotation + 1, field)) ? 1 : 0; _rotateHold = false; } else { _rotateHold = true; } if (forceDown) { // Update difficulty every 50 pieces speedCount = 0; pieceCount++; if (pieceCount % 50 == 0) { if (speed >= 10) { speed--; } } if (tetromino.WillFitAtDestination(tetromino.X, tetromino.Y + 1, tetromino.Rotation, field)) { tetromino.Y++; } else { // It can't! Lock the piece in place for (int coordinateX = 0; coordinateX < 4; coordinateX++) { for (int coordinateY = 0; coordinateY < 4; coordinateY++) { if (tetromino.Shape[tetromino.Rotate(coordinateX, coordinateY, tetromino.Rotation)] != '.') { field.PlayingField[(tetromino.X + coordinateX), (tetromino.Y + coordinateY)] = tetromino.Sprite; field.PlayingField[(tetromino.X + coordinateX), (tetromino.Y + coordinateY)] = tetromino.Sprite; } } } // Check for lines for (int coordinateY = 0; coordinateY < 4; coordinateY++) { if (tetromino.Y + coordinateY < field.Height - 1) { bool makesLine = true; for (int coordinateX = 1; coordinateX < field.PlayingField.GetLength(0) - 1; coordinateX++) { makesLine &= (field.PlayingField[coordinateX, tetromino.Y + coordinateY]) != 'B'; } if (makesLine) { // Remove Line, set to = for (int coordinateX = 1; coordinateX < field.PlayingField.GetLength(0) - 1; coordinateX++) { field.PlayingField[coordinateX, tetromino.Y + coordinateY] = 'D'; } lines.Add(tetromino.Y + coordinateY); } } } //score += 25; //if(lines.Count > 0) score += (lines.Count) * 100; //// Pick New Piece //currentX = _fieldWidth / 2; //currentY = 0; //currentRotation = 0; //currentPiece = new Random().Next() % 7; tetromino = new Tetromino(); // If piece does not fit straight away, game over! _isGameOver = !tetromino.WillFitAtDestination(tetromino.X, tetromino.Y, tetromino.Rotation, field); } } if (forceDown || keys.Any(k => k == true)) { field.UpdateField(tetromino); field.DrawField2(tetromino); field.ResetField(tetromino); // Animate Line Completion if (lines.Count > 0) { // Display Frame (cheekily to draw lines) Thread.Sleep(400); // Delay a bit foreach (var line in lines) { for (int px = 1; px < field.PlayingField.GetLength(0) - 1; px++) { for (int py = line; py > 0; py--) { field.PlayingField[px, py] = field.PlayingField[px, py - 1]; } field.PlayingField[px, 0] = 'B'; } } lines.Clear(); } } } }