当前位置:   article > 正文

入门级案例学习 - 见缝插针_见缝插针c#

见缝插针c#

入门级案例学习 - 见缝插针

创建工程和场景

导入素材,没啥好说的

开发旋转的小球和分数显示

创建旋转的小球

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-oLPnaxZo-1680961538151)(C:\Users\CoreDawg\AppData\Roaming\Typora\typora-user-images\image-20230408191257026.png)]‘

简单设置一下transform和颜色大小啥的,没啥技术含量

加一个GUI的text显示分数

EventSystem先删除掉

reset居中,字体左右上下居中

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-oA51wFSZ-1680961538152)(C:\Users\CoreDawg\AppData\Roaming\Typora\typora-user-images\image-20230408191842766.png)]

canvas的渲染模式改为World Space

因为这个模式方便缩小到游戏开发环境一样的大小

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-qJC1T6Ie-1680961538153)(C:\Users\CoreDawg\AppData\Roaming\Typora\typora-user-images\image-20230408192140702.png)]

借助scale进行整体的缩小[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-jDZB1Qxu-1680961538153)(C:\Users\CoreDawg\AppData\Roaming\Typora\typora-user-images\image-20230408193558999.png)]

事件摄像机设置成MainCamera

控制小球旋转

直接利用transform的Rotate属性控制旋转
    //声明一个旋转速度
    public float speed=90;//度数



    void Update()
    {
        //通过Rotate方法控制旋转
        //只围绕Z轴旋转,xy都为0
        transform.Rotate(new Vector3(0, 0,speed * Time.deltaTime));

    }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-iXdFt9QW-1680961538153)(C:\Users\CoreDawg\AppData\Roaming\Typora\typora-user-images\image-20230408194914975.png)]

在scene模式下能观察到旋转效果

在speed前面加上一个 - 就能改变旋转的方向

开发针的Prefab预制体

给针头添加碰撞器

针的发射

思路:实例化的屏幕外边,运动进来

创建两个空物体控制位置

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Hsq4l8NH-1680961538154)(C:\Users\CoreDawg\AppData\Roaming\Typora\typora-user-images\image-20230408195739243.png)]

这样能方便定位

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-svB3CqGY-1680961538154)(C:\Users\CoreDawg\AppData\Roaming\Typora\typora-user-images\image-20230408195846597.png)]

吧针放在StartPoint下面,把针设置成000

创建空物体GameManager 用于管理针的实例化

创建对应脚本

通过Find方法拿到点的transform组件

注意字符串要和需要的组件写的一致

    //先拿到两个点
    private Transform startPoint;
    private Transform spawnPoint;

    void Start()
    {
        //通过GameObject拿到
        startPoint = GameObject.Find("StartPoint").transform;
        spawnPoint = GameObject.Find("SpawnPoint").transform;
       

    }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
实例化针

先拿到针的预制体

 public GameObject pinPrefab;//注意public属性需要拖拽赋值
  • 1

生成针的方法

    void Start()
    {
        //通过GameObject拿到
        startPoint = GameObject.Find("StartPoint").transform;
        spawnPoint = GameObject.Find("SpawnPoint").transform;
        //调用实例化方法
        SpawnPin();
    }

    //实例化 针
    void SpawnPin()
    {
        GameObject.Instantiate(pinPrefab, spawnPoint.position, pinPrefab.transform.rotation);
    }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14

控制针移动到就位位置

Movetowards方法

当前位置,目标位置,距离

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

public class Pin : MonoBehaviour
{
    //真运动的速度
    public float speed=5;
    //因为针有两段运动,所以先声明两个布尔值
    private bool isFly = false;
    private bool isReach = false;
    //拿到位置
    private Transform startPoint;

    void Start()
    {
        startPoint = GameObject.Find("StartPoint").transform;
    }

