简体   繁体   English

在VB.NET中创建动态控件数组

[英]Creating a dynamic control array in VB.NET

Regarding a post I found here about VB6 control arrays pseudo-duplicated in .NET ... here's the link to that posting. 关于我在这里找到的有关在.NET中伪复制的VB6控制数组的文章,这是该文章的链接。

How to create Control Arrays in VB .NET 如何在VB .NET中创建控件数组

I am in need (or at least I'm thinking I'm needing) of a control array using labels. 我需要(或至少我想我需要)使用标签的控制阵列。 I started working on a form using panels to contain 49 labels each. 我开始使用面板来处理表单,每个面板包含49个标签。 After I finished the 1st panel, I copied and pasted it to make another then another and so on. 在完成第一个面板后,我将其复制并粘贴到另一个面板上,依此类推。 On the first panel I named each label with a simple unique name Num1 for label1 Num2 for 2nd label and so on to Num49. 在第一个面板上,我为每个标签命名了简单的唯一名称Num1代表label1 Num2代表第二个标签,依此类推,直到Num49。 I need each panels labels to have all the same names which of course can't work. 我需要每个面板标签都具有相同的名称,但这当然是行不通的。 All the copies I made enumerated the labels using default Label names. 我制作的所有副本都使用默认的标签名称枚举了标签。 So I need a label control array to be able to change the labels forecolors and backcolors properties for each panel according to the text value in each label. 因此,我需要一个标签控件数组,以便能够根据每个标签中的文本值来更改每个面板的标签前色和背景色属性。 Example: I will search a database for records where say column1 contains the value "1" then I want to change each label Num1 in each panel and reset the fore and back colors to highlight them from they rest of the number labels.(1 thru 49) No here's the kicker ... I need the array to be dynamic. 示例:我将在数据库中搜索记录,其中column1包含值“ 1”,然后我想更改每个面板中的每个标签Num1并重置前后颜色,以从其余数字标签中突出显示它们。(从头到尾) 49)不,这是关键。我需要动态数组。 I won't know how many panels will be needed until after the sql search on the Dbase is finished. 在Dbase上的sql搜索完成之前,我不知道需要多少面板。 Once I get the number of records for all hits for "1" in column1 I will need to Dim or ReDim the label array to accommodate the number of returned records. 一旦获得了column1中所有“ 1”匹配项的记录数,我将需要对标签数组进行Dim或ReDim处理以容纳返回的记录数。 So for example say 20 records came back with "1" in column1, I would display 20 panels with the number "1" label in each panel highlighted from the rest of the number labels. 例如,假设20条记录返回的第1列带有“ 1”,我将显示20个面板,每个面板中的数字标签为“ 1”,其余数字标签中突出显示。 Each labels text value is just the numbers from 1-49. 每个标签文本值只是1-49中的数字。 This is just a simple example as I may be using more than one column in the search and highlighting more than just one number label. 这只是一个简单的示例,因为我可能在搜索中使用多个列并突出显示多个数字标签。 So I'm thinking this may not be possible. 因此,我认为这可能无法实现。 The answer given in the original posting I linked to above by Hans Passant was the one that caught my eye as being simple and easy to implement however I need it to be dynamic in that depending on how many records come back will determine how many panels will be needed and hence the size of the control array. 汉斯·帕桑特(Hans Passant)在上面链接到我的原始帖子中给出的答案是引起我注意的一个简单易行的答案,但是我需要它是动态的,因为要取决于返回的记录数将确定将要显示多少面板需要,因此控制数组的大小。 I don't think I will be needing any event handling so that might make it much easier but there is the possibility that I might decide to have the user be able to click on a number label which would change the data to be displayed. 我认为我不需要任何事件处理,这样可能会使事情变得容易得多,但是我可能决定让用户单击数字标签来更改要显示的数据。 ie. 即。 highlighting new labels with a refined search or a subset of the 1st search. 使用精细搜索或第一搜索的子集突出显示新标签。

Any ideas ...can it be done ? 任何想法...可以做到吗?

Here's the code snippet in Hans answer to create a control array of textboxes, the one without event handling. 这是汉斯答案中的代码片段,用于创建文本框的控件数组,其中没有事件处理。 I liked this one cuz it was simple as easy. 我喜欢这个,因为它很简单。

Public Class Form1 Private OrderNumbers() As TextBox 公共类Form1私有OrderNumbers()作为TextBox

Public Sub New()
    InitializeComponent()
    OrderNumbers = New TextBox() {TextBox1, TextBox2}
End Sub

End Class 最终班

Now can this be made to create x number of textboxes depending on how many records come back in my search. 现在可以根据搜索到的多少条记录来创建x个文本框。 The items in the braces would have to be variables of some sort dependent on the number of array elements required ? 花括号中的项目必须是某种变量,具体取决于所需的数组元素数量?

