简体   繁体   中英

C# confuses Vector3 for Vector2 in Unity

While trying to make the pivot of a sprite the same position as the cursor - Vector3 objPos - and instantiating objects from the cursor position minus some difference - Vector3 diff - Unity threw an error that says "Operator '-' is ambiguous on operands of type 'Vector2' and 'Vector3'" even tho the both variables are Vector3's

public Transform baseDot;
public KeyCode mouseLeft;
public Vector2 mousePosition;
Vector2 mousePos;
Vector2 objPos;

void OnMouseOver()
{
    Vector3 diff = new Vector3(2f, 2.8f, 0f);
    float xPos = Camera.main.ScreenToWorldPoint(mousePos).x;
    float yPos = Camera.main.ScreenToWorldPoint(mousePos).y;
    mousePos = new Vector2(Input.mousePosition.x, Input.mousePosition.y);
    objPos = new Vector3(xPos, yPos, -10);

    if (Input.GetKey(mouseLeft) )
        Instantiate(baseDot, objPos-diff, baseDot.rotation);
}

C# behaves correctly here. Vector2 and Vector3 are structures (value types) and it is only possible to assign Vector3 to Vector2 because Vector2 has an implicite operator defined. This means that when you assign Vector3 to variable of type Vector2, it becomes Vector2 and the z coordinate is lost.

To resolve your issue, simply change the type of objPos to Vector3 or create a new temporary variable to store the new Vector3(xPos, yPos, -10);

To understand the behaviour, I would suggest to study reference vs value types and implicit operators.

even tho the both variables are Vector3's

That's not quite true since you defined

Vector2 objPos;

The Vector3 value you assign to it is implicitly converted to a Vector2 value.

It gets clear if you read the according API for Vector2.Vector3

Converts a Vector2 to a Vector3 .

A Vector2 can be implicitly converted into a Vector3 . (The z is set to zero in the result).

and Vector2.Vector2

Converts a Vector3 to a Vector2 .

A Vector3 can be implicitly converted into a Vector2 . (The z is discarded).

where implicit means you don't have to explicitly use a typecast but can use both types exchangeably.

Read more about implicit and explicit conversions

So in the error you get ambiguous means c# doesn't know which operation you want to use.

Either Vector2 - Vector2 or Vector3 - Vector3 exist, both are possible due to the implicit conversion .. so c# doesn't know which of the two values to change the type for.


The most obvious solution is to change the type to

Vector3 objPos;

Maybe try to define variable objPos as Vector3 , I am not sure if it has implicit/explicit cast operator defined between the types:

Vector2 objPos;
...
objPos = new Vector3(xPos, yPos, -10);

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM