2011-01-19 16 views
15

Estoy usando Visual Studio 2010 con C#. ¿Hay algún concepto en el desarrollo de Windows Forms que enlace una etiqueta con un cuadro de texto? Algo para que se muevan juntos como una unidad? En el mundo ASP.NET, existe la propiedad AssociatedControlId del control de etiqueta. También creo recordar que el diseñador de formularios MS Access tiene alguna forma de asociar (o vincular) etiquetas con controles. ¿Esta característica incluso existe en el mundo de Visual Studio?WinForms: ¿Existe un concepto de asociación de una etiqueta con un cuadro de texto?

En caso negativo, ¿cómo se agrupan las etiquetas con controles de manera que si mueve un cuadro de texto no es necesario mover la etiqueta manualmente también?

Respuesta

7

No, no hay, al menos con los controles listos para usar. Si quieres esto, puedes lograrlo con un control de usuario.

En general, los winforms no se manejan en línea de la misma forma que HTML.

0

Si desea agrupar etiquetas con otros controles (o controles de grupo en general), utilice el control System.Windows.Forms.Panel. El propósito específico del control del Panel es group collections of controls.

Más informaciónPanel Class (System.Windows.Forms)

Si desea un mayor grado de control (en lugar de utilizar un Panel), entonces se podría crear un UserControl, que encapsula un Label y una Control.

1

I 2nd @Neils respuesta de simplemente crear un control de usuario con un cuadro de texto en él. El panel se puede usar para agrupar controles, pero puede ser bastante tedioso si tiene muchos controles en el formulario.

Si desea admitir más que solo cuadros de texto, WinForms le permite crear su propio diseñador. Si hereda su diseñador de la clase ParentControlDesigner, puede colocar cualquier control que desee en su control de etiqueta personalizado.

0

Creo que la mejor opción sería usar un GroupBox.

21

No parece haber una integrada. Sin embargo, puedes lanzar tu propia clase Field. A continuación se muestra un ejemplo completo.

using System; 
using System.Collections.Generic; 
using System.Linq; 
using System.Text; 
using System.Windows.Forms; 
using System.Drawing; 

namespace FieldClassTest 
{ 
    class Field : FlowLayoutPanel 
    { 
     public Label label; 
     public TextBox text_box; 

     public Field(string label_text) 
      : base() 
     { 
      AutoSize = true; 

      label = new Label(); 
      label.Text = label_text; 
      label.AutoSize = true; 
      label.Anchor = AnchorStyles.Left; 
      label.TextAlign = ContentAlignment.MiddleLeft; 

      Controls.Add(label); 

      text_box = new TextBox(); 

      Controls.Add(text_box); 
     } 
    } 

    static class Program 
    { 
     [STAThread] 
     static void Main(string[] args) 
     { 
      Application.EnableVisualStyles(); 
      Application.SetCompatibleTextRenderingDefault(false); 

      var form = new Form(); 

      var panel = new FlowLayoutPanel(); 
      panel.FlowDirection = FlowDirection.TopDown; 
      panel.Dock = DockStyle.Fill; 

      var first_name = new Field("First Name"); 
      panel.Controls.Add(first_name); 

      var last_name = new Field("Last Name"); 
      panel.Controls.Add(last_name); 

      form.Controls.Add(panel); 

      Application.Run(form); 
     } 
    } 
} 

Esto es lo que el programa de ejemplo se parece en mi sistema:

enter image description here

+0

Con el "control de campo" en el acceso, al hacer clic en la etiqueta se da el foco al cuadro de texto vinculado. También podría, en modo de diseño, mover libremente ambos controles (etiqueta y cuadro de texto). No voy a decir que este es un ejemplo de competencia ... –

+0

@DangerZone: puedes jugar con los paneles y el acoplamiento para que el cuadro de texto llene el control del usuario. – user5226582

0

Puede utilizar los métodos de extensión para hacerlo, seguir el ejemplo:

Private associatedLabels As New Dictionary(Of Control, Label)  
<Extension()> 
Public Sub AssociateLabel(ByVal control As Control, ByVal label As Label) 
    If (Not associatedLabels.ContainsKey(control)) Then 
     associatedLabels.Add(control, label) 
    End If 
End Sub 

<Extension()> 
Public Function GetAssociatedLabel(ByVal control As Control) As Label 
    If (associatedLabels.ContainsKey(control)) Then 
     Return associatedLabels(control) 
    Else 
     Throw New Exception("There is no associated label") 
    End If 
End Function 
0

Esta es mi solución , utilizando un TableLayoutPanel para colocar la etiqueta y el control de entrada,

presetted algunas propiedades útiles: tamaño

  • Auto etiqueta por contenido
  • etiqueta superior margen de vertical-align: medio como estilo
  • Fill permanecen espacio por control de entrada

de vista previa

preview

El código puede necesitar más envuelva

internal class TextBoxField : TableLayoutPanel 
{ 
    private readonly TextBox _textBox; 

    public string Text 
    { 
     get => _textBox.Text; 
     set => _textBox.Text = value; 
    } 

    public TextBoxField(string labelText) 
    { 
     var label = new Label { Text = labelText, AutoSize = true }; 
     var labelMargin = label.Margin; 
     labelMargin.Top = 8; 
     label.Margin = labelMargin; 
     _textBox = new TextBox { Dock = DockStyle.Fill }; 

     AutoSize = true; 

     ColumnCount = 2; 
     RowCount = 1; 
     ColumnStyles.Add(new ColumnStyle()); 
     ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 100F)); 
     RowStyles.Add(new RowStyle()); 
     Controls.Add(label, 0, 0); 
     Controls.Add(_textBox, 1, 0); 
    } 
} 

internal class DateTimePickerField : TableLayoutPanel 
{ 
    private readonly DateTimePicker _dateTimePicker; 

    public DateTime Value 
    { 
     get => _dateTimePicker.Value; 
     set => _dateTimePicker.Value = value; 
    } 

    public DateTimePickerField(string labelText) 
    { 
     var label = new Label { Text = labelText, AutoSize = true }; 
     var labelMargin = label.Margin; 
     labelMargin.Top = 8; 
     label.Margin = labelMargin; 
     _dateTimePicker = new DateTimePicker { Dock = DockStyle.Fill }; 

     AutoSize = true; 

     ColumnCount = 2; 
     RowCount = 1; 
     ColumnStyles.Add(new ColumnStyle()); 
     ColumnStyles.Add(new ColumnStyle(SizeType.Percent, 100F)); 
     RowStyles.Add(new RowStyle()); 
     Controls.Add(label, 0, 0); 
     Controls.Add(_dateTimePicker, 1, 0); 
    } 
} 

Uso:

var frm = new Form 
{ 
    AutoSize = true, 
    StartPosition = FormStartPosition.CenterParent, 
    Text = "Assoc Device", 
}; 

var txtGpsCode = new TextBoxField("GpsCode") { Dock = DockStyle.Bottom, TabIndex = 1 }; 
var dtp = new DateTimePickerField("Expire date") { Dock = DockStyle.Bottom, TabIndex = 2 }; 
var button = new Button { Text = "OK", DialogResult = DialogResult.OK, Dock = DockStyle.Bottom }; 

frm.Controls.Add(txtGpsCode); 
frm.Controls.Add(dtp); 
frm.Controls.Add(button); 

frm.AcceptButton = button; 

frm.Height = 0; 

frm.ShowDialog(); 
Cuestiones relacionadas