Foros del Web » Programando para Internet » PHP » PHP-GTK »

problema con gtk_main_quit

Estas en el tema de problema con gtk_main_quit en el foro de PHP-GTK en Foros del Web. Hola Tengo un pequeño problema, es el siguiente: Tengo una ventana que tiene asociada el método "destroy" al click de un boton. En el método ...
  #1 (permalink)  
Antiguo 12/12/2003, 06:12
Avatar de boricles  
Fecha de Ingreso: diciembre-2002
Mensajes: 53
Antigüedad: 22 años, 4 meses
Puntos: 0
problema con gtk_main_quit

Hola

Tengo un pequeño problema, es el siguiente:

Tengo una ventana que tiene asociada el método "destroy" al click de un boton. En el método "destroy" realizo un gtk_main_quit. Cuando realizo un destroy de dicha ventana desde otra ventana (no generada por la acción del usuario). El sistema omite el gtk_main_quit que se encuentra en la función destroy.

Sé que es algo bien raro y no sé cual puede ser la causa de este fenómeno.

Espero haber sido claro, disculpen pero siempre tuve problemas de redacción.

Saludos y gracias por adelantado

boricles
  #2 (permalink)  
Antiguo 12/12/2003, 15:33
Avatar de epplestun  
Fecha de Ingreso: octubre-2001
Mensajes: 1.621
Antigüedad: 23 años, 5 meses
Puntos: 5
Si me e enterado de lo que dices .... es por que gtk_main_qui esta asociada a toda la ventanam, y eso cierra la aplicacion, lo que deberias de usar es gtk_grab_add (si mal no recuerdo) y jugar con ello
__________________
Usuario registrado de Linux #288725
  #3 (permalink)  
Antiguo 15/12/2003, 07:10
Avatar de boricles  
Fecha de Ingreso: diciembre-2002
Mensajes: 53
Antigüedad: 22 años, 4 meses
Puntos: 0
Antes que nada gracias por responder.

Debo aclarar una cosa. Se omite la llamada del gtk_main_quit, pero no termina de ejecutarse la aplicación. Debido a que omite el código asociado a la función destroy, obtengo una violación de segmento.

La función que sugeriste la usé, junto con la gtk_grab_remove y tampoco me sirven, sigo con el mismo problema.

Gracias nuevamente y disculpa las molestias.
  #4 (permalink)  
Antiguo 15/12/2003, 13:48
Avatar de epplestun  
Fecha de Ingreso: octubre-2001
Mensajes: 1.621
Antigüedad: 23 años, 5 meses
Puntos: 5
veamos ....
Tu aplicacion seria algo como:
Código PHP:
<?PHP
dl
("php_gtk.so"); // o .dll segun el SO
function cerrar_programa() {
return 
gtk::main_quit();
}

$v = new GtkWindow();
$v->connect('destroy''cerrar_programa');

$b = new GtkButton('Cerrar ventana');
$b->connect('clicked''cerrar_programa');
$b->show();

$v->add($b);
$v->show_all();
gtk::main();
?>
Si te he entendido tu codigo seria ese asi k .... tu diras
__________________
Usuario registrado de Linux #288725

Última edición por epplestun; 15/12/2003 a las 13:49
  #5 (permalink)  
Antiguo 16/12/2003, 05:18
Avatar de boricles  
Fecha de Ingreso: diciembre-2002
Mensajes: 53
Antigüedad: 22 años, 4 meses
Puntos: 0
El codigo es el siguiente:

static gpointer destruir(GtkObject *objeto, gpointer data)
{
if (botonseleccionado==0)
gtk_main_quit();
}
static gpointer aceptar(GtkObject *objeto, gpointer data)
{
botonseleccionado=1;
gtk_widget_destroy(window);
gtk_main_quit();
}
static gpointer funcion a()
{
window=gtk_window_new(GTK_WINDOW_TOPLEVEL);
gtk_widget_show(window);
g_signal_connect(GTK_OBJECT(window),"destroy", G_CALLBACK(destruir),NULL);
botton=gtk_button_new_whith_label("boton");
gtk_widget_show(boton);
g_signal_connect(GTK_OBJECT(boton),"click", G_CALLBACK(aceptar),NULL);
gtk_main();

¡¡
¡¡
}
El caso es que si hago click en el boton si funciona el gtk_main_quit, pero si destruyo la ventana desde fuera, osea desde otra funcion, el gtk main_quit no funciona, porque he comprobado que pasa por ahi pero no funciona.


Gracias de nuevo, y disculpa por todo
  #6 (permalink)  
Antiguo 17/12/2003, 06:02
Avatar de epplestun  
Fecha de Ingreso: octubre-2001
Mensajes: 1.621
Antigüedad: 23 años, 5 meses
Puntos: 5
Veamos, tu aplicacion es solo eso?¿ Si es asi, es:

Una ventana
Dentro de la ventana un boton

El boton cierra la ventana, y la X cierra la ventana tb. En el signal destroy de la ventana metes la funcion que cierra la ventana, y en el signal clicked del boton asignas la misma funcion que la anterior.

No tiene mas.

Lo que no entiendo es cuando dices que cierras la ventana desde fuera, desde otra funcion .... eso no lo entiendo.

Saludos!
__________________
Usuario registrado de Linux #288725
  #7 (permalink)  
Antiguo 19/12/2003, 12:57
Avatar de boricles  
Fecha de Ingreso: diciembre-2002
Mensajes: 53
Antigüedad: 22 años, 4 meses
Puntos: 0
Gracias, me explico porque creo que no me explique bien, mi aplicacion no solo consiste en esto, sino que hay es donde reside mi problema, esa funcion funciona bien, y si destruyo la ventana desde esa función funciona, el problema es que yo esa ventana la tengo declarada global, y la puedo destruir desde otra funcion, y si la destruyo desde otra funcion, cuando se hace la señal destroy de la ventana no hace caso al gtk_main_quit.

Gracias y disculpa tantas molestias.
  #8 (permalink)  
Antiguo 21/12/2003, 15:15
Avatar de epplestun  
Fecha de Ingreso: octubre-2001
Mensajes: 1.621
Antigüedad: 23 años, 5 meses
Puntos: 5
Veamos ... supongo que lo estas haciendo con C asi que ... si declaras la variable que contiene la ventana como global podras acceder a ella sin ningun problema en principio, lo mismo pasara con la funcion que cierra la ventana, deberas declararla global o publica o como quieras ... para poder hacer uso de ella desde fuera, revisa eso a ver si es por ello.

Un saludo!
__________________
Usuario registrado de Linux #288725
  #9 (permalink)  
Antiguo 22/12/2003, 06:53
 
Fecha de Ingreso: diciembre-2003
Mensajes: 7
Antigüedad: 21 años, 4 meses
Puntos: 0
¿Has revisado los parámetros que pasas a la función cuando la llamas directamente?

No se si lo habrás probado, pero yo suelo sacar mensajes para depurar el código, por ejemplo:

static gpointer destruir(GtkObject *objeto, gpointer data)
{

g_print("Entra con %i\n", botonseleccionado);

if (botonseleccionado==0)
gtk_main_quit();
}

para ver si de verdad está llegando a entrar y con qué valores,

supongo que botonseleccionado tambien es global porque si no ...

Saludos
  #10 (permalink)  
Antiguo 23/12/2003, 05:33
Avatar de marcos25  
Fecha de Ingreso: noviembre-2002
Ubicación: España
Mensajes: 164
Antigüedad: 22 años, 5 meses
Puntos: 0
Gracias por responder,

Si lo he probado, y paso por la función, lo unico que no hace es el gtk_main_quit. y si es global la variable de botonseleccionado, y los parametros tambien estan bien, y no se me ocurre porque puede ser, porque simplemente ignora el gtk_main_quit.
__________________
Si gato feliX .... ratón tristeX
  #11 (permalink)  
Antiguo 23/12/2003, 09:31
 
Fecha de Ingreso: diciembre-2003
Mensajes: 7
Antigüedad: 21 años, 4 meses
Puntos: 0
¿Podría ser que estes ejecutando gtk_main() mas de una vez?

Cada vez que ejecutas un gtk_main() se abre un nuevo bucle, según vas haciendo gtk_main_quit() se van cerrando bucles empezando por el último que creaste.

"You can nest calls to gtk_main(). In that case gtk_main_quit() will make the innermost invocation of the main loop return"

Podrías probar a hacer un par o tres de gtk_main_quit() seguidos (solo para probar a ver si así se te destruye la ventana).

La instrucción: guint gtk_main_level (void); te da el numero de bucles abiertos hasta el momento (creo que empieza por el 0).

Saludos
  #12 (permalink)  
Antiguo 24/12/2003, 13:49
Avatar de epplestun  
Fecha de Ingreso: octubre-2001
Mensajes: 1.621
Antigüedad: 23 años, 5 meses
Puntos: 5
Buenas, nose como funcionara GTK con otros lenguajes de programacion, pero en lo que respecta a PHP si mal no recuerdo, y no me equivoco, haciendo un gtk::main_quit() cierras el programa y todas las ventanas que esten asociadas a esa misma. Lo que esta claro es que para trabajar con diferentes ventanas se ha de usar gtk::grab_add() y gtk::grab_remove() yo lo que suelo hacer es tener una funcion que me "destruya" la ventana que ami me interese, mediante:

Código PHP:
function close_window($widget){
        
$window $widget->get_toplevel();  
        
gtk::grab_remove($window);
        
$window->hide();

Y la ventana que muestro la genero con:

Código PHP:
function open_window(){
    
$this->gui['window'] = &new GtkWindow(GTK_WINDOW_DIALOG);
    
gtk::grab_add($this->gui['window']);
    
$this->gui['window']->connect('destroy', array(&$this'close_window'), $widget);
        
$this->gui['window']->show_all()

Es algo tan sencillo como eso, y supongo que no solo sera en PHP, sino en todos los lenguajes que usen GTK

Un saludete!
__________________
Usuario registrado de Linux #288725
  #13 (permalink)  
Antiguo 29/12/2003, 07:38
Avatar de boricles  
Fecha de Ingreso: diciembre-2002
Mensajes: 53
Antigüedad: 22 años, 4 meses
Puntos: 0
Cita:
Mensaje Original por gerar
¿Podría ser que estes ejecutando gtk_main() mas de una vez?

Cada vez que ejecutas un gtk_main() se abre un nuevo bucle, según vas haciendo gtk_main_quit() se van cerrando bucles empezando por el último que creaste.

"You can nest calls to gtk_main(). In that case gtk_main_quit() will make the innermost invocation of the main loop return"

Podrías probar a hacer un par o tres de gtk_main_quit() seguidos (solo para probar a ver si así se te destruye la ventana).

La instrucción: guint gtk_main_level (void); te da el numero de bucles abiertos hasta el momento (creo que empieza por el 0).

Saludos

Gracias, sabrias entonces como poder cerrar un gtk_main() concreto sin que tenga que ser el último.

Gracias anticipadas
  #14 (permalink)  
Antiguo 29/12/2003, 12:01
 
Fecha de Ingreso: diciembre-2003
Mensajes: 7
Antigüedad: 21 años, 4 meses
Puntos: 0
No se puede cerrar un gtk_main concreto, se deben ir cerrando al contrario de como se abrieron.
No se muy bien lo que hace tu programa, pero te explicaré lo que yo se sobre el main loop y tal vez así puedas resolver el problema. Por cierto, esto vale para cualquier lenguaje de programación, ya que el funcionamiento de GTK+ es el mismo para todos y las instrucciones te las pongo en C porque veo que es el lenguaje que tu estas utilizando.

Como sabes, en el modelo de programación por eventos, tu creas los widgets de tu aplicación y en un momento determinado tu programa se queda parado, esperando los eventos (señales) del sistema o del usuario (como puede ser un click sobre un boton, etc). Esto en GTK+ se gestiona con lo que se denomina "bucle de eventos" (main loop) que es un bucle interno desde donde GTK+ controla los estados de los elementos de la aplicación. Cuando tu haces gtk_main() estas cediendo el control de tu programa al main loop de GTK+.

El bucle de eventos de GTK+ es único, el hecho de que hagas varios gtk_main no genera nuevos bucles que manejas eventos distintos, de hecho todas las instancias de gtk_main() son funcionalmente idénticas, todas ellas vigilan la misma cola de eventos y el mismo bucle.

La utilidad de crear varias instancias de gtk_main() en un programa, suele ser simplemente para bloquear o parar el flujo del programa mientras no se produzcan ciertas condiciones, por ejemplo en un dialogo modal para mostrar un mensaje al usuario:

gtk_window_set_modal (GTK_WINDOW (dialog));
gtk_signal_connect (GTK_OBJECT (dialog), "destroy",
GTK_SIGNAL_FUNC (gtk_main_quit()), NULL);
gtk_widget_show (dialog);
gtk_main();

Si el usuario destruye este dialogo, se ejecuta un gtk_main_quit() que anula el gtk_main() del dialogo y nos devuelve al flujo normal del programa. Por tanto, siempre hay que ir haciendo pares de gtk_main y gtk_main_quit.

Nunca deberían producirse problemas como el que comentas si se utilizan los gtk_main para hacer algo sencillo como en el ejemplo anterior, para manejos mas complicados es mejor utilizar gtk_grab_add con la técnica que nos ha mostrado epplestun.

Por tanto, como verás, las ventanas de tu aplicación no están asociadas a ningún bucle gtk_main, simplemente lo que pasa es que cuando haces el último gtk_main_quit se cierra el bucle y se acaba el programa y en consecuencia se destruyen las ventanas que quedan vivas.

En cualquier caso, puedes jugar con gtk_main_level que te devuelve el numero de gtk_main() que quedan por cerrar, ya que cada vez que haces un gtk_main se suma uno al level y cada vez que haces un gtk_main_quit se resta uno al level.

Saludos
Atención: Estás leyendo un tema que no tiene actividad desde hace más de 6 MESES, te recomendamos abrir un Nuevo tema en lugar de responder al actual.
Respuesta




La zona horaria es GMT -6. Ahora son las 11:11.