Page 1 of 2

Fastest way to get Keyboard presses

Posted: Thu Jan 24, 2008 4:18 pm
by Sinuvoid
Ok, It been awhile but here goes...

I've made a sound program that uses PLAY and INKEY commands to make sound with key presses. Is there a faster method for it to cycle through the keys in a DO LOOP? Heres the structure of what my code would look like.

Code: Select all

CLS

DO
k$ = INKEY$

CASE SELECT k$ 'or is it SELECT CASE :P

CASE "q"
PLAY "E"

CASE "w"
PLAY "F"

CASE "e"
PLAY "b"

SELECT END
LOOP

You again!

Posted: Thu Jan 24, 2008 4:47 pm
by burger2227
Actually PLAY causes the delay, not INKEY$. The PLAY notes are actual musical frequencies for certain tones, but the internal speaker does not work well enough for musicians.

ON PLAY can actually be used as a crude delay in programs too.

I suggest you PLAY around with it. You probably have already used SOUND. It delays loops some too, but code after it may execute before the sound is done.

Ted

Posted: Thu Jan 24, 2008 4:56 pm
by Sinuvoid
Yeah burger, I know that if you use "E8" that it waits around have a second
(half note) But What I want is for it to cycle through the CASE's really fast so it can pick up the key presses fast. Like lets say I had 100 CASE's. And I needed it to cycle through them really fast, how could I do that? And maybe speeding it up with something other than INKEY$.

(BTW, What CHR$'s are the arrow keys and the SHIFT button?)

Posted: Thu Jan 24, 2008 6:24 pm
by BDZ
I'm not exactly sure what you are shooting for, but try putting PLAY "MB" before the rest of your PLAY statements. That will make the notes play in the background while the program keeps executing.

Posted: Thu Jan 24, 2008 6:37 pm
by Sinuvoid
OK, sounds good, and I found a solution. Use INP command. But I need someoen to explain more about it to me and how to find the numbers(ASCII?). Example, I want it to use the arrow keys. What are they're numbers(ASCII?)?

EDIT:Nevermind, found it. Thanks for tips guys :P

Posted: Thu Jan 24, 2008 7:52 pm
by Patz QuickBASIC Creations
Though not entirely better, you could do:

Code: Select all

CLS 
DO

DO 
k$ = INKEY$ 
LOOP UNTIL K$ <> ""

SELECT CASE k$

CASE "q" 
PLAY "mbE" 

CASE "w" 
PLAY "mbF" 

CASE "e" 
PLAY "mbB" 

END SELECT
LOOP

Posted: Thu Jan 24, 2008 9:11 pm
by Sinuvoid
OK, its giving me a weird error. Paste this code into Qbasic and run, and you'll see. Is this cause its in Hex and I should convert it into decimal?

Code: Select all

DO
k = INP(&H60)

SELECT CASE k

CASE 48
PRINT CHR$(24); " ";
PLAY "MB"
PLAY ">d32<"

CASE 21
PRINT CHR$(22); " ";
PLAY "MB"
PLAY "<d32>"

CASE 50
PRINT CHR$(25); " ";
PLAY "MB"
PLAY "f32"


CASE 4B
PRINT CHR$(26); " ";
PLAY "MB"
PLAY "a32"

CASE 4D
PRINT CHR$(27); " ";
PLAY "MB"
PLAY "b32"

SELECT END

kp$ = INKEY$
IF kp$ = "1" THEN GOTO MAINM
LOOP

Posted: Thu Jan 24, 2008 9:31 pm
by Patz QuickBASIC Creations
First off, you can't use characters in CASE, ie CASE 4B, unless they are hexadecimal, in which case you need to tell it so. And, you don't need to have the INP in there, just use the one I posted, it works fine.

Posted: Thu Jan 24, 2008 9:42 pm
by Sinuvoid
1, how do I tell it???
2, I use INP because its fast :) and plus ive never used it Before so its good practise :P

EDIT: Ok, the INP isnt working for me. I've tried tut's but no luck. Can you guys explain it for me please :D

2, How can I make letters typed in the INPUT command come out as *'s (exmaple, password program)

New thread?

