none
Como ejecutar un metodo de un formulario hijo desde formulario padre RRS feed

  • Pregunta

  • Buenas tardes Amigos:

    Estoy trabajando en un proyecto y me he quedado estancado con este problema. Tengo un formulario contenedor MDI desde el cual llamo al formulario "Form1", asu vez este formulario contiene un botón (btn1) desde el cual llamo al formulario "Form2". Dado que deseo que Form2 sea contenido por el MDI lo instancio de esta manera.

    private void btn1_Click(object sender, EventArgs e)
            {
                Form2 formulario2 = new Form2();
                formulario2.MdiParent = this.MdiParent;
                formulario2.Show();
            }

    Adicionalmente en Form1 tengo un listview que es llenada con información de una base de datos. De esta manera, con su evento load, el Form2 ejecuta su método "MostrarTipos"; cabe resaltar que este método depende del valor del índice del listview del Form1. El valor del índice del listview en Form1 se lo paso al Form2 valiéndome de una variable global en Form2 llamada Form2.valorindice.

    Mi consulta es la siguiente: Lo que pretendo hacer es que cuando tenga abierto el Form2 y este variando el valor del índice del listview en Form1 me actualice lo que se muestra en Form2, es decir que ejecute el método "MostrarTipos" cada vez que se produzca el evento SelectedIndexChanged del listview. Revisando en la web he intentado hacerlo de la siguiente manera: 

    private void listview_SelectedIndexChanged(object sender, EventArgs e)
            {
                //Otras instrucciones
                //…..
                //…..
                
                // Codigo para verificar que el formulario deseado se encuentre abierto
                Form existe = Application.OpenForms.OfType<Form>().Where(pre => pre.Name == "Form2").SingleOrDefault<Form>();
                if (existe != null)
                {                               
                    Form2 formulario = new Form2();
                    formulario.MostrarTipos();                
                }           
                
            }

    Sin embargo no se observa ningún cambio en Form2 cada vez que cambio el valor del índice en el listview, también he verificado que el método en Form2 sea publico. Adicionalmente cree un botón en Form2 para ejecutar manualmente el método "MostrarTipos", de lo cual observo que si funciona correctamente.  

    Amigos les agradeceré cualquier ayuda que me puedan brindar para solucionar este problemita

    Saludos

    Raúl

    martes, 12 de marzo de 2019 21:09

Respuestas

  • Te explico por qué no funciona lo que has hecho:

                if (existe != null) {                              
                   
    Form2 formulario = new Form2();
                    formulario
    .MostrarTipos();               
               
    }  

    Fíjate que ejecutas "new" Form2. Eso instancia OTRA copia del formulario, que no se ve en pantalla porque no llamas a .Show, y luego invocas MostrarTipos sobre esa instancia oculta. Por lo tanto no se ve nada en la instancia visible que abriste antes.

    Solución: Tienes que llamar a formulario2.MostrarTipos(), siendo forrmulario2 la misma variable que usaste en btn1_Click cuando abriste esa instancia original del formulario. Obviamente eso implica que no puede ser una variable local al método btn1_click, tendrás que sacarla de ahí y darle la suficiente visibilidad para que pueda ser accesible desde el sitio donde quieras llamar a MostrarTipos.

    Si eso no te gusta, hay otra opción:

    Form2 f = Application.OpenForms.OfType<Form2>().SingleOrDefault<Form2>();
    if (f != null) f.MostrarTipos();
    

             

    miércoles, 13 de marzo de 2019 7:44
    Moderador
  • hola

    >>El valor del índice del listview en Form1 se lo paso al Form2 valiéndome de una variable global en Form2 llamada Form2.valorindice.

    por lo que veo no es una variable de instancia, si defines esta como "static" es incorrecto

    Deberias exponer una propiedad public y que sea

    Form2 frm2 = new Form2();
    
    frm2.Indice = ...;

    es a la instancia dle forma que debes asignar el valor

    >>cuando tenga abierto el Form2 y este variando el valor del índice del listview en Form1 me actualice lo que se muestra en Form2

    pero ya tienes desde el Form1 la instancia del Form2 puedes asignar directo el valor, quizas solo tengas que definir la instancia del form2 cambiando el ambito, o sea no en el metodo del evento sino a nivel del form

    private Form2 formulario2 = null; private void btn1_Click(object sender, EventArgs e) { formulario2 = new Form2(); formulario2.MdiParent = this.MdiParent; formulario2.Show(); } private void listview_SelectedIndexChanged(object sender, EventArgs e) { if(formulario2 != null) {

    formulario2.Indice = ...; formulario2.MostrarTipos(); } }

    cambiando la instancia del form2 en el form1 ya tienes acceso a este

    saludos


    Leandro Tuttini

    Blog
    MVP Profile
    Buenos Aires
    Argentina

    miércoles, 13 de marzo de 2019 13:38

