Enum flags, bitwise and Unity Script

Hi Guys,

Trying to figure out the best way to do bitwise operations in UnityScript, it seems to work, but the problem I have is that I need to convert my enum to int for any operation.

Is it possible to explicitly declare the enum as an int when you create it?

Here is stuff that works, but can I get around using parseInt() all of the time?

enum myEnum
{
	None = 0,
	First = 1,
	Second = 2,
	Third = 4
}

var someValue : int =  myEnum.First |  myEnum.Third;

var isFirst : boolean = (someValue | parseInt(myEnum.First)) == someValue;
var isSecond : boolean = (someValue | parseInt(myEnum.Second)) == someValue;
var isThird : boolean = (someValue | parseInt(myEnum.Third)) == someValue;

So if I want to do bitwise operations, I always need to cast the enum as int or it gives me an error

someValue  = someValue | parseInt(myEnum.Second);

Lastly, is there any way to get this syntax to work in UnityScript? Gives an error that it doesn’t expect the operators

enum myEnum
{
	None = 0,
	First = 1,
	Second = 1 << 1,
	Third = 1 << 2
}

Thanks

On a side note, what are the advantages in doing this bitwise stuff instead of just using some boolean values to begin with? Because the later would actually simplify quite a few things, especially with extending the editor GUI.

Enums aren’t ints; if you want ints then you should just use ints. You haven’t said what you’re trying to do, so I can’t tell you what’s the most appropriate. If you need to do bitwise operations, certainly booleans won’t help you at all since they’re completely different.

–Eric

I’m basically trying to figure out if bitwise is possible in UnityScript, and the correct way to do it.

Essentially looking for the equivalent of this:
http://stackoverflow.com/questions/8447/enum-flags-attribute

[Flags]
public enum MyColor
{
    Yellow = 1,
    Green = 2,
    Red = 4,
    Blue = 8
}

myProperties.AllowedColors = MyColor.Red | MyColor.Green | MyColor.Blue;

if((myProperties.AllowedColors  MyColor.Yellow) == MyColor.Yellow)
{
    // Yellow has been set...
}

enums work quite well in C#. I’m sure you can do them in unityscript too, but support might be better in c#.

Yeah, I really just want to learn how to do it in UnityScript if possible, even if I don’t use it.

What I did in the first post actually works with bitwise operations, but it seems like there should be a more elegant way.

I have a php/js background so UnityScript is very easy to pickup. I can do C++ etc, but still have lots to learn there, so would take a fair bit more time.

If I have to I will learn C#, but I haven’t seen a need yet.

What’s wrong with this?:

 enum MyColor
{
    Yellow = 1,
    Green = 2,
    Red = 4,
    Blue = 8
}

var allowedColors : int = MyColor.Red | MyColor.Green | MyColor.Blue;

if(allowedColors  MyColor.Red)
{
    // Red has been set...
}

When you do that, you get an error

“Operator ‘’ cannot be used with a left hand side of type ‘int’ and a right hand side of type ‘MyColor’.”

That’s why I had to do the parseInt stuff, to get around that error.

if(allowedColors MyColor.Red == MyColor.Red)

That also gives the cast error that “int” can’t be used with type “MyColor”

in c# you (annoyingly) have to cast an enum to an int… not sure if that is the case here, but try:
if(allowedColors (int)MyColor.Red == (int) MyColor.Red)

Oh sorry, I misread your post/code.

Since you’re already using an enum, you don’t need to type “allowedColors” as an int. You should continue to use it as an enum type (rather, MyColor type) until you need to convert it to an int (say, for storage/display purposes)

var allowedColors : MyColor = MyColor.Red | MyColor.Green | MyColor.Blue;
if ((allowedColors  MyColor.Red) == MyColor.Red)
{

}

Note the usage of the brackets in the IF statement (which I forgot in my first post) is required.

Yeah that’s why I was wondering if it was possible to cast a Javascript enum to an int. I’m not sure if you can do (int) in brackets to cast in javascript, but I guess parseInt is the equivalent there.

Hmm I’ll try it again, but I originally tried that and it just wasn’t working. It would allow it and not give any errors, but the If statement wouldn’t result in true.

The reason you have to cast is because in C#, the enums aren’t just a number. They’re a number associated with a type. If they had implicit operators to integers, then you’d be able to directly compare (and possibly assign) mixed enumerations. Consider the following:

enum Foo
{
	First = 1,
	Second = 2,
	Third = 3
}

enum Bar
{
	First = 1,
	Second = 2,
	Third = 3
}


Foo foo = Foo.Second;
Bar bar = Boo.Second;

//the following make no sense, and are dangerous
if (foo == bar)
if (foo == Bar.Second)
if (Foo.First == Bar.First)
foo = Bar.Third;

Staples, I did a test (in version 2.6.1) and it worked fine.

EDIT: my code:

enum MyColor
{
    Yellow = 1,
    Green = 2,
    Red = 4,
    Blue = 8
}
 
 function Awake()
 {   
    var allowedColors : MyColor = MyColor.Red | MyColor.Green | MyColor.Blue;
    Debug.Log("Allowed Colours: " + allowedColors);
    if ((allowedColors  MyColor.Red) == MyColor.Red)
    {
        Debug.Log("PASS");
    }
    else
    {
        Debug.Log("FAIL");
    }
}

Ahh okay fair enough.

Looks like your last example is working, I did try that but I must have done something wrong as it wasn’t giving me the correct result.

Thanks for the help!

Out of interest, what would be the easiest way to check if multiple bits are set. For example if you wanted to check if Red AND Green are set?

Do you have to do:

if( ((allowedColors  MyColor.Red) == MyColor.Red)   ((allowedColors  MyColor.Green) == MyColor.Green))

or

if((allowedColors  MyColor.Red  MyColor.Green) == MyColor.Red  My Color.Green)

In C# you can just do something like if((allowedColors (MyColor.Red | MyColor.Green)) can’t you?

Ugh… nevermind. I swear I tried all of this yesterday, for some reason it didn’t work. I must have been doing something wrong.

This is all working now, even the shorter version of what you did

// This works
if ((allowedColors  MyColor.Red))
    {
        Debug.Log("PASS");
    }
    else
    {
        Debug.Log("FAIL");
    }

// This works
if ((allowedColors  (MyColor.Red | MyColor.Green) ))
    {
        Debug.Log("PASS");
    }
    else
    {
        Debug.Log("FAIL");
    }

I guess your best bet is to assign it to a temporary flag then compare it the same way:

var allowedColors : MyColor = MyColor.Red | MyColor.Green | MyColor.Blue;
    var checkColors : MyColor = MyColor.Red | MyColor.Green;
    Debug.Log("Allowed Colours: " + allowedColors);
    Debug.Log("Check Colours: " + checkColors);

    if ((allowedColors  checkColors) == checkColors)
    {
        Debug.Log("PASS");
    }
    else
    {
        Debug.Log("FAIL");
    }

Though something is nagging me that there’d be an easier, inline way of doing it, but it escapes me right now.