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 

Hybrid combinations - possible or not?

 
Post new topic   Reply to topic    AutoHotkey Community Forum Index -> Ask for Help
View previous topic :: View next topic  
Author Message
Da Rossa



Joined: 06 Dec 2007
Posts: 174

PostPosted: Fri Jan 18, 2008 8:08 am    Post subject: Hybrid combinations - possible or not? Reply with quote

This time (2 in 24, I'm no flooder Razz) I was thinking about sending a macro by pressing a modificator key, like CTRL, then, with it pressed, we type a hotstring. This could be to perform other actions, not only sending keystroke macros.

Example:
::btw:: = by the way;
{shiftdn}::btw::{shiftup} = BY THE WAY <-- this is already possible

Ctrl+::ff:: (hold Ctrl then type ff) --> Run \...\Firefox.exe <-- not possible yet as far as I know.

Got it?
How do we do that?
Back to top
View user's profile Send private message
Lexikos



Joined: 17 Oct 2006
Posts: 2557
Location: Australia, Qld

PostPosted: Fri Jan 18, 2008 8:42 am    Post subject: Reply with quote

Here's one way:
Code:
Ctrl::
    Input, cmd
    MsgBox %cmd%
return
Ctrl Up::Input ; end Input
Unfortunately Ctrl must be blocked (Ctrl:: vs ~Ctrl::) since it would otherwise prevent the keystrokes from being recognized as regular text. You could use LCtrl or RCtrl instead, if you still need a Ctrl key.

Here's another way that "hooks" only alphabetic keys:
Code:
~Ctrl::
    ; Create/enable a hotkey for each letter of the alphabet.
    Loop 26
        Hotkey % "^" Chr(A_Index+96), Type, On
return
~Ctrl Up::
    Loop 26
        Hotkey % "^" Chr(A_Index+96), Type, Off

    if text
    {
        MsgBox %text%
        text =
    }
return

Type:
    text .= SubStr(A_ThisHotkey,2)
return
Back to top
View user's profile Send private message
Sakurako



Joined: 10 May 2007
Posts: 142

PostPosted: Fri Jan 18, 2008 8:51 am    Post subject: Reply with quote

Code:
^f::
KeyPressRec := KeyPressRec A_ThisHotkey
If KeyPressRec = ^f^f
{
 msgbox, done
 KeyPressRec =
}
return

_________________
Back to top
View user's profile Send private message
Da Rossa



Joined: 06 Dec 2007
Posts: 174

PostPosted: Fri Jan 18, 2008 9:27 am    Post subject: Reply with quote

Sakurako wrote:
Code:
^f::
KeyPressRec := KeyPressRec A_ThisHotkey
If KeyPressRec = ^f^f
{
 msgbox, done
 KeyPressRec =
}
return


This appears to be the closest to the goal, but I couldn't understand the logic as a whole. In that code, the only thing I can do is to set "Ctrl+FF" to trigger the action, but I couldn't change it to any other combination, for example: Holding CTRL then typing "fight" to perform the action (msgbox in the case). Where exactly should I put the letters f i g h t ?

@lexikos: your second code is almost perfect, it actually works but doesn't release the CTRL key for further different uses. I relized that although I can set any little text to be used in the hotstring while holding ctrl, this includes the traditional uses like ctrl+c, ctrl+v etc. Actually I'm seeking a way to have it trigger only when some specific hotstrings are input, not any text like your code suggests Sad
Back to top
View user's profile Send private message
Lexikos



Joined: 17 Oct 2006
Posts: 2557
Location: Australia, Qld

PostPosted: Fri Jan 18, 2008 10:02 am    Post subject: Reply with quote

Da Rossa wrote:
@lexikos: your second code is almost perfect, it actually works but doesn't release the CTRL key for further different uses.
You have full control over what it does when you type something. i.e. All you need to do is explicitly tell it what "further different uses" to allow. The following will allow Ctrl+single-key-press to perform its usual function (with the exception that you must release Ctrl first):
Code:
~Ctrl::
    ; Create/enable a hotkey for each letter of the alphabet.
    Loop 26
        Hotkey % "^" Chr(A_Index+96), Type, On
return
~Ctrl Up::
    Loop 26
        Hotkey % "^" Chr(A_Index+96), Type, Off

    if text
    {
        if StrLen(text) = 1
            Send ^%text%
        else

            MsgBox %text%
        text =
    }
return

Type:
    text .= SubStr(A_ThisHotkey,2)
return

Alternately, you could allow multiple key-presses if the string isn't recognized:
Code:
Send {Ctrl Down}%text%{Ctrl Up}
If you also pressed other keys/key combinations that aren't caught by the script, the keystrokes would end up out of order, with the ^alphabetic keystrokes grouped at the end.

Perhaps a better solution would be to check at each key-press whether the text matches part of a recognized command. If it does not, send what was typed and disable the hotkeys until Ctrl is pressed again.

Consider using a key that isn't usually used as a modifier. For instance:
Code:
$Space::
    SpaceTick := A_TickCount
   
    ; Let user enter a command/text. Does not return
    Input, seq    ; until terminated by Space Up::
   
    if (A_TickCount-SpaceTick < 250 or seq="")
    {  ; So as to not interfere with quick typing, count this as having
        Send {Space}%seq%   ; released Space before entering %seq%.
        return
    }
    ; Show entered text.
    MsgBox %seq%
return
Space Up::Input ; end Input-in-progress
I posted this as a reply to spacebar as a hotkey trigger, plus more..
Back to top
View user's profile Send private message
Lemming



Joined: 20 Dec 2005
Posts: 150
Location: Malaysia

PostPosted: Fri Jan 18, 2008 4:12 pm    Post subject: Re: Hybrid combinations - possible or not? Reply with quote

Sounds like a "detect double-presses of a hotkey" problem; you're checking whether the user pressed ctrl-f twice. The SetTimer documentation has example code for this (scroll to example #3):

http://www.autohotkey.com/docs/commands/SetTimer.htm

As a bonus, you can define the time window (e.g. within 500ms) for the double-press.

Da Rossa wrote:
This time (2 in 24, I'm no flooder Razz) I was thinking about sending a macro by pressing a modificator key, like CTRL, then, with it pressed, we type a hotstring. This could be to perform other actions, not only sending keystroke macros.

Example:
::btw:: = by the way;
{shiftdn}::btw::{shiftup} = BY THE WAY <-- this is already possible

Ctrl+::ff:: (hold Ctrl then type ff) --> Run \...\Firefox.exe <-- not possible yet as far as I know.

Got it?
How do we do that?
Back to top
View user's profile Send private message
Sakurako



Joined: 10 May 2007
Posts: 142

PostPosted: Fri Jan 18, 2008 5:03 pm    Post subject: Reply with quote

Da Rossa wrote:
Sakurako wrote:
Code:
^f::
KeyPressRec := KeyPressRec A_ThisHotkey
If KeyPressRec = ^f^f
{
 msgbox, done
 KeyPressRec =
}
return


This appears to be the closest to the goal, but I couldn't understand the logic as a whole. In that code, the only thing I can do is to set "Ctrl+FF" to trigger the action, but I couldn't change it to any other combination, for example: Holding CTRL then typing "fight" to perform the action (msgbox in the case). Where exactly should I put the letters f i g h t ? ...
Code:
KeyCheck = ^f|^i|^g|^h|^t ;List of key to detect
Loop, Parse, KeyCheck, |
 If StrLen(A_LoopField) = 1
  Hotkey, ~%A_LoopField%, KeyPress
 Else if (A_LoopField = "^c") or (A_LoopField = "^v") ;~Hotkey
  Hotkey, ~%A_LoopField%, KeyPress
 Else ;Hotkey
  Hotkey, %A_LoopField%, KeyPress
KeyNum = 0
return

KeyPress:
KeyPressRec := KeyPressRec A_ThisHotkey
IfInString, KeyPressRec, ~
{
 StringReplace, KeyPressRec, KeyPressRec, ~
 If StrLen(A_ThisHotkey) = 2
  KeyNum += 1
}
if KeyPressRec contains ^t,^f^f ;^t, ^f^f
{
 SendInput, {Backspace %KeyNum%}
 {
  msgbox, %KeyPressRec% ;command(s) to perform
 }
 KeyPressRec =
 KeyNum = 0
}
return

_________________
Back to top
View user's profile Send private message
Da Rossa



Joined: 06 Dec 2007
Posts: 174

PostPosted: Sat Jan 19, 2008 7:07 am    Post subject: Reply with quote

@ Lexikos:

your first code, this
Code:
~Ctrl::
    ; Create/enable a hotkey for each letter of the alphabet.
    Loop 26
        Hotkey % "^" Chr(A_Index+96), Type, On
return
~Ctrl Up::
    Loop 26
        Hotkey % "^" Chr(A_Index+96), Type, Off

    if text
    {
        if StrLen(text) = 1
            Send ^%text%
        else
            MsgBox %text%
        text =
    }
return

Type:
    text .= SubStr(A_ThisHotkey,2)
return

has a drawback: it slows down the past process. Also, it is impossible to have CTRL held down and pressing V repeated times to past repeated times, instead, your msgbox will popup.

(to be concluded Very Happy)
_________________
AHK is perfect.
Back to top
View user's profile Send private message
Lexikos



Joined: 17 Oct 2006
Posts: 2557
Location: Australia, Qld

PostPosted: Sun Jan 20, 2008 2:13 am    Post subject: Reply with quote

Da Rossa wrote:
your first code ... has a drawback: it slows down the past process. Also, it is impossible to have CTRL held down and pressing V repeated times to past repeated times, instead, your msgbox will popup.
Obviously you can't have Ctrl+V work immediately and allow it to be typed. That's just greedy. Razz Of course, you could always avoid registering a hotkey for it, but then you'd get false positives like "fvf" = "ff".

Anyway, I am certain my other suggestion would solve the problem more completely.
I wrote:
Perhaps a better solution would be to check at each key-press whether the text matches part of a recognized command. If it does not, send what was typed and disable the hotkeys until Ctrl is pressed again.
Back to top
View user's profile Send private message
Da Rossa



Joined: 06 Dec 2007
Posts: 174

PostPosted: Sun Jan 20, 2008 12:59 pm    Post subject: Reply with quote

Although I'm still a primary newbie, I realize that using CTRL can be too hassling. what if I chose Shift instead? The intention is: Hold down shift, press some numbers on the numpad and release Shift to run the command, either launching a program, a file, or playing a macro, making something similar to some characters triggered by alt+169 for example. It even would be fancy, like those "alarm codes" you install in your houses for protection, isn't that cool? Razz

However I still have to do some research before asking you further about this subject, I'm not following you. Sad

Thanks anyway!
_________________
AHK is perfect.
Back to top
View user's profile Send private message
Lexikos



Joined: 17 Oct 2006
Posts: 2557
Location: Australia, Qld

PostPosted: Mon Jan 21, 2008 2:12 am    Post subject: Reply with quote

It's basically the same whatever keys you choose: on trigger-key press, enable the "code" hotkeys. When one is pressed, append the appropriate character to the string. On trigger-key release, do something with the string and disable the "code" hotkeys.

Unfortunately Shift + Numpad has a complication: Windows sends different key-codes for the numpad when you hold Shift. You'll never get +Numpad4, for example, only +NumpadLeft. This makes it slightly more complicated to build the "code" string.

Personally, I think Shift + Numpad is awkward. Numpad0 + Numpad1-9 makes more sense, since it can be used one-handed.

Anyway, this is roughly what I meant earlier (additions in dark red):
Code:
#UseHook  ; doesn't seem to work correctly without this?
words =  ; this should contain the list of valid command words
(
copy
paste
)


~Ctrl::
    ; Create/enable a hotkey for each letter of the alphabet.
    Loop 26
        Hotkey % "^" Chr(A_Index+96), Type, On
return
~Ctrl Up::
    Loop 26
        Hotkey % "^" Chr(A_Index+96), Type, Off

    if text
    {
        if RegExMatch(words, "m`n)^\Q" text "\E$")  ; if %text% matches a complete word
            MsgBox %text%
        else
            Send {Ctrl Down}%text%{Ctrl Up}
        text =
    }
return

Type:
    text .= SubStr(A_ThisHotkey,2)
    if ! RegExMatch(words, "m`n)^\Q" text "\E")  ; if no word begins with %text%
        goto ~Ctrl Up  ; end now
return
Basically, it stops accepting input as soon as it knows no word can match.

Regular expressions (RegExMatch) can be considered an advanced topic. There are other ways, but RegExMatch is probably the shortest.
Back to top
View user's profile Send private message
Da Rossa



Joined: 06 Dec 2007
Posts: 174

PostPosted: Mon Jan 21, 2008 6:34 am    Post subject: Reply with quote

Hum, let's say I understood 1% of it Very Happy
How do I append the hotkeys I'm willing to set to your code?
The other problem is that I simply don't know most basic/fundamental concepts and definitions, aggravated by the fact that English is not my native language... what's, for example, a "hook"? :$
_________________
AHK is perfect.
Back to top
View user's profile Send private message
Lexikos



Joined: 17 Oct 2006
Posts: 2557
Location: Australia, Qld

PostPosted: Mon Jan 21, 2008 7:42 am    Post subject: Reply with quote

"Hook" may be defined as:
anything that catches; snare; trap.

In the context of AutoHotkey, it refers to the "keyboard hook", which is a feature of the Windows API; it "catches, snares or traps" keystrokes.

In this case, I use #UseHook as an alternative to manually prepending the $ modifier to each hotkey. Either one will force a hotkey to use the "keyboard hook", and as a side-effect prevent Send from triggering the hotkey.

All of the individual pieces of the script I posted are explained in the manual (which is of course written in English...)
Quote:
How do I append the hotkeys I'm willing to set to your code?

Code:
words =  ; this should contain the list of valid command words
(
copy
paste
ff
)
Back to top
View user's profile Send private message
Da Rossa



Joined: 06 Dec 2007
Posts: 174

PostPosted: Tue Jan 29, 2008 4:32 am    Post subject: Reply with quote

Thanks Lexikos...
But I have a better idea: I'm gonna read the entire help file, so that I can have a clue about those things. If there are other texts/articles/subjects that I should read prior to learning the AHK intermediates (I know the beginning of the introduction to basics), please let me know!
_________________
AHK is perfect.
Back to top
View user's profile Send private message
Display posts from previous:   
Post new topic   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