Makale Özeti

Makale ip girişini kolaylaştırılmak için oluşturulmuş bir kontrolü anlatıyor

Makale

   Merhabalar;

   Sizlerle bu makalemde kendimize ait bir kontrolün nasıl yaratılacağı ve bu kontrole çeşitli özelliklerin nasıl katılacağını inceleyeceğiz. Örnek olarak gayet başarılı tasarlanmış ve birçok sınama ve kontroller arası geçiş barındıran bir kontrol olan IpTextBox ı yeniden yazacağız.

   Bir kontrolü yazmadan önce özelliklerini, çalışma prensibini çok iyi analiz etmek gerekmektedir. IpTextBox ın özelliklerini listeleyecek olursak;
      1-Dört Adet textbox içermektedir ve bu textbox lara sadece rakam yazılabilmektedir.
      2-Space(Boşluk) tuşuna basıldığında bir sonraki textbox a geçmeli ve textboxtaki karakterleri seçmelidir.Ancak karakterler seçiliyken space tuşu bu işlevi gerçekleştirmemektedir.
      3-Sağ ve sol yön tuşları ile cursor textboxlar arasında geçiş yapılabilmektedir. Ancak textbox dolu ise cursorun ilk önce o textbox ın elemanları arasında hareket etmesi gerekmektedir.
      4-Bir textbox 3 karakter aldığında cursoru direkt yanındaki textbox a taşımaktadır ve yanındaki textbox dolu ise tümünü seçmektedir
      5-İlk textbox 1 ile 223 diğerleri ise 0 ile 255 arası değerler almalıdır.

   Kontrolümüzü yaratabilmek için Vs.Net te yeni bir proje açıyoruz proje tipi olarak ise Windows Control Libraryi seçiyoruz ve projemizin ismini myIpTextBox veriyoruz.
   

   Karşımıza açılan kontrol penceresine dört tane textbox koyuyoruz ve aralarına üç tane label koyuyoruz. Textboxların TextAlign özelliğini center, MaxLength özelliğini 3 yapıyoruz, boyutlarını şekildeki gibi ayarlıyoruz ve isimlerini ipTextBox1,ipTextBox2,ipTextBox3,ipTextBox4 veriyoruz ve yarattığımız Label ların Text Özelliğini . yapıyoruz ve fontunu büyüterek şekildeki gibi boyutlandırıyoruz.
   

   Artık Kontrolümüze çift tıklayarak Kod sayfasını açarak belirlediğimiz özellikler için kodlarımızı yazmaya başlayabiliriz.

Public Class myIpTextBox
   Inherits System.Windows.Forms.UserControl

