ssb
ssb

Reputation: 1472

Why is this cast from interface to class failing?

private Vector2 ResolveCollision(ICollidable moving, ICollidable stationary)
{
    if (moving.Bounds.Intersects(stationary.Bounds))
    {
        if (moving is Player)
        {
            (Player)moving.Color = Color.Red;
        }
    }
    // ...
}

I have a class Player that implements ICollidable. For debugging purposes I'm just trying to pass a bunch of ICollidables to this method and do some special stuff when it's the player. However when I try to do the cast to Player of the ICollidable I get an error telling me that ICollidable doesn't have a Color property.

Am I not able to make a cast this way or am I doing something wrong?

Upvotes: 9

Views: 394

Answers (6)

Chayemor
Chayemor

Reputation: 3707

It's not that it's not working, it's the syntax that is "somewhat" wrong.

Try this:

((Player) moving).Color = Color.Red;

Upvotes: 3

Mark Byers
Mark Byers

Reputation: 838226

I'd suggest using as instead of is:

Player player = moving as Player;
if (player != null)
{
    player.Color = Color.Red;
}

The advantage is that you only do the type check once.


The specific reason why your code doesn't work (as mentioned in other answers) is because of operator precedence. The . operator is a primary operator which has a higher precedence than the casting operator which is a unary operator. Your code is interpreted as follows:

(Player)(moving.Color) = Color.Red;

Adding the parentheses as suggested by other answers solves this issue, but changing to use as instead of is makes the issue go away completely.

Upvotes: 16

Tim Schmelter
Tim Schmelter

Reputation: 460138

You have forgotten one bracket:

change

 (Player)moving.Color = Color.Red;

to

 ((Player)moving).Color = Color.Red;

You can also use the as operator to cast.

Player p = moving as Player;
if (p != null)
{
    p.Color = Color.Red;
}

Upvotes: 2

Joey
Joey

Reputation: 354536

You need parentheses around the cast and the variable:

((Player)moving).Color = Color.Red;

otherwise you're trying to cast moving.Color to Player.

Upvotes: 2

Artem Vyshniakov
Artem Vyshniakov

Reputation: 16465

You should add additional brackets:

((Player)moving).Color = Color.Red;

Upvotes: 2

Rex M
Rex M

Reputation: 144122

Your syntax is casting Color to Player, not moving.

((Player)mover).Color = Color.Red;
//^do the cast  ^access the property from the result of the cast

Also, as tends to be a little nicer. If it fails, the result is null:

var player = moving as Player;
if(player != null)
{
    player.Color = Color.Red;
}

Upvotes: 9

Related Questions