vb.net deleting a label and textbox at runtime - vb.net

So i have a class that creates a new label and textbox when it is called. The names of each label and textbox are in a continues order counting upward using a variable called i:
"Label" & i creates the name Label1 and "Textbox" & i creates the name Textbox1
i += 1
And so on. Now i want to add a procedure that deletes the last label and textbox using i. I have tried to make this procedure using the lines of code below but this doesnt work as the string cannot be converted to system.windows.forms.control :
Form1.Controls.Remove("Label" & i)
Form1.Controls.Remove("Textbox" & i)
i -= 1
Controls is a list of controls using the line of code:
Public controls As List(Of Control)
Basically i need a way to delete a label and textbox using the variable i in the class. Any ideas? Thanks.

Try...
Form1.Controls.RemoveByKey("Label" & i)
Form1.Controls.RemoveByKey("Textbox" & i)
This does not work if you have these controls tucked in GroupBox, Panel, or some other container on your form.

I think you should try adding your controls into a panel, and then delete it as this link suggests (it's quite like what you tried, but inside a panel):
Removing Dynamically created controls in Panel

Related

Giving buttons different names through code and referring to them later on

My code creates a 5x5 grid of buttons. I am wanting to give each of these buttons different names "BtnColour1", "BtnColour2", etc. How do I give them all different names and how do I refer to each button later in the program?
Dim bytCounter As Byte
For bytCounter = 1 To 25
Dim btnColour As New Button
Me.Controls.Add(btnColour)
btnColour.Height = 50
btnColour.Width = 50
btnColour.Name = "btnColour" & bytCounter
btnColour.Enabled = False
btnColour.Left = ((bytCounter - 1) Mod 5) * 51
btnColour.Top = ((bytCounter - 1) \ 5) * 51
AddHandler btnColour.Click, AddressOf BtnClick
Your code (I guess you forgot the ending Next) does create 25 Buttons, with names btnColour1... btnColour25.
In the BtnClick event, to get the name of the clicked button, you should write something like:
Private Sub BtnClick(sender As Object, e As EventArgs)
Dim buttonName as string=CType(sender, Button).Name
'buttonName now has the clicked button name
End Sub
Of course, since you set the enabled property to False, your button click event will not fire.
In a general sense (and in addition to Spyros' answer, which is a good way to do it in an event handler - the sender is always the thing that raised the event), when you give a control a name and add it to a control's Controls collection, you can then retrieve it by that name later:
'Here you added the button to the form controls:
Me.Controls.Add(btnColour)
'later in the code you can ask for it back by name, for example:
Dim controls = Me.Controls.Find("btnColour1")
What you get back is an array of Controls. You get an array because Find can search all children (panels inside panels inside groupboxes inside forms etc) and it is thus conceivable that multiple controls in different panels will both have the same name. In your case if you know you only have one control called "btnColour1" it's safe to get it by array index:
Dim control = controls(0) 'controls variable is from the above Find
Lastly, remember that it comes back as a Control, the parent class for all controls. Because you know it's a button, it's safe to cast without check:
Dim button = DirectCast(control, Button)
Remember that if your property is available on the base Control class you don't even need a cast:
'here's a 1 line way to get the text of the button named btnColour1
'Find all controls named btnColour1, take the first, get the text
Dim t = Me.Controls.Find("btnColour1")(0).Text
If you want to refer to the buttons later in the program to change a setting without clicking the button, you can add each button to an array and call each of them with an index number:
Dim buttons(24) As Button
Then as the buttons are created, you can add each button to the array:
Dim bytCounter As Byte
For bytCounter = 1 To 25
Dim btnColour As New Button
Me.Controls.Add(btnColour)
buttons(bytCounter) = btnColour
you can then reference each button and their properties using the index number of the button in the array. You may also want to add a specific tag to each button to make each button more unique using:
btnColour.Tag = bytCounter

Is there anyway to save a multiple buttons as a list?

I am making small restaurant system project. I have 16 buttons as tables in the restaurant. I would like to change their colors or disable any of them when some events trigger (the form is loaded).
I save my button names in format TableX_ButtonY
I used a for-loop to change theirs border colors like this:
CType(Me.Controls.Find(String.Format("Table{0}Button{1}", i, x), True)(0), Button).FlatAppearance.BorderColor = Color.Blue
It will be great if I can save these buttons as a list, so I can manage it more easily.
I name their tags from 1 to 16 but I don't know how to use them correctly. Because the trigger not based on button click but rather based on the Load Form event.
Buttons are already in a collection and is a bit redundant to add them to a generic collection. In this example there are 2 buttons in a group controls collection, which could very well be any applicable container.
Dim ReservedTables() As Integer = {5, 10, 15, 20}
For Each Btn As Button In GroupBox1.Controls.OfType(Of Button)
If ReservedTables.Contains(CType(Btn.Tag, Integer)) Then
Btn.Enabled = False
End If
Next
Dim TableList As New List(Of Button)
TableList.Add(TableX_ButtonY)
For Each Table As Button in TableList
'do stuff
next
if you generated the buttons by using the designer, you can use the method you described in your question to add them all to the list

Visual Basic 2008 - Me.Controls - Textboxes - NULL -

Self taught(in progress) Visual Basic guy here.
I've searched for a clear answer on this, but so far have come up empty handed.
The problem...
I have two comboboxes. The first combobox has 10 options, second combobox has 2 options
I have 10 textboxes, with a name that includes one of the 10 options.
ex 1st textbox name - "txb_Option1Type"
2nd textbox name - "txb_Option2Type" and so on.
I have 2 tabs, with the first 5 text boxes on the 1st tab and last 5 on the 2nd tab.
I thought the following bit of code, upon a button click, would transfer the text of the chosen option in the 2nd combobox to the corresponding textbox...
`
Public Sub TransferTruckToDoorText()
Dim str_ErrorButton As String = cbx_DoorNumber.Text
Dim str_ReplaceSpacesButton As String = str_ErrorButton.Replace(" ", "")
Dim str_Button As String = str_ReplaceSpacesButton
' Null reference error on below line of code
Me.Controls("txb_" & str_Button & "Type").Text = cbx_TruckType.Text
End Sub
`
As noted in the above code, I'm getting a null reference and for the life of me cannot figure out why. I've stepped through the code, and I'm not able to find a NULL or Nothing value that could be making this catch.
Any and all help would be appreciated.
edited for clarity
The Me.Controls collection does not automatically search the child panels.
Try using the Controls.Find method for that, which includes a parameter to search the child control's control collection, too. It returns an array:
Dim c As Control() = Me.Controls.Find("txb_" & str_Button & "Type", True)
If c.Length = 1 Then
c(0).Text = cbx_TruckType.Text
End If
Me.Controls.Item("txb_" & str_Button & "Type")

String to Object as Expression

I have multiple TextBox controls Monday that will hold a value. I want to be able to add up all of the Monday textboxes and store that value as monTotal. I am getting an error message that says string cannot be converted to integer.
For i As Integer = 1 To rowCount Step 1
Dim var As Object
var = "txtMonday" & i & ".Text"
monTotal = monTotal + CInt(var)
Next
The way you are attempting to obtain a reference to the text boxes is not idiomatic of VisualBasic .NET.
var = "txtMonday" & i & ".Text" ' this is not a way to obtain a reference to the text box's text
While it would be possible to accomplish something like that using reflection, you'd be much better off refactoring your code to use an array of text boxes.
Since you are probably using Windows Forms you could perhaps implement logic to find the text box control you are interested in on the form using something like this:
' assuming container is the control that contains the text boxes
For Each ctrl In container.Controls
If (ctrl.GetType() Is GetType(TextBox)) Then
If ctrl.Name.StartsWith("txtMonday") Then
Dim txt As TextBox = CType(ctrl, TextBox)
monTotal = monTotal + CInt(txt.Text)
End If
End If
Next
The example above assumes that all the txtMonday.. text boxes are placed inside a control named container. That could be the form itself, or some other panel or table.
If all the textboxes live on the form and there are none being used for other text work you could use this. You could place all the textboxes that contain values your looking for in a separate container and get them like below, but use that control collection.
Dim amount As Double = 0
For Each tb As Textbox In Me.Controls.OfType(Of Textbox)()
amount += Convert.ToDouble(tb.Text)
Next
Dim monTotal as double=0
For Each ctrl As Control In Me.Controls
If TypeOf ctrl Is TextBox AndAlso ctrl.Name.StartsWith("txtMonday") Then
monTotal = monTotal + val(ctrl.Text)
End If
Next

Reversi VB.net logic behind it

I am trying to make the reversi game in VB.Net. I have some difficulties translating the game`s logic into vb.net
If a button is black and the button next to it is white,than the button next to the white one will be black wen pressed.
newButton.tag = colum of button + (row of button * amount of columns)
-> I made 64 buttons via a function loop and added a tag
Dim knop As Button = sender
Dim value As String = knop.Tag
If value = "...(?)" Then
knop.BackColor = Color.Black
If ....(?)
End If
End If
I already made a scheme with the label of the buttons, but I find it hard to implement the logic. Can someone help me out with thid one?
EDIT: http://i.stack.imgur.com/3gdrJ.png
If you use Dim ButtonList As List(Of List(Of Button)) and add the buttons to the form in runtime you can add each the button for each row to a list then add that list to ButtonList. Now you can access each button by the indexes in the 2 dimensional list.
Since you're changing the backcolor just use that instead of using the tag.