Peter
Peter

Reputation: 1359

provide a non-trivial setter for an interface property, but not a getter

For a Unity3d game I'm working on, I have a situation where I want a read/writeable property with a trivial getter, but a setter which does some more work. My code looks like this:

// IColor.cs
interface IColor {
    Color colorPainted { get; set; }
}

// Player.cs
public class Player : Monobehaviour, IColor {
    // ...
    public Color colorPainted {
        get { }
        set {
            colorPainted = value;
            // some other code
        }
     // ...
    }
}

I'm not sure what to do about the get part, though. I can't return colorPainted;, because that causes a stack overflow. The code as written won't compile because I'm not returning a value.

I'm no C# wizard, but it seems like I'd need to have a _colorPainted backing variable, and provide access to that through the get and set. This seems kinda verbose, though -- is there a better way to do it? In Objective-C, I'd simply leave the getter unimplemented, but that doesn't seem to work.

Upvotes: 2

Views: 387

Answers (2)

David
David

Reputation: 218828

Use a backing member to hold the value:

public class Player : Monobehaviour, IColor {
    // ...
    private Color _colorPainted;
    public Color colorPainted {
        get { return _colorPainted; }
        set {
            _colorPainted = value;
            // some other code
        }
     // ...
    }
}

In the example where you can't return the property itself, your setter won't work either. Same problem. Essentially, when you write this:

public Color colorPainted { get; set; }

What you're really writing is this, only shorter:

private Color _colorPainted;
public Color colorPainted
{
    get { return _colorPainted; }
    set { _colorPainted = value; }
}

The compiler is just handling the backing field for you, allowing you to write it in a shorter way. But when you step outside of that shorter syntax, you have to manage the backing field yourself.

Since the backing field is private, there's no difference to any code that's using the class or the interface type.

Upvotes: 2

Mike Parkhill
Mike Parkhill

Reputation: 5551

Unfortunately in C# there's no way around it. You need to provide a backing field for the property:

// Player.cs

private Color _colorPainted;

public class Player : Monobehaviour, IColor {
    // ...
    public Color colorPainted {
        get { return _colorPainted; }
        set {
            _colorPainted = value;
            // some other code
        }
     // ...
    }
}

Upvotes: 3

Related Questions