Unity2019 UIElement 笔记(九)简单练习一

那么到目前为止,已经学会了如何使用UXML和USS,那么接下来就是实际运用了。
那么在这里我会演示一个最简单的运用,如果有不足之处请大家指出。

目标

我们的目标是做出类似冒险岛1中角色属性的编辑界面,如下图:
Unity2019 UIElement 笔记(九)简单练习一
图片是直接从百度图片上找的,那我们就要开始简单的仿制这个UI布局来练习目前学到的内容。

一、创建C#脚本

首先我们创建一个C#脚本,命名为ActorState,并在里面写好我们所需要的属性

using UnityEngine;

[ExecuteInEditMode]
public class ActorState : MonoBehaviour
{
    public string m_name;
    public string m_career;
    public int m_level;
    public int m_pk;
    public string m_family;
    public int m_maxHP;
    public int m_maxMP;
    public int m_maxEXP;
    public int m_popu;

    public int m_apoint;

    public int m_str;
    public int m_agi;
    public int m_int;
    public int m_luc;
}

然后创建另外一个C#脚本,命名为ActorStateEditor,如下所示:

using UnityEditor;
using UnityEngine;
using UnityEngine.UIElements;

[CustomEditor(typeof(ActorState))]
public class ActorStateEditor : Editor
{
    public override VisualElement CreateInspectorGUI()
    {
        var visualTree = Resources.Load("actorstate_inspector_uxml") as VisualTreeAsset;
        var uxmlVE = visualTree.CloneTree();
        uxmlVE.styleSheets.Add(AssetDatabase.LoadAssetAtPath<StyleSheet>("Assets/Resources/actorstate_inspector_styles.uss"));
        return uxmlVE;
    }
}

同时创建actorstate_inspector_uxml和actorstate_inspector_styles.uss并放入Resources文件夹中。
那么前期的准备工作就做好了。

二、设置PropertyField

首先在UXML中关联PropertyField

	<editor:PropertyField binding-path="m_name" label="名称"/>

然后在USS中设置PropertyField的样式

PropertyField 
{
	border-style: solid;
	border-width: 1px 1px 1px 1px;
	border-color: #000;
	border-radius: 6px;
	padding: 2px 0px 0px 0px;
	width:220px;
	background-color: #ACD70C;
}
PropertyField TextField
{
	width:210px;
	align-self:flex-start;
}
PropertyField Label
{
	margin: 0px 0px 0px 20px;
	align-self:center;
	align-self:flex-start;
	min-width:50px;
	width:50px;
	font-size: 12;
}

这里unity的背景色貌似还不支持渐变,我就直接用单一颜色了
那么最后的结果如下
Unity2019 UIElement 笔记(九)简单练习一
效果。。。还行吧
那么让我们把其他的属性也全部放入
首先添加上IntegerField

PropertyField IntegerField
{
	width:210px;
	align-self:flex-start;
}

然后写入其他所有的属性

  <editor:PropertyField binding-path="m_name" label="名字" />
  <editor:PropertyField binding-path="m_career" label="职业" />
  <editor:PropertyField binding-path="m_level" label="等级" />
  <editor:PropertyField binding-path="m_pk" label="PK" />
  <editor:PropertyField binding-path="m_family" label="家族" />
  <editor:PropertyField binding-path="m_maxHP" label="HP" />
  <editor:PropertyField binding-path="m_maxMP" label="MP" />
  <editor:PropertyField binding-path="m_maxEXP" label="经验值" />
  <editor:PropertyField binding-path="m_popu" label="人气度" />
  
  <editor:PropertyField binding-path="m_str" label="力量" />
  <editor:PropertyField binding-path="m_agi" label="敏捷" />
  <editor:PropertyField binding-path="m_int" label="智力" />
  <editor:PropertyField binding-path="m_luc" label="运气" />

能力值属性我们待会儿单独写,现在我们已经有大部分的框了,如图
Unity2019 UIElement 笔记(九)简单练习一

三、设置container

那么我们现在需要一个大框将他们框起来,那我们就需要一个container

.container
{
	justify-content:flex-start;
}
.container__column
{
	flex-direction:column;
}
.container__row
{
	flex-wrap:wrap;
	flex-direction:row;
}

这里使用column的话,那么所有的元素都会垂直排列(这也是默认排列)。
而使用row的话,所有元素就会水平排列,如果不使用flex-wrap:wrap;那么就会变得很挤:
Unity2019 UIElement 笔记(九)简单练习一
如果使用了flex-wrap:wrap;那么就会根据大小自动换行:
Unity2019 UIElement 笔记(九)简单练习一
当然我们这边使用的是column,接下来我们需要给它一个框

/*....*/
.container__column
{
	border-style: solid;
	border-width: 1px 1px 1px 1px;
	border-color: #000;
	flex-direction:column;
}
.container__column--main
{
	align-self:center;
}
/*....*/
PropertyField 
{
	align-self:center;
	/*...*/
}

这边我还添加了一个边框,因为默认子元素是左对齐的,所以我们还要让PropertyField元素居中,为它加上align-self:center;
而container__column–main中的align-self:center;是为了让整个框在界面中居中。

<VisualElement name="main" class="container__column container__column--main">
	<!--......-->
</VisualElement>

可以看到我们的框颇具雏形了
Unity2019 UIElement 笔记(九)简单练习一
接下来让这个框往外延伸一点,并再做一个倒角,设置一下背景颜色

.container__column--main
{
	padding:4px;
	border-radius: 6px;
	background-color: #F1F1F1;
	align-self:center;
}

Unity2019 UIElement 笔记(九)简单练习一
嗯哼,还可以,那么按照这个样子作出最外面的大框,并为其加上标题

