Mausklick simulieren



  • Hi @all,

    also wie ich ein Mausklick simuliere weiß ich

    mouse_event(MOUSEEVENTF_LEFTDOWN,0,0,0,0);
    

    Aber wie kann ich einen Mausklick auf die Task-Leiste oder auf den leeren Desktop simulieren?
    Es soll dabei nichts ausgeführt werden. Es soll nur ein klick ins nichts geschehen.

    Ach ja, noch was. Mit SetForegroundWindow() setze ich den Fokus auf mein Fenster. Wie bekomme ich den Fokus da wieder runter (Vieleicht durch einen Mausklick in die Taskleiste???)?



  • Such mal nach Enum Windows, damit bekommst du alle offenen Fenster, und
    dann kannst du dir aussuchen welches den fokus erhalten soll 😉

    Devil



  • Hi Devil,

    was mach ich den, wenn nur mein Fenster offen ist.
    Ich möchte das es einmal den Fokus verliert und kurz danach wieder bekommt.

    Und was meinst Du mit Enum Windows? Ich kann darunter nichts finden.

    ***Nachtrag***

    Also Ziel ist ein Popup-Fenster welches an einer Stelle im Programm aufgeht, nicht erscheinen zu lassen. Deshalb starte ich kurz vorher einen Thread der noch der Funktion wieder geschlossen wird. Der Thread sieht so aus:

    CWnd* pFindDlg = NULL;
    	CWnd* pWnd = NULL;
    	pWnd = GetDesktopWindow();
    	while(m_Flag2)
    	{
    		try
    		{	
    			CWnd::SetForegroundWindow();
    			pFindDlg = CWnd::FindWindow(NULL,"Server ist ausgelastet");
    			if(pFindDlg != NULL)
    			{
    				pFindDlg->ShowWindow(SW_HIDE);
    				pFindDlg->SendMessage(0,0,0);
    				pWnd->SendMessage(0,0,0);
    				pFindDlg = NULL;
    			}
    		}catch(char *e)
    		{
    			//do nothing
    		}
    	}
    	pFindDlg = NULL;
    

    Dummerweise springt das Programm erst aus dieser Schleife raus, wenn ich manuell in die Taskleiste, ein anderes Fenster oder auf den Desktop klicke.
    Deshalb suche ich eine Möglichkeit diesen Mausklick im Thread zu implementieren.



  • Hi,

    Trikor schrieb:

    was mach ich den, wenn nur mein Fenster offen ist.
    Ich möchte das es einmal den Fokus verliert und kurz danach wieder bekommt.

    Du meinst wegen dem Click? Mach dein Fenster doch einfach kurz unsichtbar

    Trikor schrieb:

    Und was meinst Du mit Enum Windows? Ich kann darunter nichts finden.

    Er meinte die WinAPI Funktion EnumWindows

    Hab grad leider keine Zeit deinen Code durchzuarbeiten 😞 wegen Hausaufgaben.

    Grüße Rapha



  • Rapha schrieb:

    Du meinst wegen dem Click? Mach dein Fenster doch einfach kurz unsichtbar

    Hi Rapha,

    Der Code oben ist in einem Thread. Wenn ich jetzt in der while-Schleife das Fenster kurz unsichtbar mache, wird es wohl mächtig flackern 😞
    Deshalb die Idee mit dem Mausklick ins leere.
    Muß vermutlich hier eingearbeitet werden

    pWnd->SendMessage(0,0,0) // pWnd = GetDesktopWindow();
    

    aber ich weiß nicht genau wie.



  • Andere Frage.

    Wenn ich den den Zugriff auf das Meldungsfenster habe ( Duch FindWindow ),
    wie kann ich dem Fenster sagen, das es den Button Klick "Wiederholen" ausführen soll.
    Das Fenster hat 3 Button "Wechseln zu", "Wiederholen" und deaktiv "Abbrechen"
    Ich denke mal irgendwie mir SendMessage, weiß aber nicht, ob das richtig ist und wenn ja, wie ich die Parameter übergeben muß.

    Und ich verzweifel langsam wirklich.



  • Trikor schrieb:

    Wenn ich den den Zugriff auf das Meldungsfenster habe ( Duch FindWindow ),
    wie kann ich dem Fenster sagen, das es den Button Klick "Wiederholen" ausführen soll.
    Das Fenster hat 3 Button "Wechseln zu", "Wiederholen" und deaktiv "Abbrechen"
    Ich denke mal irgendwie mir SendMessage, weiß aber nicht, ob das richtig ist und wenn ja, wie ich die Parameter übergeben muß.

    Hol dir mit FindWindowEx ein Handle auf den Wiederholen Button, berechne seine Koordinaten, setz den Mauscursor mit SetCursorPos und mit mouse_event einen Mausklick simulieren...



  • Hi Rapha,

    geht das auch, wenn das Fenster bereits nicht mehr sichtar ist?
    Schließlich kommt ja als erstes ShowWindow(SW_HIDE).



  • welches Fenster meinst du?
    Wenn das Fehlermeldungsfenster unsichtbar ist, bekommst du zwar das Handle aber der virtuelle Mausklick wird das Fenster nicht "treffen".



  • Das ist ja das Problem.
    Deshalb dachte ich ja auch an nen Mausklick auf den Desktop oder in der Taskleiste. Halt ausserhalb meines Programms.
    Ich kriege es halt nur nicht hin.
    Aber vieleicht gehe ich das ganze auch falsch an. Ich erkläre es nochmal genau.

    Weil in PrepareToEncode die Fehlermeldung ständig auftaucht (welche allerdings nach der Initialisierung am MediaServer weg ist), will ich die Fehlermeldung verschwinden lassen, indem ich vorher einen Thread starte und nach der Initialisierung den Thread beende.

    m_Flag2 = 1;
    	CWinThread* pThread2 = AfxBeginThread (FensterThread, this);
    	try
    	{
    		if ( SUCCEEDED( hr ) )
    		{
    			hr = pEncoder->PrepareToEncode(VARIANT_TRUE);
    		}	
    		m_Flag2 = 0;
    
    	}catch(char *e)
    	{
    		//do nothing
    	}
    

    Im Thread suche ich das Fenster und mache es mit ShowWindow(SW_HIDE) unsichtbar.

    // Feststellen ob Hauptdialog im Vordergrund ist.
    	CWnd* pFindDlg = NULL;
    	while(m_Flag2)
    	{
    		try
    		{	
    			CWnd::SetForegroundWindow();
    			pFindDlg = CWnd::FindWindow(NULL,"Server ist ausgelastet");
    			if(pFindDlg != NULL)
    			{
    				pFindDlg->ShowWindow(SW_HIDE);
                    // hier muß wohl der manuelle Weg dargestellt werden. 
    				pFindDlg = NULL;
    			}
    		}catch(char *e)
    		{
    			//do nothing
    		}
    	}
    	pFindDlg = NULL;
    

    Leider wird (wenn der Thread gestartet wurde) PrepareToEncode nicht mehr automatisch beendet. Dies geschieht erst, wenn ich z.B. ein Mausklick auf den Desktop, auf die Taskleiste oder ein anderes Programm mache und danach wieder in mein Hauptfenster klicke. Danach läuft alles wieder wie geschmiert weiter.
    PrepareToEncode wird beendet und danach auch der Thread.
    Ich kriege es allerdings nicht hin, die manuelle Prozedur in der Threadfunktion zu implementieren. *Verzweifel, dreh durch* 😕

    Hoffentlich ist das so erklärt, das Ihr was damit anfangen könnt. 😉



  • So, hab jetzt mal ein etwas anderen Ansatz.
    Im Thread versuche ich jetzt den Wiederholen-Button zu treffen.
    Spy++ sagt, der ist von der Klasse "Button" mit Namen "Wie&derholen"
    Deshalb versuche ich es jetzt so:

    // Feststellen ob Hauptdialog im Vordergrund ist.
    	CWnd* pFindDlg = NULL;
    	CWnd* pWnd = NULL;
    	//pWnd = GetDesktopWindow();
    	while(m_Flag2)
    	{
    		try
    		{	
    			//CWnd::SetForegroundWindow();
    			pFindDlg = CWnd::FindWindow(NULL,"Server ist ausgelastet");
    			if(pFindDlg != NULL)
    			{
    				HWND hControl = pFindDlg->GetSafeHwnd();
    				//pWnd->FindWindowEx(m_hWnd,hControl,"Button","Wie&derholen");
    				pWnd->FindWindow("Button","Wie&derholen");
    				if(pWnd!=NULL)
    					pWnd->PostMessage(BM_CLICK,0,0);
    				pFindDlg->ShowWindow(SW_HIDE);
    				CWnd::SetForegroundWindow();
    				pFindDlg = NULL;
    				pWnd = NULL;
    			}
    		}catch(char *e)
    		{
    			//do nothing
    		}
    	}
    	pFindDlg = NULL;
    

    Habe keine Ahnung, ob
    //pWnd->FindWindowEx(m_hWnd,hControl,"Button","Wie&derholen");
    oder
    pWnd->FindWindow("Button","Wie&derholen");
    richtig ist. Zumindest macht er es noch nicht ganz so, wie er es soll.

    Traut sich jemand zu den Code zu berichtigen?


Anmelden zum Antworten