HuldaGnodim 发表于 2021-8-12 09:41

unity教程之制作连连看小教程

哈哈,周末了总算有时间完善一下做的连连看了,顺便写个小教程分享给大家,哇哈哈~
文章出处【狗刨学习网】
开始正题:


连连看的规则大家应该都知道,选中的两个图片相同,并且不能多于两个拐点能连在一块,这两个图片就可以消掉;
连通的类型:
1 直线型;
2 一个拐点;
3 两个拐点;
下面开始介绍这三种连通类型

直线型:
直线型分两种,一种是横向,一种是竖向;
首先是横向连接

http://www.gopedu.com/files/user/2015/01-19/09081605395f612842.jpg?4.5.1


A,B两点的x坐标相同,图片类型相同,从A点开始到B点检测,如果AB两点之间没有其他图片就销毁AB两个图片,竖向的和横向的类似
一个拐点:

http://www.gopedu.com/files/user/2015/01-19/0909051987b3633879.jpg?4.5.1



AB两点的x坐标和y坐标都不相同的时候开始检测一个拐点是否可以连接,通过AB两点计算出CD两点,然后分别检测AC,BC,AD,BD是否可以通过直线型连接到一起,显然AB两点可以通过A>C,C>B连接到一起,

两个拐点:

http://www.gopedu.com/files/user/2015/01-19/090946ad9865266879.jpg?4.5.1



AB两点,从A开始,横向和竖向把所有和A能直线连接的点找出来,用这些点和B点做一个拐点的检测,显然A点下边的那个点可以通过绿色的那个点可以通过一个拐点的方式和B点连接起来,

哈哈,是不是很简单啊,上边的就是连连看的核心内容

接下来详细介绍一下各个脚本的作用,(哇哈哈,以注释的形式给大家介绍吧)
GameManager.cs游戏的核心代码,产生图片,判断是否可以销毁等