.container__column--out
{
	padding:4px;
	border-radius: 6px;
	background-color: #444444;
	border-color: #FFF;
	align-self:center;
}
.midTitle
{
	align-self:center;
	font-size:16;
	color:#EEB422;
}
<VisualElement name="main" class="container__column container__column--out">
  <Label name="title" text="角色属性" class="midTitle"/>
  <VisualElement name="main" class="container__column container__column--main">
	<!--......-->
  </VisualElement>
</VisualElement>

最后我们的成果就像这样
Unity2019 UIElement 笔记(九)简单练习一

四、制作能力点面板

其实这个能力点的面板有点麻烦,但是,我们可以理解成这样:能力点将整个UI分为了三部分,我们现在只要分开上下两部分,并为中间添加上一部分就可以了。
那么这里我自己做了一下,这里放上完整代码:

CSS部分

/*----------------------container----------------------*/
.container
{
	justify-content:flex-start;
}
.container__column
{
	border-style: solid;
	border-width: 1px 1px 1px 1px;
	border-color: #000;
	flex-direction:column;
}
.container__column--main
{
	padding:4px;
	background-color: #F1F1F1;
	align-self:center;
}
.container__column--main__down
{
	border-radius: 0px 0px 6px 6px;
}
.container__column--main__up
{
	border-radius: 6px 6px 0px 0px;
}
.container__column--mid
{
	width:230px;
	height:50px;
	background-color: #3AADEE;
	border-width: 0px 1px;
	border-color: #000;
}
.container__column--out
{
	padding:4px;
	border-radius: 6px;
	background-color: #444444;
	border-color: #FFF;
	align-self:center;
}
.container__row
{
	flex-wrap:wrap;
	flex-direction:row;
}
/*----------------------midTitle----------------------*/
.midTitle
{
	align-self:center;
	font-size:16;
	color:#EEB422;
}
.midTitle__white
{
	align-self:flex-start;
	padding:5px 0px 0px 20px;
	font-style: bold;
	color:#FFFFFF;
}
/*----------------------PropertyField----------------------*/
PropertyField 
{
	align-self:center;
	border-style: solid;
	border-width: 1px 1px 1px 1px;
	border-color: #000;
	border-radius: 6px;
	padding: 2px 0px 0px 0px;
	width:220px;
	background-color: #C2EE35;
}
PropertyField IntegerField
{
	width:210px;
	align-self:flex-start;
}
PropertyField TextField
{
	width:210px;
	align-self:flex-start;
}
PropertyField Label
{
	margin: 0px 0px 0px 20px;
	align-self:center;
	align-self:flex-start;
	min-width:50px;
	width:50px;
	font-size: 12;
}
/*----------------------TextField----------------------*/
.tField
{
	align-self:center;
	width:60px;
	margin:0px 0px 0px 80px;
}
/*----------------------Button----------------------*/
.btn
{
	width:75px;
	margin:8px 0px 0px 5px;
	background-image:none;
	background-color:#B3DA1F;
	border-radius:4px;
	border-style: solid;
	border-width: 1px 1px 1px 1px;
	border-color: #CCCCCC;
	font-size:13;
}
.btn:active:after
{
	background-color:#E8EF8F;
}

XML部分

<VisualElement name="main" class="container__column container__column--out">
  <Label name="title" text="角色属性" class="midTitle"/>
  <VisualElement name="main1" class="container__column container__column--main container__column--main__up">
   <editor:PropertyField binding-path="m_name" label="名字" />
   <editor:PropertyField binding-path="m_career" label="职业" />
   <editor:PropertyField binding-path="m_level" label="等级" />
   <editor:PropertyField binding-path="m_pk" label="PK" />
   <editor:PropertyField binding-path="m_family" label="家族" />
   <editor:PropertyField binding-path="m_maxHP" label="HP" />
   <editor:PropertyField binding-path="m_maxMP" label="MP" />
   <editor:PropertyField binding-path="m_maxEXP" label="经验值" />
   <editor:PropertyField binding-path="m_popu" label="人气度" />
  </VisualElement>
  <VisualElement name="mid" class="container__column container__column--mid">
   <VisualElement class="container__row">
     <VisualElement class="container">
      <Label name="atitle" text="能力点" class="midTitle midTitle__white"/>
      <TextField name="text" class="tField"/>
     </VisualElement>
     <Button name="Button" text="分配属性" class="btn"/>
   </VisualElement>
  </VisualElement>
  <VisualElement name="main3" class="container__column container__column--main container__column--main__down">
   <editor:PropertyField binding-path="m_str" label="力量" />
   <editor:PropertyField binding-path="m_agi" label="敏捷" />
   <editor:PropertyField binding-path="m_int" label="智力" />
   <editor:PropertyField binding-path="m_luc" label="运气" />
  </VisualElement>
</VisualElement>

结果

Unity2019 UIElement 笔记(九)简单练习一

总结

经过这个简单的练习,对于Unity这个新的UIElement系统我有了简单的了解,相较于之间的系统,我觉得方便了不少,可还是有一些麻烦的地方,但总的来说更棒了,个人而言更加喜欢这个新系统。
就我个人而言,我本身并没有HTML和CSS方面的知识储备,对于我和那些没学过这方面内容的人,稍微有点吃亏,但是HTML和CSS本身就是一个完整的体系,某些在Unity官方文档中没有提到的内容,去百度上找也不是特别麻烦。
做起来的话,由于没什么经验,可能会显得比较冗杂,我个人觉得我的USS部分写的有些复杂,而在UXML部分也可以选择使用模板。
这个案例就到这里结束了吧,下一次会做一个有关模板的案例,并且还有最重要的事件系统没有介绍,先挖个坑吧,就这样。