private void board_PictureBox_Click(object sender, EventArgs e)
        {
            if (players[turn] is HumanPlayer && start_CheckBox.Checked)
            {
                int blockSide = board_PictureBox.Width / Board.size;
                Point p = PointToClient(Cursor.Position);

                p.X = (p.X - all_TableLayoutPanel.Location.X - boardAndLog_TabControl.Location.X - board_TabPage.Location.X - board_PictureBox.Location.X - boardOffset) / blockSide;
                p.Y = (p.Y - all_TableLayoutPanel.Location.Y - boardAndLog_TabControl.Location.Y - board_TabPage.Location.Y - board_PictureBox.Location.Y - boardOffset) / blockSide;

                Position position = Board.Position(p.Y, p.X);
                linkedPositionByHuman = Array.Find(movablePositions, linkedPosition => linkedPosition.position == position);

                lock (board)
                {
                    Monitor.Pulse(board);
                }
            }
        }
        private void InitializeReversi()
        {
            if (thread != null)
            {
                thread.Abort();
                thread = null;
            }

            if (thread2 != null)
            {
                thread2.Abort();
                thread2 = null;
            }

            size = int.Parse(size_ComboBox.Text);
            pattern = (Pattern)pattern_ComboBox.SelectedItem;
            phase = 0;
            turn = State.Black;
            board = new Board(size, pattern);
            boardForResize = board.Clone();
            players = new Dictionary<State, Player>();
            players[State.Black] = (Player)blackPlayer_ComboBox.SelectedValue;
            players[State.White] = (Player)whitePlayer_ComboBox.SelectedValue;
            linkedPosition = LinkedPosition.Out;
            linkedPositionByHuman = LinkedPosition.Out;
            seed_ComboBox.Items[0] = Environment.TickCount;
            seed = int.Parse(seed_ComboBox.Text);
            random = new Random(seed);
            start_CheckBox.Checked = false;
            history_ComboBox.Items.Clear();
            history_ComboBox.Items.Add(phase);
            iteration = int.Parse(iteration_ComboBox.Text);
            alphaBetaDepth = int.Parse(alphaBetaDepth_ComboBox.Text);
            evaluationFunction = (EvaluationFunction)evaluationFunction_ComboBox.SelectedValue;
            iterativeDeepeningDepth = int.Parse(iterativeDeepeningDepth_ComboBox.Text);
            basePlayer = (Player)basePlayer_ComboBox.SelectedValue;
            movablePositions = board.MovablePositions(turn);

            board_PictureBox.Image = BoardImage(board);
            information_PictureBox.Image = InformationImage(board, turn);
            phase_ExtendedLabel.Text = PhaseText();
            text_ExtendedLabel.Text = StartText();
            _ProgressBar.Value = 0;
            _ProgressBar.Style = ProgressBarStyle.Blocks;
            log_TextBox.Text = StartText() + Environment.NewLine + Environment.NewLine;

            start_CheckBox.Enabled = true;
        }
        private void StartReversi(List<Position> positions = null)
        {
            for (int p = history_ComboBox.Items.Count - 1; p > phase; p--)
            {
                history_ComboBox.Items.RemoveAt(p);
            }

            int index = 0;
            Stopwatch stopwatch = new Stopwatch();
            Stopwatch stopwatch2 = new Stopwatch();

            stopwatch.Start();

            Invoke((MethodInvoker)(() =>
            {
                Form1.log_TextBox.AppendText("Start Date-Time = " + DateTime.Now + Environment.NewLine + Environment.NewLine);
            }));

            while (start_CheckBox.Checked || positions != null)
            {
                State notTurn = turn.Not();

                if (movablePositions.Length != 0)
                {
                    if (positions == null)
                    {
                        Invoke((MethodInvoker)(() =>
                        {
                            log_TextBox.AppendText("movablePositions = " + movablePositions.Select(lp => Board.PositionString(lp.position)).ToStringExtension() + Environment.NewLine);
                        }));

                        stopwatch2.Restart();
                        linkedPosition = players[turn].Choose(board, turn);
                        stopwatch2.Stop();

                        Invoke((MethodInvoker)(() =>
                        {
                            Form1.log_TextBox.AppendText("Time [ms] = " + stopwatch2.ElapsedMilliseconds + Environment.NewLine);
                        }));
                    }
                    else
                    {
                        if (index == positions.Count)
                        {
                            break;
                        }

                        Invoke((MethodInvoker)(() =>
                        {
                            log_TextBox.AppendText("movablePositions = " + movablePositions.Select(lp => Board.PositionString(lp.position)).ToStringExtension() + Environment.NewLine);
                        }));

                        Position position = positions[index++];
                        linkedPosition = Array.Find(movablePositions, lp => lp.position == position);

                        if (linkedPosition == null)
                        {
                            Form2 message = new Form2("Message", true, "Invalid Move: " + Board.PositionString(position), true);

                            Invoke((MethodInvoker)(() =>
                            {
                                message.ShowDialog(this);
                            }));

                            message.Dispose();

                            return;
                        }
                    }

                    if (!start_CheckBox.Checked && positions == null)
                    {
                        break;
                    }

                    linkedPosition = Array.Find(movablePositions, lp => lp.position == linkedPosition.position);
                    board.Move(turn, linkedPosition);

                    Invoke((MethodInvoker)(() =>
                    {
                        text_ExtendedLabel.Text = MiddleText();
                        log_TextBox.AppendText(MiddleText() + Environment.NewLine);
                    }));
                }
                else
                {
                    if (!board.CanMove(notTurn))
                    {
                        Invoke((MethodInvoker)(() =>
                        {
                            text_ExtendedLabel.Text = EndText();
                            log_TextBox.AppendText(EndText() + Environment.NewLine + Environment.NewLine);
                            start_CheckBox.Checked = false;
                        }));

                        break;
                    }

                    Invoke((MethodInvoker)(() =>
                    {
                        text_ExtendedLabel.Text = PassText();
                        log_TextBox.AppendText(PassText() + Environment.NewLine);
                    }));

                    if (pass_CheckBox.Checked)
                    {
                        Form2 message = new Form2("Message", true, PassText(), true);

                        Invoke((MethodInvoker)(() =>
                        {
                            message.ShowDialog(this);
                        }));

                        message.Dispose();
                    }
                }

                turn = notTurn;
                phase++;

                movablePositions = board.MovablePositions(turn);
                boardForResize = board.Clone();

                Invoke((MethodInvoker)(() =>
                {
                    phase_ExtendedLabel.Text = PhaseText();
                    log_TextBox.AppendText(ScoreText() + Environment.NewLine);
                    log_TextBox.AppendText(PhaseText() + Environment.NewLine + Environment.NewLine);
                    history_ComboBox.Items.Add(phase);
                    board_PictureBox.Image = BoardImage(board);
                    information_PictureBox.Image = InformationImage(board, turn);
                }));

                Thread.Sleep(delay);
            }

            stopwatch.Stop();

            Invoke((MethodInvoker)(() =>
            {
                Form1.log_TextBox.AppendText("Stop Date-Time = " + DateTime.Now + Environment.NewLine);
                Form1.log_TextBox.AppendText("Time [ms] = " + stopwatch.ElapsedMilliseconds + Environment.NewLine + Environment.NewLine);
            }));
        }
        private void history_ComboBox_SelectedIndexChanged(object sender, EventArgs e)
        {
            if (history_ComboBox.SelectedIndex == -1)
            {
                return;
            }

            start_CheckBox.Checked = false;

            while (thread != null && thread.ThreadState != System.Threading.ThreadState.WaitSleepJoin && thread.ThreadState != System.Threading.ThreadState.Stopped)
            {
                Thread.Sleep(100);
            }

            int phase = history_ComboBox.SelectedIndex;

            if (this.phase > phase)
            {
                while (this.phase > phase)
                {
                    turn = turn.Not();

                    this.phase--;
                    MoveInformation moveInformation = board.moveInformations[board.index - 1];

                    if (moveInformation.turn != turn)
                    {
                        continue;
                    }

                    board.Unmove();
                }
            }
            else
            {
                while (this.phase < phase)
                {
                    this.phase++;
                    MoveInformation moveInformation = board.moveInformations[board.index];

                    if (moveInformation.turn != turn)
                    {
                        turn = turn.Not();

                        continue;
                    }

                    board.Move(turn, moveInformation.linkedPosition);

                    turn = turn.Not();
                }
            }

            linkedPosition = board.index == 0 ? LinkedPosition.Out : board.moveInformations[board.index - 1].linkedPosition;
            movablePositions = board.MovablePositions(turn);

            phase_ExtendedLabel.Text = PhaseText();
            board_PictureBox.Image = BoardImage(board);
            information_PictureBox.Image = InformationImage(board, turn);
        }