AutoHotkey Homepage AutoHotkey Community
Let's help each other out
 
 FAQFAQ   SearchSearch   MemberlistMemberlist   RegisterRegister 
 ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

Is there any way to get Shift to toggle like Caps lock?

 
Reply to topic    AutoHotkey Community Forum Index -> Ask for Help
View previous topic :: View next topic  
Author Message
bbint



Joined: 17 Sep 2008
Posts: 19

PostPosted: Mon Jun 08, 2009 7:35 pm    Post subject: Is there any way to get Shift to toggle like Caps lock? Reply with quote

Right now, I need 2 buttons:

Code:
Shift::Send {Shift down}
LCtrl::Send {Shift up}


I’d like to be able to press shift, press the buttons that I want shift-modified, and then press shift to release/toggle off, just like caps lock

I want to be able to activate shift and deactivate shift by only pressing shift

Code:
Shift::
Send {Shift down}
However, if previous key was shift down
That is,
If previous GetKeyState(shift down)
Then Send {Shift up}
Return


This is incorrect because GetKeyState always sees that shift is down as soon as I press shift

I need GetKeyState to see any {Shift down} that is not in the remapping

I’m not sure as to how to stop from going around in circles

I just found these 2 posts with code that seem relevant, but I don’t understand them

Of the 2 pieces of code in the 2 posts, which one works for me?

Thanks for any help

http://www.autohotkey.com/forum/viewtopic.php?t=43107&highlight=toggle+shift

by Icarus

Code:
#SingleInstance Force

; Define source keys (on the keyboard)
; Define target keys
; In this example, pressing "a" will send "q" and "b" will send "w"
Source := "abcdefghijklmnopqrstuvwxyz1234567890-=[];'\,./"
Target := "qwertyuiqwertyuiquwyteriuyqtweriuytiquywetriuy"

; Loop through all source keys and create a hotkey for each
Loop parse, Source
   Hotkey $%A_LoopField%, PressKey

Return

; This function handles all hotkeys
PressKey:
   
   ; First, remove the $ sign
   StringReplace ThisHotkey, A_ThisHotkey, $
   
   ; Find the position of the pressed key in the "Source" string
   Position := InStr( Source, ThisHotkey )
   
   ; Pull the "twin" of the source character from the target string
   TargetChar := SubStr( Target, Position, 1 )
   
   ; If caps lock is on, send Shift+TheKey, else, send only TheKey
   If( GetKeyState( "CAPSLOCK", "T" ) )
      SendInput +%TargetChar%
   Else
      SendInput %TargetChar%   
   
Return

ESC::ExitApp


http://www.autohotkey.com/forum/viewtopic.php?t=39485&highlight=toggle+shift

by animeaime

thid code looks simpler, but animeaime is replying to someone who only needs "wasd" modified for his game

Code:
#SingleInstance Force
#NoEnv

Shifted := false
return

;Toggle <Shifted>
Control::Shifted := !Shifted

;Sends wasd
$w::Send("w")
$a::Send("a")
$s::Send("s")
$d::Send("d")

Send(Key)
{
    ;if <Shifted>, sends +%Key%
    ;else, sends %Key%

    global Shifted
   
    if Shifted
        Send, +%Key%
    else
        Send, %Key%
}
Back to top
View user's profile Send private message
Superfraggle



Joined: 02 Nov 2004
Posts: 1019
Location: London, UK

PostPosted: Mon Jun 08, 2009 8:48 pm    Post subject: Reply with quote

Code:
$shift::
Shifted:=!Shifted
If (shifted)
  Send,{Shift Down}
else
  Send,{Shift UP}
REturn


Ok thats strange, pressing left shift will activate and deactivate the shift lock. Pressing right shift will activate, but not de-activate.
_________________
Steve F AKA Superfraggle

http://r.yuwie.com/superfraggle
Back to top
View user's profile Send private message MSN Messenger
sinkfaze



Joined: 18 Mar 2008
Posts: 5044
Location: the tunnel(?=light)

PostPosted: Mon Jun 08, 2009 9:05 pm    Post subject: Reply with quote

Here is my solution tweaking Icarus' example a little bit:

Code:
Source := "abcdefghijklmnopqrstuvwxyz1234567890-=[];'\,./"
State = 0 ; variable used to toggle shift state

