Laya runtime 扩展脚本 附加脚本

参考
runtime使用
扩展脚本的使用
附加脚本的使用
按照上面的教程,发现扩展脚本实际上也是在用runtime,而附加脚本则是多了一个子元素:

一、IDE中不同表现

box1使用了扩展脚本,box2使用了runtime,box3使用了附加脚本,ui文件是这样的:

//注意,扩展脚本和附加脚本的文件后缀不同,分别是prop和script
//MonkeyProp.prop:
<MonkeyProp className="game.MonkeyProp">
    <prop name="speed" tips="数字类型" type="number"/>
    <prop name="userName" tips="人物名称" type="string"/>
</MonkeyProp>

//MonkeyProp2.script:
<MonkeyProp2 className="game.MonkeyProp2">
    <prop name="speed" tips="数字类型" type="number"/>
    <prop name="userName" tips="人物名称" type="string"/>
</MonkeyProp2>

//TestGapUI.ui:
<Box x="268" y="150" appendProps="laya/pages/MonkeyProp.prop"
 speed="4" userName="xxa" var="box1" editorInfo="compId=45">
  <Image skin="game/doll_1.png" y="41" editorInfo="compId=43"/>
  <Label text="label" x="34" fontSize="36" width="102" height="36"
 name="userN" align="center" color="#100808" editorInfo="compId=44"/>
</Box>

<Box x="292" y="435" runtime="game.MonkeyProp" var="box2" editorInfo="compId=46">
  <Image skin="game/doll_1.png" y="41" editorInfo="compId=47"/>
  <Label text="label" x="34" fontSize="36" width="102" height="36"
 name="userN" align="center" color="#100808" editorInfo="compId=48"/>
</Box>

<Box y="703" x="302" var="box3" editorInfo="compId=49">
  <Image y="41" skin="game/doll_1.png" editorInfo="compId=50"/>
  <Label x="34" width="102" text="label" name="userN" height="36"
 fontSize="36" color="#100808" align="center" editorInfo="compId=51"/>
  <Script editorInfo="source=laya/pages/MonkeyProp2.script;compId=53"/>
</Box>

在IDE中,设置那两个自定义属性speed和userName的位置也不同。扩展脚本因为是继承自组件本身,所以自定义属性就在点击box1时就能看到。而附加脚本,是直接变成box3的一个子元素了,需要选中子元素才能编辑。


image.png
二、生成的UI:

看一下生成的ui,box1和box2都是同样的类型,而box3还是Box类型。

export class TestGapUI extends View {
    public box1:game.MonkeyProp;
    public box2:game.MonkeyProp;
        public box3:Laya.Box;

