AS3使用自定义元数据标记,类似C#的类属性、成员属性
原创文章,未经允许,请勿转载
在AS3 使用元数据标签最多的应该是swf标签了,如:
[SWF(backgroundColor = 0x000000, frameRate = 24, width = 1000, height = 600)]
那么能不能自定义我们自己的标签,然后在运行时,获取那些含有自定义标签的类或者类成员,然后达到注入的目的呢?答案是肯定的,在robotleg等一些开源框架中也用到了注入。
要是有元数据标签需要在编译器的扩展参数中指定-keep-as3-metadatac参数:
-keep-as3-metadata+=Inject,BindData
后面的Inject、BindData就是下面的例子要用的两个标签
需要注意的是这个编译参数只需要在一个运行库中指定即可,比如我们使用swc,那么编译这个swc指定了-keep-as3-metadatac参数,那么在使用swc的库的项目是不需要再指定的。在-keep-as3-metadatac参数使用“+=”是为了避免把别的参数定义覆盖掉。
比如Test1.as类使用元标签:
package
{
/**
* ...
* @author yoyo
*/
[Inject]
public class Test1
{
[BindData(param1="abc")]
public var s:String = 'ssss';
public function Test1()
{
}
}
};
接下来我们做注入操作,在不需要直接引用s成员的情况下,根据BindDta标签,修改这个成员变量的值:
package
{
import flash.display.Sprite;
import flash.events.Event;
import flash.utils.describeType;
import flash.xml.XMLNode;
/**
* ...
* @author yoyo
*/
public class Main extends Sprite
{
public function Main():void
{
if (stage)
init();
else
addEventListener(Event.ADDED_TO_STAGE, init);
}
private function init(e:Event = null):void
{
removeEventListener(Event.ADDED_TO_STAGE, init);
// describeType方法返回的信息类似下面的xml
/**
<type name="Test1" base="Object" isDynamic="false" isFinal="false" isStatic="false">
<extendsClass type="Object"/>
<variable name="s" type="String">
<metadata name="BindData">
<arg key="param1" value="abc"/>
</metadata>
<metadata name="__go_to_definition_help">
<arg key="pos" value="131"/>
</metadata>
</variable>
<metadata name="Inject"/>
<metadata name="__go_to_ctor_definition_help">
<arg key="pos" value="173"/>
</metadata>
<metadata name="__go_to_definition_help">
<arg key="pos" value="79"/>
</metadata>
</type>
*/
var t:Test1 = new Test1();
initMeta(t);
trace(t.s);//打印修改后的值
}
/**
* 开始对这个对象进行注入
* @param obj
*/
private function initMeta(obj:*):void
{
var xml:XML = describeType(obj);
var typeName:String = xml.@name;
initClassMeta(obj,typeName,xml);
for (var i:int = 0, len:int = xml.variable.length(); i < len;i++)
{
var variables:XML = xml.variable[i];
initVariableMeta(obj,typeName,variables);
}
}
/**
* 获取含有自定义标签的类对象
* @param xml
*/
private function initClassMeta(obj:*,typeName:String,xml:XML):void
{
for (var i:int = 0, len:int = xml.metadata.length(); i < len;i++)
{
var mata:XML = xml.metadata[i];
var metaName:String = mata.@name;
switch (metaName)
{
case 'Inject':
trace(typeName + ',Inject:' + metaName);
break;
}
}
}
/**
* 获取含有自定义标签的成员变量
* @param xml
*/
private function initVariableMeta(obj:*,typeName:String,xml:XML):void
{
var name:String = xml.@name;
var type:String = xml.@type;
for (var i:int = 0, len:int = xml.metadata.length(); i < len;i++)
{
var mata:XML = xml.metadata[i];
var metaName:String = mata.@name;
switch (metaName)
{
case 'BindData':
trace(typeName + ',BindData:' + metaName + '(' + mata.arg[0].@value + ')');
obj[name] = 'inject';//修改这个成员变量的值
break;
}
}
}
}
}
来源:悠游悠游,原文地址:https://yymmss.com/p/186.html