+ Windows Form Designer generated code
   Dim ipTextBoxes(3) As TextBox
   Dim ipLabels(2) As Label
   Bu kısımda kontrolümüzü tanımlayan ve Vs.Net tarafından oluşturulan kodları görüyoruz ve biri labellarımızı biri ise textboxlarımızı taşımak üzere tasarladığımız iki tane dizi yaratıyoruz. Bu diziler ileride her textbox için ayrı ayrı kod yazmamızı engelleyecek ve daha genel yapılarda iş yapabilmemize faydalı olacak ve bize büyük kolaylık sağlayacaktır.

   Private Sub myIpTextBox_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
      ipTextBoxes(0) = Me.ipTextBox1
      ipTextBoxes(1) = Me.ipTextBox2
      ipTextBoxes(2) = Me.ipTextBox3
      ipTextBoxes(3) = Me.ipTextBox4

      ipLabels(0) = Me.ipLabel1
      ipLabels(1) = Me.ipLabel2
      ipLabels(2) = Me.ipLabel3

      For Each tb As TextBox In ipTextBoxes
         AddHandler tb.KeyPress, AddressOf eKeyPress
         AddHandler tb.KeyDown, AddressOf eKeyDown
         AddHandler tb.TextChanged, AddressOf eTextChanged
         AddHandler tb.LostFocus, AddressOf eLostFocus
      Next
   End Sub

   Dizilerimize kontrolümüzde bulunan nesneleri atıyoruz ve textbox dizisi elamanları arasında dolaşarak her bir elemanın KeyPress,Keydown,TextChanged,LostFocus olaylarını kendi belirlediğimiz tek bir fonksiyona atıyoruz. Bu işlem het textboxın olayları için ayrı ayrı kod yazmamızı engelleyecektir.

   Sub eLostFocus(ByVal sender As Object, ByVal e As System.EventArgs)
      If Not (CType(sender, TextBox).Text.Length = 0 Or CType(sender, TextBox).Text.Length = 3) Then
         If Not eValidate(sender, e) Then
            CType(sender, TextBox).Focus()
         End If
      End If
   End Sub

    Herhangi bir textboxımız focus u kaybetttiği zaman kontrolun loadında belirttiğimiz gibi bu sub çalışacaktır. Bu sub ise focus u kaybeden textbox ın içeriği boş değilse vede 3 karakter barındırmıyorsa eValidate isimli sub ımızı çağırıp içeriğin 5. maddemizde belirtilen sayı kriterlerine uygun olup olmadığını kontrol eden sub dır. Üç karakterde bu işlemin gerçekleşmeme sebebi ise 3. karakter yazıldıgı zaman zaten focus un program tarafından başka bir nesneye aktarılmasıdır. Eğer eValidate fonksiyonundan dönen değer olumsuzsa focus aynı nesne üzerinde kalacaktır. eValidate fonksiyonu yazıldığı yerde daha detaylı incelenecektir.

   Sub eTextChanged(ByVal sender As Object, ByVal e As System.EventArgs)
      If CType(sender, TextBox).Text.Length = 3 Then
         If eValidate(sender, e) Then
            If Not ipTextBoxes.IndexOf(ipTextBoxes, sender) = ipTextBoxes.Length - 1 Then
               ipTextBoxes(ipTextBoxes.IndexOf(ipTextBoxes, sender) + 1).Focus()
               ipTextBoxes(ipTextBoxes.IndexOf(ipTextBoxes, sender) + 1).SelectAll()
            End If
         End If
      End If
   End Sub

    Textboxlarımızdan herhangibirinin içindeki metin değiştiğinde tetiklenecek bu subda ise değişmiş metin üç karakterden oluşuyorsa ve eValidate fonksiyonunda belirtilen kriterler sağlanıyorsa yani true dönüyorsa focus bir sonraki nesneye verilecektir ve bir sonraki nesnede bulunan metin seçilecektir. Ancak bu işlem 4 adet textbox dizimizin en son elemanı için yapılmayacaktır.

   Function eValidate(ByVal sender As Object, ByVal e As System.EventArgs) As Boolean
      Dim minValue As Int16
      Dim maxValue As Int16
      If ipTextBoxes.IndexOf(ipTextBoxes, sender) = 0 Then
         minValue = 1
         maxValue = 223
      Else
         minValue = 0
         maxValue = 255
      End If
      If CType(sender, TextBox).Text.Length > 0 Then
         If Not (Convert.ToInt16(CType(sender, TextBox).Text) >= minValue And Convert.ToInt16(CType(sender, TextBox).Text) <= maxValue) Then
            MessageBox.Show(minValue.ToString & " ile " & maxValue.ToString & " arası bir sayı girin")
            CType(sender, TextBox).SelectAll()
            Return False
         Else
            Return True
         End If
      Else
         Return True
      End If
   End Function

    Kontrol yaptığımız bu fonksiyonda eğer fonksiyona parametre olarak gelen nesne textbox dizimizdeki ilk nesne ise kontrol kriteri 1 ve 223 olarak eğer başka bir nesne ise 0 ve 255 olarak belirlemiyor ve gönderilen nesnedeki değerin bu aralıkta olup olmadığı kontrol ediliyor. eğer cevap olmsuz ise kullanıcıya bir messagebox gösteriyoruz ve içinde bulunduğu nesnenin metnin seçtiriyoruz, fonksiyonumuz ise geriye false değer döndürüyor. Eğer kriter sağlanmış ise geriye true değeri döndürüyoruz.

   Sub eKeyDown(ByVal sender As Object, ByVal e As System.Windows.Forms.KeyEventArgs)
      If e.KeyCode = 39 Then
         If Not ipTextBoxes.IndexOf(ipTextBoxes, sender) = ipTextBoxes.Length - 1 Then
            If CType(sender, TextBox).SelectionStart = CType(sender, TextBox).Text.Length Then
                If eValidate(sender, e) Then
                  ipTextBoxes(ipTextBoxes.IndexOf(ipTextBoxes, sender) + 1).Focus()
                End If
            End If
         End If
      ElseIf e.KeyCode = 37 Then
         If Not ipTextBoxes.IndexOf(ipTextBoxes, sender) = 0 Then
            If CType(sender, TextBox).SelectionStart = 0 Then
                If eValidate(sender, e) Then
                  ipTextBoxes(ipTextBoxes.IndexOf(ipTextBoxes, sender) - 1).Focus()
               End If
            End If
         End If
      End If
   End Sub

    Bu subımızda ise sağ veya sol yön tuşlarıyla yapabileceğimiz nesneler arası geçişi kontrol ediyoruz. Bir nesnenin son elamanına gitmeden diğer nesneye geçmek mümkün olmuyor.

   Sub eKeyPress(ByVal sender As Object, ByVal e As System.Windows.Forms.KeyPressEventArgs)
      If Asc(e.KeyChar) >= 48 And Asc(e.KeyChar) <= 57 Then
         e.Handled = False
      ElseIf Asc(e.KeyChar) = 32 Then
         If Not ipTextBoxes.IndexOf(ipTextBoxes, sender) = ipTextBoxes.Length - 1 And CType(sender, TextBox).SelectionLength = 0 Then
            If eValidate(sender, e) Then
               ipTextBoxes(ipTextBoxes.IndexOf(ipTextBoxes, sender) + 1).Focus()
               ipTextBoxes(ipTextBoxes.IndexOf(ipTextBoxes, sender) + 1).SelectAll()
            End If
         End If
         e.Handled = True
      ElseIf Asc(e.KeyChar) = 8 Then
         If CType(sender, TextBox).Text.Length = 0 And ipTextBoxes.IndexOf(ipTextBoxes, sender) > 0 Then
            ipTextBoxes(ipTextBoxes.IndexOf(ipTextBoxes, sender) - 1).Focus()
            ipTextBoxes(ipTextBoxes.IndexOf(ipTextBoxes, sender) - 1).SelectionStart = CType(ipTextBoxes(ipTextBoxes.IndexOf(ipTextBoxes, sender) - 1), TextBox).Text.Length
         End If
         e.Handled = False
      Else
         e.Handled = True
      End If
   End Sub

    Bu kısımda ise textboxımız üzerinde yapılabilecek temel sınırlandırmaları yapıyoruz. Herhangi bir tuşa basıldığında devreye giren bu sub ascii kodu sadece 48 ile 57 arası olan yani sadece rakamlar olan karakterleri kabul ediyor,ascii kodu 32 olan space tuşunda ise bir yandaki kontrole geçiyor ve ascii kodu 8 olan backspace tuşunada izin veriyoruz diğer bütün tuşların basılmasında bu tuşların basılmasını iptal ediyoruz.

   Private Sub eBackColorChanged(ByVal sender As Object, ByVal e As EventArgs) Handles MyBase.BackColorChanged
      For Each tb As TextBox In ipTextBoxes
         tb.BackColor = Me.BackColor
      Next
      For Each lb As Label In ipLabels
         lb.BackColor = Me.BackColor
      Next
   End Sub

   Bu kısmında ise kontrolümüzün rengi değiştiği zaman içinde bulunan textbox ve labellarında arka renginin değişmesi için gerekli kodumuzu yazıyoruz.

   Private Sub eForeColorChanged(ByVal sender As Object, ByVal e As EventArgs) Handles MyBase.ForeColorChanged
      For Each tb As TextBox In ipTextBoxes
         tb.ForeColor = Me.ForeColor
      Next
      For Each lb As Label In ipLabels
         lb.ForeColor = Me.ForeColor
      Next
   End Sub

   Bu kısmında ise kontrolümüzün rengi değiştiği zaman içinde bulunan textbox ve labellarında ön renginin değişmesi için gerekli kodumuzu yazıyoruz.

   Private Sub eFontChanged(ByVal sender As Object, ByVal e As EventArgs) Handles MyBase.FontChanged
      For Each tb As TextBox In ipTextBoxes
         tb.Font = Me.Font
      Next
      For Each lb As Label In ipLabels
         lb.Font = Me.Font
      Next
   End Sub

   Bu kısmında ise kontrolümüzün rengi değiştiği zaman içinde bulunan textbox ve labellarında fontunun değişmesi için gerekli kodumuzu yazıyoruz.

   Private Sub ipTextBox_Resize(ByVal sender As Object, ByVal e As System.EventArgs) Handles MyBase.Resize
      Dim txtWidth As Integer = CInt((Me.Width - (ipLabel1.Width * 3)) / 4)
      Dim txtTop As Integer = CInt((Me.Height - ipTextBox1.Height) / 2)

      ipTextBox1.Top = txtTop
      ipTextBox2.Top = txtTop
      ipTextBox3.Top = txtTop
      ipTextBox4.Top = txtTop

      ipTextBox1.Width = txtWidth
      ipTextBox2.Width = txtWidth
      ipTextBox3.Width = txtWidth
      ipTextBox4.Width = txtWidth

      ipLabel1.Top = txtTop
      ipLabel2.Top = txtTop
      ipLabel3.Top = txtTop

      ipLabel1.Height = ipTextBox1.Height
      ipLabel2.Height = ipTextBox1.Height
      ipLabel3.Height = ipTextBox1.Height

      ipLabel1.Left = ipTextBox2.Left - ipLabel1.Width
      ipLabel2.Left = ipTextBox3.Left - ipLabel2.Width
      ipLabel3.Left = ipTextBox4.Left - ipLabel3.Width

      ipTextBox1.Left = 0
      ipTextBox2.Left = ipTextBox1.Left + ipTextBox1.Width + ipLabel1.Width
      ipTextBox3.Left = ipTextBox2.Left + ipTextBox2.Width + ipLabel2.Width
      ipTextBox4.Left = ipTextBox3.Left + ipTextBox3.Width + ipLabel3.Width
    End Sub
End Class

   Bu kısmında ise kontrolümüzün boyutu değiştiği zaman içinde bulunan textbox ve labellarında yeni kontrol boyuna göre yeniden boyutlandırılması için gerekli kodumuzu yazıyoruz.

   Bu kısımdan sonra projemizi build ediyoruz veya çalıştırıyoruz.Bunun sonucunda bin klasörü altında yaratılmış olan dll dosyamızı tamamen faklı bir projemize veya aynı solutionda başka bir projeye eklemek sureti ile bu kontrolü direkt kullanabilir hale geliyoruz.

   Bu makaleye ait kodları ve örnekleri indirmek için tıklayınız
Tamer ÖZ

oztamer@hotmail.com
tamer.oz@yazgelistir.com
oztamer@hotmail.com