    public static  uiView:any ={"type":"View","props":{"width":750,"height":1334},"child":[...
    constructor(){ super()}
    createChildren():void {
                View.regComponent("game.MonkeyProp",game.MonkeyProp);
                View.regComponent("game.MonkeyProp2",game.MonkeyProp2);
        super.createChildren();
        this.createView(ui.TestGapUI.uiView);

    }

uiView部分太长,截取box1和box2看一下:

{"type":"Box","props":{"y":150,"x":268,"var":"box1","userName":"xxa","speed":4,"runtime":"game.MonkeyProp"},

{"type":"Box","props":{"y":435,"x":292,"var":"box2","runtime":"game.MonkeyProp"},

{"type":"Box","props":{"y":703,"x":302,"var":"box3"},
"child":[{"type":"Image","props":{"y":41,"skin":"game/doll_1.png"}},
{"type":"Label","props":{"x":34,"width":102,"text":"label","name":"userN",
"height":36,"fontSize":36,"color":"#100808","align":"center"}},
{"type":"Script","props":{"userName":"extraName","speed":3,"runtime":"game.MonkeyProp2"}

可以看到,扩展脚本是runtime的增强版:可以在IDE上指定属性,然后把属性值导出到ui配置中,并且把这个值自动映射类的属性中。而附加脚本,直接就是多了一个Script类型的子元素。那么它是怎么解析的?
在View.as的createComp方法中可以看到:

if (node.type == "Script") {
    if ("owner" in tChild) {
        tChild["owner"] = comp;
    } else if ("target" in tChild) {
        tChild["target"] = comp;
    }
} else if (node.props.renderType == "mask" || node.props.name == "mask") {
    comp.mask = tChild;
} else {
    tChild is Sprite && comp.addChild(tChild);
}

所以,附加脚本就必需要定义owner或target属性
另外,这个方法也能看到runtime那些属性映射的操作:

var props:Object = uiView.props;
for (var prop:String in props) {
    var value:String = props[prop];
    setCompValue(comp, prop, value, view, dataMap);
}
三、扩展脚本和附加脚本对应的类:

1.扩展脚本MonkeyProp.ts

namespace game {
    export class MonkeyProp extends Laya.Box {
        /**攻击速度(也可以不用定义该变量,在这里定义是为了打开该类的时候能够一目了然的看到对应的脚本中添加了哪些属性)**/
        public speed: number = 0;
        /**人物名称(也可以不用定义该变量,在这里定义是为了打开该类的时候能够一目了然的看到对应的脚本中添加了哪些属性)**/
        public userName: string = "";
        /**记录状态**/
        private boo: boolean = false;

        constructor() {
            super();
            console.log("MonkeyProp");
            //自定义的脚本会有时序问题,所以在此添加一个延时
            this.frameOnce(2, this, this.onFrame);
        }

        private onFrame(): void {
            //通过子元素的name值获取该对象
            var userN: Laya.Label = this.getChildByName("userN") as Laya.Label;
            //设置文本内容为属性栏中给的值
            userN.text = this.userName;
            this.frameLoop(1, this, this.onLoop);
        }

        /**
         *设置帧循环,实现左右移动 
         * 
         */
        private onLoop(): void {
            if (this.x <= 0) {
                this.boo = false;
                this.x += this.speed;
            }
            else if (this.x < Laya.stage.width - this.width && this.boo == false) {
                this.x += this.speed;
            }
            else if (this.x >= Laya.stage.width - this.width || this.boo == true) {
                this.x -= this.speed;
                this.boo = true;
            }
        }
    }
}

2.附加脚本MonkeyProp2.ts

namespace game {
    export class MonkeyProp2 {
        /**攻击速度(也可以不用定义该变量,在这里定义是为了打开该类的时候能够一目了然的看到对应的脚本中添加了哪些属性)**/
        public speed: number = 0;
        /**人物名称(也可以不用定义该变量,在这里定义是为了打开该类的时候能够一目了然的看到对应的脚本中添加了哪些属性)**/
        public userName: string = "";
        /**记录状态**/
        private boo: boolean = false;
        /**定义一个变量来接收Box组件实例**/        
        private monkeyBox:Laya.Sprite;

        /**
         *设置owner函数,可以直接获取到添加附加脚本的组件实例 
         * @param value
         * 
         */        
        public set owner(value:any){
            this.monkeyBox = value;
            //自定义的脚本会有时序问题,所以在此添加一个延时
            this.monkeyBox.frameOnce(2,this,this.onLoaded);
        }

        private onLoaded():void
        {
            //通过子元素的name值获取该对象
            var userN:Laya.Label = this.monkeyBox.getChildByName("userN") as Laya.Label;
            //设置文本内容为属性栏中给的值
            userN.text = this.userName;
            this.monkeyBox.frameLoop(1,this,this.onLoop);
        }

        /**
         *设置帧循环,实现左右移动 
         * 
         */
        private onLoop(): void {
            if (this.monkeyBox.x <= 0) {
                this.boo = false;
                this.monkeyBox.x += this.speed;
            }
            else if (this.monkeyBox.x < Laya.stage.width - this.monkeyBox.width && this.boo == false) {
                this.monkeyBox.x += this.speed;
            }
            else if (this.monkeyBox.x >= Laya.stage.width - this.monkeyBox.width || this.boo == true) {
                this.monkeyBox.x -= this.speed;
                this.boo = true;
            }
        }
    }
}
四、应用场景

1.更改Laya组件的默认行为,但是又不想直接改源代码,毕竟那样更新引擎时很麻烦。此时就可以用runtime继承一下默认的组件,然后override一下某些方法。如果是想添加一些额外属性,并且在IDE中指定不同的值,就可以用扩展脚本了,它算是runtime的可视化增强版,与IDE配合得更紧密。
2.某些组件要实现相同的行为,最常见的例子就是一个Image支持点击缩放效果的ScaleButton,用runtime就行了。参见官方示例中的:


image.png

3.附加脚本,目前没有用到。个人理解,它和扩展脚本的区别,就像组合和继承的区别一样。
4.比较不爽的是扩展脚本和附加脚本都需要延时:

//自定义的脚本会有时序问题,所以在此添加一个延时
this.monkeyBox.frameOnce(2,this,this.onLoaded);

所以还是优先考虑使用runTime吧

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 204,590评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 86,808评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 151,151评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,779评论 1 277
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,773评论 5 367
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,656评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,022评论 3 398
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,678评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 41,038评论 1 299
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,659评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,756评论 1 330
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,411评论 4 321
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,005评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,973评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,203评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 45,053评论 2 350
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,495评论 2 343

推荐阅读更多精彩内容

  • Android 自定义View的各种姿势1 Activity的显示之ViewRootImpl详解 Activity...
    passiontim阅读 171,442评论 25 707
  • 发现 关注 消息 iOS 第三方库、插件、知名博客总结 作者大灰狼的小绵羊哥哥关注 2017.06.26 09:4...
    肇东周阅读 12,019评论 4 62
  • 《你只是看起来很努力》 李尚龙 路 一步步地走,走得很慢,但没有停。正在努力的你并不孤独,其实,努力的人从来没有孤...
    别动放那阅读 347评论 2 1
  • 突然从睡梦中醒来 像往常一样 翻手机 屏幕里那刺眼的话语 让心冷却无让眼睛相信 看着看着入睡了… 梦里有你快乐的模...
    米夏小雨阅读 165评论 0 1