Author Topic: One Key Input  (Read 2948 times)

0 Members and 1 Guest are viewing this topic.

Offline SMcNeill

  • QB64 Developer
  • Forum Resident
  • Posts: 3972
    • Steve’s QB64 Archive Forum
One Key Input
« on: October 04, 2021, 12:55:45 pm »
For the Halloween Challenge that @bplus and @johnno56 have been talking about recently, one of the rules is to set up a program so that it only works with a single key being used.  For many folks, this could be a rather difficult thing to add into a game (How the heck do we get alphabetic responses with just the space bar??), so I thought I'd whip up a really simple little demo for one way to do this:

Code: QB64: [Select]
  1. Selection$ = "<Will be accepted after two seconds inactivity>": terminate = Timer: t = Timer
  2.  
  3.     Cls
  4.     k = _KeyDown(32)
  5.     DisplayKeys Selection
  6.     If t = 0 Then
  7.         If k Then t = Timer: Selection = (Selection + 1) Mod 26
  8.     Else
  9.         If Timer > t + 2 Then
  10.             Selection$ = Chr$(65 + Selection)
  11.             t = 0
  12.         Else
  13.             If k Then t = Timer: Selection = (Selection + 1) Mod 26
  14.             Selection$ = "<Will be accepted after two seconds inactivity>"
  15.         End If
  16.     End If
  17.     If t <> 0 Then terminate = Timer
  18.     Locate 5, 1: Print "SELECTED: "; Selection$; Chr$(13); "TERMINATION IN: "; _Ceil(terminate - Timer) + 5
  19.     _Display
  20.     _Limit 5
  21. Loop Until Timer > terminate + 5 '5 seconds of zero activity after a selection will terminate the program completely.
  22.  
  23. Sub DisplayKeys (Selection)
  24.     Color Red
  25.     Locate Selection \ 13 + 1, (Selection Mod 13) * 3 + 2: Print "[ ]"
  26.     Color BrightWhite
  27.     For j = 0 To 1
  28.         For i = 0 To 12
  29.             Locate j + 1, (i + 1) * 3: Print Chr$(65 + 13 * j + i)
  30.     Next i, j

