猜數字是個很簡單的小遊戲,我在設計這個遊戲時,除了一些判斷的程式碼之外, 另外有一個非常重要的地方也是要去特別注意的,那就是使用者的上手度,簡易性, 我僅量讓使用者單單使用鍵盤就能去玩這個遊戲,而不用去動用到滑鼠,就像 一些資料庫的程式都會在使用者按下Enter鍵後,都會自動跳到下一個欄位一樣, 這雖然只是一些小小的處理,但是對使用者而言可能代表了更大的善意和體貼, 使用者可能只是個初學者,因此簡單易懂的操作介面是設計程式時絕對不能忘記的, 不過,話雖如此,我在進行連線對戰時還是不十分方便,還要改進...

那麼,這一週我們就開始講解程式的內容吧! 我們先看看From_Load開始,這邊的是一些參數(如遊戲難度)的初始設定及 表單置中的處理,而在Form_Activate的部份則是將程式的Focus設定到遊戲開始的按鍵上, 接下來程式的重點就轉到遊戲進行的流程上了,在正式講解程式之前,我們先來瞭解 一下幾個變數和它的意義
Public ConnectType As Integer
連線時扮演的角色,Server or Client
在進行連線的時候,只有當連線主機的一方能夠進行一些遊戲的設定, 否則萬一這邊把難度設為3個數字,另一邊又設為4個數字,那就會有問題囉!
可以設定的值有兩個
CONNECT_SERVER = 1
CONNECT_CLIENT = 2

Public MyComputerName As String
電腦名稱,連線時可用來當連線的依據,如果在網路上的芳鄰看的到對方的電 腦時,要與對方連線對戰,只要輸入這個名稱,不需要打對方的IP address

Public ConnectStatus As Boolean
判斷目前是否處於連線狀態中

Dim CPUNumber As String
電腦或對手要讓自己猜的號碼

Dim UserNumber As String
自己要讓對手猜的號碼

Dim CPUArray() As Integer
電腦的AI用的判斷陣列

Dim CPUArraySUM As Integer
陣列總數

Dim GAME_NUMBER As Integer
遊戲要猜的數字個數 (2 ~ 4)

Dim FormatString As String
"00" ~ "0000"

稍微先記住一下這些變數的用途,接者看程式的時候會比較容易瞭解, 我們先看難度設定的這一段程式(以四個數字為例)

Private Sub LevelHard_Click()
Dim i As Integer
If ConnectStatus = True And ConnectType = CONNECT_CLIENT Then
   MsgBox "User端不能設定遊戲難度,請由Server端設定", , Me.Caption
   Exit Sub
End If

我們在這裡要先判斷目前的連線狀態,如果在連線中,又不是連線主機的話,
那麼程式就不允許使用者變更設定,因此就Show出一段Message告知使用者,
再跳離程式


GAME_NUMBER = 4
設定遊戲難度為4個數字


FormatString = ""
For i% = 1 To GAME_NUMBER
     FormatString = FormatString & "0"
Next i%
依遊戲難度設定formatString(變數要補幾個0用的),這在後面的判斷會用上,


LevelHard.Checked = vbChecked
LevelNormal.Checked = vbUnchecked
LevelEasy.Checked = vbUnchecked
這裡就很單純的只是改變一下menu,沒有什麼需要特別注意的

End Sub

難度設定完成了,也沒有什麼需要注意的了,就按下開始遊戲吧!
Private Sub cmdGameStart_Click()
Dim x As String

'Check Connect Status
'If False (Not Net Batter) Input Game Number
'   Then Check Number Error,If No Error Then Reset All the Game Data,Game Start
'If Connect Status True(Net Batter)
'   If ConnectType = CLIENT then Exit
'   Else Input Game Number,Send Message to Client ,Disable Menu and Command Button
'   Wait Client Response
   

If ConnectStatus = False Then
   x = InputBox("請輸入你要讓對方猜的" & Format$(GAME_NUMBER, "0") & "位數字", Me.Caption)
Else
   If ConnectType = CONNECT_CLIENT Then
      MsgBox "User端不能主動開始遊戲!請由Server端開始新遊戲", , Me.Caption
      Exit Sub
   End If

   x = InputBox("請輸入你要讓電腦猜的" & Format$(GAME_NUMBER, "0") & "位數字", Me.Caption)
End If

先請使用者輸入要讓對方(電腦)猜的數字,和剛才的難度設定一樣,如果連線狀態時,
一切都要等連線主機的回應,因此非連線主機的話,必需要跳離程式,不能繼續執行


接者要判斷使用者輸入的數字格式是否正確
1.長度對不對

If Len(x) <> GAME_NUMBER Then
   MsgBox "長度錯誤,請重新輸入", , Me.Caption
   Exit Sub
End If



2.是不是數字?是數字的話,有沒有小於0

If IsNumeric(x) = False Then
   MsgBox "輸入錯誤", , Me.Caption
   x = ""
   Exit Sub
ElseIf CLng(x) < 0 Then
   MsgBox "輸入錯誤", , Me.Caption
   x = ""
   Exit Sub
End If




3.輸入的數字有沒有重覆?CheckSameNumber是個很簡單的比較式,將
  字串一個一個取出來與其它數字比對,應該不用我講了吧!

If CheckSameNumber(x) = True Then
   MsgBox "數字重覆,請重新輸入", , Me.Caption
   Exit Sub
End If


假設一切都沒有問題的話,就將這個數字存到UserNumber
UserNumber = x