    void Update()
    {
        if (isFly == false)//还没开始向圆球移动
        {
            if (isReach == false)//没到达开始点
            {
                //把移动得到的新的位置给到针
                transform.position= Vector3.MoveTowards(transform.position, startPoint.position, speed * Time.deltaTime);
            }

        }
    }


}

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
判断是否达到目标位置
                if (Vector3.Distance(transform.position, startPoint.position) < 0.05f)
                {
                    isReach =true;//等于true之后就不会再重复执行这段代码了,节约性能
                }
            }
  • 1
  • 2
  • 3
  • 4
  • 5

控制针的插入

鼠标输入控制发射
    //Update方法检测鼠标输入
    void Update()
    {
        if (Input.GetMouseButtonDown(0))
        {

        }
    }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
给针加一个飞行方法

首先对针的实例化进行补充

    //持有一个当前针的引用
    private Pin currentPin;
  • 1
  • 2
    //实例化 针
    void SpawnPin()
    {
        currentPin = GameObject.Instantiate(pinPrefab, spawnPoint.position, pinPrefab.transform.rotation).GetComponent<Pin>();
    }
  • 1
  • 2
  • 3
  • 4
  • 5

完善鼠标方法调用

    //Update方法检测鼠标输入
    void Update()
    {
        if (Input.GetMouseButtonDown(0))
        {
            currentPin.StartFly();
        }
    }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8

确定飞行方法的基础条件

    public void StartFly()
    {
        isFly = true;
        isReach = true;
    }
  • 1
  • 2
  • 3
  • 4
  • 5

用Find方法拿到圆的位置

    private Transform circle;

    void Start()
    {
        circle = GameObject.Find("Circle").transform;
    }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6

运动

        else
        {
            transform.position = Vector3.MoveTowards(transform.position, circle.position, speed * Time.deltaTime);
            //判断是否到达目标位置
            //注意不能到达圆圈的中心,而是到达圆圈的边缘就好


        }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8

控制针达到的位置和针的连环发射

控制距离

计算针头和圆圈的差距

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-QQJbQrqn-1680961538154)(C:\Users\CoreDawg\AppData\Roaming\Typora\typora-user-images\image-20230408205045583.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-6NKl5Sc9-1680961538155)(C:\Users\CoreDawg\AppData\Roaming\Typora\typora-user-images\image-20230408205054684.png)]

1.7-0.18=1.52

    //声明目标位置
    private Vector3 targetCirclePos;
  • 1
  • 2
        targetCirclePos = circle.position;
        targetCirclePos.y -= 1.52f;
  • 1
  • 2

修改移动

  else
        {
            transform.position = Vector3.MoveTowards(transform.position, targetCirclePos, speed * Time.deltaTime);
            //判断是否到达目标位置
            //注意不能到达圆圈的中心,而是到达圆圈的边缘就好


        }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
让针与小球一起运动
            if (Vector3.Distance(transform.position, targetCirclePos) < 0.05f)
            {
                transform.position = targetCirclePos;//直接把目标位置设置给针
                //设置父物体为小球,就会一起运动了
                transform.parent = circle;
                isFly = false;//结束执行
            }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7

实例化下一个针

    //Update方法检测鼠标输入
    void Update()
    {
        if (Input.GetMouseButtonDown(0))
        {
            currentPin.StartFly();
            SpawnPin();//重新实例化一个新的针
        }
    }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9

针头的碰撞和游戏结束的处理

通过针头的碰撞判定游戏失败

先给针头加刚体组件

然后在碰撞里面勾选trigger

重力设置为0

给针头上tag

游戏失败的方法:

    //游戏失败的方法
    public void GameOver()
    {

    }
  • 1
  • 2
  • 3
  • 4
  • 5

在针头的判断里调用失败方法

    //触发器
    private void OnTriggerEnter2D(Collider2D collision)
    {
        //先判断另一个碰撞体是不是也是针头
        if (collision.tag == "PinHead")
        {
            //先查找GameManager
            GameObject.Find("GameManager").GetComponent<GameManager>().GameOver();
        }
    }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10