Todas las respuestas

  • Te explico por qué no funciona lo que has hecho:

                if (existe != null) {                              
                   
    Form2 formulario = new Form2();
                    formulario
    .MostrarTipos();               
               
    }  

    Fíjate que ejecutas "new" Form2. Eso instancia OTRA copia del formulario, que no se ve en pantalla porque no llamas a .Show, y luego invocas MostrarTipos sobre esa instancia oculta. Por lo tanto no se ve nada en la instancia visible que abriste antes.

    Solución: Tienes que llamar a formulario2.MostrarTipos(), siendo forrmulario2 la misma variable que usaste en btn1_Click cuando abriste esa instancia original del formulario. Obviamente eso implica que no puede ser una variable local al método btn1_click, tendrás que sacarla de ahí y darle la suficiente visibilidad para que pueda ser accesible desde el sitio donde quieras llamar a MostrarTipos.

    Si eso no te gusta, hay otra opción:

    Form2 f = Application.OpenForms.OfType<Form2>().SingleOrDefault<Form2>();
    if (f != null) f.MostrarTipos();
    

             

    miércoles, 13 de marzo de 2019 7:44
    Moderador
  • hola

    >>El valor del índice del listview en Form1 se lo paso al Form2 valiéndome de una variable global en Form2 llamada Form2.valorindice.

    por lo que veo no es una variable de instancia, si defines esta como "static" es incorrecto

    Deberias exponer una propiedad public y que sea

    Form2 frm2 = new Form2();
    
    frm2.Indice = ...;

    es a la instancia dle forma que debes asignar el valor

    >>cuando tenga abierto el Form2 y este variando el valor del índice del listview en Form1 me actualice lo que se muestra en Form2

    pero ya tienes desde el Form1 la instancia del Form2 puedes asignar directo el valor, quizas solo tengas que definir la instancia del form2 cambiando el ambito, o sea no en el metodo del evento sino a nivel del form

    private Form2 formulario2 = null; private void btn1_Click(object sender, EventArgs e) { formulario2 = new Form2(); formulario2.MdiParent = this.MdiParent; formulario2.Show(); } private void listview_SelectedIndexChanged(object sender, EventArgs e) { if(formulario2 != null) {

    formulario2.Indice = ...; formulario2.MostrarTipos(); } }

    cambiando la instancia del form2 en el form1 ya tienes acceso a este

    saludos


    Leandro Tuttini

    Blog
    MVP Profile
    Buenos Aires
    Argentina

    miércoles, 13 de marzo de 2019 13:38
  • Hola Alberto, muchas gracias por tu respuesta y recomendaciones. La segunda opción funciono

    Saludos

    Raúl

    jueves, 14 de marzo de 2019 16:12
  • Hola Leandro, muchas gracias por tu ayuda. Probé como lo recomendaste y también funciona.

    Saludos

    Raúl

    jueves, 14 de marzo de 2019 16:14