如果是在進行連線對戰的話,接者就必需要將進行遊戲的要求送給對方
接下來的情形比較複雜,等後面一點會寫一篇專門解釋連線的流程
If ConnectStatus = True Then
   SendMsgToUser GAME_MSG & MSG_GAME_START & Format$(GAME_NUMBER, "0") & UserNumber
   GameSetUP.Enabled = False
   cmdGameStart.Enabled = False
   Me.Caption = "請稍候...傳送資料中....正在等待對方回應....."
   Exit Sub
End If


接下來我們要來產生電腦要讓我們猜的數字,以及電腦要用來
判斷我們數字的亂數陣列
Dim i%, j% ReDim ArrayTemp(1 To (10 ^ GAME_NUMBER) - 1) As Integer 先設定一個陣列,大小是10的N次方-1,N=要猜的數字數 等一下要用來放置電腦要猜我們數字用的 2 - 1~99 3 - 1~999 4 - 1~9999 On Error GoTo CheckInputError CPUNumber = "" CPUArraySUM = 0 lstCPURecord.Clear lstUserRecord.Clear txtUserInput.Text = "" txtCPUInput.Text = "" 先將一些相關物件,變數清除 Call GetRandomArray(10, 10) For i% = 1 To GAME_NUMBER CPUNumber = CPUNumber & Format$(rndFlag(i) - 1, "0") Next i% 利用GetRandomArray()將1~10亂數排列存放進rndFlag這個陣列中, 我們再依遊戲的需求取出自己需要的數目就是電腦要讓我們猜的 數字囉!GetRandomArray是作者用來產生不重覆的亂數的副程式, 等一下再分析給你們看 For i% = 1 To (10 ^ GAME_NUMBER) - 1 If CheckSameNumber(Format$(i%, FormatString)) <> True Then CPUArraySUM = CPUArraySUM + 1 ArrayTemp(CPUArraySUM) = i% End If Next i% ReDim CPUArray(1 To CPUArraySUM) For i% = 1 To CPUArraySUM CPUArray(i%) = ArrayTemp(i%) Next i% 接下來我們要整理一下電腦猜數字的陣列,將絕對不可能的數字剃掉 (就是數字重覆的部份啦),將所有有可能的數字存到CPUArray陣列中 接下來把一些該秀的Message秀出來,遊戲就可以進行囉! lblUserNumber = UserNumber lblCPUNumber = CPUNumber txtUserInput.Enabled = True GameSetUP.Enabled = False NetButter.Enabled = False With cmdGameStart If .Caption = "遊戲開始" Then .Caption = "重開新局" Else .Caption = "遊戲開始" End If End With MsgBox "遊戲開始", , Me.Caption txtUserInput.SetFocus Exit Sub CheckInputError: If Err = 13 Then MsgBox "輸入錯誤", , Me.Caption End If Resume QuitError QuitError: Exit Sub End Sub

接者我們暫時把焦點移開,來看GetRandomArray這個副程式, 這段副程式雖然效率不是很好,不過在很多地方都用的著,記下來準沒錯! 來看一下這一段程式吧!

這個陣列需要傳入幾個參數,第一個參數代表你要取幾個數字,
第二個參數則代表你要取的亂數的範圍最大值

Private Sub GetRandomArray(aNo As Integer, bNo As Integer)
   Dim i%, j%, count%
   Dim rNo As Integer
   Dim flag() As Integer

   ReDim rndFlag(1 To aNo)
   For i% = 1 To aNo
      rndFlag(i%) = 0
   Next i%
   
   rndFlag是一個已經宣告過的數字陣列,待會求出來的值就是放
   在這個陣列裡,我們先將陣列的值歸零



   ReDim flag(1 To bNo)
   For i% = 1 To bNo
      flag(i%) = 0
   Next i%
   這個flag則是另一個暫存的陣列,大小則和我們要取的最大值一樣,
   這是用來判斷我們是否已經取過這一個值的,相同的,我們也先
   把陣列的值歸零



   For i% = 1 To aNo      總共要取aNo個亂數,所以For迴圈就是1 to aNo
      rNo = GetRandomNo(bNo - i% + 1)    
          先用GetRandomNo取得一個亂數,注意!亂數取的範圍每次都不一樣喔!
          會越來越小


      count% = 0     計算用的變數,歸零
      For j% = 1 To bNo
         If flag(j%) = 0 Then
            count = count + 1

            如果這一個數字還沒有取出來的話
            就比對一下count與亂數相不相同
            如果一樣,就取出這個數字囉
            將flag設為1,繼續取下一個數字吧
      
            If count = rNo Then
               flag(j%) = 1
               rndFlag(i%) = j%
               Exit For
            End If
         End If
      Next j%
   Next i%

   ReDim flag(0)
End Sub

為什麼這樣可以取出不同的數字呢?不知道你們有沒有看懂, 我就以GetRandomArray(10,10)來舉例說明一下
第一次取亂數時rNo最大為 10-1+1=10
假設我們取到了2 那麼推演下來會得到rndFlag(1)=2
第二次最大的值變成10-2+1=9
在推演的過程中遇到flag(2)時自然會跳過去,這裡你應該就能查覺到為什麼取得的亂 數值需要逐次遞減,如果我們在這一次依然取十為最大值,但是得到的也是十, 那麼你就推演不出這次rndFlag該填的值了
這樣子解說希望你們會懂, 猜數字這個遊戲其實挺單純的,這一週先到此為止, 下一週與CPU對戰的部份就應該可以一次講解完畢了, 敬請....
下一週....?嗯....>_<
下一週不知到底是什麼時候.... 總之,儘量就是了,謝謝網友們的支持,請等待正常更新的日子到來吧...
See you next time~
回到VB教學教室