Consulta: Api ejecutar programa devolviendo hwnd, obtener sus ventanas...

Iniciado por ‡‡‡ Ðξλ†Ћ Щλ†ζЋ ‡‡‡, 30 Noviembre 2009, 06:06 AM

0 Miembros y 1 Visitante están viendo este tema.

‡‡‡ Ðξλ†Ћ Щλ†ζЋ ‡‡‡

Hola, como estan:  ;D

Vengo en busca de su ayuda, pues llevo varias semanas buscando y leyendo sobre lo que a continuacion les consultaré, y no consigo resolverlo.  :-[

Estoy haciendo una aplicacion en VB para automatizar bastantes procesos, con la intencion de ahorrarnos a un cuate y a mi, un tiempo considerable, en un procedimiento que hacemos muy a menudo, alla en el trabajo.  :P  :P

Ya llevo una buena parte del codigo, el problema es que estoy atorado con las api's, porque aunque me encuentro una e investigo como se usa, no se cuales son las que realmente necesito.

Los detalles estan asi: (mas adelante pondre algunos ejemplos, de varias pruebas que he hecho, pero que no le he encontrado el resultado que busco)

1.- Estoy buscando una api que ejecute un programa, y al mismo tiempo, me devuelva su hwnd, su classname, o de a perdis, su caption.
2.- Una vez que esa api me regreso alguno de los 3 valores que comente antes, que api debo usar, que me permita visualizar sus botones, controles, y demas, para manipularlos, x ej, presionar el boton Aceptar, u obtener o asignar texto a una caja de texto determinada.
3.- Obtener la(s) subventana(s), de la ventana (o programa que se ejecuto), para manipular los controles de tales subventanas.

Como adicional:
4.- Muchos de esos programas a ejecutar, estan en una unidad de red, y quiero hacer un proceso que me este monitoreando si todavia esta "conectada" la unidad de red. Que me recomiendan: usar el filesystemobject y DriveExists, o una api como el winsock, u otra, si consideran mas efectiva?

5.- Tomando en cuenta el punto anterior, tengo el programa en VB que esta ejecutando todos los procesos que debe. Ahora, si a ese programa le agrego un modulo con Do While para que monitoree la conexion con la unidad de red, y lo llamo en algun punto, se va a quedar dentro del Do While, por siempre, a menos que se pierda la conexion con la unidad de red.
Por otro lado, puedo hacer un script u otro mini-programa que este checando lo de la conexion, y que cuando se pierda la conexion, termine el programa principal, pero si lo termina, no sabria que procesos concluyo y cuales faltaron.
Mi pregunta es: como puedo hacer que un modulo, dentro del programa principal, o un 2do programa este checando la conexion con la unidad, y que en el momento en el que se haya perdido tal, le envie el aviso al programa principal, de forma que éste, al recibirlo, muestre un status (ej msgbox o archivo de texto { para esto no es necesario que me indiquen como }), y se finalice el programa principal, o en su caso los 2 programas.

Ejemplos (punto 1, 2, 3):  :P  :P  :P
Me encontre con findwindow, para obtener la ventana (el programa) a trabajar, indicando el caption, y me funciono por ejemplo si tengo la calculadora abierta, pero muchos programas son externos, por lo que no se si me vaya a devolver una ventana diferente a la que requiero.
Tambien me encontre shellexecute, y probe con la calculadora, y me devolvio un 42 (???). Usando getwindowtext, en el parametro hwnd, le pase el valor obtenido con shellexecute, y al hacer un msgbox de la variable que guardo getwindowtext, me regreso 0. (Espero haberme explicado).
Estas fueron unas, de varias pruebas sin logro, que he realizado.


Espero me puedan ayudar...
Por favor, no me malentiendan. No estoy solicitando el progama ya hecho, sino una idea de que apis y opciones puedo seguir.
No soy muy novato en esto de la programacion, e incluso, le dedico mucho tiempo, por lo que les puedo decir que leo e investigo mucho, pero realmente estoy perdido en este momento, con los puntos que les comenté.

Les agradezco de antemano su ayuda.  ;)

Les envio un cordial saludo.
;D  ;D  ;D

seba123neo

investiga estas api's...en internet o en el api guide hay ejemplos de como usarlas.

FindWindow
FindWindowEx
GetClassName
GetParent
GetWindowText
GetWindowTextLength
EnumWindows
EnumChildWindows
La característica extraordinaria de las leyes de la física es que se aplican en todos lados, sea que tú elijas o no creer en ellas. Lo bueno de las ciencias es que siempre tienen la verdad, quieras creerla o no.

Neil deGrasse Tyson

‡‡‡ Ðξλ†Ћ Щλ†ζЋ ‡‡‡

Gracias seba123neo:

Pero me quedo en las mismas.

Ponle que FindWindowEx, GetParent, EnumWindows y EnumChildWindows no las he investigado, aunque ya las habia visto, y lo mas seguro es que las use para obtener los controles de una ventana y demas.

Pero las otras si ya las he investigado.
Se que FindWindow te busca una ventana por el parametro que le pases, ya sea el titulo de la ventana o su classname, pero si le pasas el titulo, y hay 2 aplicaciones con el mismo nombre, igual te toma la ventana que no quieres. Por otro lado, muchas de las aplicaciones, como decia anteriormente, son externas. Quiza si copio un ejemplo que me encontre, me coloque sobre la aplicacion y vea su classname, pero no he encontrado informacion acerca de si el classname cambia cada que abras la misma aplicacion.

GetClassName devuelve obviamente el classname, pero por ejemplo:
(disculpen si no se debe insertar un link, pero no recuerdo si se debe o no)
http://www.recursosvisualbasic.com.ar/htm/listado-api/88-hwnd-class-name-parent.htm
En esta sección:

Código (vb) [Seleccionar]
'Obtiene la coordenada del Mouse 
Ret = GetCursorPos(Cor) 
'Recuperamos el HWND de la ventana asociada a esa coordenada 
Handle = WindowFromPoint(Cor.x, Cor.y) 
'Handle de la ventana padre 
hParent = GetParent(Handle) 
'Llenamos un Buffer 
ClassName = Space$(128) 
'Recupera el Classname y lo devuelve en el Buffer 
Ret = GetClassName(Handle, ClassName, 128)

me necesito colocar sobre la ventana, para que me devuelva el classname, lo cual no me sirve, pues la idea es hacerlo sin que tenga que meter mano yo.

GetWindowText devuelve el titulo de la ventana, pero vuelvo a lo mismo: y si hay 2 ventanas con el mismo nombre?
GetWindowTextLength devuelve la longitud del titulo de la ventana, pero lo mismo de antes...

Lo que estoy buscando es esto, por ejemplo:
Para el punto 1, que sin este, para que me sigo al 2 o 3... me encontre que el Shell de VB te devuelve el hInstance (segun recuerdo xq con todo lo que he leido de esto, ya no lo recuerdo bien). La api ShellExecute tambien te regresa el hInstance, pero no he encontrado una api que te devuelva el hWnd, por el hInstance. Igual me encontre con una funcion en la MSDN llamada GetWinhWnd, pero es una funcion x, no es ninguna api.
Lo que requiero es una api que me devuelva la hWnd de la aplicacion que ejecuto, y quiza de ahi ya haga un bucle para ir obteniendo sus controles y subventanas.

Para el punto 4 y 5, me encontre con DoEvents, el cual voy a probar, pero igual no se si aplique para lo que requiero.

Por eso es que estoy consultandoles a ustedes. Para saber si me pueden sugerir algo.

Bueno, pues espero haberme explicado, y que me puedan comentar algunas opciones o quiza codigo para echarle ojo y darme una idea de que rumbo tomar.

Les agradezco
Un saludo

Por cierto, me descargue el api guide hace como 3 semanas y tambien he visto el visor api que trae el VB, pero si no se cual aplique, no me resuelve el saber su sintaxis.

Dessa

Cita de: BlaKore_Alpha en  1 Diciembre 2009, 04:36 AM

Se que FindWindow te busca una ventana por el parametro que le pases, ya sea el titulo de la ventana o su classname, pero si le pasas el titulo, y hay 2 aplicaciones con el mismo nombre, igual te toma la ventana que no quieres.


En el caso que haya mas de una ventana con el mismo nombre FindWindow te devuelve el Hwnd de la ultima ventana que se ejecutó, quiere decir que no te podes equivocar de ventana si vos mismo ejecutas la aplicacion externa desde tu code e inmediatamente obtenes su Hwnd.




 
Adrian Desanti

‡‡‡ Ðξλ†Ћ Щλ†ζЋ ‡‡‡

Vientos amigo!!!   :laugh:  :laugh: Super, el dato!!!

A partir de esto, ya puedo tomar la primera ruta, y probar y seguir investigando lo que me comento tambien seba123neo.

Te agradezco mucho este dato  ;D

Si me pudieran sugerir algo para el punto 4 y 5, mientras investigo lo de las apis, que seguro he de volver a consultarles  :P  :P. Si soy muy novato con las api's  :-[

Gracias
Saludos

P.D. Espero terminarlo pronto, para mostrarselos, a ver que les parece. Para que me den su opinion. Y si ayuda a alguien, pues que mejor  :)

Dessa


Aclaración: en el caso de que haya mas de una ventana con el mismo nombre FindWindow te devuelve el Hwnd de la ultima ventana que se ejecutó o mejor dicho la ultima que obtuvo el foco



S2
Adrian Desanti

MCKSys Argentina

Hola!

Para comunicarte entre 2 aplicaciones, puedes usar SendMessage, pero vas a tener que modificar el WindowProc de la ventana que va a recibir el mensaje, a fin de poder procesarlo.

La MSDN tiene ejemplos de cómo hacer ésto.

Saludos!

MCKSys Argentina

"Si piensas que algo está bien sólo porque todo el mundo lo cree, no estás pensando."


BlackZeroX

creo que entendi que en el punto Numero 5 buscas MultiTheard o MultiHilos

revisa esta liga:

http://www.pscode.com/vb/scripts/ShowCode.asp?txtCodeId=31786&lngWId=1

Para sincronisar puedes usar las "APIS Atom" ( Hay otras pero no recuerdo sus nombres )

Con el ejemplo del PSC y las apis ATOM te olvidas del SendMessage, Post, etc [ Para la comunicacion entre procesos ]

Dulces Lunas!¡.
The Dark Shadow is my passion.

‡‡‡ Ðξλ†Ћ Щλ†ζЋ ‡‡‡

Perfecto!!!  ;D  :laugh:

En este momento empiezo a investigar las sugerencias que me dieron.

MCKSys Argentina
Algo vi de SendMessage, pero no le hice mucho caso. Voy a investigarlo mas a fondo, porque la neta tampoco se que es eso del WinProc.

░▒▓BlackZeroҖ▓▒░
Si, en el punto 5 es precisamente lo que busco. Igual, voy a investigar lo de las API's Atom, PSC, y demas.

Les agradezco nuevamente su apoyo.
Que tengan buen dia.
Aqui seguimos...  :laugh:  :laugh:

‡‡‡ Ðξλ†Ћ Щλ†ζЋ ‡‡‡

Hola como estan  :)
Yo aqui batallando un poco con lo mismo que les preguntaba anteriormente  :P
Espero me puedan ayudar...

La primera consulta es como se usa EnumProcesses.
La he buscado mucho y he entendido por decirlo asi, el conecpto de los parametros:
pProcessIds [out] A pointer to an array that receives the list of process identifiers.
cb [in] The size of the pProcessIds array, in bytes.
pBytesReturned [out] The number of bytes returned in the pProcessIds array.
pero no entiendo que valores numericos asignar en cb y pBytesReturned.

Por ejemplo, en http://foro.elhacker.net/empty-t248082.0.html;msg1194841#msg1194841
cb = 8
cbNeeded = 96
Do While cb <= cbNeeded
cb = cb * 2
ReDim ProcessIDs(cb / 4) As Long
lRet = EnumProcesses(ProcessIDs(1), cb, cbNeeded)
Loop
NumElements = cbNeeded / 4

:huh:  :huh:
Por que cb es 8? Por que no 9 o 7, o 120?
Lo mismo para cbNeeded?
Por que cb se multiplica x 2 y luego en el redim y NumElements, se divide entre 4?
Por que el array es directamente dividido entre 4?

O en http://foro.elhacker.net/empty-t246534.0.html;msg1191015#msg1191015
ReDim lProcesses(1023) As Long
If EnumProcesses(lProcesses(0), 1024 * 4, lRet) Then
For N = 0 To (lRet \ 4) - 1

Por que ahora se multiplica entre 4, y luego se divide entre 4, menos 1?

Si alguien pudiera por favor, poner un ejemplo, unicamente de enumprocesses, mas o menos sencillo, y comentar porque de las divisiones y procesos? En el ApiGuide, y en muchas paginas, vienen ejemplos bastante extensos, y hacen uso de OpenProcess, CloseProcess, etc, pero si no consigo entender EnumProcesses, no tiene caso seguir con Open..., etc.  :P


Por otro lado, hablando del multithread que quiero hacer, estuve investigando acerca de la Api de la liga que comento ░▒▓BlackZeroҖ▓▒░, incluso otras mencionadas en la msdn, CreateThread en el ApiGuide, etc, pero parece que es muy inestable usarlos en VB6, por lo que no va a ser una opcion.
Me encontre que tambien se podia usar un Timer, pero como el programa realiza varias instrucciones, el Timer ejecuta las instrucciones que contiene, al terminar los demas procesos, asi que tampoco va a ser alternativa.

Ahora, me encontre con DDE. No he probado, pero ¿consideran que si dejo la aplicacion como servidor, y el comando listen (y los demas que sean necesarios), y realizando otra aplicacion como cliente, al perder conexion con la unidad de red, el cliente envie algun valor, y el servidor, al recibirlo, realice lo que tenga que hacer, aun cuando no haya terminado los procesos?
Tambien por otro lado, me encontre que DDE ya es anticuado. Que ahora se tiene OLE. ¿se puede hacer algo parecido con OLE, a DDE?
Y tambien me encontre con que, en lugar de usar DDE y OLE, se puede usar un ActiveX. ¿Que sería, un DLL ActiveX o un EXE ActiveX? El archivo, se encuentra en la misma maquina. ¿Saben de alguna pagina donde se exponga un ejemplo parecido?

Como ven WinSock? El problema que le veo, aunque no lo se con seguridad, es que todos los equipos donde ejecutaría el programa, aunque se tienen permisos de admin, y todo, tienen ciertas cosas restringidas por politicas de seguridad, el antivirus, y el firewall, que pudiera bloquearme el puerto que pudiera ocupar para realizar la comunicacion entre aplicaciones.

Ojala me puedan dar una guia o referencia, sus comentarios y opiniones.  ;)

Bueno, despues del choro mareador de preguntas, me despido.  :)
Nos vemos pronto.

P.D. No encontre lo de las APIS Atom. ¿No es Atom APIS? ¿Se basan en xml? Es que no se xml