[*] using UnityEngine;
[*] using System.Collections;
[*] using System.Collections.Generic;
[*]
[*] public class GameManager : MonoBehaviour
[*] {
[*]   public DrawLine drawLine;//画线
[*]   public GameObject tilePrefab;//tile的预制
[*]   public List<Tile> tiles;//开始实例化的时候存放tile
[*]   public List<Tile> _tiles;//存放随机摆放的tile
[*]   public List<Tile> tilesEdge;//为了边界处可以有拐点,把棋盘四周的tile放在这里,这里的tile看不到
[*]   public int x, y;//棋牌的大小,两个数必须是偶数
[*]   private Tile tileA;
[*]   private Tile tileB;
[*]   private bool destroy;
[*]   private Vector3 mousePos;
[*]   private enum stepType//控制游戏的状态
[*]   {
[*]         one,
[*]         two,
[*]         three
[*]   }
[*]   private stepType _stepType;
[*]
[*]   void Start ()
[*]   {
[*]         this.gameObject.transform.position = Vector3.zero;
[*]         Spawn ();
[*]         _stepType = stepType.one;
[*]   }
[*]
[*]   private void Spawn ()//实例化tile
[*]   {
[*]         float num = (x * y - (2 * x + 2 * y - 4)) * 0.5f;
[*]         for (int i = 0; i <num; i ++) {
[*]             int idTex = Random.Range (20, 45);
[*]             GameObject obj = Instantiate (tilePrefab) as GameObject;
[*]             GameObject obj2 = Instantiate (tilePrefab) as GameObject;
[*]             Tile tile = obj.GetComponent<Tile> ();
[*]             Tile tile2 = obj2.GetComponent<Tile> ();
[*]             tile.Init (idTex);
[*]             tile2.Init (idTex);
[*]             tiles.Add (tile);
[*]             tiles.Add (tile2);
[*]         }
[*]         for (int i = 0; i<((2*x+2*y) -4); i++) {//实例化边缘的tile
[*]             GameObject obj = Instantiate (tilePrefab) as GameObject;
[*]             obj.name = "edage";
[*]             Tile tile = obj.GetComponent<Tile> ();
[*]             tilesEdge.Add (tile);
[*]         }
[*]         CreatTile ();
[*]         for (int i = 0; i < _tiles.Count; i++) {
[*]             _tiles .transform.name = i.ToString ();
[*]             _tiles .id = i;
[*]         }
[*]         this.transform.position = new Vector3 (-(x / 2.0f - 0.5f), -(y / 2.0f - 0.5f), 0);
[*]   }
[*]
[*]   private void CreatTile ()//随机摆放tile,如果是边缘的就放在边缘位置
[*]   {
[*]         int idTex = 0;
[*]         float _y = 0.0f;
[*]         for (int i = 0; i < y; i ++) {
[*]             float _x = 0.0f;
[*]             for (int j = 0; j < x; j ++) {
[*]               if (i == 0 || j == 0 || i == y - 1 || j == x - 1) {
[*]                     tilesEdge .transform.position = new Vector3 (_x, _y, 0);
[*]                     tilesEdge .pos = new Vector2 (_x, _y);
[*]                     tilesEdge .transform.rotation = new Quaternion (0, 0, 180, 0);
[*]                     tilesEdge .transform.parent = this.gameObject.transform;
[*]                     _tiles.Add (tilesEdge );
[*]                     tilesEdge .transform.localScale = Vector3.zero;
[*]                     tilesEdge .type = false;
[*]                     tilesEdge.RemoveAt (0);
[*]               } else {
[*]                     int id = Mathf.FloorToInt (Random.Range (0, tiles.Count));
[*]                     tiles .transform.position = new Vector3 (_x, _y, 0);
[*]                     tiles .pos = new Vector2 (_x, _y);
[*]                     tiles .transform.rotation = new Quaternion (0, 0, 180, 0);
[*]                     tiles .transform.parent = this.gameObject.transform;
[*]                     _tiles.Add (tiles );
[*]                     tiles.RemoveAt (id);
[*]               }
[*]               _x += 1;
[*]             }
[*]             _y += 1;
[*]         }
[*]   }
[*]
[*]   private void SelectTile ()//开始选择图片,通过射线方式选中,如果tileA和tileB不相同,则tileA等于tileB开始下一个检测
[*]   {
[*]         Ray ray = Camera.mainCamera.ScreenPointToRay (mousePos);
[*]         RaycastHit hit;
[*]         int mask = 1 << 8;
[*]         if (Physics.Raycast (ray, out hit, mask)) {
[*]             if (tileA == null) {
[*]               tileA = hit.transform.GetComponent<Tile> ();
[*]               tileA.SetTileTexture (1);
[*] //                print ("tileA = hit.transform.GetComponent<Tile> ();" + tileA.transform.name);
[*]             } else {
[*]               tileB = hit.transform.GetComponent<Tile> ();
[*]               tileB.SetTileTexture (1);
[*] //                print ("tileB = hit.transform.GetComponent<Tile> ();" + tileB.transform.name);
[*]               Compare (tileA, tileB);
[*]               if (tileA == null ;; tileB == null) {
[*]
[*] //                  print ("a and b is null");
[*]               }
[*]             }
[*] //            hit.transform.GetComponent
[*]         }
[*]   }
[*]
[*]   private void Compare (Tile tile1, Tile tile2)//比较两个点是否可以连接到一起
[*]   {
[*]         // same card
[*]         _stepType = stepType.one;
[*]         drawLine.waypoints.Add (tile1.transform); //第一个选择的tile是画线的起始位置,
[*]         drawLine.transform.position = tile1.transform.position;
[*]         destroy = false;
[*]         print ("compare");
[*]         if (tile1.pos.x == tile2.pos.x ;; tile1.pos.y == tile2.pos.y) {如果选中的是同一个图片返回
[*]             tileA.SetTileTexture (0);
[*] //            tileB.SetTileTexture (0);
[*]             tileA = tileB;
[*]             tileB = null;
[*] //            tileA.SetTileTexture (1);
[*]             return;
[*]         } else if (tile1.pos.x == tile2.pos.x ;; tile1.pos.y != tile2.pos.y) {//如果两点的x相等,竖向检测
[*]             print ("check y");
[*]             destroy = CheckY (tile1, tile2);
[*]             if (destroy)
[*]               drawLine.waypoints.Add (tile2.transform);
[*]         } else if (tile1.pos.x != tile2.pos.x ;; tile1.pos.y == tile2.pos.y) {//如果两点的y相等,横向检测
[*]             print ("check x");
[*]             destroy = CheckX (tile1, tile2);
[*]             if (destroy)
[*]               drawLine.waypoints.Add (tile2.transform);
[*]         }
[*]         if (!destroy) {//不符合直线连接方式的开始进行一个拐点的检测
[*]             _stepType = stepType.two;
[*]             destroy = CheckTwoStep (tile1, tile2);
[*] //            print ("destroy = CheckTwoStep (tile1, tile1);:" + destroy);
[*]             print ("check two step");
[*]             if (!destroy) {//不符合直线和一个拐点检测的开始进行两个拐点的检测
[*]               _stepType = stepType.three;
[*]               destroy = CheckThreeStep (tile1, tile2);
[*]               print ("check three:" + destroy);
[*]               print ("tile1.idTex:" + tile1.idTex + "tile1.idTex:" + tile1.idTex);
[*]             }
[*]         }
[*]         if (destroy) {//如果符合销毁条件销毁图片,并开始画线
[*]             tile1.transform.localScale = Vector3.zero;
[*]             tile2.transform.localScale = Vector3.zero;
[*]             tile1.type = false;
[*]             tile2.type = false;

页: [1]
查看完整版本: unity教程之制作连连看小教程