Imports System.Drawing
Imports System.Windows.Forms

Public Class Form1
    Inherits Form

    Private gridSize As Integer = -1
    Private letterButtons As List(Of Button) = New List(Of Button)()
    Private selectedLetters As List(Of Button) = New List(Of Button)()
    Private currentWord As String = ""
    Private score As Integer = 0
    Private wordList As List(Of String) = New List(Of String)()
    Private lblScore As Label
    Private lblWord As Label
    Private btnSubmit As Button
    Private btnReset As Button
    Private btnNewGame As Button
    Private rtbWords As RichTextBox
    Private ReadOnly rng As New Random()

    ' Letter frequencies for English (simplified)
    Private ReadOnly letterFrequencies As Dictionary(Of Char, Integer) = New Dictionary(Of Char, Integer)() From {
        {"A", 9}, {"B", 2}, {"C", 2}, {"D", 4}, {"E", 12}, {"F", 2}, {"G", 3},
        {"H", 2}, {"I", 9}, {"J", 1}, {"K", 1}, {"L", 4}, {"M", 2}, {"N", 6},
        {"O", 8}, {"P", 2}, {"Q", 1}, {"R", 6}, {"S", 4}, {"T", 6}, {"U", 4},
        {"V", 2}, {"W", 2}, {"X", 1}, {"Y", 2}, {"Z", 1}
    }

    Public Sub New()
        InitializeForm()
        StartNewGame()
    End Sub

    Private Sub InitializeForm()
        Me.Text = "Double Word Game"
        Me.Size = New Size(800, (600))
        Me.StartPosition = FormStartPosition.CenterScreen
        Me.BackColor = Color.LightBlue

        ' Create controls dynamically
        CreateDynamicControls()

        ' Load word list (simplified)
        LoadWordList()
    End Sub

    Private Sub CreateDynamicControls()
        ' Score label
        lblScore = New Label()
        lblScore.Text = "Score: 0"
        lblScore.Font = New Font("Arial", 14, FontStyle.Bold)
        lblScore.ForeColor = Color.DarkBlue
        lblScore.Location = New Point(20, 20)
        lblScore.Size = New Size(150, 30)
        Me.Controls.Add(lblScore)

        ' Current word label
        lblWord = New Label()
        lblWord.Text = "Current Word: "
        lblWord.Font = New Font("Arial", 12)
        lblWord.Location = New Point(20, 60)
        lblWord.Size = New Size(300, 30)
        Me.Controls.Add(lblWord)

        ' Submit button
        btnSubmit = New Button()
        btnSubmit.Text = "Submit Word"
        btnSubmit.Font = New Font("Arial", 10)
        btnSubmit.Location = New Point(20, 100)
        btnSubmit.Size = New Size(120, 35)
        btnSubmit.BackColor = Color.LightGreen
        AddHandler btnSubmit.Click, AddressOf SubmitWord
        Me.Controls.Add(btnSubmit)

        ' Reset selection button
        btnReset = New Button()
        btnReset.Text = "Reset Selection"
        btnReset.Font = New Font("Arial", 10)
        btnReset.Location = New Point(150, 100)
        btnReset.Size = New Size(120, 35)
        btnReset.BackColor = Color.LightCoral
        AddHandler btnReset.Click, AddressOf ResetSelection
        Me.Controls.Add(btnReset)

        ' New game button
        btnNewGame = New Button()
        btnNewGame.Text = "New Game"
        btnNewGame.Font = New Font("Arial", 10)
        btnNewGame.Location = New Point(280, 100)
        btnNewGame.Size = New Size(120, 35)
        btnNewGame.BackColor = Color.LightGoldenrodYellow
        AddHandler btnNewGame.Click, AddressOf StartNewGame
        Me.Controls.Add(btnNewGame)

        ' Words found list
        rtbWords = New RichTextBox()
        rtbWords.Location = New Point(500, 20)
        rtbWords.Size = New Size(250, 520)
        rtbWords.Font = New Font("Arial", 10)
        rtbWords.Text = "Words Found:" & vbCrLf & vbCrLf
        rtbWords.ReadOnly = True
        Me.Controls.Add(rtbWords)
    End Sub

    Private Sub StartNewGame(sender As Object, e As EventArgs)
        StartNewGame()
    End Sub

    Private Sub StartNewGame()
        ' Clear previous game
        ClearLetterGrid()
        wordList.Clear()
        rtbWords.Text = "Words Found:" & vbCrLf & vbCrLf
        score = 0
        UpdateScore()
        ResetSelection()

        ' Ask for grid size
        Dim input As String = InputBox("Enter grid size (4-8):", "New Game", "5")
        If Not Integer.TryParse(input, gridSize) OrElse gridSize < 4 OrElse gridSize > 8 Then
            gridSize = 5 ' Default size
        End If

        ' Create letter grid
        CreateLetterGrid()
    End Sub

    Private Sub CreateLetterGrid()
        Dim startX As Integer = 20
        Dim startY As Integer = 150
        Dim buttonSize As Integer = 50
        Dim spacing As Integer = 5

        For row As Integer = 0 To gridSize - 1
            For col As Integer = 0 To gridSize - 1
                Dim btn As New Button()
                btn.Size = New Size(buttonSize, buttonSize)
                btn.Location = New Point(startX + col * (buttonSize + spacing),
                                         startY + row * (buttonSize + spacing))
                btn.Font = New Font("Arial", 14, FontStyle.Bold)
                btn.BackColor = Color.White
                btn.ForeColor = Color.DarkBlue
                btn.Text = GetRandomLetter()
                btn.Tag = New Point(row, col) ' Store position

                AddHandler btn.Click, AddressOf LetterButton_Click
                AddHandler btn.MouseEnter, AddressOf LetterButton_MouseEnter
                AddHandler btn.MouseLeave, AddressOf LetterButton_MouseLeave

                letterButtons.Add(btn)
                Me.Controls.Add(btn)
            Next
        Next
    End Sub

    Private Sub ClearLetterGrid()
        For Each btn As Button In letterButtons
            Me.Controls.Remove(btn)
            btn.Dispose()
        Next
        letterButtons.Clear()
        selectedLetters.Clear()
    End Sub

    Private Function GetRandomLetter() As String
        ' Weighted random letter selection based on frequency
        Dim totalWeight As Integer = 0

        For Each freq In letterFrequencies.Values
            totalWeight += freq
        Next

        Dim randomNumber As Integer = rng.Next(1, totalWeight + 1)
        Dim cumulativeWeight As Integer = 0

        For Each kvp In letterFrequencies
            cumulativeWeight += kvp.Value

            If randomNumber <= cumulativeWeight Then
                Return kvp.Key.ToString()
            End If
        Next

        Return "A"
    End Function

    Private Sub LetterButton_Click(sender As Object, e As EventArgs)
        Dim btn As Button = DirectCast(sender, Button)

        ' Check if this button is adjacent to the last selected button
        If selectedLetters.Count > 0 Then
            Dim lastBtn As Button = selectedLetters.Last()
            Dim lastPos As Point = DirectCast(lastBtn.Tag, Point)
            Dim currentPos As Point = DirectCast(btn.Tag, Point)

            ' Calculate distance (adjacent includes diagonal)
            Dim rowDiff As Integer = Math.Abs(lastPos.X - currentPos.X)
            Dim colDiff As Integer = Math.Abs(lastPos.Y - currentPos.Y)

            If rowDiff > 1 OrElse colDiff > 1 Then
                MessageBox.Show("Must select adjacent letters!", "Invalid Move",
                              MessageBoxButtons.OK, MessageBoxIcon.Warning)
                Return
            End If
        End If

        ' Check if already selected
        If selectedLetters.Contains(btn) Then
            ' Deselect if clicking the last selected letter
            If btn Is selectedLetters.Last() Then
                selectedLetters.Remove(btn)
                btn.BackColor = Color.White
                UpdateCurrentWord()
                Return
            End If
            MessageBox.Show("Letter already selected!", "Invalid Move",
                          MessageBoxButtons.OK, MessageBoxIcon.Warning)
            Return
        End If

        ' Add to selection
        selectedLetters.Add(btn)
        btn.BackColor = Color.LightSkyBlue
        UpdateCurrentWord()
    End Sub

    Private Sub LetterButton_MouseEnter(sender As Object, e As EventArgs)
        Dim btn As Button = DirectCast(sender, Button)
        If Not selectedLetters.Contains(btn) Then
            btn.BackColor = Color.LightGray
        End If
    End Sub

    Private Sub LetterButton_MouseLeave(sender As Object, e As EventArgs)
        Dim btn As Button = DirectCast(sender, Button)
        If Not selectedLetters.Contains(btn) Then
            btn.BackColor = Color.White
        End If
    End Sub

    Private Sub UpdateCurrentWord()
        currentWord = ""
        For Each btn As Button In selectedLetters
            currentWord &= btn.Text
        Next
        lblWord.Text = "Current Word: " & currentWord
    End Sub

    Private Sub SubmitWord(sender As Object, e As EventArgs)
        If currentWord.Length < 3 Then
            MessageBox.Show("Word must be at least 3 letters long!", "Invalid Word",
                          MessageBoxButtons.OK, MessageBoxIcon.Warning)
            Return
        End If

        If wordList.Contains(currentWord.ToUpper()) Then
            MessageBox.Show("Word already found!", "Duplicate Word",
                          MessageBoxButtons.OK, MessageBoxIcon.Information)
            Return
        End If

        ' Simple validation - in real game would check against dictionary
        If IsValidWord(currentWord) Then
            ' Calculate score
            Dim wordScore As Integer = CalculateScore(currentWord)
            score += wordScore

            ' Add to found words
            wordList.Add(currentWord.ToUpper())
            rtbWords.AppendText(currentWord.ToUpper() & " (+" & wordScore & ")" & vbCrLf)

            ' Update display
            UpdateScore()

            ' Reset selection for next word
            ResetSelection()

            ' Check for bonus
            If currentWord.Length >= 6 Then
                MessageBox.Show("Great! " & currentWord.Length & "-letter word!",
                              "Bonus Word", MessageBoxButtons.OK, MessageBoxIcon.Information)
            End If
        Else
            MessageBox.Show("Invalid word! Try again.", "Invalid Word",
                          MessageBoxButtons.OK, MessageBoxIcon.Warning)
        End If
    End Sub

    Private Function IsValidWord(word As String) As Boolean
        ' In a real game, you would check against a dictionary
        ' For this example, we'll accept any word of 3+ letters
        Return word.Length >= 3 AndAlso word.All(Function(c) Char.IsLetter(c))
    End Function

    Private Function CalculateScore(word As String) As Integer
        ' Simple scoring: length-based with bonus for longer words
        Dim baseScore As Integer = word.Length * 10

        ' Bonus for words with 6+ letters
        If word.Length >= 6 Then
            baseScore *= 2
        End If

        ' Bonus for using less common letters
        For Each letter In word.ToUpper()
            If letterFrequencies.ContainsKey(letter) AndAlso letterFrequencies(letter) <= 2 Then
                baseScore += 5
            End If
        Next

        Return baseScore
    End Function

    Private Sub ResetSelection(sender As Object, e As EventArgs)
        ResetSelection()
    End Sub

    Private Sub ResetSelection()
        For Each btn As Button In selectedLetters
            btn.BackColor = Color.White
        Next
        selectedLetters.Clear()
        currentWord = ""
        lblWord.Text = "Current Word: "
    End Sub

    Private Sub UpdateScore()
        lblScore.Text = "Score: " & score.ToString()
    End Sub

    Private Sub LoadWordList()
        ' In a real game, load from a dictionary file
        ' For demo, we'll use a small list
        ' This would typically be loaded from a file
    End Sub

    Protected Overrides Sub OnFormClosing(e As FormClosingEventArgs)
        Dim result As DialogResult = MessageBox.Show("Are you sure you want to quit?", "Quit Game",
                                                   MessageBoxButtons.YesNo, MessageBoxIcon.Question)
        If result = DialogResult.No Then
            e.Cancel = True
        End If
    End Sub
End Class

' Program entry point
Module Program
    Sub Main()
        Application.EnableVisualStyles()
        Application.SetCompatibleTextRenderingDefault(False)
        Application.Run(New Form1())
    End Sub
End Module
