01 Trail Renderer

使用Trail Renderer制作流星拖尾demo,这个参考网上教程做的。后来需要在流星到达一定高度后渐隐然后销毁,就设置其梯度alpha值渐变。开始之前需要创建一个材质,然后选择Shader为Particles/Additive,然后给Trail Renderer用。

主要代码如下:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class Star : MonoBehaviour
{
    public float speedX = -1;
    public float speedY = -1;
    public float speedZ = 0;
    public float lowestHeight = 0;
    public float alphaDecreaseSpeed = 0.1f;

    private bool triggered = false;
    private float size = -1;
    private TrailRenderer trailRenderer;
    private Gradient colorGradient;
    private GradientColorKey[] colorKeys;
    private GradientAlphaKey[] alphaKeys;

    void Awake()
    {
        GetComponent<Rigidbody>().velocity = new Vector3(speedX, speedY, speedZ);
        trailRenderer = GetComponentInChildren<TrailRenderer>();
        colorGradient = trailRenderer.colorGradient;
        colorKeys = colorGradient.colorKeys;
        alphaKeys = colorGradient.alphaKeys;
    }

    private void Update()
    {
        if(triggered)
        {
            return;
        }

        if(transform.position.y < lowestHeight)
        {
            StartCoroutine(GradientAlpha());
            triggered = true;
        }
    }

    IEnumerator GradientAlpha()
    {
        while (alphaKeys[0].alpha >= 0)
        {
            alphaKeys = trailRenderer.colorGradient.alphaKeys;
            alphaKeys = new GradientAlphaKey[] {
                new GradientAlphaKey(alphaKeys[0].alpha - alphaDecreaseSpeed, 0),
                new GradientAlphaKey(alphaKeys[1].alpha - alphaDecreaseSpeed, 1)};

            colorGradient.SetKeys(colorKeys, alphaKeys);
            trailRenderer.colorGradient = colorGradient;

            yield return new WaitForSeconds(0.1f);
        }

        Destroy(gameObject);
    }
}

这个主要就是设置alpha,color是单独的,不含alpha的,这一点要注意。另外SetKeys只是对colorGradient变量生效,别忘了将trailRenderer的colorGradient重新赋值。此外还可以对其渐变颜色和宽度进行控制,这里就不介绍了。

效果如下:

Unity与C#学习记录 - 09

为了方便参考我做了预制体,链接如下:

https://download.csdn.net/download/u012911347/11071535

02 AssetBundle

前面的学习记录中有Resources Load等方法加载资源的介绍,现在则需要学习下AssetBundle的简单使用。

首先,在Project窗口建立一个测试用的预制体如Cube,然后在其Inspector面板下面能看到AssetBundle的设置:

Unity与C#学习记录 - 09

这里我设置好了,左侧的设置需要的类别信息,右边则设置具体资源名称,如我设置类别为models,资源为cube。然后写一段代码:

#if UNITY_EDITOR
using UnityEngine;
using System.IO;
using UnityEditor;

public class TestAssetBundle : MonoBehaviour
{
	void Start ()
	{
		
	}
	
	void Update ()
	{
		
	}
}

public class CreateAssetBundles
{
    [MenuItem("Assets/Build AssetBundles")]
    static void BuildAllAssetBundles()
    {
        string dir = "AssetBundles";

        if (!Directory.Exists(dir))
        {
            Directory.CreateDirectory(dir);
        }

        BuildPipeline.BuildAssetBundles(dir, BuildAssetBundleOptions.None, BuildTarget.StandaloneWindows64);
    }
}
#endif

主要是CreateAssetBundles类的静态方法,在Editor模式中,会在Assets工具栏下添加一个自定义的“Build AssetBundles”选项,点击执行后会得到如下AssetBundles:

Unity与C#学习记录 - 09

这里BuildPipeline.BuildAssetBundles的参数中,dir指定的是以Assets目录为参考的,所以我上面代码的AssetBundles目录就和Assets同级,需要放在Assets目录下就写成Assets/AssetBundles。另外注意AssetBundles编译后的东西是区分平台的,因为那些shader和材质是要适配特定平台的。上面的代码指定了用于Windows64,所以下面还是用Windows上Unity Editor进行加载。

把上面的AssetBundles目录拷贝到服务器,然后用下面的代码加载:

