Page 1 of 1

Como saber si una venta Dialog esta abierta

Posted: Thu Mar 31, 2011 7:46 pm
by txon
Ahora que he empezado a trabajar con Dialogos NOWAIT, me encuentro con el problema que cada vez que pulso sobre la misma opcion del menu se me abre de nuevo una ventana de dialogo, previamente abierta, pudiendo tener el usuario abiertas las mismas ventanas vez tras vez.
¿Existe alguna funcion para saber si dicha ventana ya esta abierta, y si es afirmativo que devuelva un valor que me pueda servir para indicarselo al usuario, evitando que se vuelva a abrir?

Gracias de antemano.

Uns saludo.

Re: Como saber si una venta Dialog esta abierta

Posted: Thu Mar 31, 2011 9:16 pm
by armando.lagunas
Hola,

yo realizo lo siguiente:

en el programa main de tu aplicación coloca lo siguiente:

Code: Select all

#include "fivewin.ch"
memvar oApp
function main
public oApp
...
...
oApp:Taplication()
...
...
return nil

CLASS Taplication

   DATA aProc INIT {NIL,NIL,NIL,.....}    // n dialogos NOWAIT
   ...
   ...
ENDCLASS
 
y después al comienso de tu prg que contenga el dialogo NOWAIT
colocas esto:

Code: Select all

#include "fivewin.ch"

memvar oApp

function dialogonowait()

   IF oApp:aProc[1] = Nil   // el procedimiento, si es  nil quiere decir que lo has ejecutado una vez
       oApp:aProc[1] := ProcName() // a qui le asignas el nombre del procedimiento
   ELSE  
       MsgStop("Este procedimiento se encuentra activo") 
       RETURN Nil
   ENDIF
   ...
   ...
   DEFINE DIALOG oDlg RESOURCE ...
      ...
   ACTIVATE DIALOG NOWAIT CENTER VALID ( oApp:aProc[1]:=NIL, .T.) // aqui lo dejas nil al cerrar el dialog

RETURN nil
 
solamente cuando salgas del dialogo, ya sea con la "X" o ESC o la tecla que definiste como salida, se ejecuta el valid final del dialogo y la variable vuelve a quedar Nil, y asi puedes ejecutarlo nuevamente.

espero que me entiendas y te sirva, saludos

Re: Como saber si una venta Dialog esta abierta

Posted: Fri Apr 01, 2011 9:51 am
by txon
Armando, gracias por tu ayuda, creo que entiendo el sistema, voy a hacer unas pruebas.

Re: Como saber si una venta Dialog esta abierta

Posted: Fri Apr 01, 2011 1:20 pm
by Patricio Avalos Aguirre
Hola

Prueba de esta manera

Code: Select all

MENU oMenu POPUP 2007
MENUITEM "&Ciudades" ACTION NewTablas( oMenuItem ) FILE "IMAGEN\NEWIMG ciu16x16.bmp"
...
return 

//-----------------------------------------------------------
PROCEDURE NewTablas( oItem )

oItem:Disable()

ACTIVATE DIALOG NOWAIT CENTER VALID ( oItem:Enable(), .t. )

return
 

Re: Como saber si una venta Dialog esta abierta

Posted: Sat Apr 02, 2011 10:47 pm
by JmGarcia
Hola txon,

Yo uso esta función para ver las ventanas activas abiertas:

Code: Select all

local aTitles:={},aHandles:={},hWnd:=GETWINDOW(GETDESKTOPWINDOW(),GW_CHILD)
WHILE hWnd != 0 
   cTitle:=alltrim(GETWINDOWTEXT(hWnd))
   if cTitle<>""
      if IsWindowVisible(hWnd) .and. GETWINDOW(hWnd,GW_OWNER)==0 // Solo las ventanas visibles
         aadd(aTitles,cTitle)
         aadd(aHandles,hWnd)
      endif
   endif
   hWnd:=GETWINDOW(hWnd,GW_HWNDNEXT) 
ENDDO
Si cualquier título (variable cTitle) de dialogo/ventana coincide con el buscado ya sabes que esta abierto.

De todas formas el metodo de Armando esta muy bien.

Re: Como saber si una venta Dialog esta abierta

Posted: Mon Apr 04, 2011 1:37 pm
by MarioG
Amigos;
Les dejo el codigo de una clase, publica, desarrolada por Manuel Expósito Suarez

Code: Select all

//----------------------------------------------------------------------------//
//  AUTOR.....: Manuel Exp¢sito Su rez    Soft 4U '2001                       //
//  e-Mail....: maex14@dipusevilla.es                                         //
//  CLASE.....: TWCapture                                                     //
//  FECHA MOD.: 18/08/2001                                                    //
//  VERSION...: 1.00                                                          //
//  PROPOSITO.: Captura una ventana abierta por nuestro programa o por otra   //
//              aplicacion para poder enviarle mensajes como si fuera una     //
//              ventana mas de nuestro programa.                              //
//----------------------------------------------------------------------------//
//  DATAS.....: * lCapture tiene un valor logico, .f. si la ventana no se     //
//              pudo capturar y .t. si si se hizo                             //
//                                                                            //
//  METODOS...: * New( cTitle ) es el constructor, cTitle es el titulo de una //
//              ventana, si se le pasa intentara capturarla y pondra .t. en   //
//              ::lCapture                                                    //
//              * WCapture se encarga de buscar la ventana y asignarla a      //
//              nuestro objeto TWindow. Si la captura podremos interactuar    //
//              como si fuera una ventana mas de nuestra aplicacion           //
//                                                                            //
//  NOTAS.....: TWCapture esta heredada de TWindows por lo que tendremos a    //
//              nuestra disposicion todas las datas y metodos de esta clase.  //
//              No distingue entre mayusculas y minuscula pero si se tienen   //
//              en cuenta los espacios                                        //
//----------------------------------------------------------------------------//

#include "Objects.ch"

//----------------------------------------------------------------------------//

CLASS TWCapture FROM TWindow

    DATA lCaptured  AS LOGICAL

    METHOD New( cTitle ) CONSTRUCTOR
    METHOD WCapture( cTitle )

ENDCLASS

//----------------------------------------------------------------------------//

METHOD New( cTitle ) CLASS TWCapture

    if( ValType( cTitle ) == "C", ::WCapture( cTitle ), ::lCaptured := .f. )

return( Self )

//----------------------------------------------------------------------------//

METHOD WCapture( cTitle ) CLASS TWCapture

   local hWnd := FindWindow( 0, cTitle )

   ::lCaptured := ( hWnd > 0 )
   ::hWnd := if( ::lCaptured, hWnd, 0 )

return( ::lCaptured )

//----------------------------------------------------------------------------//
 
un sample:

Code: Select all

//----------------------------------------------------------------------------//
// TWCapture by Manu Exposito
// Demo02 de la clase TWCapture
//----------------------------------------------------------------------------//

#define CRLF chr( 13 ) + chr( 10 )

function Main()

    local oWnd := TWCapture():New()
    local cTitle := space( 40 )

    oWnd:WCapture( "demo02 - bloc de notas" )

    if !oWnd:lCaptured      // Si no esta la ventana la ejecutamos nosotros
        WinExec( "NotePad.exe demo02.prg" )
        oWnd:WCapture( "demo02 - bloc de notas" )  // y la capturamos
    endif

    Jugar( oWnd )

return nil

//----------------------------------------------------------------------------//

static function Jugar( oWnd )

        local cTitle := oWnd:cTitle

        if oWnd:lCaptured

            MsgAlert( "Muy bien, ya lo tenemos" + CRLF + ;
                      "_ la ventana con titulo: " + cTitle + ;
                      CRLF + "Ahora vamos a jugar con ella" )

            MsgInfo( "La centramos" )
            oWnd:Center()

            MsgInfo( "Pinto una linea" )
            oWnd:Line( 0, 0, 500, 500 )

            MsgInfo( "La desplazo arriba a la izquierda" )
            oWnd:Move( 0, 0 )

            MsgInfo( "Ahora minimizo" )
            oWnd:Minimize()

            MsgInfo( "Ahora maximizo" )
            oWnd:Maximize()

            MsgInfo( "La restauro" )
            oWnd:Restore()

            MsgInfo( "Ahora cambio titulo" )
            oWnd:SetText( "TWCapture captura ventanas - by Manu Exposito 2001" )

            MsgInfo( "Ahora la oculto" )
            oWnd:Hide()

            MsgInfo( "Ahora la muestro" )
            oWnd:Show()

            MsgInfo( "y ahora termino" )
            oWnd:End()

        else

            MsgStop( "No se pudo capturar ninguna ventana" )
            oWnd := nil

        endif

return( nil )

//----------------------------------------------------------------------------//
 

Re: Como saber si una venta Dialog esta abierta

Posted: Mon Apr 04, 2011 3:54 pm
by Silvio
nooooo
use simply the theorie of josè of alanit

CLASS tApplication
DATA oDlg


and then

Function test()

if oApp():oDlg != nil
if oApp():nEdit > 0
return nil
else
oApp():oDlg:End()
SysRefresh()
endif
endif


your procedure

return nil

if yoy make an operation sample an insert or modiy
you must insert
oApp():nEdit ++
and then at end
oApp():nEdit --


it run ok

search on alanit website the fsdi class

Re: Como saber si una venta Dialog esta abierta

Posted: Tue Apr 05, 2011 11:39 am
by txon
En primer lugar gracias a todos por vuestra ayuda.

Finalmente me en decidido por el sistema de Armando, y he aprovechado para hacer algunas modificaciones que espero que a alguien mas le resulten utiles.

1) En nuestro procedimiento main()

Code: Select all

FUNCTION Main()

oApp:TAplicacion()
*
*
RETURN nil
 
2) Creamos la clase

Code: Select all

// Clase para guarda los dialogos abiertos y asi evitar que se dupliquen

CLASS TAplicacion

    // Nº Procedimientos abiertos (En este caso maximo 10)

    DATA aProc INIT {nil,nil,nil,nil,nil,nil,nil,nil,nil,nil}

ENDCLASS
 
3) Creamos una funcion que comprueba los procedimientos

Code: Select all

// Comprobacion de procedimientos abiertos (nNombre -> Nombre del procedimiento a comprobar, nMaximo -> Nº de veces que puede estar abierto a la vez)

FUNCTION FAplicacion(nNombre,nMaximo)

    Local i
    Local nProc:=0  // Numero de procedimientos abiertos
    Local nVeces:=0 // Numero de veces que esta abierto el mismo procedimiento

    // Comprueba si existe procedimiento
    FOR i=1 TO LEN(oApp:aProc)
        IF oApp:aProc[i] == nNombre
             nVeces++
        ENDIF
        nProc:=nProc+IIF(oApp:aProc[i]==nil,0,1)
    NEXT i

    IF nVeces>=nMaximo
         MsgAlert("Este procedimiento ya está abierto "+STR(nVeces,2)+" veces","Aviso")
         RETURN 0
    ENDIF

    // En caso de que no exista o no sobrepase el maximo de veces, comprueba nº maximo de procedimientos abiertos
    IF nProc>=LEN(oApp:aProc)
         MsgAlert("Máximo nº de procedimientos abiertos "+STR(LEN(oApp:aProc),2)+", no puede abrir más."+CRLF+"Cierre alguno que no esté utilizando.","Aviso")
         RETURN 0
    ENDIF

    // Guardamos nuevo procedimiento
    FOR i=1 TO LEN(oApp:aProc)
        IF oApp:aProc[i]==nil
             oApp:aProc[i]:=nNombre
             EXIT
        ENDIF
    NEXT i

RETURN i // Devolvemos el numero de posicion de nuestro procedimiento en el array aProc[]
 
4) Desde cada uno de nuestros programas llamamos a la funcion FAplicacion()

Code: Select all

FUNCTION MiPrograma()

Local nProc 

    // Comprobamos si el procedimiento esta abierto
    nProc:=FAplicacion(ProcName(),2)  // Guardamos el nº de posicion de la tabla de procedimientos aProc[]
    IF nProc==0
         RETURN cCod
    ENDIF

        DEFINE DIALOG oDlg RESOURCE ...
               *
               *
         ACTIVATE DIALOG oDlg CENTER ;
              VALID (oApp:aProc[nProc]:=nil,.t.) // Nos aseguramos de dejar el procedimiento vacio

 
Un saludo a todos y gracias por vuestra ayuda