Posted: Fri Jan 25, 2008 1:39 pm
by burger2227
Don't use INPUT...........use an INKEY$ loop that runs until a user presses the enter key. INKEY can also filter out certain key entries, such a only number or letter presses. Look up the ASCII codes for the type of entry you need.

When a valid key is pressed, just print an asterisk. You can also allow backspacing by checking for Character code 8.

Apparently you cannot use CHR$ and (8) in a text here LOL.

INP(&H60) reads the keyboard scancodes. A key release is 128 more than the press value returned. Make a DO loop and just PRINT it. Use LOOP UNTIL code = 1, the escape key. Few of the scancodes are the same as ASCII.

INP is for reading a port value. OUT changes the values.

Ted

Posted: Fri Jan 25, 2008 4:16 pm
by Sinuvoid
Can you tell me in depth how to use the INP command please burger :D I've looked at tuts and QB help but no luck :(

EDIT: CHR$(what??)

Posted: Sat Jan 26, 2008 1:17 pm
by Seb McClouth
Lee wrote:2, How can I make letters typed in the INPUT command come out as *'s (exmaple, password program)
I'm used this routine in a older vrsion of QBinux:

Code: Select all

        DO 
          PRINT tdspl$;"   " 'Display storing variable 
          press$ = INKEY$ 
          IF press$ <THEN> 0 THEN 
                sb = LEN(dspl$) 
                Ndspl$ = MID$(dspl$, 1, (sb - 1)) 
                dspl$ = Ndspl$ 
            ELSEIF press$ = CHR$(13) THEN 
                EXIT DO 
         ELSE 
                dspl$ = dspl$ + press$ 
                tdspl$=tdspl$ + "*"
         END IF 
  END IF 
  LOOP 
I use locate to print it on the same line. The code is not written by me, just adapted by me. The code was written by Rattrapmax6.

Here's his code:
Rattrapmax6 wrote:]Right.. I sat back and wrote a more simulated Password system, it asks for username, then the password.. and while you type the pasword it displays it as: "******"..

Very nice, and something you can play with, look over, and learn from maybe.. :wink:

Psssys.bas (Made in FreeBasic, Tested in QBasic.. Runs well in both..)

Code: Select all

'Username/Password system by Rattrapmax6(Kevin(x.t.r.GRAPHICS))
' Two test usernames: User1 and Admin
'Passwords: User1 = Enter || Admin = LetMeIn
' System is case-insensitive.. :)

CLS 'Clear screen
PRINT "Welcome!"
PRINT "Enter User:";
DO
    LOCATE 2, 12: PRINT dspl$; "   " 'Display storing varible
    press$ = INKEY$
    IF press$ <THEN> 0 THEN
            sb = LEN(dspl$)
            Ndspl$ = MID$(dspl$, 1, (sb - 1))
            dspl$ = Ndspl$
        'Filter Enter, Exit for checking
        ELSEIF press$ = CHR$(13) THEN
            EXIT DO
        'Add up user input to varible
        ELSE
            dspl$ = dspl$ + press$
        END IF
    END IF
LOOP

SELECT CASE UCASE$(dspl$)
CASE "USER1"
    PRINT "Enter Pasword:";
    usr$ = dspl$
    dspl$ = ""
    DO
        LOCATE 3, 15: PRINT pss$; "   "' NEW, print the ** for the varible
        press$ = INKEY$
        IF press$ <THEN> 0 THEN
                sb = LEN(dspl$)
                Ndspl$ = MID$(dspl$, 1, (sb - 1))
                Npss$ = MID$(pss$, 1, (sb - 1)) 'NEW, Subtract ***
                dspl$ = Ndspl$
                pss$ = Npss$ 'Restore the ***
            ELSEIF press$ = CHR$(13) THEN
                EXIT DO
            ELSE
               dspl$ = dspl$ + press$
               pss$ = pss$ + "*" 'NEW, calculate how many ***
            END IF
        END IF
    LOOP
    IF UCASE$(dspl$) = "ENTER" THEN 
        PRINT "Welcome to our servers, "; usr$; "!"
        PRINT "Press any key to end..."
        SLEEP
        END
    ELSE
        PRINT "Username and password to not compute!"
        PRINT "Press any key do end..."
        SLEEP
        END
    END IF
CASE "ADMIN"
    PRINT "Enter Pasword:";
    usr$ = dspl$
    dspl$ = ""
    DO
        LOCATE 3, 15: PRINT pss$; "   "
        press$ = INKEY$
        IF press$ <THEN> 0 THEN
                sb = LEN(dspl$)
                Ndspl$ = MID$(dspl$, 1, (sb - 1))
                Npss$ = MID$(pss$, 1, (sb - 1))
                dspl$ = Ndspl$
                pss$ = Npss$
            ELSEIF press$ = CHR$(13) THEN
                EXIT DO
            ELSE
               dspl$ = dspl$ + press$
               pss$ = pss$ + "*"
            END IF
        END IF
    LOOP
    IF UCASE$(dspl$) = "LETMEIN" THEN 
        PRINT "Welcome to our servers, "; usr$; "!"
        PRINT "Press any key to end..."
        SLEEP
        END
    ELSE
        PRINT "Username and password do not compute!"
        PRINT "Press any key to end..."
        SLEEP
        END
    END IF
CASE ELSE
    PRINT "No user under that name: Try again..."
    PRINT "Press any key to end..."
    SLEEP
    END
END SELECT 
[/quote]

Posted: Sat Jan 26, 2008 4:52 pm
by Sinuvoid
thanks McClouth! Sure that'll help :)

Now, can someone explain teh INP command in some detail please.
I'm using it to get input from the keyboard but when I use it, it like prints out 8 "Hey's" or whatever. What Im I doing wrong? Here's an example:

Code: Select all

CLS
DO
k = INP(&H60)

CASE SELECT k

CASE 2
PRINT "This is number 2";

CASE 3
PRINT "This is number 3";

END SELECT
LOOP

Posted: Sat Jan 26, 2008 5:51 pm
by Seb McClouth
I suspect that INP(&H60) doesn't work the same as INKEY$.

I'll check it out later for you.

Your silly

Posted: Sat Jan 26, 2008 7:44 pm
by burger2227
This will show you the codes returned when you press most any keys. Save this routine in case you try to use the codes in a program for reference:

Code: Select all

DO 
   scancode = INP(&H60)
   LOCATE 5, 10: PRINT scancode
LOOP UNTIL scancode = 1  'escape key press
Notice that the release code is 128 more than the press code. The codes do not change for upper or lower cases either.

Ted

Posted: Sat Jan 26, 2008 9:49 pm
by Sinuvoid
Thanks Burger and McClouth. Question Burger, Why when I make a program (like my last post) and press 2 or 3 it prints out like 8 of them?

Posted: Sat Jan 26, 2008 9:55 pm
by Patz QuickBASIC Creations
I made this a long time ago... Hopefully you can get it to work without too much work. I've commented it so you can see exactly what's going on and exactly how to use it... Basic knowledge of LOCATE a major plus.

http://pastebin.ca/874102

Posted: Sat Jan 26, 2008 10:05 pm
by Sinuvoid
Complicated, but useful :P So to back space I guess, it involves messing around with the LOCATE command...btw, do you know my problem? (With the INP command in my previous post :P )

Posted: Sun Jan 27, 2008 10:24 am
by Patz QuickBASIC Creations
I don't recommend using INP, as if you make the program correctly, INKEY$ should be enough for most purposes.

To use backspace, you have to print a blank space (CHR$(32) or " "), and then locate back to that space. That's the most simple way to do it.

Edit: To do something similar to the pssys program above, just make a program with the PInput$ function, and then do the following code.

Code: Select all

DO UNTIL UserAllowed%
 CLS
 PRINT "Username:"
 User$ = PINPUT$(15,1,30,0,"")
 PRINT "Password:"
 Pass$ = PINPUT$(15,2,30,ASC("*"),"")
 IF User$ = "USER1" AND Pass$ = "ENTER" THEN UserAllowed% = 1
 IF User$ = "ADMIN" AND Pass$ = "LETMEIN" THEN UserAllowed% = 1
LOOP

Posted: Sun Jan 27, 2008 12:46 pm
by Seb McClouth
I had posted a big post with some links concerning &H60 and INP but indeed like Pats said, better use Inkey$.

I guess the post got lost somehow, well no worries.