[VB6] การตรวจสอบข้อมูล (Validate Data) สำหรับ TextBox Control
การตรวจสอบข้อมูล หรือ Validate Data เป็นส่วนสำคัญอย่างมาก ในการดัก Error โดยเฉพาะค่าทางตัวเลข เพราะเราจะดักค่า หรือเช็คความถูกต้องก่อนที่จะนำค่าไปคำนวณผล โดยที่ไม่ต้องมาใช้คำสั่ง IF ซ้อนๆกัน และเหตุการณ์ที่ต้องทำซ้ำๆ ด้งนั้นเราควรจะนำโค้ดไปเก็บไว้ในลักษณะของ Public Function (รับค่าและคืนค่าได้) เพื่อให้ฟอร์มทุกฟอร์มมองเห็นได้ และลดจำนวนโค้ดลงไป ในโค้ดชุดนี้แอดมินได้เพิ่มเรื่องของการทำไฮไลท์เพื่อแสดงตำแหน่งโฟกัสการป้อนข้อมูล และที่สำคัญคือการแก้ปัญหาในเรื่องการกด Enter ในการเลื่อนตำแหน่งโฟกัส ซึ่งจะมีปัญหามาตั้งแต่ Windows 8+ ทำให้เกิด Error หรือที่เรียกว่า Permission Denied (Run Time Error 70)http://www.g2gsoft.com/webboard/images/VB6/ValidateVB6.jpg
การทำไฮไลท์ให้กับตำแหน่งโฟกัส
http://www.g2gsoft.com/webboard/images/VB6/ValidateVB6-01.jpg
เทคนิคการเรียงลำดับ TabIndex
http://www.g2gsoft.com/webboard/images/VB6/ValidateVB6-02.jpg
ควรย้ายฟังค์ชั่นเหล่านี้ให้ไปอยู่ในโมดูล และประกาศเป็นแบบ Public
มาดูโค้ดฉบับเต็มกันเถอะ ... Option Explicit
' / ---------------------------------------------------------------------------
Private Sub Form_Load()
' / ---------------------------------------------------------------------------
'/ เคลียร์ค่าใน TextBox ทั้งหมด
txtAlphabet.Text = ""
txtAlphabetUCase.Text = ""
txtInteger.Text = "0"
txtDouble.Text = "0.00"
'/ จัดเรียงลำดับของการโฟกัส หรือ TabIndex (ไปทำในตอน Designer จะง่ายกว่า)
txtAlphabet.TabIndex = 0
txtAlphabetUCase.TabIndex = 1
txtInteger.TabIndex = 2
txtDouble.TabIndex = 3
End Sub
' / ---------------------------------------------------------------------------
' / เหตุการณ์ในการที่ TextBox ได้รับโฟกัส
Private Sub txtAlphabet_GotFocus()
' / ---------------------------------------------------------------------------
'/ ทำไฮไลท์แถบแสง โดยเรียกไปยังฟังค์ชั่น HLText และส่งชื่อ Control ไปด้วย
Call HLText(txtAlphabet)
End Sub
' / ---------------------------------------------------------------------------
Private Sub txtAlphabet_KeyPress(KeyAscii As Integer)
' / ---------------------------------------------------------------------------
' / หากเกิดการกด Enter ให้ส่งคีย์ TAB เพื่อเลื่อนตำแหน่งโฟกัสไปยัง Control ถัดไป
' / VB6 ไม่มีเหตุการณ์กด Enter แล้วเลื่อนโฟกัส ต้องใช้การส่งคีย์ (SendKeys) การกด TAB แทน
If KeyAscii = 13 Then
Sendkeys "{TAB}"
KeyAscii = 0 '/ ปิดเสียง
Else
'/ ส่งค่า KeyAscii ที่กดลงไปบนคีย์แต่ละตัว ไปให้กับฟังค์ชั่น CheckAlphabet และส่งค่ากลับคืนมา
'/ หากเป็นตัวอักษรภาษาอังกฤษก็จะคืนค่า Ascii Code A - Z (65 - 90), a - z (97 - 122)
'/ หากไม่ใช่ ก็จะคืนค่า 0 กลับมา เสมือนว่าไม่มีการกดคีย์ใดๆเลย
KeyAscii = CheckAlphabet(KeyAscii)
End If
End Sub
' / ---------------------------------------------------------------------------
' / เหตุการณ์ในการที่ TextBox ได้รับโฟกัส
Private Sub txtAlphabetUCase_GotFocus()
' / ---------------------------------------------------------------------------
'/ ทำไฮไลท์แถบแสง โดยเรียกไปยังฟังค์ชั่น HLText และส่งชื่อ Control ไปด้วย
Call HLText(txtAlphabetUCase)
End Sub
' / ---------------------------------------------------------------------------
Private Sub txtAlphabetUCase_KeyPress(KeyAscii As Integer)
' / ---------------------------------------------------------------------------
' / หากเกิดการกด Enter ให้ส่งคีย์ TAB เพื่อเลื่อนตำแหน่งโฟกัสไปยัง Control ถัดไป
If KeyAscii = 13 Then
Sendkeys "{TAB}"
KeyAscii = 0 '/ ปิดเสียง
Else
'/ รับค่าตัวอักษรภาษาอังกฤษทั้งตัวใหญตัวเล็ก แต่กดตัวอักษรตัวเล็ก a - z จะแปลงเป็นตัวอักษรตัวใหญ่ A - Z ให้อัตโนมัติ
KeyAscii = Asc(UCase(Chr(CheckAlphabet(KeyAscii))))
End If
End Sub
' / ---------------------------------------------------------------------------
' / เหตุการณ์ในการที่ TextBox ได้รับโฟกัส
Private Sub txtDouble_GotFocus()
' / ---------------------------------------------------------------------------
'/ ทำไฮไลท์แถบแสง โดยเรียกไปยังฟังค์ชั่น HLText และส่งชื่อ Control ไปด้วย
Call HLText(txtDouble)
End Sub
' / ---------------------------------------------------------------------------
Private Sub txtDouble_KeyPress(KeyAscii As Integer)
' / ---------------------------------------------------------------------------
' / หากเกิดการกด Enter ให้ส่งคีย์ TAB เพื่อเลื่อนตำแหน่งโฟกัสไปยัง Control ถัดไป
If KeyAscii = 13 Then
Sendkeys "{TAB}"
KeyAscii = 0 '/ ปิดเสียง
Else
'/ ส่งค่า KeyAscii ที่กดลงไปบนคีย์แต่ละตัว ไปให้กับฟังค์ชั่น CheckAlphabet และส่งค่ากลับคืนมา
'/ หากเป็นตัวอักษรภาษาอังกฤษก็จะคืนค่า Ascii Code A - Z (65 - 90), a - z (97 - 122)
'/ หากไม่ใช่ ก็จะคืนค่า 0 กลับมา เสมือนว่าไม่มีการกดคีย์ใดๆเลย
KeyAscii = CheckCurrency(KeyAscii, txtDouble)
End If
End Sub
' / ---------------------------------------------------------------------------
' / เหตุการณ์ที่ TextBox หลุดโฟกัสไป
Private Sub txtDouble_LostFocus()
' / ---------------------------------------------------------------------------
'/ ป้องกันค่าว่าง ก่อนที่จะนำค่าไปเก็บหรือคำนวณ
If Trim(txtDouble.Text) = "" Then
txtDouble.Text = "0.00"
Else
'/ จัดรูปแบบให้กับค่าตัวเลขแบบทศนิยม
txtDouble.Text = Format(CDbl(txtDouble.Text), "0.00")
End If
End Sub
' / ---------------------------------------------------------------------------
' / เหตุการณ์ในการที่ TextBox ได้รับโฟกัส
Private Sub txtInteger_GotFocus()
' / ---------------------------------------------------------------------------
'/ ทำไฮไลท์
Call HLText(txtInteger)
End Sub
' / ---------------------------------------------------------------------------
' / เหตุการณ์ที่ TextBox หลุดโฟกัสไป
Private Sub txtInteger_LostFocus()
' / ---------------------------------------------------------------------------
'/ ป้องกันค่าว่าง ก่อนที่จะนำค่าไปเก็บหรือคำนวณ
If Trim(txtInteger.Text) = "" Then
txtInteger.Text = "0"
Else
'/ จัดรูปแบบให้กับค่าตัวเลขแบบจำนวนเต็ม
txtInteger.Text = Format(CInt(txtInteger.Text), "0")
End If
End Sub
' / ---------------------------------------------------------------------------
' / โปรแกรมย่อยเหตุการณ์ (Event) ในการรับค่าการกดคีย์บนแป้นคีย์บอร์ดทีละตัว
Private Sub txtInteger_KeyPress(KeyAscii As Integer)
'/ ---------------------------------------------------------------------------
' / หากเกิดการกด Enter ให้ส่งคีย์ TAB เพื่อเลื่อนตำแหน่งโฟกัสไปยัง Control ถัดไป
If KeyAscii = 13 Then
Sendkeys "{TAB}"
KeyAscii = 0 '/ ปิดเสียง
Else
'/ ส่งค่า KeyAscii ที่กดลงไปบนคีย์แต่ละตัว ไปให้กับฟังค์ชั่น CheckDigitOnly และส่งค่ากลับมา
'/ หากเป็นตัวเลขก็จะคืนค่า Ascii Code 48 - 57 (หรือคีย์ 0 - 9) กลับคืนมา
'/ หากไม่ใช่ ก็จะคืนค่า 0 กลับมา เสมือนว่าไม่มีการกดคีย์ใดๆเลย
KeyAscii = CheckDigitOnly(KeyAscii)
End If
End Sub
' / ---------------------------------------------------------------------------
' / ฟังค์ชั่นในการทำไฮไลท์เมื่อ TextBox ถูก Focus
' / ---------------------------------------------------------------------------
Public Sub HLText(ByRef sText)
On Error Resume Next
With sText
.SelStart = 0
.SelLength = Len(sText.Text)
End With
End Sub
' / ---------------------------------------------------------------------------
' / แก้ปัญหาเรื่อง SendKeys ตั้งแต่ Windows 8+
Public Sub Sendkeys(Text As String, Optional Wait As Boolean = False)
' / ---------------------------------------------------------------------------
Dim WshShell As Object
Set WshShell = CreateObject("Wscript.shell")
WshShell.Sendkeys Text, Wait
Set WshShell = Nothing
End Sub
' / ---------------------------------------------------------------------------
' / ฟังค์ชั่นในการตรวจสอบว่าคีย์ที่กดลงไปนั้นมันเป็น 0 - 9 หรือไม่
' / รับค่า KeyAscii จาก TextBox เข้ามาทีละตัว และเช็คค่า ASCII Code
' / หากเป็นตัวเลขก็คืนค่าตัวมันเองกลับ ก็คือยอมรับการกดคีย์นั่นเอง
' / หากไม่ใช่ก็คืนค่ากลับเป็น 0 เสมือนไม่มีการกดคีย์ใดๆนั่นเอง
Public Function CheckDigitOnly(ByVal Index As Integer) As Integer
'/ ---------------------------------------------------------------------------
Select Case Index
'/ ASCII Code หากมีค่า 48 - 57 ก็คือเลข 0 - 9 ก็คืนค่าตัวมันเองกลับไป
Case 48 To 57
Case 8, 13 ' Backspace = 8, Enter = 13
'/ หากไม่ใช่คีย์ที่กดใน 2 Case ด้านบน ก็คืนค่า 0 กลับไป เสมือนว่าไม่มีการกดคีย์ใดๆ
Case Else
Index = 0
End Select
CheckDigitOnly = Index
End Function
'/ ---------------------------------------------------------------------------
' / ฟังค์ชั่นในการตรวจสอบว่าคีย์ที่กดลงไปนั้นมันเป็น 0 - 9 และ . หรือไม่
' / และเครื่องหมายจุด (.) จะรับได้เพียงค่าเดียวเท่านั้น
Public Function CheckCurrency(Index As Integer, Ctrl As TextBox) As Integer
'/ ---------------------------------------------------------------------------
Select Case Index
' 0 - 9 and Return index = KeyAscii
Case 48 To 57
' Back Space and Return index = KeyAscii
Case 8
' Enter and Return index = KeyAscii
Case 13
Case 46 ' รหัส Ascii Codeของเครื่องหมายจุด
If InStr(Ctrl, ".") Then Index = 0 '/ ใช้ฟังค์ชั่น InStr (In String) เพื่อหาเครื่องหมายจุดใน TextBox
Case Else
Index = 0
End Select
CheckCurrency = Index ' Return ค่ากลับตามที่ได้ตรวจสอบ
End Function
'/ ---------------------------------------------------------------------------
' / ฟังค์ชั่นในการรับค่าตัวอักษรภาษาอังกฤษเท่านั้น
'/ ---------------------------------------------------------------------------
Public Function CheckAlphabet(Index As Integer) As Integer
Select Case Index
'/ ASCII Code A - Z (65 - 90), a - z (97 - 122)
Case 65 To 90, 97 To 122 '/ หรือค่าอื่นๆที่เราต้องการ , Asc(" "), Asc("-"), Asc("&"), Asc("."), Asc("*"), Asc("[ DISCUZ_CODE_0 ]quot;), Asc("/"), Asc("+"), Asc("%")
CheckAlphabet = Index
'/ Back Space
Case 8
'/ Enter
Case 13
'Case 42 ' *
'Case 43 ' +
'Case 45 ' -
'Case 46 ' .
'Case 47 ' /
Case Else
Index = 0
End Select
'/ Return ค่ากลับ
CheckAlphabet = Index
End Function
ดาวน์โหลดโค้ด VB6 (SP1) ฉบับเต็มได้จากที่นี่ ...
หน้า:
[1]