[C++ - WinAPI] Bot der Metin im Hintergrund steuert

12/17/2009 21:09 Machtl#1
Guten Tag
Zuallererst: Ich hoffe das ist der richtige Bereich in diesem Forum für meine Frage. Zudem: Ich kann C++ (mehr oder weniger) hab allerdings ziemlich wenig Ahnung von dem WinAPI Zeug :)

Ich möchte nun einen Bot schreiben, der an das Metin Fenster im Hintergrund Nachrichten sendet bzw. Tastatureingaben simuliert. Als Übung soll er einfach mal die Taste 1 drücken. Nun habe ich mir diesen Code aus meinem Gedächtnis zusammengezimmert:
Code:
metin_fenster = FindWindow(NULL,TEXT("METIN2"));
PostMessage(metin_fenster,WM_KEYDOWN,'1',NULL);
Leider schreibt er die 1 nur in das Chatfenster, den Quickslot spricht er nicht an.

Dann habe ich etwas im Internet geforscht und es mit einem etwas anderen Code probiert. Hier mal der ganze Code:
Code:
#include <iostream>
#include <windows.h>

using namespace std;

HWND metin_fenster;

int main()
{
	metin_fenster = FindWindow(NULL,TEXT("METIN2"));
	
	INPUT	f_4 = {INPUT_KEYBOARD, {0x34,NULL,NULL,NULL,NULL}};
	DWORD   dwCurrentProcessId;
	DWORD	dwCurrentThreadId  = GetWindowThreadProcessId(metin_fenster,&dwCurrentProcessId);
	DWORD   dwMyThreadId  = GetCurrentThreadId(); 
	while(true)
	{
		//PostMessage(metin_fenster,WM_KEYDOWN,'1',NULL);
		AttachThreadInput(dwMyThreadId,dwCurrentThreadId,TRUE); 
		SetFocus(metin_fenster);
		SendInput(1,&f_4,sizeof(f_4));
		AttachThreadInput(dwMyThreadId,dwCurrentThreadId,FALSE);
		Sleep(20000);
	}
	return 0;
}
Selbes Ergebnis :(

Meine amateurhafte Diagnose lautet: Metin holt sich die Tastatureingabe nicht über die Windows-Messages, aber wie denn dann? Via DirectX? OpenGL?

Ich hoffe mir kann von euch jemand helfen ;)
Danke im vorraus

Mfg
Machtl
12/17/2009 22:03 ms​#2
Ich vermute mal Metin2 benutzt dafür DirectInput, also müsstest du diese Funktionen dann hooken.
12/31/2009 16:35 Machtl#3
Guten Tag ich bin es nochmal.

Ich habe mich ein wenig schlau gemacht über DirectInput.
Um den Tastaturstatus auszuwerten muss man eine Methode von Direct Input Device aufrufen und bekommt den Status jeder einzelnen Taste in einem 256x1 Byte großem array serviert. Nun hab ich mir gedacht wenn ich an die Adresse dieses Arrays rankomme kann die Bytes so manipulieren, dass Metin denkt eine Taste wäre gedrückt wurden. also hab ich mal die Cheatengine angeworfen und ein bisschen gestöbert und habe auch etwas gefunden. Wenn ich jetzt aber mittels WriteProcessMemory() unter besagter Adresse 0x80 hinschreibe (Heisst soviel wie: Taste ist gedrückt) sehe ich das in der Cheatengine auch, dass unter dieser Adresse ein neuer Wert ist aber Metin2 zeigt sich davon völlig unbeeindruckt und rührt sich nicht.
Das alles wäre sehr viel hilfreicher, wenn man genau wüsste wie Metin eingaben aufnimmt.
Die Adresse auf die ich den Wert 0x80 geschrieben habe ist übrigens 0x0068C889. Das ist das W, der Char sollte also nach vorn laufen.

Mfg
Machtl
01/01/2010 12:56 ^darkwing#4
Hab auch so meine Probleme mit DirecInput, ähnlich wie bei dir. Ich meine ich habe die richtige Adresse des Arrays gefunden aber dennoch will es nicht funktionieren.

Achja generell gibts zwei Möglichkeiten bei DirectInput:

* Immediate -> GetDeviceState()
* Buffered -> GetDeviceData()

Bei Immediate kannst du einfach als Test mal 0x80 an die entsprechende Stelle schreiben, funktioniert (Also bei mir bei einer Testanwendung).

Buffered sieht schon anderes aus. Da sind es Objekte im Array, du müsstes also selbst ein Objekt anlegen und es an die entsprechende Stelle schreiben. (Funktioniert bei meiner Testanwendung)

Also ich such nach Testanwendungen (Code) und passe ihn meinen Bedürfnissen an und Teste einfach bissl rum.

Deswegen solltest du erstmal herausfinden wie das Spiel seinen Input bekommt -> OllyDbg.

In der DirectX Dokumentation steht das ganze noch ausführlicher. ;)