但是这个会多次触发,怎么控制只处理一次呢,定义一个布尔变量

    private bool isGameOver=false;//是否游戏失败
  • 1
    //游戏失败的方法
    public void GameOver()
    {
        if (isGameOver) return;
        //禁用掉小球的旋转
        GameObject.Find("Circle").GetComponent<RotateSelf>().enabled = false;



        isGameOver = true;
    }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11

补充游戏失败的方法

控制分数的显示

定义一个变量存储当前分数

   private int score = 0;
  • 1

持有一个Text组件

 //持有一个Text组件
   public Text scoreText;
  • 1
  • 2
每次按下鼠标分数增加
    void Update()
    {
        if (isGameOver) return;
        if (Input.GetMouseButtonDown(0))
        {
            score++;
            scoreText.text = score.ToString();
            currentPin.StartFly();
            SpawnPin();//重新实例化一个新的针
        }
    }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
游戏结束的动画思路

颜色梗概 - 通过camera的背景颜色渐变

失败之后修改size - 整体画面变大

游戏重启

游戏结束动画的显示(课程结束)

通过camera组件实现动画控制
    //拿到camera组件
    private Camera maincamera;
  • 1
  • 2

赋值

    void Start()
    {
        maincamera = Camera.main;
    }
  • 1
  • 2
  • 3
  • 4
协程控制动画

定义动画速度

  //定义一个动画速度方法
    public float speed = 3;
  • 1
  • 2

协程

    IEnumerator GameOverAnimation()
    {
        while (true)
        {
            //颜色
            maincamera.backgroundColor = Color.Lerp(maincamera.backgroundColor, Color.red, speed * Time.deltaTime);
            //尺寸
            maincamera.orthographicSize = Mathf.Lerp(maincamera.orthographicSize, 4, speed * Time.deltaTime);
            //判断到达目标值循环结束
            if (Mathf.Abs(maincamera.orthographicSize - 4) < 0.01f)
            {
                break;
            }
            yield return 0;//每次循环暂停一帧
        }
        //让动画暂停一下
        yield return new WaitForSeconds(1);
    }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18

Lerp方法:插值运算,由当前渐变到目标

重新加载场景
SceneManager.LoadScene(SceneManager.GetActiveScene().buildIndex);
  • 1
    //游戏失败的方法
    public void GameOver()
    {
        if (isGameOver) return;
        //禁用掉小球的旋转
        GameObject.Find("Circle").GetComponent<RotateSelf>().enabled = false;

        StartCoroutine(GameOverAnimation());

        isGameOver = true;
    }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11

调用动画

所有脚步

针头
using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class PinHead : MonoBehaviour
{
    //触发器
    private void OnTriggerEnter2D(Collider2D collision)
    {
        //先判断另一个碰撞体是不是也是针头
        if (collision.tag == "PinHead")
        {
            //先查找GameManager
            GameObject.Find("GameManager").GetComponent<GameManager>().GameOver();
        }
    }


}

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class Pin : MonoBehaviour
{
    //真运动的速度
    public float speed=5;
    //因为针有两段运动,所以先声明两个布尔值
    private bool isFly = false;
    private bool isReach = false;
    //拿到点位置
    private Transform startPoint;
    //拿到圆的位置
    public Transform circle;
    //声明目标位置
    private Vector3 targetCirclePos;

    void Start()
    {
        startPoint = GameObject.Find("StartPoint").transform;
        //通过标签查找circle
        //circle = GameObject.FindGameObjectsWithTag("Circle").transform;
        circle = GameObject.Find("Circle").transform;
        targetCirclePos = circle.position;
        targetCirclePos.y -= 1.52f;
    }

    void Update()
    {
        if (isFly == false)//还没开始向圆球移动
        {
            if (isReach == false)//没到达开始点
            {
                //把移动得到的新的位置给到针
                transform.position= Vector3.MoveTowards(transform.position, startPoint.position, speed * Time.deltaTime);
                if (Vector3.Distance(transform.position, startPoint.position) < 0.05f)
                {
                    isReach =true;//等于true之后就不会再重复执行这段代码了,节约性能
                }
            }

        }
        else
        {
            transform.position = Vector3.MoveTowards(transform.position, targetCirclePos, speed * Time.deltaTime);
            //判断是否到达目标位置
            //注意不能到达圆圈的中心,而是到达圆圈的边缘就好
            if (Vector3.Distance(transform.position, targetCirclePos) < 0.05f)
            {
                transform.position = targetCirclePos;//直接把目标位置设置给针
                //设置父物体为小球,就会一起运动了
                transform.parent = circle;
                isFly = false;//结束执行
            }

        }
    }


    public void StartFly()
    {
        isFly = true;
        isReach = true;
    }

}

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
管理器
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
using UnityEngine.SceneManagement;

