13.Unity2D 横版 可上下左右移动的双向平台(双向行走+可移动+单独判定)+随机平台生成

这篇具有很好参考价值的文章主要介绍了13.Unity2D 横版 可上下左右移动的双向平台(双向行走+可移动+单独判定)+随机平台生成。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

13.Unity2D 横版 可上下左右移动的双向平台(双向行走+可移动+单独判定)+随机平台生成

 

 总目录https://blog.csdn.net/qq_54263076/category_11900070.html?spm=1001.2014.3001.5482

大多数平台教程全是碰撞体的可移动平台,并没有可跳上的平台,并且要求按下键会从平台上跳下来。有也只是通过控制平台的“2D平台效果碰撞体”组件的单向平台的旋转偏移来做,但是这样会出现一个问题,当有多个人或者多个NPC在同一个平台上,如果有一个人按下键会导致所有人都跳下来,虽然其他人并没有按下键。如同下面:(看不懂原理没关系,就看个示范结果)

 13.Unity2D 横版 可上下左右移动的双向平台(双向行走+可移动+单独判定)+随机平台生成

所以为了解决这个问题,我们需要对能进行跳跃平台的人物自己碰撞体短时间消失,射线检测是必要的。如果不懂射线检测,欢迎看我下面的博客

11.Unity2D 横版 简单AI 之背后受击转身+寻路跟随敌人+模块化+射线检测_ζั͡ ั͡雾 ั͡狼 ั͡✾的博客-CSDN博客Unity2D 横版 简单AI 之背后受击转身+寻路跟随敌人+模块化+射线检测。回顾上节课,我们已经完成了范围内检索敌人自动攻击,随机移动功能。1.敌人背后受击转身+背部攻击伤害翻倍2.寻路跟随敌人随机移动的坏处就是看到敌人(主角)会略过去,按照自己的行为行走,所以我们要再写一个行为脚本,用来看到敌人后的行为,当然如果没有看到敌人还是随机移动的函数,其中黄线为视线线,变红色为找到主角,并记录此时主角的位置......https://blog.csdn.net/qq_54263076/article/details/125756448?spm=1001.2014.3001.5501并且能进行跳跃平台的人物(主角+NPC)都有CharacterPanel脚本,所以将平台检测写入这个脚本就行。

开始

1.可上下左右移的可跳上去的碰撞体平台

(1)创建平台预制体。精灵渲染组件+碰撞+平台效果碰撞器(可以单方面跳上去,但不能跳下来)。

13.Unity2D 横版 可上下左右移动的双向平台(双向行走+可移动+单独判定)+随机平台生成

 (2)创建platformMove脚本,用来控制平台上下或左右循环移动,加入这个预制体

13.Unity2D 横版 可上下左右移动的双向平台(双向行走+可移动+单独判定)+随机平台生成

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

public class platformMove : MonoBehaviour
{
    public float waitTime = 0.5f;//定值等待时间
    private float _waitTime ;//等待时间
    public float Speed = 1;//速度
    public Vector3 StartPoi;//起始位置
    public Vector3 EndPoi;//需要移动目标位置
    private bool IsStoE=true;//是否是起始点到终止点的状态
    platformMove(Vector3 EndPoi)//构造函数,赋值终点
    {
        this.EndPoi = EndPoi;
    }
    // Start is called before the first frame update
    void Start()
    {
        _waitTime = waitTime;
        StartPoi = transform.position;//初始化起始位置
 /*       EndPoi = transform.position + 2 * Vector3.right;//用来测试,实际的目标点是通过赋值*/

    }

