|
You last visited: Today at 03:34
Advertisement
AutoIt Do/Until Schleife bis Farbe da ist
Discussion on AutoIt Do/Until Schleife bis Farbe da ist within the AutoIt forum part of the Coders Den category.
01/18/2012, 14:33
|
#1
|
elite*gold: 0
Join Date: Jun 2011
Posts: 9
Received Thanks: 0
|
AutoIt Do/Until Schleife bis Farbe da ist
Hallo,
wie kann man in diesem Script in den Schleifen darstellen, dass wenn eine bestimme Farbe mit einer bestimmten Abweichung vorliegt, die Schleife eingeleitet oder beendet wird? Habs so probiert, geht aber nicht.
Kann jemand helfen?
$farbe=0
$farbe2=0
$farbe3=0
Do
send("{space down}")
sleep(50)
send("{space up}")
Sleep(10)
$farbe = PixelSearch(***,***,***,***,FARBE,20)
Until IsArray($farbe) = True
;jetzt kommt ein menü im spiel. 2 möglichkeiten hat das menü, je nach dem ;was man vorher geschafft hat. die möglichkeiten unterscheiden sich in den ;farben.
$farbe3 = PixelSearch(1100,750,1100,750,0xFD0000,20)
If IsArray($farbe3) = True Then
Sleep(1000)
Send("{Enter down}")
Sleep(50)
Send("{Enter up}")
Else
Sleep(1000)
Send("{Enter}")
EndIf
|
|
|
01/18/2012, 15:26
|
#2
|
elite*gold: 0
Join Date: May 2008
Posts: 23
Received Thanks: 10
|
Du kannst mit Hilfe der Funktion "AdlibRegister" eine Funktion alle X-Milisekunden aufrufen lassen - optimal für eine Farbsuche ohne Schleife.
Währenddessen macht dein Script einfach weiter (in meinem Beispiel wartet es einfach in der Skript-nötigen While-Schleife (z.B. für GUI-Input).
Code:
Global $aColorMode[3]
Global $Color1 = 0xFFB700, $Color2 = 0xFFFFFF
AdlibRegister("_Colorsearch", 500) ; Ruft die Funktion die Farbe zu suchen alle 500ms (jede halbe Sekunde) auf
While 1
Sleep(100)
WEnd
Func _Colorsearch()
Local $aColorArray
$aColorMode[0] = 0
send("{space down}")
sleep(50)
send("{space up}")
Sleep(10)
$aColorArray = PixelSearch(w,y,x,z, $Color1, 20) ; Farbe 1 nach der gesucht wird
If Not @error Then ; Farbe 1 gefunden
$aColorMode[0] = 1
$aColorMode[1] = $aColorArray[0] ; PosX
$aColorMode[2] = $aColorArray[1] ; PosY
Else ; Farbe 1 nicht gefunden
$aColorArray = PixelSearch(w,y,x,z, $Color2, 20); Farbe 2 nach der gesucht wird (nur wenn Farbe 1 nicht gefunden wurde)
If Not @error Then ; Farbe 2 gefunden
$aColorMode[0] = 2
$aColorMode[1] = $aColorArray[0] ; PosX
$aColorMode[2] = $aColorArray[1] ; PosY
EndIf
EndIf
If $aColorMode[0] > 0 Then _ColorFound($aColorMode[0])
EndFunc
Func _ColorFound($pMode)
AdlibUnRegister("_Colorsearch") ; stopt den automatischen Aufruf der Such-Funktion
Select
Case $pMode = 1 ; Wenn Farbe 1 gefunden wurde
; was auch immer du hier machen willst
Case $pMode = 2 ; Wenn Farbe 2 gefunden wurde
; ... what ever
Case Else
; Fehlermeldung
MsgBox(48, "Error", "Unbekannter Modus: " & $pMode)
EndSelect
EndFunc
|
|
|
01/18/2012, 15:38
|
#3
|
elite*gold: 0
Join Date: Jun 2011
Posts: 9
Received Thanks: 0
|
Vielleicht hätte ich erwähnen sollen, das erst nach dem einige male Enter, Space und "d" gedrückt wurde die Farbensuche beginnen darf. Dann befindet sich Fifa nämlich in einer Fussballpartie, es soll halt mit der Suche nach Schwarz überprüft werden, ob das Halbzeitpausenmenü schon da ist. Wenn das der Fall ist drückt der Bot es mit Enter weg, die 2. Halbzeit startet. Am Ende gibt es 2 Möglichkeiten eines Menüs- entweder man hat gewonnen, dann befindet sich bei xx,xx ein roter Pixel. Wenn nicht, irgendeine andere Farbe. Nachdem die Spielberichte weggedrückt wurden soll der Bot im Hauptmenü nicht mehr nach Farben suchen.
|
|
|
01/18/2012, 15:49
|
#4
|
elite*gold: 0
Join Date: May 2008
Posts: 23
Received Thanks: 10
|
Was du davor oder danach machst, kannst du ja einfach einfügen.
Kurze Erklärung zu meinen Codeschnipsel:
Alle 500ms drückt er die Tasten:
send("{space down}")
sleep(50)
send("{space up}")
Sleep(10)
Danach sucht er nach Farbe 1 und 2. Wenn er eine von beiden gefunden hat, springt er in die Funktion "_ColorFound".
Dort kannst du bei Case = 1 bzw. Case = 2 definieren, was er machen soll, sobald er die jeweilige Farbe gefunden hat.
Sollte er keine der Farben gefunden haben, sucht er alle 500ms nach den beiden Farben (und drückt die 2 Tasten wieder), bis er eine von beiden gefunden hat.
|
|
|
01/18/2012, 16:02
|
#5
|
elite*gold: 0
Join Date: Jun 2011
Posts: 9
Received Thanks: 0
|
Klappt mittlerweile. Trotzdem Danke!
|
|
|
01/18/2012, 16:51
|
#6
|
elite*gold: 0
Join Date: May 2008
Posts: 23
Received Thanks: 10
|
Naja, du hattest ja kurz deinen Code gepostet.
Du solltest es vermeiden alles innerhalb der While-Schleife des Skriptes zu haben.
Erstelle lieber einzelne Funktionen, die du immer wieder aufrufst, anstatt innerhalb der Skript-Schleife alles per Do-Until zu machen.
Z.B.:
Code:
#include <ButtonConstants.au3>
#include <GUIConstantsEx.au3>
#include <StaticConstants.au3>
#include <WindowsConstants.au3>
Global $StateMatch = "Start"
Global $Color_HalbzeitEins = 0x373937, $Color_HalbzeitZwei = 0x181919
Opt("GUIOnEventMode", 1)
; Fenster zum Starten und Überwachen des aktuellen Fortschrittes
$W_Main = GUICreate("Form1", 208, 143, -1, -1)
$Btn_Start = GUICtrlCreateButton("Start", 64, 40, 75, 25)
$Ll_State = GUICtrlCreateLabel("Status: ", 16, 96, 40, 17)
$Ll_State_Dat = GUICtrlCreateLabel("Label2", 64, 96, 116, 33)
GUICtrlSetOnEvent($Btn_Start, "_GuiControl")
GUISetOnEvent($GUI_EVENT_CLOSE, "_GuiControl")
GUISetState(@SW_SHOW)
While 1
Sleep(100)
WEnd
Func _GameController()
AdlibRegister("_ShowGameState", 500) ; Generiert einen permanenten Tooltip mit aktuellen Informationen und aktualisiert das UI
GUICtrlSetState($Btn_Start, $GUI_DISABLE) ; deaktiviert den Start-Button bis 1 Runde beendet wurde
_Spielvorbereitung()
_HalbZeitAktionen(1)
_HalbZeitAktionen(2)
GUICtrlSetState($Btn_Start, $GUI_ENABLE) ; aktiviert den Start-Button wieder
_StopLoops()
EndFunc
Func _StopLoops()
AdlibUnRegister("_ShowGameState")
AdlibUnRegister("_GameController")
EndFunc
Func _Spielvorbereitung()
$StateMatch = "Vorbereitung"
Sleep(10000)
Send("{Enter}")
Sleep(1000)
Send("{Enter}")
Sleep(1000)
Send("{down}")
Sleep(1000)
Send("{Enter}")
Sleep(1000)
; Turnierauswahl
Send("{Left}")
Sleep(1000)
Send("{Enter}")
Sleep(400)
Send("{Up}")
Sleep(250)
Send("{Enter}")
Sleep(1000)
; Spielplan
For $i = 1 To $i = 7 Step 1
Send("{Enter}")
Sleep(1500)
Next
EndFunc
Func _HalbZeitAktionen($pHalbzeit = 1)
Local $Farbe
Select
Case $pHalbzeit = 1 ; 1. Halbzeit
$StateMatch = "1. Halbzeit"
Do
Sleep(10)
Send("{d down}")
Sleep(1000)
Send("{d up}")
send("{space down}")
sleep(50)
send("{space up}")
Sleep(10)
$Farbe = PixelGetColor (560, 520)
Until $Farbe = $Color_HalbzeitEins
send("{enter}")
Sleep(1000)
Case $pHalbzeit = 2 ; 2. Halbzeit
$StateMatch = "2. Halbzeit"
Do
Sleep(10)
Send("{d down}")
Sleep(1000)
Send("{d up}")
send("{space down}")
sleep(50)
send("{space up}")
Sleep(10)
$Farbe = PixelGetColor (112, 972)
Until $Farbe = $Color_HalbzeitZwei
EndSelect
EndFunc
Func _ShowGameState($pInfo = 0)
Local $tDisplaypData
Select
Case $pInfo = 0 ; Standard: Zeigt aktuellen Spielstatus
$tDisplaypData = "Aktueller Spielstatus: " & $StateMatch
Case $pInfo = 1 ; Skript pausiert
$tDisplaypData = "Skript pausiert!" & @CRLF & "Spielstatus: " & $StateMatch
EndSelect
ToolTip($tDisplaypData, -1, -1, "Fortschritt") ; aktualisiert den Tooltip
GUICtrlSetData($Ll_State_Dat, $tDisplaypData) ; aktualisiert das GUI
EndFunc
Func _GuiControl()
Select
Case @GUI_CtrlId = $GUI_EVENT_CLOSE ; schließen button des Fenster gedrückt
Exit
Case @GUI_CtrlId = $Btn_Start ; start gedrückt
AdlibRegister("_GameController")
EndSelect
EndFunc
|
|
|
01/19/2012, 22:43
|
#7
|
elite*gold: 0
Join Date: Jun 2011
Posts: 9
Received Thanks: 0
|
Ich bin noch Anfänger in Auto-It,werde das in Zukunft dann auch in einzelne Funktionen teilen. Jetzt war ich gerade dabei mein Skript zu verbessern, es funktioniert zwar, aber an manchen stellen zu langsam. Diesen Teil hab ich geändert. Allerdings funktioniert PixelGetColor nicht, er führt immer den Else Teil der Schleife aus obwohl die Farbe 100%tig an der Stelle 1E1F1E ist (hab extra nochmal nur ein PixelGetColor Skript geschrieben und per MsgBox kam die auch raus). 
Was ist daran bitte falsch?!
Do
Sleep(10)
Send("{d down}")
Sleep(1000)
Send("{d up}")
Sleep(10)
send("{space down}")
sleep(1000)
send("{space up}")
Sleep(1000)
$farbe=PixelGetColor(976,684)
If Hex($farbe, 6)='1E1F1E' Then
Sleep(10)
send("{enter down}")
Sleep(20)
send("{enter up}")
Sleep(120)
ExitLoop 2
Else
Sleep(10)
send("{enter down}")
Sleep(20)
send("{enter up}")
Sleep(120)
EndIf
Until Hex($farbe, 6) = '1E1F1E'
|
|
|
01/19/2012, 22:53
|
#8
|
elite*gold: 0
Join Date: Mar 2009
Posts: 7,260
Received Thanks: 33,149
|
Code:
If Hex($farbe, 6)='1E1F1E'
Das kann nicht funktionieren. Du versucht eine Zahl mit einem String zu vergleichen, was in AutoIt eigentlich noch möglich wäre, wenn der String nur Zahlen enthalten würde.
Richtig wäre es so:
Code:
If Hex($Farbe) == 0x1E1F1E Then
;oder einfach:
If $Farbe == 0x1E1F1E Then
Die einzelnen Sachen in mehrere Funktionen aufzuteilen ist außerdem nur dann sinnvoll, wenn diese Codestücke öfters verwendet werden. Wenn du sie nur einmal in der While-Schleife brauchst, hat es keinen Sinn sie in Funktionen aufzuteilen.
|
|
|
01/19/2012, 23:10
|
#9
|
elite*gold: 0
Join Date: Jun 2011
Posts: 9
Received Thanks: 0
|
Gut das hab ich geändert. Geht aber trotzdem noch nicht, er findet die Farbe nicht. Ich hab hier nochmal einen Screenshot. Bei 976,684 liegt die Farbe 0x1E1F1E vor, aber es klappt einfach nicht. Kann AutoIt evtl. bei Vollbildspielen die Farbe nicht richtig auslesen? Vielleicht hat es auch was damit zu tun: Bei Fifa hat man bei Screenshots das Problem, das sie komplett grau sind, wenn man sie über die Druck Taste macht. Mit Fraps klappt es.
|
|
|
01/19/2012, 23:16
|
#10
|
elite*gold: 280
Join Date: May 2007
Posts: 2,818
Received Thanks: 3,483
|
der Hex(...) befehl hat doch aber als rückgabe wert einen string :P
es ist zwar einfacher direkt die farbe mit dem hex-wert zu vergleichen, aber das kann nicht die fehlerquelle sein =)
Edit:
um herauszufinden wo das problem liegt, musst du schon für realistische bedinungen sorgen, und in einer dauerschleife das ganze checken.
hier mal ein beispiel-tool für den dauercheck auf den pixel:
Code:
Dim $color, $tmp
While Sleep(50)
$color = PixelGetColor(976,684)
ToolTip('0x'&Hex($color))
If $color<>$tmp Then
MsgBox(0, 'Notice', 'Die Farbe auf dem Pixel hat sich geändert auf 0x'&Hex($color))
$tmp=$color
EndIf
WEnd
|
|
|
01/19/2012, 23:32
|
#11
|
elite*gold: 0
Join Date: Jun 2011
Posts: 9
Received Thanks: 0
|
Quote:
Originally Posted by lolkop
Code:
Dim $color, $tmp
While Sleep(50)
$color = PixelGetColor(976,684)
ToolTip('0x'&Hex($color))
If $color<>$tmp Then
MsgBox(0, 'Notice', 'Die Farbe auf dem Pixel hat sich geändert auf 0x'&Hex($color))
$tmp=$color
EndIf
WEnd
|
Ich verstehe das Skript nicht genau. Er schreibt in $color die Farbe rein, gibt sie als Hex aus. Color ist ungleich $tmp, also gibt er wieder, aber in einer MsgBox aus, das gleiche aus. Wie funktioniert der dann permanent?
|
|
|
01/19/2012, 23:48
|
#12
|
elite*gold: 0
Join Date: Mar 2009
Posts: 7,260
Received Thanks: 33,149
|
$tmp übernimmt nach der ersten MsgBox() den Wert von $color. Die MsgBox() wird also nur dann wieder ausgegeben, wenn sich die Farbe des Pixels ändert uns sich somit der aktuelle Farbwert ($color) vom alten Wert ($tmp) unterscheidet. Bleibt die Farbe des Pixels immer gleich, wirst du nur einmal eine MsgBox() Ausgabe bekommen.
|
|
|
01/19/2012, 23:50
|
#13
|
elite*gold: 280
Join Date: May 2007
Posts: 2,818
Received Thanks: 3,483
|
Quote:
Originally Posted by xFreshness
Ich verstehe das Skript nicht genau. Er schreibt in $color die Farbe rein, gibt sie als Hex aus. Color ist ungleich $tmp, also gibt er wieder, aber in einer MsgBox aus, das gleiche aus. Wie funktioniert der dann permanent?
|
ich war davon ausgegengen, das du dir sicher bist, das der pixel dauerhaft diese farbe hat. so kannst du testen ob dies wirklich der fall ist.
sobald die farbe sich ändert popt hier eine msgbox auf, welche dich darauf hinweist.
interesannt hieran ist, ob tatsächlich die farbe ausgelesen wird, von welcher du hier ausgehst.
|
|
|
01/19/2012, 23:55
|
#14
|
elite*gold: 0
Join Date: Jun 2011
Posts: 9
Received Thanks: 0
|
Laut deinem Pixelchecker ist die Farbe: 0x001E1F1E.
Warum sind das denn 8 Zahlen nach dem x?
|
|
|
01/20/2012, 00:02
|
#15
|
elite*gold: 280
Join Date: May 2007
Posts: 2,818
Received Thanks: 3,483
|
weil autoit im normalfall mit dword/int hex werten arbeitet.
poste bitte einmal dein gesamtes script hier, damit wir nachvollziehen können warum du im <then case> ein exitloop auf level 2 ebene anwendest.
|
|
|
Similar Threads
|
Hilfe bei der autoit while schleife
03/05/2010 - Metin2 - 7 Replies
Hallo,
also ich habe ein problem und weiß nicht wie ich das lösen kann :(
ich will einen Multihack machen für metin2
aber wenn ich eine value freezen muss dann mache ich eine while schleife und dann kann man keinen anderen Button mehr aktivieren :(
z.B. (ein anderes von mit erstelltes programm)
Code:
|
All times are GMT +1. The time now is 03:35.
|
|