public class GameManager : MonoBehaviour
{
    //先拿到两个点
    private Transform startPoint;
    private Transform spawnPoint;
    //持有一个当前针的引用
    private Pin currentPin;

    public GameObject pinPrefab;//注意public属性需要拖拽赋值

    private bool isGameOver = false;//是否游戏失败

    private int score = 0;
    //持有一个Text组件
    public Text scoreText;
    //拿到camera组件
    private Camera maincamera;
    //定义一个动画速度方法
    public float speed = 3;

    void Start()
    {
        //通过GameObject拿到
        startPoint = GameObject.Find("StartPoint").transform;
        spawnPoint = GameObject.Find("SpawnPoint").transform;
        maincamera = Camera.main;
        //调用实例化方法
        SpawnPin();
    }

    //实例化 针
    void SpawnPin()
    {
        currentPin = GameObject.Instantiate(pinPrefab, spawnPoint.position, pinPrefab.transform.rotation).GetComponent<Pin>();
    }

    //游戏失败的方法
    public void GameOver()
    {
        if (isGameOver) return;
        //禁用掉小球的旋转
        GameObject.Find("Circle").GetComponent<RotateSelf>().enabled = false;

        StartCoroutine(GameOverAnimation());

        isGameOver = true;
    }

    //Update方法检测鼠标输入
    void Update()
    {
        if (isGameOver) return;
        if (Input.GetMouseButtonDown(0))
        {
            score++;
            scoreText.text = score.ToString();
            currentPin.StartFly();
            SpawnPin();//重新实例化一个新的针
        }
    }
    IEnumerator GameOverAnimation()
    {
        while (true)
        {
            //颜色
            maincamera.backgroundColor = Color.Lerp(maincamera.backgroundColor, Color.red, speed * Time.deltaTime);
            //尺寸
            maincamera.orthographicSize = Mathf.Lerp(maincamera.orthographicSize, 4, speed * Time.deltaTime);
            //判断到达目标值循环结束
            if (Mathf.Abs(maincamera.orthographicSize - 4) < 0.01f)
            {
                break;
            }
            yield return 0;//每次循环暂停一帧
        }
        //让动画暂停一下
        yield return new WaitForSeconds(0.3f);
        SceneManager.LoadScene(SceneManager.GetActiveScene().buildIndex);
    }
}

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
旋转
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class RotateSelf : MonoBehaviour
{
    //声明一个旋转速度
    public float speed=90;//度数



    void Update()
    {
        //通过Rotate方法控制旋转
        //只围绕Z轴旋转,xy都为0
        transform.Rotate(new Vector3(0, 0,speed * Time.deltaTime));

    }
}

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20

判断到达目标值循环结束
if (Mathf.Abs(maincamera.orthographicSize - 4) < 0.01f)
{
break;
}
yield return 0;//每次循环暂停一帧
}
//让动画暂停一下
yield return new WaitForSeconds(0.3f);
SceneManager.LoadScene(SceneManager.GetActiveScene().buildIndex);
}
}


#### 旋转

~~~C#
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class RotateSelf : MonoBehaviour
{
    //声明一个旋转速度
    public float speed=90;//度数



    void Update()
    {
        //通过Rotate方法控制旋转
        //只围绕Z轴旋转,xy都为0
        transform.Rotate(new Vector3(0, 0,speed * Time.deltaTime));

    }
}

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/article/detail/48078
推荐阅读
相关标签
  

闽ICP备14008679号