我遇到了问题..我希望每次按下其中一个箭头键都会创建我的火球。
- 它可以工作,但是:如果(例如)我按向下箭头,然后,在按下向下箭头的同时,我同时按下另一个箭头,(例如)向左箭头,它不会创建一个左边的火球。 但是使用右箭头,一切正常(因为它是if语句中的第一个)。
- 我知道代码从上到下都有效,我无法改变这一点。但也许我可以找到一种方法来避免这种情况,让我的工作成为我想要的。
(我想要创建fireSphere就像在Isaac的Binding中一样:如果你按下左边它会向左射击,如果向右,它会向右射击,但是如果先按向左箭头,然后向左射击按下箭头,你按向右箭头,它会向右射击。如果你先按右键也一样)
(英语是我的第二语言,如果你不理解我,请告诉我!我会更好地解释自己) 谢谢!
if (Input.GetButton("RightArrow") && Time.time > timeToFire)
{
timeToFire = Time.time + 1 / fireRate;
Instantiate(fireSphere, firePoint.position, firePoint.rotation);
}
if (Input.GetButton("LeftArrow") && Time.time > timeToFire)
{
timeToFire = Time.time + 1 / fireRate;
Instantiate(fireSphere, firePoint.position, firePoint.rotation);
}
if (Input.GetButton("UpArrow") && Time.time > timeToFire)
{
timeToFire = Time.time + 1 / fireRate;
Instantiate(fireSphere, firePoint.position, firePoint.rotation);
}
if (Input.GetButton("DownArrow") && Time.time > timeToFire)
{
timeToFire = Time.time + 1 / fireRate;
Instantiate(fireSphere, firePoint.position, firePoint.rotation);
}
答案 0 :(得分:2)
此代码允许同时按下并保持所有箭头键,最后一个箭头键指示方向。
实施例: 按住←→↓,将使用↓。如果你放开→然后↓,它将使用←。
(也使用Input.GetKey
和KeyCode
)
public float FireRate;
public float NextFire;
private List<KeyCode> keysPressed;
private KeyCode right = KeyCode.RightArrow;
private KeyCode left = KeyCode.LeftArrow;
private KeyCode up = KeyCode.UpArrow;
private KeyCode down = KeyCode.DownArrow;
private void Awake()
{
keysPressed = new List<KeyCode>();
}
private void Update()
{
if(Input.GetKeyDown(right))
AddKey(right);
if(Input.GetKeyDown(left))
AddKey(left);
if(Input.GetKeyDown(up))
AddKey(up);
if(Input.GetKeyDown(down))
AddKey(down);
if(Input.GetKeyUp(right))
RemoveKey(right);
if(Input.GetKeyUp(left))
RemoveKey(left);
if(Input.GetKeyUp(up))
RemoveKey(up);
if(Input.GetKeyUp(down))
RemoveKey(down);
if((Time.time > NextFire) == false)
return;
if(Input.GetKey(right) || Input.GetKey(left) || Input.GetKey(up) || Input.GetKey(down))
{
NextFire = Time.time + FireRate;
Fire();
}
}
private void AddKey(KeyCode k)
{
keysPressed.Add(k);
}
private void RemoveKey(KeyCode k)
{
keysPressed.Remove(k);
}
private void Fire()
{
if(keysPressed[keysPressed.Count - 1] == right)
Debug.Log("right");
else if(keysPressed[keysPressed.Count - 1] == left)
Debug.Log("left");
else if(keysPressed[keysPressed.Count - 1] == up)
Debug.Log("up");
else if(keysPressed[keysPressed.Count - 1] == down)
Debug.Log("down");
}
这个订单仍有问题的唯一一点是当你实际上一次按下2个或更多键时。
由于列表操作,此解决方案可能不是最高性能,但我现在可以提出的其他选项也有其缺点或不允许这种灵活性。
答案 1 :(得分:0)
请参阅代码部分:
if (Input.GetButton("LeftArrow") && Time.time > timeToFire)
{
timeToFire = Time.time + 1 / fireRate;
Instantiate(fireSphere, firePoint.position, firePoint.rotation);
}
if (Input.GetButton("UpArrow") && Time.time > timeToFire)
{
timeToFire = Time.time + 1 / fireRate;
Instantiate(fireSphere, firePoint.position, firePoint.rotation);
}
如果按下LeftArrow
和UpArrow
键,则会满足两个if语句的第一个条件。
我假设Time.time
在开头大于timeToFire
,因此第一个语句会触发。在第一个状态中,您将timeToFire
设置为大于Time.time
(+ (1/fireRate)
)的值。
=&GT;这使得第二个if语句无法评估为true。 那就像
一样int a = 5;
if(SomeTrueStatement() && a < 10)
{
a = 20;
}
//This never happens because a is now > 10
if(SomeOtherTrueStatement() a < 10)
{
//Code
}
可能的解决方案: 我不知道开箱即用,如果你能分辨出哪个键首先被按下了,但是如果按下最后一个按键只按下一个键,你知道,如果现在按下了2个键,它们中的哪一个是后来按键。
[Pseudocode]
if(OnlyOneKeyPressed())
{
savedPressedKey = SaveKeyPressed(GetPressedKey());
pressedKey = GetPressedKey();
}
else if(TwoKeysPressed())
pressedKey = GetAllPressedKeys().Exclude(savedPressedKey);
if(pressedKey == "ArrowUp" && ...)
...
...
答案 2 :(得分:0)
事实证明我的想法与@ Gunnar-b非常相似:
protected List<KeyCode> Directions = new List<KeyCode>();
protected void Update()
{
var hasDirection = TrackKey(KeyCode.UpArrow) || TrackKey(KeyCode.DownArrow) || TrackKey(KeyCode.LeftArrow) || TrackKey(KeyCode.RightArrow);
if (!hasDirection)
{
Directions.Clear();
return;
}
// Has a direction. Check "Last" item in list (top of stack) and proceed.
Quaternion rotation = Quaternion.identity;
switch (Directions[Directions.Count -1])
{
case KeyCode.UpArrow: // Set Rotation Here
break;
case KeyCode.DownArrow: // Set Rotation Here
break;
case KeyCode.LeftArrow: // Set Rotation Here
break;
case KeyCode.RightArrow: // Set Rotation Here
break;
}
// Instantiate fireball using rotation from above
Instantiate(prefab, position, rotation);
}
protected bool TrackKey(KeyCode key)
{
// if key was released, remove each item where the item equals key
if (Input.GetKeyUp(key)) Directions.RemoveAll(item => item == key);
// Always adds to end, virtual 'Stack'
if (Input.GetKeyDown(key)) Directions.Add(key);
return Input.GetKey(key);
}