I used an item script that I found online that picks up an Item. It was intended for first-person raycasting but I changed it to detect if my player triggers the item. I wanted the item to lock to my player's hand 1 second after the animation plays. I tried invoking but I learned I can't do that with parameters. I then tried Coroutines but they were complicated and I could not get it to work. I made a new void that I invoke after 1 second which I want to start my PickItem void. However, I don't know how to do this. I don't understand how parameters work either.
public int number = 1;
Animator animator;
private int i;
private GameObject[] Item;
private bool inrange;
// Reference to the character camera.
[SerializeField]
private Camera characterCamera;
// Reference to the slot for holding picked item.
[SerializeField]
private Transform slot;
// Reference to the currently held item.
private PickableItem pickedItem;
My OnTriggerStay code.
private void OnTriggerStay(Collider other)
{
if (other.gameObject.tag == "Item")
{
inrange = true;
if (inrange == true && (number % 2) == 1)
{
// Check if object is pickable
var pickable = other.gameObject.GetComponent<PickableItem>();
// If object has PickableItem class
if (pickable)
{
//Invoke delay after 1 seconds
Invoke("delay", 1f);
}
}
}
}
My delay void:
public void delay()
{
number = number 1;
PickItem();
}
My PickItem void:
// I don't under stand this line of code either
/// <param name="item">Item.</param>
public void PickItem(PickableItem item)
{
// Assign reference
pickedItem = item;
// Disable rigidbody and reset velocities
item.Rb.isKinematic = true;
item.Rb.velocity = Vector3.zero;
item.Rb.angularVelocity = Vector3.zero;
// Set Slot as a parent
item.transform.SetParent(slot);
// Reset position and rotation
item.transform.localPosition = Vector3.zero;
item.transform.localEulerAngles = Vector3.zero;
item.GetComponent<MeshCollider>().enabled = false;
}
I know coroutines are probably better in this case but I could not get them working.
CodePudding user response:
Coroutines make this simple. Use WaitForSeconds
to create the delay:
IEnumerator DelayPickup(PickableItem item)
{
yield return new WaitForSeconds(1f);
number ;
PickItem(item);
}
Call it like this:
private void OnTriggerStay(Collider other)
{
if (other.gameObject.CompareTag("Item"))
{
inrange = true;
// inrange is true here by assignment, don't need to check again
if (number % 2 == 1)
{
// Check if object is pickable
var pickable = other.gameObject.GetComponent<PickableItem>();
// If object has PickableItem class
if (pickable)
{
StartCoroutine(DelayPickup(pickable));
}
}
}
}
By the way, they aren't called "voids", they're methods with a return type of void
.