Reputation: 10702
Let's say I have a Custom Event Class, and it has several Event types stored in static Constant:
package customEvents
{
public class
{
public static const DISAPPEAR_COMPLETELY:String = "disappearCompletely";
public static const SIT_DOWN:String = "sitDown";
public static const STAND_UP:String = "standUp";
public static const SAIL_TO_THE_MOON:String = "sailToTheMoon";
public static const GO_TO_SLEEP:String = "goToSleep";
public static const GO_SLOWLY:String = "goSlowly";
public function MyCustomEvent(type:String)
{
super(type);
}
}
}
Is there an easy way to validate that the type
passed to the Constructor is one of the Static Constants of the Class, without having to check it against each value?
Upvotes: 0
Views: 959
Reputation: 76
Christian is correct -- and the question contains a somewhat ambiguous term. When you are checking for event "types", they are not datatypes, i.e. class objects, they are simply string values that pass along the particular "flavour" of the event to the listening object.
Personally, I don't think you need runtime validation of event types. If your code attempts to use an event constant which does not exist, such as
obj.addEventListener(CustomEvent.TYPE_WHICH_DOES_NOT_EXIST, handlerMethod);
...you're going to get a compiler error before your code is even run. If you use raw string values for event types, then you're defeating the purpose of using event constants anyways.
Upvotes: 1
Reputation: 10409
While both of these answers offer different solutions to validating the string values, they don't answer the question about having to check the values. Which you have to do, at the very least because the values of the constants are Strings themselves.
So the answer is no -- not if you're extending Event, anyway. Since that initial parameter has to be a String (insofar as you're extending Event), no matter how many levels of indirection you use, you'll still end up checking the arguments against a list of valid values. Passing in anything other than a String will throw a runtime error.
Upvotes: 1
Reputation: 1373
To extend off of Dan R's answer, you could create a strict event (like the way you'd do enums) class like so:
import flash.utils.Dictionary;
import flash.utils.describeType;
import flash.utils.getQualifiedClassName;
public class StrictEvent
{
private static var VALID_EVENTS:Dictionary = new Dictionary();
public static function initEvents(inType:*):void {
var events:Object = {};
var description:XML = describeType(inType);
var constants:XMLList = description.constant;
for each(var constant:XML in constants) {
events[inType[constant.@name]] = true;
}
VALID_EVENTS[getQualifiedClassName(inType)] = events;
}
public function StrictEvent(type:String)
{
var className:String = getQualifiedClassName(this);
if(VALID_EVENTS[className][type]) {
// init
} else {
throw new Error("Error! " + type);
}
}
}
Then, you could define your custom event class by extending the strict event class and calling initEvents in the static initializer. Here is your example with this method:
public class CustomEvent extends StrictEvent
{
public static const DISAPPEAR_COMPLETELY:String = "disappearCompletely";
public static const SIT_DOWN:String = "sitDown";
public static const STAND_UP:String = "standUp";
public static const SAIL_TO_THE_MOON:String = "sailToTheMoon";
public static const GO_TO_SLEEP:String = "goToSleep";
public static const GO_SLOWLY:String = "goSlowly";
public function CustomEvent(type:String) {
super(type);
}
{
initEvents(CustomEvent);
}
}
Now, each time it creates an event it only has to look up the event object and see if the type is in that object. It also means you don't have to manually add all the constants in the initializer.
Upvotes: 1
Reputation: 5418
There are a few ways you can attack this:
Your code sample seems to be an event class. If that's the case, you can't use the first option, as you wouldn't want to change the signature of the constructor if you don't need to.
package customEvents
{
public class
{
private static var typeList:ArrayCollection;
public static const DISAPPEAR_COMPLETELY:String = "disappearCompletely";
public static const SIT_DOWN:String = "sitDown";
<... lines deleted ...>
public static const GO_SLOWLY:String = "goSlowly";
// static constructor
{
typeList = new ArrayCollection();
typeList.addItem(DISAPPEAR_COMPLETELY);
typeList.addItem(SIT_DOWN);
<... lines deleted ...>
typeList.addItem(GO_SLOWLY);
public function MyCustomEvent(type:String)
{
if (typeList.contains(type)
super(type);
else
throw new Error("Invalid type");
}
}
}
Upvotes: 0
Reputation: 82078
If you were to make each of the static constants as lower-case Strings of the upper-case constant names, then you could do:
if( class.hasOwnProperty( type.toUpperCase() ) )
{
// Do something
}
else
{
// Failure
}
Upvotes: 0