    // Update is called once per frame
    void Update()
    {
        Vector2 StoE = (EndPoi - StartPoi).normalized;//起始点指向终止点的单位方向向量
     
        if (_waitTime > 0)
        {
                _waitTime -= Time.deltaTime;
        }
        else
        {
            if (IsStoE)//是起始点到终止点的状态
            {
                gameObject.transform.Translate(Speed * Time.deltaTime * StoE);
                if (Vector2.Dot((EndPoi- transform.position),StoE)<0)//如果到达终点 点乘夹角是180
                {
                    _waitTime = waitTime;//等待时间重置
                    IsStoE = false;//改变状态
                }

            }
            else {
  
                gameObject.transform.Translate(-Speed * Time.deltaTime * StoE);
                if (Vector2.Dot((StartPoi - transform.position), -StoE) < 0)//如果到达起点 点乘夹角是180
                {
                
                    _waitTime = waitTime;//等待时间重置
                    IsStoE = true;//改变状态
                }


            }
        }
    }



}

(3)在随机生成地图的脚本中加入随机生成各种平台(可忽略

13.Unity2D 横版 可上下左右移动的双向平台(双向行走+可移动+单独判定)+随机平台生成

12.Unity2D 横版 TileMap随机生成简易横版瓦片地图+随机生成环境(花草树石)精灵图+2d-extras+协程的应用_ζั͡ ั͡雾 ั͡狼 ั͡✾的博客-CSDN博客_tilemap 随机Unity2D 横版 TileMap随机生成简易横版瓦片地图+随机生成环境(花草树石)精灵图+2d-extras+协程的应用。思路就是先生成瓦片,再进行创建能通过的通道。生成瓦片的时候先随机生成瓦片起始点,再通过一个协程从瓦片起始点开始延长不等长度(因为是横版游戏,在横向上的延伸要求高)注意需要修改环境瓦片地图的平铺轴和精灵图片的锚点位置,确保随机生成的精灵图是接触与地面而不是悬空的。(由于随机生成的环境精灵图大小不一样,但锚点都在中间,所以需要修改锚点) ...https://wulang.blog.csdn.net/article/details/125777090?spm=1001.2014.3001.5502

首先新建一个空物体用来统一管理生成平台预制体,及其图层

13.Unity2D 横版 可上下左右移动的双向平台(双向行走+可移动+单独判定)+随机平台生成

地图生成脚本更新(在调试阶段为了快速生成地图,我将yeid return从for循环外移出去了,以后写加载条的时候可以再放回去减少性能消耗)

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.Tilemaps;
public class GroundTIleMap : MonoBehaviour
{
    public Tilemap ground_tilemap;//拖动获取地面瓦片地图
    public Tilemap environ_tilemap;
    public TileBase groundTile;//拖动获取地面规则瓦片Rule Tile,-
    public TileBase environTile;//拖动获取环境规则瓦片
    public Vector2Int lowerLeftCoo = new Vector2Int(-18, -7);//地图起始左下角位置
    public int width = 20;//地图宽度
    public int length = 100;//地图长度
    public float groundStartPro = 0.10f;//生成地面起始点的概率
    public Vector2Int groundLenRan = new Vector2Int(3, 10);//起始地面点生成的长度范围
    public float environmentRich = 0.5f;//环境丰富度
    public GameObject[] itemsRandom;//随机物品组
    public float itemsRich = 0.05f;//随机物品丰富度
    public GameObject[] platformRandom;//随机平台组
    public float platformRich = 0.05f;//平台丰富度
    private List<Vector2Int> canEndPlat=new List<Vector2Int>();//可能的平台终点落点
    // Start is called before the first frame update
    void Start()
    {

        StartCoroutine(GroundStartPoi());
    }

    // Update is called once per frame
    IEnumerator GroundStartPoi()//生成地面起始点 用协程可以缓慢一步步生成地图,性能消耗少
    {
        yield return null;
        ground_tilemap.ClearAllTiles();
        Debug.Log("开始生成地面");
        for (int i = lowerLeftCoo.x; i < (this.length + lowerLeftCoo.x); i++)
        {
            for (int j = lowerLeftCoo.y; j < (this.width + lowerLeftCoo.y); j++)
            {
               /* yield return null;*/
                bool IsGround = j < (this.width + 3) ? (Random.value <= groundStartPro) : (Random.value <= groundStartPro + 0.05);//三元表达式,地面三行更容易生成地面起始点
                if (IsGround) StartCoroutine(GroundExtension(i, j));

            }
        }
        Debug.Log("结束生成地面");
        StartCoroutine(ClearChannel());//执行完GroundStartPoi(),GroundExtension()生成地面,开始清除产生能走的通道

    }
    IEnumerator GroundExtension(int i, int j)//从地面起始点开始延长
    {
        yield return null;
        int groundLen = Random.Range(groundLenRan.x, groundLenRan.y);
        for (int m = i; m <= i + groundLen; m++)
        {
           /* yield return null;*/
            ground_tilemap.SetTile(new Vector3Int(m, j, 0), groundTile);
        }

    }
    //清除,产生通道,思路就是从底层有方块的地方,开始判断上面。如果没有方块的话,就清除俩层/三层的通道
    IEnumerator ClearChannel()
    {
        yield return null;
        Debug.Log("开始产生通道");
        for (int i = lowerLeftCoo.x; i < (this.length + lowerLeftCoo.x); i++)
        {
            for (int j = lowerLeftCoo.y; j < (this.width + lowerLeftCoo.y - 1); j++)//最高层上面必然没有方块,不需要判断,-1
            {
                if (ground_tilemap.GetTile(new Vector3Int(i, j, 0)) != null&& ground_tilemap.GetTile(new Vector3Int(i, j + 1, 0)) == null)//如果此处不为空方块,如果此处上方为空方块
                {

                        ground_tilemap.SetTilesBlock(new BoundsInt(i - 2, j + 1, 0, 3, 3, 1), new TileBase[] { null, null, null, null, null, null, null, null, null });//将上方3x3格子置空

                }
               /* yield return null;*/

            }
        }
        Debug.Log("产生通道完成");
        StartCoroutine(GeneratePlatform());

    }

    IEnumerator GeneratePlatform()
    {
        yield return null;
        Debug.Log("开始生成平台");
        for (int i = lowerLeftCoo.x; i < (this.length + lowerLeftCoo.x); i++)
        {
            for (int j = lowerLeftCoo.y; j < (this.width + lowerLeftCoo.y); j++)
            {//Y平台
                if (ground_tilemap.GetTile(new Vector3Int(i, j, 0)) != null && ground_tilemap.GetTile(new Vector3Int(i, j + 1, 0)) == null)//起点 如果此处不为空方块,且上方为空
                {
                    if (Random.value < platformRich*0.5)//随机
                    {
                        Vector2Int EndCellPoi = CanYEndPlat(i, j);
                        if (EndCellPoi != Vector2Int.zero)//当y轴落点不为0,即列表返回了一个数据
                        {
                            //清空目标点与生成点的地面瓦片
                            for (int n = j + 1; n < EndCellPoi.y; n++)
                            {
                                ground_tilemap.SetTile(new Vector3Int(i, n, 0), null);
                              
                            }
                            //随机选取平台生成
                            int r = Random.Range(0, platformRandom.Length);
                            GameObject plat = platformRandom[r];
                            plat.GetComponent<platformMove>().EndPoi = ground_tilemap.CellToWorld(new Vector3Int(EndCellPoi.x, EndCellPoi.y, 0));//平台赋值终点 转世界坐标
                            //生成平台在PlatForm下统一图层管理
                            Instantiate(plat, ground_tilemap.CellToWorld(new Vector3Int(i, j + 1, 0)), Quaternion.Euler(0, 0, 0), GameObject.Find("PlatForm").transform);
                        };
                    }
                    
                }
             //X平台
                if (ground_tilemap.GetTile(new Vector3Int(i, j, 0)) == null && ground_tilemap.GetTile(new Vector3Int(i-1, j , 0)) == null)//起点 如果此处为空方块,且左边方为空
                {
                    Debug.Log( " " + new Vector3Int(i, j, 0));
                    if (Random.value < platformRich * 0.5)//随机
                    {
                        Vector2Int EndCellPoi = CanXEndPlat(i, j);
                        if (EndCellPoi != Vector2Int.zero)//当x轴落点不为0,即列表返回了一个数据
                        {
                            //清空目标点与生成点的地面瓦片
                            for (int m = i + 1; m < EndCellPoi.x; m++)
                            {
                                ground_tilemap.SetTile(new Vector3Int(m, j, 0), null);
                            }
                            //随机选取平台生成
                            Debug.Log(EndCellPoi + " " + new Vector3Int(i, j, 0));
                            int r = Random.Range(0, platformRandom.Length);
                            GameObject plat = platformRandom[r];
                            plat.GetComponent<platformMove>().EndPoi = ground_tilemap.CellToWorld(new Vector3Int(EndCellPoi.x, EndCellPoi.y, 0));//平台赋值终点 转世界坐标
                                                                                                                                                 //生成平台在PlatForm下统一图层管理
                            Instantiate(plat, ground_tilemap.CellToWorld(new Vector3Int(i, j, 0)), Quaternion.Euler(0, 0, 0), GameObject.Find("PlatForm").transform);
                        };
                    }
                }
            }
        }
        Debug.Log("结束生成平台");
        StartCoroutine(GenerateEnviron());

    }
    //可能Y轴上平台终点落点
    private Vector2Int CanYEndPlat(int i, int j)
    {
        canEndPlat.Clear();//清空可能终点落点列表
        for (int y = i + 1; y < (this.width + lowerLeftCoo.y); y++)
        {
            if (((ground_tilemap.GetTile(new Vector3Int(i, y, 0)) != null && ground_tilemap.GetTile(new Vector3Int(i, y + 1, 0)) == null)
                || (ground_tilemap.GetTile(new Vector3Int(i, y, 0)) == null && (ground_tilemap.GetTile(new Vector3Int(i - 1, y, 0)) != null || ground_tilemap.GetTile(new Vector3Int(i + 1, y, 0)) != null))
                )&& Mathf.Abs(y - j) > 3)//找到起点头上的方块为可能落点(起码要高度大于三)(有方块且头顶为空方块的地方,没方块的地方隔壁却有方块的地方)
            {
                canEndPlat.Add(new Vector2Int(i, y+1));
            }
        }
        if (canEndPlat.Count != 0)
        { //随机返回一个可能落点
            int r = Random.Range(0, canEndPlat.Count);
            return canEndPlat[r];
        }
        else { return Vector2Int.zero; }

    }
    //可能X轴上平台终点落点
    private Vector2Int CanXEndPlat(int i,int j) {
        canEndPlat.Clear();//清空可能终点落点列表
         for(int x=i+1;x< (this.length + lowerLeftCoo.x); x++)
        {
            if ((ground_tilemap.GetTile(new Vector3Int(x, j - 2, 0)) == null && ground_tilemap.GetTile(new Vector3Int(x, j +2, 0)) == null 
                && ground_tilemap.GetTile(new Vector3Int(x, j -1, 0)) == null && ground_tilemap.GetTile(new Vector3Int(x, j+1, 0)) == null
                && ground_tilemap.GetTile(new Vector3Int(x, j, 0)) == null && ground_tilemap.GetTile(new Vector3Int(x+1,j , 0)) != null)
                &&(Mathf.Abs(x - i) > 2&& Mathf.Abs(x - i)< 6))//可能落点上下各俩块都为空,且右边有方块
            {
                canEndPlat.Add(new Vector2Int(x, j));
            }
        }
        if(canEndPlat.Count!=0)
        { //随机返回一个可能落点
            int r = Random.Range(0, canEndPlat.Count);
            return canEndPlat[r]; 
        }
        else { return Vector2Int.zero; }
        
    }
   
    //生成环境
    IEnumerator GenerateEnviron()
    {
        yield return null;
        Debug.Log("开始生成花草和随机物品");
        for (int i = lowerLeftCoo.x; i < (this.length + lowerLeftCoo.x); i++)
        {
            for (int j = lowerLeftCoo.y; j < (this.width + lowerLeftCoo.y); j++)
            {
                if (ground_tilemap.GetTile(new Vector3Int(i, j, 0)) == groundTile && ground_tilemap.GetTile(new Vector3Int(i, j + 1, 0)) == null)//如果此处为地面,上面为空方块
                {
                    //花草
                    if (Random.value < environmentRich)//随机
                    { environ_tilemap.SetTile(new Vector3Int(i, j + 1, 0), environTile); }
                    //随机物品
                    if (Random.value < itemsRich)//随机
                    {
                        int index = Random.Range(0, itemsRandom.Length );
                        Instantiate(itemsRandom[index], environ_tilemap.CellToWorld(new Vector3Int(i, j + 2, 0)), Quaternion.Euler(0, 0, 0),GameObject.Find("ItemsManager").transform); //坐标转换}
                    }
                  /*  yield return null;*/

                }
            }
        }
        Debug.Log("结束生成花草和随机物品");
    }

}

2.双向平台(实际是在按住下键瞬间取消了角色的碰撞体)

给平台预制体添加标签platform

13.Unity2D 横版 可上下左右移动的双向平台(双向行走+可移动+单独判定)+随机平台生成

角色的控制脚本更新

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

public class playerControl : MonoBehaviour
{

    private Rigidbody2D rig;//2D刚体
    private CharacterPanel characterPanel;//获取角色面板
    private Animator ani;//动画控制器
    private AnimatorStateInfo state;//动画状态
                                    // Start is called before the first frame update
    void Start()
    {
        rig = GetComponent<Rigidbody2D>();//获取刚体
        ani = GetComponent<Animator>();//获取动画控制器
        characterPanel = GetComponent<CharacterPanel>();//获取角色面板


    }

    // Update is called once per frame
    void Update()
    {
        move();//移动函数
        attack();//攻击函数-四连击

    }
    private void move()
    {    //水平,垂直俩个轴系
        float h = Input.GetAxis("Horizontal");
        float v = Input.GetAxis("Vertical");
        float dir = Input.GetAxisRaw("Horizontal");//方向-1 0 1

        //跳跃
        if (v > 0 && transform.GetComponent<CharacterPanel>().Iscanjump == true)
        {
            characterPanel.jump();
        }
        //长按高跳
        if (rig.velocity.y > 0 && Input.GetKey(KeyCode.W) || Input.GetKey(KeyCode.UpArrow) && transform.GetComponent<CharacterPanel>().Iscanjump == false)
        {
            rig.velocity += Vector2.up * 0.2f;//长按高跳额外得到向上速度
        }

        //方向改变
        if (dir != 0)
        {
            transform.localScale = new Vector3(dir * Mathf.Abs(transform.localScale.x), transform.localScale.y, transform.localScale.z);//通过改变scale改变方向
        }
        //按键左右移动
        Vector3 vt = new Vector3(h, 0, 0).normalized;//vt为俩个轴系合成的方向向量,normalized单位化
                                                     //移动动画
        if (dir != 0)
        {
            ani.SetBool("Ismove", true);
        }
        else { ani.SetBool("Ismove", false); }

        //空中左右移动,为地面jumpcharacterPanel.speedVertiacal倍
        if (h != 0 && transform.GetComponent<CharacterPanel>().Iscanjump == false)
        {
            gameObject.transform.Translate(vt * characterPanel.speed * characterPanel.jumpspeedVertiacal * Time.deltaTime);//通过这个函数来使用vt使得左右移动
        }
        //地面左右移动
        else { gameObject.transform.Translate(vt * characterPanel.speed * Time.deltaTime); }

        //按下键从平台上跳下来
        if (Input.GetKeyDown(KeyCode.S))
        {
            RaycastHit2D hit = Physics2D.Raycast(transform.position, new Vector2(0, -1),
                              Mathf.Infinity, LayerMask.GetMask("tilemap"));
            if (hit.collider.CompareTag("platform"))//检测到平台
            {
                transform.GetComponent<Collider2D>().enabled = false;
                StartCoroutine(EnableCollider());

            }
            Debug.DrawRay(transform.position, new Vector2(0, -1), Color.blue);
        }

    

    }
    IEnumerator EnableCollider()
    {
        yield return new WaitForSeconds(0.15f);
        transform.GetComponent<Collider2D>().enabled = true;

    }
    private void attack() {
        

        state = ani.GetCurrentAnimatorStateInfo(0);
        //判断播放完
        if ((state.IsName("attack1") || state.IsName("attack2") || state.IsName("attack3") || state.IsName("attack4")) && state.normalizedTime >= 1.0f)
        {
            
            ani.SetInteger("attack", 0);

        }

        if (Input.GetKey(KeyCode.J))
        {
    
            if (state.IsName("idle")||  state.IsName("move") && ani.GetInteger("attack")==0 )
            {
            
                ani.SetInteger("attack", 1);
            } else if (state.IsName("attack1")&& ani.GetInteger("attack") == 1 )
            {
                ani.SetInteger("attack", 2);
            }
            else if (state.IsName("attack2") && ani.GetInteger("attack") == 2)
            {
                ani.SetInteger("attack", 3);
            }
            else if (state.IsName("attack3") && ani.GetInteger("attack") == 3)
            {
                ani.SetInteger("attack", 4);
            }
        }
        if (state.normalizedTime >=1.0f) 
        {
            ani.SetFloat("normalizedTime", state.normalizedTime);
        }


        }
}

为了防止平台到地面时按下键取消碰撞盒导致穿过地面,和由于离散检测敌人和角色有时会穿过地面,我们可以在角色共有脚中加入防本卡脱离机制,也是通过射线检测完成的

CharacterPanel脚步更新(如果不管这个bug可以忽略此内容)文章来源地址https://www.toymoban.com/news/detail-444383.html

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
public class CharacterPanel : MonoBehaviour
{
    public bool Iscanjump = false;//是否能跳跃,默认不能
    public float Hpmax = 100;//最大生命
    public float Hp = 100;//生命
    public float Atk = 10;//攻击力
    public float AtkRan = 1;//攻击浮动
    public float Def = 10;//防御力
    public float lookdir;//获取初始Scale.x,用于转向 
    public float dropConst = 15;//下坠常数
    public float speed = 10;//地面移动速度
    public float jumpspeedUp = 20;//上升速度
    public float jumpspeedVertiacal = 0.5f;//空中左右移动速度
    private Rigidbody2D rig;//2D刚体
    private Animator ani;
    private Transform Canvas;//获取角色个人UI面板
    // Start is called before the first frame update
    void Start()
    {
        Canvas = transform.Find("Canvas");
        ani = transform.GetComponent<Animator>();
      
        rig = GetComponent<Rigidbody2D>();//获取刚体
    }

    // Update is called once per frame
    void FixedUpdate()
    {
        lookdir = transform.localScale.x;
        check();
        //跳跃优化手感
        Quickjump();
        //检测卡地面脱离
        OutLockGround();
    }
    //标准化检查
    private void check()
    {
        if (Hp > Hpmax) Hp = Hpmax;//血量不超过上限
        if (Hp <= 0) { Hp = 0;death(); };//血量不超过下限,且死亡
    }
    //受伤,其他脚本调用
    public void hurt(float atk)
    {
       float hurtnum= (20 * atk / (20 + Def)) + Random.Range(-AtkRan, AtkRan);
        //受伤动画 为什么要将触发器中的受伤动画移动在角色面板的hurt函数下?因为受伤不仅有角色攻击受伤,还有陷阱,掉落等伤害,所以直接血量减少时播放受伤动画更加好
        transform.GetComponent<Animator>().SetBool("Ishurt", true);
        StartCoroutine(endHurt());//开启协程结束受伤动画
        //伤害数值显示
        Canvas.GetComponent<CharaCanvas>().ShowHurtText(hurtnum);
        Hp -= hurtnum;

    
    }
    IEnumerator endHurt()
    {
        yield return 0;//此处暂停,下一帧执行
        transform.GetComponent<Animator>().SetBool("Ishurt", false);
    }
    //死亡
    private void death()
    {
        ani.SetBool("Isdeath",true);
    }
    //跳跃
    public void jump()
    {
        if (Iscanjump == true)
        {
            rig.velocity = new Vector2(0, jumpspeedUp);//设置刚体速度,给予向量
        }
    }
    //优化跳跃手感,迅速下落,放入帧频率更新函数里面
    public void Quickjump()
    {
        float a = dropConst * 5 - Mathf.Abs(rig.velocity.y);//通过下坠常数,空中速度快为0时,下坠常数a越大,即越快速 度过这个状态
        rig.velocity -= Vector2.up * a * Time.deltaTime;
    }
    //卡住地面脱离
    public void OutLockGround()
    {
        RaycastHit2D hit = Physics2D.Raycast(transform.position, new Vector2(0, -1),
                                 0.5f, LayerMask.GetMask("tilemap"));
        if (hit.collider.CompareTag("ground"))//检测到地面
        {
            transform.Translate(new Vector3(0,1,0));
        }
        Debug.DrawRay(transform.position, new Vector2(0, -1), Color.blue);

    }









    //以下是敌人的调运行为函数,主角有自己的控制脚本
    //转向
    public void Turndir()
    {
          transform.localScale = new Vector3(-lookdir, transform.localScale.y, transform.localScale.z);//通过改变scale改变方向
    }
    //移动
    public void move()
    {
        if (lookdir == 0) lookdir =0.001f;//预防除零问题弹错
        Vector3 vt = new Vector3(lookdir/Mathf.Abs(lookdir), 0, 0);
        //空中左右移动,为地面jumpcharacterPanel.speedVertiacal倍
        if (Iscanjump == false)
        {
            gameObject.transform.Translate(jumpspeedVertiacal * speed * Time.deltaTime * vt);//通过这个函数来使用vt使得左右移动
        }
        //地面左右移动
        else { gameObject.transform.Translate(speed * Time.deltaTime * vt); }
        ani.SetBool("Ismove", true);

    }
    //等待
    public void idle()
    {
        ani.SetBool("Ismove", false);
    }
}

到了这里,关于13.Unity2D 横版 可上下左右移动的双向平台(双向行走+可移动+单独判定)+随机平台生成的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包赞助服务器费用

相关文章

  • 6.Unity2D 横版 受击反馈+跟随血条+延时/延迟扣血+协程的应用

    6.Unity2D 横版 受击反馈+跟随血条+延时/延迟扣血+协程的应用

    总目录 https://blog.csdn.net/qq_54263076/category_11900070.html?spm=1001.2014.3001.5482  1. 受击反馈 用 Unity 探究 2D 游戏的打击感_技术宅也爱玩游戏的博客-CSDN博客_unity击退 引言这是我毕业设计的一部分emmm……我的毕设和格斗游戏相关,而对于打击感的研究算是其中我比较在意的一环。现在

    2023年04月08日
    浏览(28)
  • 10.Unity2D 横版 简单AI 之 敌人随机移动+自动巡逻+障碍物跳跃+悬崖处转身+射线检测

    10.Unity2D 横版 简单AI 之 敌人随机移动+自动巡逻+障碍物跳跃+悬崖处转身+射线检测

    总目录 9.Unity2D 简单AI 之 敌人跳跃条件优化+自动范围内检测敌人发起攻击(索敌)+对象池优化+主角受伤死亡_ζั͡ ั͡雾 ั͡狼 ั͡✾的博客-CSDN博客 Unity2D 简单AI 之 敌人跳跃条件优化+自动范围内检测敌人攻击+敌人二连击。在敌人预制体下,创建空物体EnemyCanAttack,改成不

    2023年04月20日
    浏览(24)
  • Unity:鼠标【上下左右滑动时】控制相机【左右张望】和【上下抬头】

    Unity:鼠标【上下左右滑动时】控制相机【左右张望】和【上下抬头】

    相机旋转,看着是小事,但是却关系到用户的直观体验。旋转对了母慈子孝,旋转错了则翻江倒海。 鼠标左右移动时,控制相机左右转动 鼠标上下移动时,控制相机抬头低头 你可以在GPT里提问,他的回答也很给力,能转,但是都不符合人体的看东西的特点。 后来还是的自己

    2024年02月10日
    浏览(11)
  • [Unity] Tilemap瓦片左右翻转(上下翻转)

    [Unity] Tilemap瓦片左右翻转(上下翻转)

    Tile(瓦片)左右翻转感觉是很常用的一个功能啊!看了一些教程都没有提及,心想难道要把每张Sprite再做一张对称的、再做成瓦片吗? 图片量x2 、瓦片量x2、不现实!一定有方法! 搜索了了半天没找到方法,结果自己偶然在奇怪的地方不一小心找到了~~ 记录一下! 菜单栏

    2024年01月22日
    浏览(7)
  • Unity 控制摄像机镜头的上下左右移动

            private float FollowPosx,FollowPosy;     private float moveAmount=5;   //控制镜头的移动速度     // Update is called once per frame     void Update()     {         if (Input.mousePosition.y Screen.height * 0.9)//如果鼠标位置在顶部,就向上移动         {             FollowPosy += moveAmount * Time.delta

    2024年02月11日
    浏览(14)
  • Unity2D学习笔记-Tilemap

    Unity2D学习笔记-Tilemap

    tilemap算是接触了几次,但是无论是看视频还是看文章都一知半解,这次把编辑地图的开始步骤搞清楚。 首先要知道tilemap是做什么的。 这里提到的Tilemap其实不止是Tilemap:Tilemap本身是地图编辑器(虽然我更倾向于理解为“场景”,不过编辑地图才是核心)。之前学的印象是,

    2023年04月09日
    浏览(9)
  • Unity2D实现子弹追踪目标

    Unity2D实现子弹追踪目标

    实现子弹追踪目标有很多种方法,首先是一开始就选定了目标的位置,然后按照曲线运动轨迹的方式,持续运动到目标点,不过如果目标移动了,就得将对应的轨迹重新计算一次,另外如果需要设置范围的话更不好做。另一种是锐角追踪,就是在目标进入识别范围后,将子弹

    2024年02月06日
    浏览(11)
  • Unity2D小狐狸教程笔记

    Unity2D小狐狸教程笔记

    下载 https://unity.cn/releases 默认显示方式 window - layout - default SampleScene : Project - 文件目录 Scene -游戏画面 asset store - 素材商店 在asset store下载素材 sunnyland shift + sapace 放大窗口 1.背景导入 每个格子16像素: Pixels Per Unit 16px 2.绘制瓷砖式地图 新建瓦片图层:左上角/右键 2D object

    2024年01月24日
    浏览(15)
  • Unity2d游戏项目--小狐狸

    Unity2d游戏项目--小狐狸

    (一) 在文件夹中找到back图片,并在检查器面板中将back图片的每单位像素数设置为16。 (文件所在地) (面板设置) (二) 将图片拖入到场景中 (一) 生成矩形的瓦片地图 (二) 打开平铺调色板 (三) 新建并命名为map,在原目录新建一个文件夹,用于存放你在这个瓦

    2024年02月03日
    浏览(12)
  • 【Unity2D】角色动画的切换

    【Unity2D】角色动画的切换

    第一种方法是设置一个中间状态,从中间状态向其余各种状态切换,且各状态向其他状态需要设置参数 实现动作转移时右键点击Make Transition即可  实现动画转移需要设置条件 点击一种动画到另一种动画的线 ,然后点击加号添加Condition 比如机器人从向左走切换到向右走的条件

    2024年02月15日
    浏览(9)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包