博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Unity应用架构设计(4)——设计可复用的SubView和SubViewModel(Part 1)
阅读量:6295 次
发布时间:2019-06-22

本文共 3035 字,大约阅读时间需要 10 分钟。

『可复用』这个词相信大家都熟悉,通过『可复用』的组件,可以大大提高软件开发效率。 值得注意的事,当我们设计一个可复用的面向对象组件时,需要保证其独立性,也就是我们熟知的『高内聚,低耦合』原则。

组件化设计的思路

不管是开发客户端应用程序还是开发服务器端应用程序,『组件』这个词我们并不陌生。不管是在iOS中的xib,还是在AngularJS的Component,或者后端开发的 User Control,可复用的组件是面向对象开发的基础。所以在Unity 3D 框架设计时,组件化是核心的概念。那么如何去设计SubView和SubViewModel,我总结出几条原则:

  • 当一个功能被不同的场合频繁用到,建议将这个功能抽象成SubView(SubViewModel)
  • SubView(SubViewModel)应该保持高内聚,低耦合原则
  • SubViewModel不应该处理具体的业务逻辑,它很单纯,可通过委托Delegate的方式交由外部处理

构建SubView和SubViewModel

假设现在有如下一个需求,需要绑定角色的信息到头像上,如下图所示:

o_facebox.png

这是一个很常见的需求,创建一个MonoBehaviour,定义Public的变量并引用这些控件,最后再将这个MonoBehaviour附加到GameObject上,很快就能完成。当然,我不能说这样的实施是错误的,毕竟我们只要保证运行正确就可以了。

看到左上角的勋章吗,这个勋章会在不同的场景出现,我们优先把它考虑成一个SubView(BadgeView),也就是最外层的FaceBoxView里嵌套了一个BadgeView

public class FaceBoxView:UnityGuiView
{ public Text nameText; public Text levelText; public Image faceImage; public BadgeView badgeView;}

我们在分析一下BadgeView需要什么数据?它需要武器的Icon和属性颜色,所以我们抽象出一个Badge的DataModel:

public class Badge{    public string Icon { get; set; }    public string ElementColor { get; set; }}

所以对于FaceBoxViewModel而言,它为FaceBoxView服务。FaceBoxView需要什么数据,它就提供什么数据。显然它需要提供Name,Level,Face以及Badge组件的DataModel:

public class FaceBoxViewModel:ViewModelBase{    public readonly BindableProperty
Name=new BindableProperty
(); public readonly BindableProperty
Level=new BindableProperty
(); public readonly BindableProperty
Face=new BindableProperty
(); public readonly BindableProperty
Badge=new BindableProperty
(); public override void OnStartReveal() { base.OnStartReveal(); Initialization(); } public void Initialization() { Name.Value = "比尔"; Level.Value = 9; Face.Value = "Avatar204_Face"; Badge.Value = new Badge() {Icon = "Icon_WeaponRod", ElementColor = "1CB9FFFF"}; }}

因为Badge是BindableProperty类型对象,特点是当Badge Value改变时,触发的OnValueChanged事件就可以给BadgeViewModel传递数据,从而初始化BadgeView:

protected override void OnInitialize()    {        base.OnInitialize();        Binder.Add
("Name",OnNamePropertyVlaueChanged); Binder.Add
("Level",OnLevelPropertyValueChanged); Binder.Add
("Face",OnFacePropertyValueChanged); Binder.Add
("Badge",OnBadgePropertyValueChanged); } private void OnBadgePropertyValueChanged(Badge oldValue, Badge newValue) { badgeView.BindingContext = new BadgeViewModel() ; badgeView.BindingContext.Initialization(newValue); }

我们可以看到,组件化的实施从代码量上是变得复杂了,组件的颗粒度越细,那么嵌套的层次就越深,如果某个功能只出现一次,并且不会被复用,那么我不推荐将它变为一个SubView(SubViewModel)

小结

本文为大家介绍怎样将组件化模式思想引入到Unity 3D中,在我的uMVVM框架中,组件化是核心,就像用户控件一样,随拿随走,它们保持高度独立,这样的好处是不会产生紧耦合。还值得一提的是,其实Unity 3D本身的开发模式就是基于组件化开发的。只要创建一个MonoBehaviour组件然后附加到GameObject上就能正常运行。但需要注意的事,如果没有好的约束,一个GameObject上就会附加好多个MonoBehaviour,GameObject的子GameObject也会附加很多个MonoBehaviour,久而久之,整个层级结构会变得异常复杂和难以维护。uMVVM的理念是只需要一个View,View是唯一的入口,并且View可以是非常复杂,里面维护了所有的SubView,所以换UI也好,换功能也罢,只要关注于对应的View即可。

源代码托管在Github上,

转载地址:http://vopta.baihongyu.com/

你可能感兴趣的文章
Item 23 不要在代码中使用新的原生态类型(raw type)
查看>>
为网页添加留言功能
查看>>
JavaScript—数组(17)
查看>>
Android 密钥保护和 C/S 网络传输安全理论指南
查看>>
以太坊ERC20代币合约优化版
查看>>
Why I Began
查看>>
同一台电脑上Windows 7和Ubuntu 14.04的CPU温度和GPU温度对比
查看>>
js数组的操作
查看>>
springmvc Could not write content: No serializer
查看>>
Python系语言发展综述
查看>>
新手 开博
查看>>
借助开源工具高效完成Java应用的运行分析
查看>>
163 yum
查看>>
第三章:Shiro的配置——深入浅出学Shiro细粒度权限开发框架
查看>>
80后创业的经验谈(转,朴实但实用!推荐)
查看>>
让Windows图片查看器和windows资源管理器显示WebP格式
查看>>
我的友情链接
查看>>
vim使用点滴
查看>>
embedded linux学习中几个需要明确的概念
查看>>
mysql常用语法
查看>>