Journey, I've been slowly moving from VB6 to VB.NET and working on similar issues with having to build arrays for use in loops. 旅程,我一直在缓慢地从VB6迁移到VB.NET,并致力于解决类似的问题,必须构建用于循环的数组。 If the panels will be the same in appearance, you might try building one panel with the 49 labels with appropriate names so you can see what it will look like, then when you get the result of your search, dynamically add (or remove existing if doing a second search) panels with labels using the first panel as a template for spacing. 如果面板的外观相同,则可以尝试使用带有适当名称的49个标签构建一个面板,以便看到其外观,然后在获得搜索结果时动态添加(或删除现有的)进行第二次搜索),并使用第一个面板作为间距模板将带有标签的面板。 Then use panel Name and Label Name Substring to help identify the controls. 然后使用面板名称和标签名称子字符串来帮助识别控件。 Or if you know the upper limit for how many panels you will need, you can build them all and use the panel Visible property to show or hide them as needed. 或者,如果您知道需要多少个面板的上限,则可以全部构建它们,并根据需要使用面板的Visible属性显示或隐藏它们。

Suggestions for "appropriate names", use the "index number" as part of the name, using 0's for padding to get the same length for each name: Panels: pnl001, pnl002 ... 对于“适当名称”的建议,使用“索引号”作为名称的一部分,使用0填充以获取每个名称的相同长度:面板:pnl001,pnl002 ...

Labels: first 4 characters "lblN", next 3=Panel Number, last 2=Label Number, remember to NOT name other non-panel labels starting with "lblN" 标签:前4个字符“ lblN”,后3个=面板编号,后2个=标签编号,切记不要以“ lblN”开头命名其他非面板标签

in pnl001: lblN00101, lblN00102,...,lblN00149 在pnl001中:lblN00101,lblN00102,...,lblN00149

in pnl002: lblN00201, lblN00202,...,lblN00249 在pnl002中:lblN00201,lblN00202,...,lblN00249

Use Substring to get the "index". 使用子字符串获取“索引”。 Panel number for a label would be Val(vCtrl.Name.Substring(3, 3)) 标签的面板号为Val(vCtrl.Name.Substring(3,3))

If you decide to handle more complex results, if you store the panels in an array, vPnl(), you could make a subroutine to loop thru the panels with a For/Next, then loop thru the panel's controls and match the label names or their "index" last 2 characters with the search results. 如果决定处理更复杂的结果,如果将面板存储在数组vPnl()中,则可以创建一个子例程以使用For / Next循环通过面板,然后循环通过面板的控件并匹配标签名称或搜索结果的最后2个字符。

If you decide to make the labels "clickable", if you are dynamically adding the controls, at the same time you can add the Event Handler. 如果您决定使标签为“可单击”,并且要动态添加控件,则可以同时添加事件处理程序。 If the panels are built in design mode then the handler can be added using a loop in Form_Load so you don't have to remember to add the handler if you add more panels. 如果面板是在设计模式下构建的,则可以使用Form_Load中的循环添加处理程序,因此,如果添加更多的面板,则不必记住要添加处理程序。

AddHandler vCtrl(vF).DoubleClick, AddressOf lblN_DoubleClick AddHandler vCtrl(vF).DoubleClick,AddressOf lblN_DoubleClick

Here's a link to adding controls dynamically How to programmatically add controls to a form in VB.NET 这是动态添加控件的链接如何以编程方式将控件添加到VB.NET中的表单

To loop through the labels in the panels: 要遍历面板中的标签:

    Dim vPnl() As Panel ' get the count on records result, then load array

    'pass the search result count and value to test for to a subroutine
    Private Sub proResult(ByVal pResultCt as Integer,ByVal pTest as Integer)
     pResultCt=pResultCt+1
 ' arrays are zero based, add 1 so your loops can be For x=1 to pResultCt
     ReDim vPnl(pResultCt)

     'store the first panel using 1 as index
     vPnl(1)=pnl001
     'dynamically create the number of panels needed
     'store each Panel in vPnl() as you add them
     . . .
     ' or show them and hide the rest if the panels are already built
     '  if doing this way then store the Panels in vPnl() array in Form_Load
     '  and do not use the ReDim above, loop thru the form controls, count
     '  the panels, redim vPnl() using the count+1 so it does not have to be 0 based,
     ' loop thru the form controls again looking
     '  for panel names and use vPnl(VAL(vCtl.Name.Substring(3,3)))=vCtl

     'loop through the panels
     For vF=1 to pResultCt 
      'loop through the controls in the panel, looking for labels
      ' start names with distinct pattern like "lblN"
      ' for the 1-49 label names, like "lblN00101","lblN00102"
      For Each vCtrl As Control In vPnl(vF).Controls
       If vCtrl.Name Like "lblN*" Then
        'get the label "index", VB6 would be VAL(RIGHT(vCtrl.Name,2))
        ' be careful with Substring, the startIndex parameter is 0 based LEFT(vCtrl.Name,2)
        '  would be vCtrl.Name.Substring(0,2)

        vK = Val(vCtrl.Name.Substring(Len(vCtrl.Name) - 2, 2))

        ' now you have the "index" of this label, panel vF, label vK
        ' you could do an If/Then based on it
        If vK=pTest then
         vCtrl.BackColor=Color.Yellow
        Else
         vCtrl.BackColor=Color.White
        End If
        ' or store it in an array variable for future use
      Next
     Next
    End Sub

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM