Thanks, ideas keep coming naturally when you are too lazy to practice execution/click many buttons/master piano builds and I really don’t like focusing on cooldowns while fighting
; first I've done it with external main loop and Sleep but
; setTimer function is actually simpler and more powerful
SendMode Input
#NoEnv
#SingleInstance Force
#MaxHotkeysPerInterval 1000
#MaxThreadsPerHotkey 1
#KeyHistory 50
SetWorkingDir %A_ScriptDir%
doom_bolt_allowed := true
AllowDoomBolt()
{
global doom_bolt_allowed
doom_bolt_allowed := true
}
~*RButton::
KeyWait, RButton, T0.2
if ErrorLevel
{
counter := 0
while GetKeyState("RButton", "P")
{
if doom_bolt_allowed
{
send {0}
doom_bolt_allowed := false
SetTimer, AllowDoomBolt, -13000
/*
'-13000' above makes AllowDoomBolt run only once after 13s
whereas with '13000' the function would run every 13s
*/
}
if !Mod(counter-5, 40) ;blood of dreeg
send {9}
if !Mod(counter-20, 100) ;seal of consumption
send {8}
Sleep, 100
counter := Mod(counter + 1, 2600)
}
}
Return
Code can be probably rewritten with Timers only instead of the counter.
OUTDATED there’s a better version without loop and sleeps using timers
Automatic camera (following your character)
b - rotate left
n - rotate right
~*LButton::
KeyWait, LButton, T0.2 ;need to hold the button for 200ms to follow
if ErrorLevel
{
while GetKeyState("LButton", "P")
{
WinGetActiveStats, Title, Width, Height, X, Y
MouseGetPos, xpos, ypos
xpos := xpos - Width/2 ;vector from the middle of the screen to the cursor
ypos := Height/2 - ypos
if xpos*xpos + ypos*ypos < 40000 ;<200 pix from center -> no rotation
continue
if (ypos > 0) and ( Abs(ATan(xpos / ypos)) * 57.29578 < 20)
continue ; 20° degrees from 12 o'clock -> 40° no rotation sector
if xpos > 0 ;right half of screen -> rotate right
{
Send {n down}
Sleep, 100 ; haven't tested other values here
Send {n up}
}
else ;left half of screen -> rotate left
{
Send {b down}
Sleep, 100
Send {b up}
}
Sleep, 20
}
}
Return
[edit] added 200 pixel protection (no rotation if cursor is closer than 200 pixels to the middle of the screen) so that there’s no rotation during melee fights
[edit2] changing sector of no rotation near 12 o’clock from 10 x 2 = 20° to 20 x 2 = 40° degrees so that there’s less rotation and direction changes when moving upwards and changing direction only slightly; set this parameter to your liking
this is a-freakin-mazing!
If I just copy your text now AHK open an error message which says it doesn’t accept ;
Fixed. The ‘;’ shouldn’t be right after the code, there should be ’ ’ (space) in between
BTW another thing that could be added to the script is blocking the rotation for some time after you press buttons responsible for using skills
For example when you use a Movement Skill, the rotation stops (because it’s a little bit weird when the screen is rotatin when you are in the middle of animation)
You can also check this script Faster camera rotation using keyboard or scroll wheel I’ve been using it and now I may switch to this (need to test it longer)
The biggest problem of the script is that if I minimize GD and want to use my mouse without typing b or n I have to close the script everytime
Can I configure a global pause key for AHK?
Here’s a fuller version of script with suspension of hotkeys when Grim Dawn is minimized (the initial setting are recommended as well)
SendMode Input
#NoEnv
#SingleInstance Force
#MaxHotkeysPerInterval 1000
#MaxThreadsPerHotkey 1
#KeyHistory 50
SetWorkingDir %A_ScriptDir%
hotkeys_turned_on := true
Loop
{
Sleep, 1000
if WinActive("Grim Dawn", , "Grim Dawn ")
{
if hotkeys_turned_on
continue
}
else if !hotkeys_turned_on
continue
hotkeys_turned_on ^= true
Suspend, Toggle
}
~*LButton::
KeyWait, LButton, T0.2 ;need to hold the button for 200ms to follow
if ErrorLevel
{
while GetKeyState("LButton", "P")
{
WinGetActiveStats, Title, Width, Height, X, Y
MouseGetPos, xpos, ypos
xpos := xpos - Width/2 ;vector from the middle of the screen to the cursor
ypos := Height/2 - ypos
if xpos*xpos + ypos*ypos < 40000 ;<200 pix from center -> no rotation
continue
if (ypos > 0) and (Abs(ATan(xpos / ypos)) * 57.29578 < 20)
continue ; 20° degrees from 12 o'clock -> 40° no rotation sector
if xpos > 0 ;right half of screen -> rotate right
{
Send {n down}
Sleep, 100 ; haven't tested other values here
Send {n up}
}
else ;left half of screen -> rotate left
{
Send {b down}
Sleep, 100
Send {b up}
}
Sleep, 20
}
}
Return
Sometimes people use something similar to
#IfWinActive ahk_class Grim Dawn
to make script only work in a particular application but such lines don’t work perfectly for me
Adding a specific hotkey to pause a script also work I think
Tab::Suspend
Perfect, thanks.
Because you mentioned it in the other thread.
If people get dizzy it is mostly because they play at a low framerate (30 for me) and have motion blur disabled.
I play with nearly stable 144 fps and adaptive sync enabled but I think even 60 fps should be enough.
GD does not have the motion blur option so I guess a high framerate is the only solution.
You may be on to something but I personally just never get dizzy (in any real life situation) so I think that the genetic factor plays a role as well. In Grim Dawn I have 40 - 50 FPS
Also try playing Grim Dawn with a controller. It’s great. And you can use controller for fighting and mouse for shopping and the game dynamically switches between them. Rotating the camera with the right stick is great and you can configure everything in Steam Big Picture (for example I set my analog to activate Wind Devil whenever I touch it so it’s cast kinda automatically when I move my character with this analog stick)
I unfortunately don’t know how to use AutoHotkey with gamepads, it’s definitely not straightforward.
Didn’t know you can play GD with controller just that well. Will definitly try that out.
Have you tried to remap the xinput inputs to other keys which work with AHK?
Just an idea.
Also depends on controller for sure. For the steam controller that shouldn’t be a problem in general.
It should work but the syntaxis must be
#IfWinActive, Grim Dawn
all the text below this switch will be working only if Grim Dawn window is active.
I’m 90% sure I tested it before but it was not working 100% of the time or as expected and I moved to this ugly Loop as a consequence.
[edit] Ok, I’ve tested it and it works now. I’m keeping it for further testing.
Test failed. This makes script also work when you are using Grim Tools website -> because the tab in web browser start with “Grim Dawn”. However you can fix it with
SetTitleMatchMode, 3
#IfWinActive, Grim Dawn
The first line forces the window title to exactly match IfWinActive argument (not start with it)
That may have been the reason I ditched IfWinActive before
Haven’t tried anything yet but when I was browsing the internet for some code it seem like too much work/no guarantee it will work in the end.
However you can kinda use AHK scripts if you bind some keyboard key to gamepad button (in Steam Controller Configuration Legacy Keys submenu). Then it works like this
- you press some gamepad button
- it makes chosen keyboard key to be pressed
- Grim Dawn switches automatically from Gamepad mode to Mouse & Keyboard mode (wish these two modes could work together)
- And know you have to move the analog stick for Grim Dawn to go back to Gamepad mode again unless you don’t want your controller to work
That’s how Inquisitor Seal cast under your feet when using controller works
The easiest way to use M&K actions without modifying xinput and staying in gamepad mode would be a hardware converter like CronusMAX.
But surely you have to buy it first.
a) From my experience, event mode is way better for games (esp on slower pcs) than input.
Input is ofc faster, but its TOO fast (since it has no inherit delay, + it buffers).
using my script(s) in input mode, the game(s) often fails to recognize an action or modifier states get fubar.
eventmode increased stability of scripts alot plus you can set a global delay and presstime
b) in gd at least, you can send the keys in blind mode what reduces strain on the games i/o. that reduces the chances for stalling shift modifier eg when you use mouse + shift combo for hold position casting. (gd doesnt care when you use modifiers on action keys) eg shift-5 fires slot5 as 5 does.
c) mind to explain the reasons for your autoexec choices?
i often play with them and im curious about why you chose those.
#NoEnv
#SingleInstance Force
*#MaxHotkeysPerInterval 1000 *
#MaxThreadsPerHotkey 1
#KeyHistory 50
p.s
Setkeydelay, delay, pressduration
is crucial in messy situations (and individual dependent on machine specs)
yep, using always those in scripts, keep attention to the different formats/usages
clientstring = Grim Dawn
#If WinActive(clientstring)
#If
for hotkey part of the script and
IfWinActive, %clientstring%
{ }
for the timers etc.
combo together with mode 3
p.s use the build in windows spy to get the necessary information
LWin::
gosub, stoptimersandcounters
send {lwin}
sleep 50
Pause on
return
Its nifty because it sets the script on pause when you tab out via winkey in addition to suspend/ the stuff that is ex/included by
ifwinactive or #if winactive () etc.
Thanks a lot for the tips. I need more time to process them since I’m not so advanced.
Especially the configurable event mode seems very interesting since I may be able to remove all those ugly Sleeps from the code with it if I understand correctly.
btw Could you share some of your scripts for Grim Dawn (even for other game would be useful) so that I could learn from them?
[edit] The 80% of the script, for example Capslock hotkey
SetTitleMatchMode, 3
#IfWinActive, Grim Dawn
CapsLock::m
doesn’t work in the Event mode. Do you know what may be the reason (I checked various SetKeyDelay arguments and it didn’t help)?