Gamemaking.cs
using System;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Threading;
//自己記録用です。XAML上で若干弄らないと動きません
namespace Gamemaking
{
public class Board //テトリスの画面レイアウトの実装
{
private int Rows;
private int Cols;
private int Score;
private int LinesFilled;
private Tetramino currTetramino;
private Label[,] BlockControls;
static private Brush NoBrush = Brushes.Transparent; //静的変数に格納する
static private Brush SilverBrush = Brushes.Gray;// 上に同じ
public Board(Grid TetrisGrid)
{
Rows = TetrisGrid.RowDefinitions.Count;
Cols = TetrisGrid.ColumnDefinitions.Count;
Score = 0;
LinesFilled = 0;
BlockControls = new Label[Cols, Rows];
for (int i = 0; i < Cols; i++)
{
for (int j = 0; j < Rows; j++)
{
BlockControls[i, j] = new Label();
BlockControls[i, j].Background = NoBrush;
BlockControls[i, j].BorderBrush = SilverBrush;
BlockControls[i, j].BorderThickness = new Thickness(1, 1, 1, 1);
Grid.SetRow(BlockControls[i, j], j);
Grid.SetColumn(BlockControls[i, j], i);
TetrisGrid.Children.Add(BlockControls[i, j]);
}
}
currTetramino = new Tetramino();
currTetraminoDraw();
}
public int getScore()
{
return Score;
}
public int getLines()
{
return LinesFilled;
}
private void currTetraminoDraw()
{
Point Position = currTetramino.getCurrPosition();
Point[] Shape = currTetramino.getCurrShape();
Brush Color = currTetramino.getCurrColor();
foreach (Point S in Shape)
{
BlockControls[(int)(S.X + Position.X) + ((Cols / 2) - 1),
(int)(S.Y + Position.Y) + 2].Background = Color;
}
}
private void currTetraminoErase()
{
Point Position = currTetramino.getCurrPosition();
Point[] Shape = currTetramino.getCurrShape();
foreach (Point S in Shape)
{
BlockControls[(int)(S.X + Position.X) + ((Cols / 2) - 1),
(int)(S.Y + Position.Y) + 2].Background = NoBrush;
}
}
private void CheckRows()
{
bool full;
for (int i = Rows - 1; i > 0; i--)
{
full = true;
for (int j = 0; j < Cols; j++)
{
if (BlockControls[j, i].Background == NoBrush)
{
full = false;
}
}
if (full)
{
RemoveRow(i);
Score += 100;
LinesFilled += 1;
}
}
}
private void RemoveRow(int row)
{
for (int i = row; i > 2; i--)
{
for (int j = 0; j < Cols; j++)
{
BlockControls[j, i].Background = BlockControls[j, i - 1].Background;
}
}
}
public void currTetraminoMovLeft()
{
Point Position = currTetramino.getCurrPosition();
Point[] Shape = currTetramino.getCurrShape();
bool move = true;
currTetraminoErase();
foreach (Point S in Shape)
{
if (((int)(S.X + Position.X) + ((Cols / 2) - 1) - 1) < 0)
{
move = false;
}
else if (BlockControls[((int)(S.X + Position.X) + ((Cols / 2) - 1) - 1),
(int)(Position.Y) + 2].Background != NoBrush)
{
move = false;
}
}
if (move)
{
currTetramino.movLeft();
currTetraminoDraw();
}
else
{
currTetraminoDraw();
}
}
public void currTetraminoMovRight()
{
Point Position = currTetramino.getCurrPosition();
Point[] Shape = currTetramino.getCurrShape();
bool move = true;
foreach (Point S in Shape)
{
if (((int)(S.X + Position.X) + ((Cols / 2) - 1) + 1) >= Cols)
{
move = false;
}
else if (BlockControls[((int)(S.X + Position.X) + ((Cols / 2) - 1) + 1),
(int)(Position.Y) + 2].Background != NoBrush)
{
move = false;
}
}
if (move)
{
currTetramino.movRight();
currTetraminoDraw();
}
else
{
currTetraminoDraw();
}
}
public void currTetraminoMovDown()
{
Point Position = currTetramino.getCurrPosition();
Point[] Shape = currTetramino.getCurrShape();
bool move = true;
foreach (Point S in Shape)
{
if (((int)(S.Y + Position.Y) + 2 + 1) >= Rows)
{
move = false;
}
else if (BlockControls[((int)(S.X + Position.X) + ((Cols / 2) - 1)),
(int)(Position.Y) + 2 + 1].Background != NoBrush)
{
move = false;
}
}
if (move)
{
currTetramino.movDown();
currTetraminoDraw();
}
else
{
CheckRows();
currTetramino = new Tetramino();
currTetraminoDraw();
}
}
public void currTetraminoMovRotate()
{
Point Position = currTetramino.getCurrPosition();
Point[] Shape = currTetramino.getCurrShape();
Point[] S = new Point[4];
bool move = true;
Shape.CopyTo(S, 0);
currTetraminoErase();
for (int i = 0; i < S.Length; i++)
{
double x = S[i].X;
S[i].X = S[i].Y * -1;
S[i].Y = x;
if (((int)((S[i].Y + Position.Y) + 2)) >= Rows)
{
move = false;
}
else if (((int)(S[i].X + Position.X) + ((Cols / 2) - 1)) < 0)
{
move = false;
}
else if (((int)(S[i].X + Position.X) + ((Cols / 2) - 1)) >= Rows)
{
move = false;
}
else if (BlockControls[((int)(S[i].X + Position.X) + ((Cols / 2) - 1)),
(int)(S[i].Y + Position.Y) + 2].Background != NoBrush)
{
move = false;
}
}
if (move)
{
currTetramino.movRotate();
currTetraminoDraw();
}
else
{
currTetraminoDraw();
}
}
public class Tetramino//ブロックの生成など
{
private Point currPosition; //ブロックの位置
private Point[] currShape;//ブロックの形
private Brush currColor;//ブロックの色指定
private bool rotate; //ブロックの回転?
public Tetramino()
{//上四つの設定
currPosition = new Point(0, 0);
currColor = Brushes.Transparent;
currShape = setRandomShape();
}
public Brush getCurrColor()//色
{
return currColor;
}
public Point getCurrPosition()//位置
{
return currPosition;
}
public Point[] getCurrShape()//形
{
return currShape;
}
public void movLeft()//以下4つ動きのための関数
{
currPosition.X -= 1;
}
public void movRight()
{
currPosition.X += 1;
}
public void movDown()
{
currPosition.Y += 1;
}
public void movRotate()//ブロックの回転
{
if (rotate)
{
for (int i = 0; i < currShape.Length; i++)
{
double x = currShape[i].X;
currShape[i].X = currShape[i].Y * -1;
currShape[i].Y = x;
}
}
}
private Point[] setRandomShape()
{//ブロックの形と色のパターンをswtich文で実装。
Random rand = new Random();
switch (rand.Next() % 7)
{
case 0:
rotate = true;
currColor = Brushes.Cyan;
return new Point[] {
new Point(0,0),
new Point(-1,0),
new Point(1,0),
new Point(2,0)
};
case 1:
rotate = true;
currColor = Brushes.Blue;
return new Point[] {
new Point(1,-1),
new Point(-1,0),
new Point(0,0),
new Point(1,0)
};
case 2:
rotate = true;
currColor = Brushes.Yellow;
return new Point[] {
new Point(0,0),
new Point(-1,0),
new Point(1,0),
new Point(1,-1)
};
case 3:
rotate = false;
currColor = Brushes.Orange;
return new Point[] {
new Point(0,0),
new Point(0,1),
new Point(1,0),
new Point(1,1)
};
case 4:
rotate = true;
currColor = Brushes.Green;
return new Point[] {
new Point(0,0),
new Point(-1,0),
new Point(0,-1),
new Point(1,0)
};
case 5:
rotate = true;
currColor = Brushes.Purple;
return new Point[] {
new Point(0,0),
new Point(-1,0),
new Point(0,-1),
new Point(1,1)
};
case 6:
rotate = true;
currColor = Brushes.Red;
return new Point[] {
new Point(0,0),
new Point(-1,0),
new Point(0,1),
new Point(1,1)
};
default:
return null;
}
}
}
}
/// <summary>
/// Interaction logic for MainWindow.xaml
/// </summary>
public partial class MainWindow : Window
{
DispatcherTimer Timer;
Board myBoard;
public MainWindow()
{
InitializeComponent();
}
void MainWindow_Initialized(object sender, EventArgs e)
{
Timer = new DispatcherTimer();
Timer.Tick += new EventHandler(GameTick);
Timer.Interval = new TimeSpan(0, 0, 0, 0, 400);
GameStart();
}
private void GameStart()
{
MainGrid.Children.Clear();
myBoard = new Board(MainGrid);
Timer.Start();
}
void GameTick(object sender, EventArgs e)
{
Scores.Content = myBoard.getScore().ToString("0000000000");
Lines.Content = myBoard.getLines().ToString("00000000000");
myBoard.currTetraminoMovDown();
}
private void GamePause()
{
if (Timer.IsEnabled) Timer.Stop();
else Timer.Start();
}
private void HandleKeyDown(object sender, KeyEventArgs e)
{
switch (e.Key)
{
case Key.Left:
if (Timer.IsEnabled) myBoard.currTetraminoMovLeft();
break;
case Key.Right:
if (Timer.IsEnabled) myBoard.currTetraminoMovRight();
break;
case Key.Down:
if (Timer.IsEnabled) myBoard.currTetraminoMovDown();
break;
case Key.Up:
if (Timer.IsEnabled) myBoard.currTetraminoMovRotate();
break;
case Key.F2:
GameStart();
break;
case Key.F3:
GamePause();
break;
}
}
}
}