ollections;
using System.Collections.Generic;
using UnityEngine;

public class TestLoadAssetbundle : MonoBehaviour
{
    public string url;

    void Start ()
    {
        StartCoroutine(DownloadModel());
    }
    
    void Update ()
    {
        
    }

    IEnumerator DownloadModel()
    {
        WWW www = new WWW(url);
        yield return www;
        AssetBundle assetBundle = www.assetBundle;
        GameObject go = Instantiate(assetBundle.LoadAsset("cube")) as GameObject;
    }
}

这里url为:

http://192.168.206.197/AssetBundles/models.cube

这样成功加载了该立方体:

Unity与C#学习记录 - 09

03 Unity Log补充

unity常见的三种日志级别,info是白色的,warning是黄色的,error则是红色的。其实还可以对打印出来的日志做自定义颜色处理,如:

Debug.Log("<color=green> test" + "</color>");

这样该条日志就会变成绿色,效果:

Unity与C#学习记录 - 09

关于Unity日志回调可以用logMessageReceivedThreaded,该方法在收到日志记录时触发,可以是主线程或者其他线程的。示例如下:

void Start ()
{
    Application.logMessageReceivedThreaded += MyLog;
    Debug.Log("<color=green> test" + "</color>");
}

void MyLog(string condition, string stackTrace, LogType type)
{
    Debug.Log(stackTrace);
}

我这里只是演示做法,一般对该日志回调进行监控是用于记录运行状态的,会搜集信息写入本地文件中。

04 xml文件读取

XML是指Extensible Markup Language,也就是可扩展标记语言。这里参考下面的博客简单学习下用C#对xml文件进行简单独写:

https://www.cnblogs.com/han1982/p/4072571.html

首先是文件格式要求:

 1、XML只能有一个根节点。
 2、XML有开始标记就必须有结束标记。
 3、XML元素的属性值必须有引号。
 4、XML必须有结束标记,大小写必须跟开始标记一致。
 5、XML文件编码必须跟encoding指定编码要一致。

xml文件示例内容如下:

<?xml version="1.0" encoding="utf-8"?>
<MyP>
  <P1>
    <Person id="cz001">
      <Name>张三</Name>
      <Age>18</Age>
    </Person>
    <Person id="cz002">
      <Name>李四</Name>
      <Age>19</Age>
    </Person>
    <Person id="cz003">
      <Name>王五</Name>
      <Age>20</Age>
    </Person>
  </P1>
  <P2>
    <Person>
      <Name>张三2</Name>
      <Age>18</Age>
    </Person>
    <Person>
      <Name>李四2</Name>
      <Age>19</Age>
    </Person>
    <Person>
      <Name>王五2</Name>
      <Age>20</Age>
    </Person>
  </P2>
</MyP>

节点下面套节点,节点可以有属性,如上面的id信息。下面一段代码可以创建一个简单的xml文件并添加节点和属性信息:

void WriteXDoc()
{
    // 创建XML对象
    XDocument xDoc = new XDocument();

    // 创建一个根节点
    XElement root = new XElement("Root");
    xDoc.Add(root); //将根节点加入到XML对象中
    
    // 创建一个子节点
    XElement xele = new XElement("User");

    // 加入到根节点
    root.Add(xele);
    
    // 添加属性
    XAttribute attr = new XAttribute("ID", 1);
    xele.Add(attr);
    xele.SetElementValue("Name", "张三");
    xele.SetElementValue("Age", "18");

    //保存xml文件
    xDoc.Save(Application.streamingAssetsPath + "/test.xml");
}

得到的xml文件内容为:

<?xml version="1.0" encoding="utf-8"?>
<Root>
  <User ID="1">
    <Name>张三</Name>
    <Age>18</Age>
  </User>
</Root>

读取示例代码如下:

void ReadXDoc()
{
    XDocument xDoc = XDocument.Load(Application.streamingAssetsPath + "/test.xml");
    XElement root = xDoc.Root;

    foreach (XElement element in root.Elements())
    {
        foreach (XAttribute attr in element.Attributes())
        {
            Debug.Log(" [" + attr.Name.ToString() + "=" + attr.Value + "]");
        }

        // 获取该元素Name
        Debug.Log(element.Element("Name").Value);

        // 获取该元素Age
        Debug.Log(element.Element("Age").Value);
    }
}

 

相关文章: