tutorial suscribirse example evento event delegate custom c# events

c# - suscribirse - ¿Cómo paso las variables a un método de evento de botones?



eventhandler c# tutorial (8)

¿No puede establecer una propiedad o variable miembro en el formulario que alberga el botón y acceder a ellos desde el evento de clic de botón?

EDITAR: sugerencia de clase de botón personalizado después de comentarios de retroalimentación (no es la misma sugerencia que la anterior)

class MyButton : Button { private Type m_TYpe; private object m_Object; public object Object { get { return m_Object; } set { m_Object = value; } } public Type TYpe { get { return m_TYpe; } set { m_TYpe = value; } } } Button1Click(object sender, EventArgs args) { MyButton mb = (sender as MyButton); //then you can access Mb.Type //and Mb.object }

Necesito poder pasar dos objetos al método que se está activando cuando hago clic en un botón. ¿Cómo hago esto?

Hasta ahora he estado buscando la creación de un evento cambiado Args:

public class CompArgs : System.EventArgs { private object metode; private Type typen; public CompArgs(object m, Type t) { this.metode = m; this.typen = t; } public object Metode() { return metode; } public Type Typen() { return typen; } }

Pero, ¿cómo lo usaría? ¿Es posible anular de alguna manera el evento de clic del botón para usar un controlador de eventos personalizado, que toma CompArgs como parámetro?

private void button1_Click(object sender, EventArgs e) { Assembly assembly = Assembly.LoadFile(@"c:/components.dll"); int counter = 0; foreach (Type type in assembly.GetTypes()) { if (type.IsClass == true) { Button btn = new Button(); btn.Location = new Point(174 + (counter * 100),10); btn.Size = new Size(95, 23); btn.Name = type.Name; btn.Text = type.Name; btn.UseVisualStyleBackColor = true; this.Controls.Add(btn); object obj = Activator.CreateInstance(type); //I need to pass on obj and type to the btn_Click btn.Click += new eventHandler(btn_Click); counter++; } } }

Y el evento-método donde lo necesito:

private void btn_Click(object sender, CompArgs ca) { MessageBox.Show((string)ca.Typen().InvokeMember("getMyName", BindingFlags.Default | BindingFlags.InvokeMethod, null, ca.Metode(), null)); }


Me gustaría crear un nuevo botón y anular el método OnClick. En lugar de pasar el EventArgs, pase una nueva clase derivada con sus miembros adicionales.

En el delegado que recibe el evento, convierta los EventArgs dados a la clase más derivada que espera obtener, o bien configure un nuevo Evento que se activará al mismo tiempo que se presiona el botón y conéctese a ese lugar para hacer cosas. más implícito

Código de ejemplo:

public partial class Form1 : Form { public Form1() { InitializeComponent(); ButtonEx b1 = new ButtonEx(); b1.OnCustomClickEvent += new ButtonEx.OnCustomClickEventHandler(b1_OnCustomClickEvent); } void b1_OnCustomClickEvent(object sender, ButtonEx.CustomEventArgs eventArgs) { string p1 = eventArgs.CustomProperty1; string p2 = eventArgs.CustomProperty2; } } public class ButtonEx : Button { public class CustomEventArgs : EventArgs { public String CustomProperty1; public String CustomProperty2; } protected override void OnClick(EventArgs e) { base.OnClick(e); if(OnCustomClickEvent != null) { OnCustomClickEvent(this, new CustomEventArgs()); } } public event OnCustomClickEventHandler OnCustomClickEvent; public delegate void OnCustomClickEventHandler(object sender , CustomEventArgs eventArgs); }


Necesitaría ver más código para dar una mejor respuesta, pero podría crear un evento que tome su CompArgs como parámetro y se active cuando se capture el botón Evento


No estoy seguro de si esto existe en Winforms pero sí en WPF: hay un objeto "etiqueta" en todos los controles a los que puede adjuntar cualquier objeto. Podría guardar el objeto que desea pasar y luego, en el caso de que el controlador lo lea, volver a sacarlo del objeto remitente.

private void Button_Click(object sender, RoutedEventArgs e) { var note = (sender as FrameworkElement).Tag as Note; //Do something with note here }


No puede usar su propia clase de argumento de evento personalizado para una firma de controlador de eventos predefinida. Al menos, el tipo de argumento de evento personalizado nunca será utilizado por ninguna llamada predeterminada al controlador (que solo será del tipo EventArgs en el caso de un botón); potencialmente, podría llamar al manejador usted mismo, pasando su tipo personalizado, sin embargo, tendría que tener lógica para volver a EventArgs un EventArgs al que se había convertido.

Como una posible solución (dependiendo de su situación), considere un tipo compuesto para encapsular los elementos que necesita, al igual que con su tipo de argumento de evento, pero mantenga la instancia requerida como una variable accesible que pueda utilizarse desde el controlador de eventos, o por lo menos, por el método / s que invoca el controlador incluso.

Por ejemplo, define tu tipo ...

public class MyType { public object AccessibleItem { get; set; } }

Y, en tu clase de forma ...

private MyType MyTypeInstance = new MyType(); private void Button_Click(object sender, EventArgs e) { //here we can set the item, if needs be... MyTypeInstance.AccessibleItem = new Anything(); //or access the item to use as required... DoSomeMagicWithMyObject(MyTypeInstance.AccessibleItem); }

EDITAR:

Bien, mirando su código actual, solo puedo ofrecerle esto por ahora (no agrega los elementos al contenedor de control de formularios y usa un iterador variable dentro de Linq (que creo que está mal visto o simplemente equivocado) (?), pero hey...):

private void BuildButtonToObjectDictionary() { int counter = 0; var assembly = Assembly.LoadFile(@"c:/components.dll"); var buttonToObjectDictionary = ( from type in assembly.GetTypes() where type.IsClass && !type.IsAbstract select new { Button = new Button { Name = type.Name, Text = type.Name, Size = new Size(95, 25), Location = new Point(175 + (counter * 100), 10), UseVisualStyleBackColor = true }, Item = Activator.CreateInstance(type), Index = counter++ }); }


Podrías usar la propiedad Tag del botón. Puede agregar un valor de cadena a esta propiedad desde la ventana de propiedades del diseñador y luego recogerlo dentro del controlador como sigue:

private void MyButton_Click(object sender, EventArgs e) { string tagValue = ((Button) sender).Tag; if(tag == "blah") { // Do something } }


Si abre el archivo de formulario.Designer.cs, verá todo el código generado automáticamente por VS. Aquí puede modificar el método llamado al hacer clic en el botón (o agregar un segundo método).

this.yourButton.Location = new System.Drawing.Point(211, 51); this.yourButton.Name = "yourButton"; this.yourButton.Size = new System.Drawing.Size(75, 23); this.yourButton.TabIndex = 0; this.yourButton.Text = "yourButton"; this.yourButton.UseVisualStyleBackColor = true; this.yourButton.Click += new System.EventHandler(this.yourMethodHere(object1, object2);

Espero que esto ayude.


Wow, ustedes están haciendo esto completamente difícil. No hay necesidad de ninguna clase personalizada o anulaciones de métodos. En este ejemplo, solo necesito pasar un número de índice de tabulación. Puede especificar lo que desee, siempre que su método espere ese tipo de valor.

button.Click += (sender, EventArgs) => { buttonNext_Click(sender, EventArgs, item.NextTabIndex); }; void buttonNext_Click(object sender, EventArgs e, int index) { //your code }