My whole little demo here comes in at around 30 lines of code or so, so something like this should be easy enough to implement in just about any sort of program someone would need it in.  The only real change might be a need to alter the termination part of the program (in this case it's just 5 seconds of total inactivity) to whatever suits your program needs instead.  (For example, hangman might terminate after the player either wins or dies...)

Usage...  Just press the SPACEBAR.  If you can't figure it out after that, I've did something wrong!   It's just a simple 1-key input routine!  :P
https://github.com/SteveMcNeill/Steve64 — A github collection of all things Steve!

Offline bplus

  • Global Moderator
  • Forum Resident
  • Posts: 8053
  • b = b + ...
Re: One Key Input
« Reply #1 on: October 04, 2021, 01:48:50 pm »
Yeah I suppose that would work and easier to understand than what I am using; it could all fit on one line too.
Just keep punching the spacebar until you're on your choice and then wait. Each punch might add to timer I imagine.
Oh verification would not be needed, just allot of spacebar punching.

Do suggest a different highlight color than dark red for that background, I couldn't even see it in semi cloudy afternoon here in Ohio.

Well, I guess I will rewrite this method into one function and install and test.

Offline SMcNeill

  • QB64 Developer
  • Forum Resident
  • Posts: 3972
    • Steve’s QB64 Archive Forum
Re: One Key Input
« Reply #2 on: October 04, 2021, 01:55:55 pm »
You can also hold down the spacebar to autoscroll, without having to beat the key to death.  The limit 5 will max increment 5 characters per second, so you should be able to choose the letter you desire within 5 seconds or so.

I imagine something like this would work real nice and easy for a Hangman-like game.
https://github.com/SteveMcNeill/Steve64 — A github collection of all things Steve!

Offline bplus

  • Global Moderator
  • Forum Resident
  • Posts: 8053
  • b = b + ...
Re: One Key Input
« Reply #3 on: October 04, 2021, 03:08:17 pm »
Quote
I imagine something like this would work real nice and easy for a Hangman-like game.

Yeah, it would work pretty nice for Game I have for challenge, here is Function I came up with:
Code: QB64: [Select]
  1. _Title "One Key System modified by bplus" ' b+ mod 2021-10-04
  2. ' 2021-10-04 Steve One Key System   https://www.qb64.org/forum/index.php?topic=4255.msg136324#msg136324
  3. ' 2021-10-04 bplus mod to a single Function for returning user input
  4. Color 11, 0: Cls 'get black background
  5.     Print: Print "Select letter using spacebar to scroll to it: ";
  6.     c$ = choice$(24, 25, " 1234ABCDEFGHIKKLMNOPQRSTUVWXYZ")
  7.     here: If c$ <> " " Then Print c$ Else c$ = choice$(24, 25, " 1234ABCDEFGHIKKLMNOPQRSTUVWXYZ"): GoTo here:
  8. Loop Until c$ = "Q"
  9.  
  10. Function choice$ (row, col, selection$)
  11.     fg~& = _DefaultColor: bg~& = _BackgroundColor: place& = 0
  12.     saveRow = CsrLin: saveCol = Pos(0): t = Timer
  13.     GoSub show
  14.     Do
  15.         k$ = InKey$
  16.         If k$ = Chr$(27) Then System ' emergency exit
  17.         GoSub show:
  18.         If k$ = " " Then
  19.             t = Timer: place = (place + 1) Mod Len(selection$)
  20.         Else ' watch out for midnight!
  21.             If Timer - t > 4 Then choice$ = Mid$(selection$, place + 1, 1): Locate saveRow, saveCol: Exit Function
  22.         End If
  23.         _Limit 7 'so can hold down spacebar, nice
  24.     Loop
  25.     show:
  26.     Locate row, col
  27.     For i = 1 To Len(selection$)
  28.         If i = place + 1 Then Color bg~&, fg~& Else Color fg~&, bg~&
  29.         Locate row, col - 1 + i: Print Mid$(selection$, i, 1);
  30.     Next
  31.     Color fg~&, bg~&
  32.     Return
  33.  

I am leaving a space at the start of selections to signal the app that the user left to find Pete in the Submarine.

Offline johnno56

  • Forum Resident
  • Posts: 1270
  • Live long and prosper.
Re: One Key Input
« Reply #4 on: October 04, 2021, 04:18:44 pm »
Cool... One slight problem... Keyboard buffer may be a thing... Holding Space to scroll; Release... and the 'selector' keeps moving for a short time... I do not know the QB64 commands well enough to fix that... Moo Ha Ha....
Logic is the beginning of wisdom.

Offline bplus

  • Global Moderator
  • Forum Resident
  • Posts: 8053
  • b = b + ...
Re: One Key Input
« Reply #5 on: October 04, 2021, 04:30:57 pm »
Cool... One slight problem... Keyboard buffer may be a thing... Holding Space to scroll; Release... and the 'selector' keeps moving for a short time... I do not know the QB64 commands well enough to fix that... Moo Ha Ha....

You could employ _KeyClear which clears keyboard buffer but I like trying to play shuffle board with the Spacebar, man it's a b when the you go slightly past the letter you want!

Offline SMcNeill

  • QB64 Developer
  • Forum Resident
  • Posts: 3972
    • Steve’s QB64 Archive Forum
Re: One Key Input
« Reply #6 on: October 04, 2021, 05:00:05 pm »
Cool... One slight problem... Keyboard buffer may be a thing... Holding Space to scroll; Release... and the 'selector' keeps moving for a short time... I do not know the QB64 commands well enough to fix that... Moo Ha Ha....

No keyboard buffer.  You’re not bothering to check if a series of keys were pressed.  All we need to know is if a _KEYDOWN even is occurring or not.
https://github.com/SteveMcNeill/Steve64 — A github collection of all things Steve!

Offline TempodiBasic

  • Forum Resident
  • Posts: 1792
Re: One Key Input
« Reply #7 on: October 04, 2021, 07:27:08 pm »
Well
I find fine your different proposals to get input using a line/table of the choices available (set of characters).
I have build this binary selection method that you can evaluate here
https://www.qb64.org/forum/index.php?topic=4257.msg136345#msg136345
Programming isn't difficult, only it's  consuming time and coffee

Offline bplus

  • Global Moderator
  • Forum Resident
  • Posts: 8053
  • b = b + ...
Re: One Key Input
« Reply #8 on: October 09, 2021, 12:53:43 pm »
I have Steve's idea evolved to this in my code, free for anyone who wants to use in challenge and needs letters or menu choices by number up to 10 digits.

Code: QB64: [Select]
  1. _Title "One Key - Best so far Choice$" ' b+ 2021-10-09
  2. ' Best in my opinion One Key Control as date above
  3.  
  4.  
  5. 'setup for Choice$ function
  6. Dim Shared KeyTimer, place ' preserve values between choice$ calls
  7. KeyTimer = Timer ' <<<<<<<<< init outside main choice calling loop
  8.     Cls
  9.  
  10.     '
  11.     ' Here we can run all the backgound graphics we want with no pauses waiting for input
  12.     '
  13.  
  14.     Print "Use this One Key tool to Input your name or something using only spacebar!"
  15.     Print "Select by spacing until highlite is over your choice letter or menu #."
  16.     Print "Use Menu #1 at end of letters to signal the end of you input, like enter."
  17.     Print "Use Menu #2 to actually insert a space in the text!"
  18.     Print "Use escape to quit"
  19.     Print
  20.     Print "Progress: "; text$
  21.     '''' KeyTimer = Timer ' <<<<<<<<<<<<<<<<<<<<<<<<<<<< no not just before calling choice, start outside loop
  22.     c$ = choice$(10, 5, " A B C D E F G H I J K L M N O P Q R S T U V W X Y Z 1 2 ")
  23.     If c$ <> "" And c$ <> " " And c$ <> "1" And c$ <> "2" Then text$ = text$ + c$
  24.     If c$ = "1" Then
  25.         Print "User input "; text$; ", resetting for another go."
  26.         KeyTimer = Timer 'reset for another go round
  27.         text$ = ""
  28.         _Delay 3
  29.     End If
  30.     If c$ = "2" Then text$ = text$ + " "
  31.     _Limit 30
  32.  
  33. Function choice$ (row, col, selection$) ' One Key User Input System with tiny little setup
  34.     ' setup  for best results space out selections$ for one letter at a time choice
  35.     ' dim shared KeyTimer in main, set KeyTimer like KeyTimer = timer outside main loop with Choice$
  36.     Dim As _Unsigned Long fg, bg
  37.     Dim As Integer saveRow, saveCol, i
  38.     Dim k$
  39.     fg~& = _DefaultColor: bg~& = _BackgroundColor
  40.     saveRow = CsrLin: saveCol = Pos(0)
  41.     If _KeyDown(27) Then System ' emergency exit
  42.     GoSub show:
  43.     k$ = InKey$
  44.     If k$ = " " Then KeyTimer = Timer: place = (place + 1) Mod Len(selection$)
  45.     If Timer - KeyTimer >= 4 Then choice$ = Mid$(selection$, place + 1, 1): place = 0
  46.     Locate saveRow, saveCol: Exit Function
  47.  
  48.     show:
  49.     Locate row, col
  50.     For i = 1 To Len(selection$)
  51.         If i = place + 1 Then Color bg~&, fg~& Else Color fg~&, bg~&
  52.         Locate row, col - 1 + i: Print Mid$(selection$, i, 1);
  53.     Next
  54.     '_Display  now the main loop handles since this is no longer a loop
  55.     Color fg~&, bg~&
  56.     Return

This does not cover the midnight problem with timer, who's up that late anymore? :)

Offline Cobalt

  • QB64 Developer
  • Forum Resident
  • Posts: 878
  • At 60 I become highly radioactive!
Re: One Key Input
« Reply #9 on: October 12, 2021, 03:43:23 am »
Why does this sound like some kind of Atari wana-be challenge? Hell they only gave you that one damn button.

Does mouse movement count? hover the mouse over something and use the 'one' button to activate that option.
Granted after becoming radioactive I only have a half-life!

Offline bplus

  • Global Moderator
  • Forum Resident
  • Posts: 8053
  • b = b + ...
Re: One Key Input
« Reply #10 on: October 12, 2021, 09:42:35 am »
Why does this sound like some kind of Atari wana-be challenge? Hell they only gave you that one damn button.

Does mouse movement count? hover the mouse over something and use the 'one' button to activate that option.

@Cobalt

Yes it does come from a Competition and discussion here at this forum and a Halloween Challenge for this forum that extends the specification for extra credit a Halloween Theme and/or screen 0 text, Console would count too I should think.
https://www.qb64.org/forum/index.php?topic=4245.msg136193#msg136193

Using the mouse positioning has already been ruled out, Steve brought it up maybe in the above link.
https://www.qb64.org/forum/index.php?topic=4245.msg136415#msg136415

Pete, Dav and I so far have posted code taking up the challenge. Pete stayed in Screen 0 (extra credit) and converted old code to Halloween Theme in link above, I think, Yes Here:
https://www.qb64.org/forum/index.php?topic=4245.msg136564#msg136564

Dav has a One key Halloween Game and has hinted at a bundle of them (graphics mode).
Dav's Jack Stack: https://www.qb64.org/forum/index.php?topic=4258.msg136358#msg136358

I am running a graphics version for Halloween and another Screen 0 variation on the Crypt-o-Gram Game in Text Mode: https://www.qb64.org/forum/index.php?topic=4258.msg136358#msg136358

Offline Cobalt

  • QB64 Developer
  • Forum Resident
  • Posts: 878
  • At 60 I become highly radioactive!
Re: One Key Input
« Reply #11 on: October 12, 2021, 12:21:03 pm »
Well really haven't felt like programing lately, but I will give this a shot. Probably don't have the time but who knows.
Granted after becoming radioactive I only have a half-life!

Offline TempodiBasic

  • Forum Resident
  • Posts: 1792
Re: One Key Input
« Reply #12 on: October 15, 2021, 05:35:15 am »
One Key Challange
I have understood that the input system allowed was only Keyboard. No mouse No joystick.

about snippets posted here, they are very remarkable.
All 3 codes use the method
wait input, do while input, stop more than X time = finished
so you count time of waiting only at moment that input stops,
moreover until timeout, you can restart the choice procedure to change your selection.

I think that I'll turn my binary search including this time using method that is fastest to choose for all the humans (it lets remember me the Hall of Fame panel of cabinet videogames),
the previous one is good for other goals (just think when you play a videogame that let you choose the starting level from a panel).

Thanks for talking and sharing

PS
@SMcNeill
Steve , I know you are professional and expert.... why do you post an Old BASIC style snippet? With all those CHR$?
It is great but so poor flexible and poor reusable! How many code Should I change to show the alphabet in QWERTY order at the place of natural order?  :P


Programming isn't difficult, only it's  consuming time and coffee