Roman e3e11e2556 任务:编写玩法框架
1.制作障碍系统

(1.制作几种类型的障碍物的预制体
((*.编写障碍物基类,以下几种均继承自基类,含碰撞体,RememberY(生成障碍物时该有多大的Y)
((1.矮障碍,仅碰撞体
((2.高障碍,仅碰撞体
((3.可冲破障碍
(((1.除基本碰撞体外,额外包含一个触发器,比碰撞体先检测到马,同时获取马的x速度,大于阈值则给障碍做破碎,用马的力度决定破碎力,关闭碎块和马的碰撞
(((*.导入某2D破碎插件
((4.人马分离障碍
(((WAIT,需要等待人马分离系统先搭建

(2.编写障碍物生成系统
((1.每若干时间,生成一个随机一种障碍,若干的范围可控
(((1.设计协程,从预制体列表中随机出一种,并在计算好的位置实例化,随后等待范围内的若干时间,然后检查马的存活情况,若马仍存活,重新调用本协程
((2.生成的位置:x在相机右侧若干不变距离,y根据障碍物的不同而不同,需要计算保存。

(3.编写障碍物消亡系统
((1.每个障碍物和碎片都会在离开镜头后被删除
2022-07-30 00:47:44 +08:00

178 lines
5.2 KiB
C#

using UnityEngine;
using System.Collections;
using System.Collections.Generic;
using UnityEditor;
[RequireComponent(typeof(Rigidbody2D))]
public class Explodable : MonoBehaviour
{
public System.Action<List<GameObject>> OnFragmentsGenerated;
public bool allowRuntimeFragmentation = false;
public int extraPoints = 0;
public int subshatterSteps = 0;
public string fragmentLayer = "Default";
public string sortingLayerName = "Default";
public int orderInLayer = 0;
public enum ShatterType
{
Triangle,
Voronoi
};
public ShatterType shatterType;
public List<GameObject> fragments = new List<GameObject>();
private List<List<Vector2>> polygons = new List<List<Vector2>>();
/// <summary>
/// Creates fragments if necessary and destroys original gameobject
/// </summary>
public void explode()
{
//if fragments were not created before runtime then create them now
if (fragments.Count == 0 && allowRuntimeFragmentation)
{
generateFragments();
}
//otherwise unparent and activate them
else
{
foreach (GameObject frag in fragments)
{
frag.transform.parent = null;
frag.SetActive(true);
}
}
//if fragments exist destroy the original
if (fragments.Count > 0)
{
Destroy(gameObject);
}
}
/// <summary>
/// Creates fragments and then disables them
/// </summary>
public void fragmentInEditor()
{
if (fragments.Count > 0)
{
deleteFragments();
}
generateFragments();
setPolygonsForDrawing();
foreach (GameObject frag in fragments)
{
frag.transform.parent = transform;
frag.SetActive(false);
}
}
public void deleteFragments()
{
foreach (GameObject frag in fragments)
{
if (Application.isEditor)
{
DestroyImmediate(frag);
}
else
{
Destroy(frag);
}
}
fragments.Clear();
polygons.Clear();
}
/// <summary>
/// Turns Gameobject into multiple fragments
/// </summary>
private void generateFragments()
{
fragments = new List<GameObject>();
switch (shatterType)
{
case ShatterType.Triangle:
fragments = SpriteExploder.GenerateTriangularPieces(gameObject, extraPoints, subshatterSteps);
break;
case ShatterType.Voronoi:
fragments = SpriteExploder.GenerateVoronoiPieces(gameObject, extraPoints, subshatterSteps);
break;
default:
Debug.Log("invalid choice");
break;
}
//sets additional aspects of the fragments
foreach (GameObject p in fragments)
{
if (p != null)
{
p.layer = LayerMask.NameToLayer(fragmentLayer);
p.GetComponent<Renderer>().sortingLayerName = sortingLayerName;
p.GetComponent<Renderer>().sortingOrder = orderInLayer;
}
}
foreach (ExplodableAddon addon in GetComponents<ExplodableAddon>())
{
if (addon.enabled)
{
addon.OnFragmentsGenerated(fragments);
}
}
}
private void setPolygonsForDrawing()
{
polygons.Clear();
List<Vector2> polygon;
foreach (GameObject frag in fragments)
{
polygon = new List<Vector2>();
foreach (Vector2 point in frag.GetComponent<PolygonCollider2D>().points)
{
Vector2 offset = rotateAroundPivot((Vector2)frag.transform.position, (Vector2)transform.position, Quaternion.Inverse(transform.rotation)) - (Vector2)transform.position;
offset.x /= transform.localScale.x;
offset.y /= transform.localScale.y;
polygon.Add(point + offset);
}
polygons.Add(polygon);
}
}
private Vector2 rotateAroundPivot(Vector2 point, Vector2 pivot, Quaternion angle)
{
Vector2 dir = point - pivot;
dir = angle * dir;
point = dir + pivot;
return point;
}
void OnDrawGizmos()
{
if (Application.isEditor)
{
if (polygons.Count == 0 && fragments.Count != 0)
{
setPolygonsForDrawing();
}
Gizmos.color = Color.blue;
Gizmos.matrix = transform.localToWorldMatrix;
Vector2 offset = (Vector2)transform.position * 0;
foreach (List<Vector2> polygon in polygons)
{
for (int i = 0; i < polygon.Count; i++)
{
if (i + 1 == polygon.Count)
{
Gizmos.DrawLine(polygon[i] + offset, polygon[0] + offset);
}
else
{
Gizmos.DrawLine(polygon[i] + offset, polygon[i + 1] + offset);
}
}
}
}
}
}