- Home /
How to detect which key is pressed?
I am trying to determine which Keyboard key is pressed to use that in a switch statement, but apparently the code I try to use is not working. It was taken more or less directly from the Script Reference, but 'Event.current' doesn't seem to detect my keyboard strokes. When I print it to the status bar, it says 'Null'.
var pressKey;
var dirEvent : Event = Event.current;
if(dirEvent.isKey) {
pressKey = dirEvent.keyCode;
}
Can you elaborate to why you want to do it this way over using specific inputs. ie Input.getButton/key etc
Well...Input.Get$$anonymous$$ey returns true or false, so I have to query each button separately. I would prefer a function that returns the pressed $$anonymous$$ey, so I can use a Switch() statement ins$$anonymous$$d of multiple if() statements. It looks nicer and also Switch() has a default that is used whenever a button is pressed that I did not specify.
surely if the condition of the switch is the bool result from a Input.get$$anonymous$$ey call then you can still use it that way without any extra ifs.
To maybe make it clearer, here is the current version of the script. I have resorted to the multiple If statements and it does work, but I have encountered an error, that only happens sporadically, so I would still be thankful for a more elegant solution.
var speed = 1;
private var heading;
private var oldPos;
private var newPos;
function Awake () {
transform.position = Vector3(0, 0, 0);
}
function Update () {
if(Input.any$$anonymous$$ey) {
statics.playerActive = true;
}
if(statics.playerActive) {
statics.turnActive = true;
statics.playerActive = false;
}
}
function FixedUpdate () {
if(statics.turnActive) {
if(statics.currentDuration == 0) {
plDirection ();
}
statics.currentDuration += 1;
oldPos = transform.position;
newPos = oldPos + Vector3(heading.x+statics.g*heading.y, 0, statics.b*heading.y);
transform.Translate((newPos-oldPos)*speed, Space.World);
if(statics.currentDuration == statics.turnDuration) {
statics.currentDuration = 0;
statics.turnActive = false;
heading = Vector2(0, 0);
}
}
}
function plDirection () {
if(Input.Get$$anonymous$$ey ($$anonymous$$eyCode.G)) {
heading = Vector2(1, 0);
}
if(Input.Get$$anonymous$$ey ($$anonymous$$eyCode.D)) {
heading = Vector2(-1, 0);
}
if(Input.Get$$anonymous$$ey ($$anonymous$$eyCode.T)) {
heading = Vector2(0, 1);
}
if(Input.Get$$anonymous$$ey ($$anonymous$$eyCode.R)) {
heading = Vector2(-1, 1);
}
if(Input.Get$$anonymous$$ey ($$anonymous$$eyCode.V)) {
heading = Vector2(1, -1);
}
if(Input.Get$$anonymous$$ey ($$anonymous$$eyCode.C)) {
heading = Vector2(0, -1);
}
}
It makes the player move a certain distance on a Hex Grid while at the same time activate the 'Turn' for the other GameObjects.
What is the error you are getting, just incase someone spots a solution to that (it cant hurt)?
Answer by jamesflowerdew · Apr 08, 2015 at 01:27 PM
foreach(KeyCode vKey in System.Enum.GetValues(typeof(KeyCode))){
if(Input.GetKey(vKey)){
//your code here
}
}
:) this detects what key has been pressed. I use it for my custom input manaer.
@jamesflowerdew If you would not $$anonymous$$d, could please explain to me how this works? I ask not out of doubt of the answer's validity, but simply in an attempt to understand this confounding code.
@$$anonymous$$derbuns it's been a year but for anyone else who might want an explanation: The line
foreach($$anonymous$$eyCode v$$anonymous$$ey in System.Enum.GetValues(typeof($$anonymous$$eyCode)))
Iterates over every $$anonymous$$eyCode in the System. System.Enum.GetValues(typeof($$anonymous$$eyCode)) gets every enum value of type $$anonymous$$eyCode as an array.
The body of the foreach loop just checks if our current value 'v$$anonymous$$ey' is currently pressed. The loop performs this check for every possible value of 'v$$anonymous$$ey.'
Its 2020 and I see people still Brute forcing their way out. GG :D
Answer by geniusprime · May 22, 2016 at 10:23 AM
The following code worked for me. It is based of of @jamesflowerdew. Firstly a KeyCode variable is created. This variable would store the custom key press. The DetectInput() function captures the key input by the user and stores it in kCode. kCode is then used in the Input.GetKeyDown(KeyCode) function. With this approach you should be able to create an array or a series of KeyCode variables that have specified functions and theese KeyCode variables can be changed to any input key the user wants.
So you will be able to create a
KeyCode jumpKCode
jumpKCode can be used in the following for you jump trigger
if( Input.GetKeyDown(jumpKCode))
{
Jump();
}
jumpKCode can be assign any key input. Hopefully this makes sense to anyone who is struggling with this.
private bool bDetectKey;
private KeyCode kCode; //this stores your custom key
void Update ()
{
if(Input.GetKeyDown(KeyCode.Return))
{
if (bDetectKey)
bDetectKey = false;
else
bDetectKey = true;
}
if(bDetectKey) //this detects the key being pressed and saves it to kCode
DetectInput();
if(Input.GetKeyDown(kCode)) //the kCode is then compared like a standard Input.GetKeyDown(KeyCode) boolean
{
print("Custom key worked");
}
}
public void DetectInput()
{
foreach(KeyCode vkey in System.Enum.GetValues(typeof(KeyCode)))
{
if(Input.GetKey(vkey))
{
if (vkey != KeyCode.Return)
{
kCode = vkey; //this saves the key being pressed
bDetectKey = false;
}
}
}
}
Answer by mcarriere · Sep 12, 2011 at 04:54 PM
Your question doesn't give too much information, but here are a few options:
If you are absolutely tied to using a switch statement to iterate through your keys, you could do something like this:
var myKeys : Array;
function Start() {
myKeys = new Array();
myKeys.Add(KeyCode.W);
myKeys.Add(KeyCode.S);
myKeys.Add(KeyCode.A);
myKeys.Add(KeyCode.D);
}
function Update () {
for (var key : KeyCode in myKeys)
{
if (Input.GetKeyDown(key))
{
switch (key)
{
case KeyCode.W:
Debug.Log("W!");
break;
case KeyCode.S:
Debug.Log("S!");
break;
case KeyCode.A:
Debug.Log("A!");
break;
case KeyCode.D:
Debug.Log("D!");
break;
}
}
}
}
However, it would probably be slightly cleaner if you did this:
if (Input.GetKeyDown(KeyCode.W))
{
}
if (Input.GetKeyDown(KeyCode.S))
{
}
if (Input.GetKeyDown(KeyCode.A))
{
}
if (Input.GetKeyDown(KeyCode.D))
{
}
Change the consecutive "if"s to "else if" if you only want one input to work at a time. Change "GetKeyDown" to "GetKey", if you want it to recognize the input every frame.
If you had read all the comments added to the original questions, you would have had more information, including the 'if(Input.Getkey)' variant.
The loop would be an idea, but I think I stay with the current version. The default value of the switch would have been handy, but I just placed the default value into the variable before all the if statements, so it gets overridden, when a valid key is pressed, and stays the same, if another key is pressed.
But thanks anyway.
If anyone is interested, here is the current script (-snippet).
function plDirection () {
statics.plHeading = Vector2(0, 0);
if(Input.Get$$anonymous$$ey ($$anonymous$$eyCode.G)) {
statics.plHeading = Vector2(1, 0);
}
if(Input.Get$$anonymous$$ey ($$anonymous$$eyCode.D)) {
statics.plHeading = Vector2(-1, 0);
}
if(Input.Get$$anonymous$$ey ($$anonymous$$eyCode.T)) {
statics.plHeading = Vector2(0, 1);
}
if(Input.Get$$anonymous$$ey ($$anonymous$$eyCode.R)) {
statics.plHeading = Vector2(-1, 1);
}
if(Input.Get$$anonymous$$ey ($$anonymous$$eyCode.V)) {
statics.plHeading = Vector2(1, -1);
}
if(Input.Get$$anonymous$$ey ($$anonymous$$eyCode.C)) {
statics.plHeading = Vector2(0, -1);
}
}
I'm a bit confused, I just did a text search on the page, and this comment and my answer were the only ones to suggest using Input.Get$$anonymous$$ey(). Either way, glad you found a solution.
thanks for your explain. Change "Get$$anonymous$$eyDown" to "Get$$anonymous$$ey", if you want it to recognize the input every frame. It helped me alot :)
Answer by Scenia · Jun 15, 2013 at 02:15 PM
You can avoid using many ifs, but you can't avoid using Input.GetKey(Down). The trick is the following: switch(argument) compares the argument to each case. By using true as the argument, you can use boolean statements as cases:
switch(true) {
case Input.GetKey("g"):
statics.plHeading = Vector2(1,0);
break;
case Input.GetKey("d"):
// and so on...
default:
// this way, you can still use a default statement
}
Answer by Maister · Mar 17, 2016 at 10:27 PM
The method described from Scenia does not work for me. The compiler says, that after the "case"-statement has to be a constant value.
However I thought it would be nice having a dictionary with the button name as key and the function to call as value:
using System.Collections.Generic;
using UnityEngine;
private Dictionary<string, InputDelegate> myKeys;
private delegate void InputDelegate();
private InputDelegate myTempDelegate;
private void start()
{
this.myKeys = new Dictionary<string, InputDelegate> ();
this.myTempDelegate = Fire;
myKeys.Add ("Fire1",myTempDelegate);
this.myTempDelegate = Inventory;
myKeys.Add ("Inventory",myTempDelegate);
}
private Update()
{
if (Input.anyKeyDown)
{
foreach (var dic in this.myKeys)
{
if (Input.GetButtonDown (dic.Key))
{
dic.Value ();
}
}
}
}
private void Fire()
{
//do all the stuff to fire
}
private void Inventory()
{
//open up the inventory
}
You would need to specify a key for the button "inventory" in the input manager, since it is not there by default. This way, you keep your update method short and tidy, but get the key-function-binding section in the start method, which could get long, if you are having many keys. For general movement of a character you should do something like this:
private void FixedUpdate()
{
// read inputs
float h = Input.GetAxis ("Horizontal");
float v = CrossPlatformInputManager.GetAxis("Vertical");
bool crouch = Input.GetKey(KeyCode.C);
//do all the physics stuff...
//...
}
Anyway.. I guess in terms of performance you could / (should?) stick with the method of having all the if (Input.GetKeyDown(...)) 's in the update method.
$$anonymous$$eep in $$anonymous$$d Unity works with different script languages, which have different rules. $$anonymous$$y solution is for JavaScript/UnityScript, so it's not too surprising it doesn't work if you try to use it in a C# script. JavaScript also has neither the concept of Dictionaries, nor delegates, so the reverse is also true and your solution won't work in a JS script. Since the original question is in JS (which you can recognize by looking at the variable type declaration, as well as from the tag right next to the question title), it's safe to assume OP wants a solution that works in JS.
Your answer
Follow this Question
Related Questions
A node in a childnode? 1 Answer
Cube terrain with perlin noise 1 Answer
Singletons in music script? 2 Answers
How To Make Ammo & Realod for Gun & Spark for Gun ? 0 Answers