Loop, parse, Source
  Hotkey $%A_LoopField%, PressKey
return

LShift::
if !State ; if state = 0
  State++ ; sets state = 1 to turn on
else      ; if state = 1
  State-- ; sets state = 0 to turn off
return

PressKey:

if (State = 1 && InStr(Source,SubStr(A_ThisHotkey,2))) ; if toggle state on and key exists in source list
  Send % "+" SubStr(A_ThisHotkey,2) ; send shifted key
else
  Send % SubStr(A_ThisHotkey,2) ; send unshifted key
return

_________________
Try Quick Search for Autohotkey or see the tutorial for newbies.
Back to top
View user's profile Send private message Send e-mail
MRCS



Joined: 08 Jun 2009
Posts: 2

PostPosted: Tue Jun 09, 2009 1:07 am    Post subject: Reply with quote

I don't know whether this will help you or not, but I wanted my CapsLock to still work the same after making the common change to have Shift turn off CapsLock.

After configuring the Shift key to turn off Caps Lock (either by Attributes or ScanCode methods), two scripts needed to be created. The first one I named CapsLockR.ahk and contains the following script:
CapsLock UP::Run C:\Documents and Settings\k\CapsLock.ahk

The second one is named CapsLock.ahk and has this script:
GetKeyState, state, CapsLock, T
if state = D
SetCapsLockState, off
else
SetCapsLockState, on
exit
Back to top
View user's profile Send private message
bbint



Joined: 17 Sep 2008
Posts: 19

PostPosted: Tue Jun 09, 2009 10:56 pm    Post subject: Reply with quote

last noob question.. is sinkfaze's code supposed to work if I just copy and paste that?

$%A_LoopField%
PressKey

am I supposed to replace any of those?

thanks
Back to top
View user's profile Send private message
sinkfaze



Joined: 18 Mar 2008
Posts: 5044
Location: the tunnel(?=light)

PostPosted: Tue Jun 09, 2009 11:16 pm    Post subject: Reply with quote

bbint wrote:
...is sinkfaze's code supposed to work if I just copy and paste that?


Yes, that code is ready to work as is. The $ is a designator for how the hotkey works when it is assigned via the Hotkey command, but it is also included in the A_ThisHotkey variable when it is called to send the character. This:

Code:
SubStr(A_ThisHotkey,2)


Removes the $ from A_ThisHotkey so only the character is sent.
_________________
Try Quick Search for Autohotkey or see the tutorial for newbies.
Back to top
View user's profile Send private message Send e-mail
Lexikos



Joined: 17 Oct 2006
Posts: 7295
Location: Australia

PostPosted: Wed Jun 10, 2009 9:22 am    Post subject: Reply with quote

That script seems like overkill to me. Do you essentially want StickyKeys, but only for the (left) Shift key?
Quote:
This is incorrect because GetKeyState always sees that shift is down as soon as I press shift
Unless you specify "P" for the second parameter of GetKeyState, it returns the logical state of the key. Since the hotkey Shift:: blocks the native function of the key, its logical state should not change when you press the key. By contrast, hotkeys with the ~ modifier do not block the key's native function.

The following works for me:
Code:
LShift:: Send % "{Blind}{LShift " . (GetKeyState("LShift") ? "Up}" : "Down}")
... or the more readable version:
Code:
LShift::
    if GetKeyState("LShift") ; LShift is logically down. Release it.
        Send {Blind}{LShift Up}
    else ; LShift is logically up. Press it.
        Send {Blind}{LShift Down}
return
(See also [VxE]'s := guide ? ( to the ternary ) : ( operator ).)

If you did not want to rely on GetKeyState, you could toggle a variable:
Code:
LShift:: Send % "{Blind}{LShift " . ((lshift:=!lshift) ? "Down}" : "Up}")
(I'm sure this has been demonstrated countless times across the forum.)
Back to top
View user's profile Send private message Visit poster's website
Display posts from previous:   
Reply to topic    AutoHotkey Community Forum Index -> Ask for Help All times are GMT
Page 1 of 1

 
Jump to:  
You can post new topics in this forum
You can reply to topics in this forum


Powered by phpBB © 2001, 2005 phpBB Group