效果:(如下图所示)
操作方法:
搭建小地图UI
截取图片
创建地面
挂载如下代码:
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
[RequireComponent(typeof(MeshFilter), typeof(MeshCollider), typeof(MeshRenderer))]
public class Map : MonoBehaviour
{
//宽高
[SerializeField] private int w, h;
//颜色1和颜色2,用于设置渐变
[SerializeField] private Color color1, color2;
//存储水面上面的顶点的集合
public List<Vector3> verticesPositions;
//纹理
private Texture2D _texture;
//顶点辅助器
private VertexHelper vh;
//mesh网格
private Mesh _mesh;
// Start is called before the first frame update
void Start()
{
verticesPositions= new List<Vector3>();
_texture = new(w + 1, h + 1);
vh = new();
_mesh = new();
//循环宽高
for (int i = 0; i <= w; i++)
{
for (int j = 0; j <= h; j++)
{
//柏林噪声获取高度
float y = Mathf.PerlinNoise(i * 0.2f, j * 0.2f);
//uv坐标
float uvx = (float)i / w;
float uvy = (float)j / h;
//添加顶点
vh.AddVert(new(i, y * 5, j), Color.white, new(uvx, uvy));
//设置纹理颜色
_texture.SetPixel(i, j, Color.Lerp(color1, color2, y));
//绘制三角
if (i < w && j < h && y * 5 > 1.3f)
{
vh.AddTriangle(j + i * (h + 1), j + 1 + i * (h + 1), j + 1 + 1 + h + i * (h + 1));
vh.AddTriangle(j + i * (h + 1), j + 1 + 1 + h + i * (h + 1), j + 1 + h + i * (h + 1));
}
}
}
//顶点辅助器给mesh网格赋值
vh.FillMesh(_mesh);
//mesh赋值给网格过滤器
GetComponent<MeshFilter>().mesh = _mesh;
//新建材质球
Material material = new(Shader.Find("Standard"))
{
mainTexture = _texture
};
//网格渲染器赋值材质球
GetComponent<MeshRenderer>().material = material;
//网格碰撞器赋值mesh网格
GetComponent<MeshCollider>().sharedMesh = _mesh;
//加载水面
Instantiate(Resources.Load<GameObject>("Water"));
//设置纹理打包模式
_texture.wrapMode = TextureWrapMode.Clamp;
//应用纹理更改
_texture.Apply();
}
// Update is called once per frame
void Update()
{
}
}
小地图挂载
using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.AI;
using UnityEngine.EventSystems;
using UnityEngine.UI;
//Image有Mask,两个Image子类,一个挂脚本,一个作为中心点
public class SmallMap : MonoBehaviour, IPointerClickHandler
{
//创建地图脚本的引用,用来获取其中的装饰物集合
public NavMeshManager navMesh;
//玩家
public Transform player;
//地图的rectTransform
public RectTransform _rectTransform, Startpoint;
//玩家的对象
public NavMeshAgent nav;
//控制缩放的Slider
public Slider Slider;
//存储路径点的图片的集合
public List<GameObject> imageList = new List<GameObject>();
private void Awake()
{
Slider.value = 1;
_rectTransform = GetComponent<RectTransform>();
}
private void Update()
{
//实时获取大地图的比例(100是柏林噪声地图的宽高)
float x = nav.transform.position.x / 100;
float y = nav.transform.position.z / 100;
//中心点跟随移动
_rectTransform.pivot = new Vector2(x, y);
//滑动条控制缩放
//_rectTransform.localScale = Vector3.one * Slider.value;
//滚轮控制缩放
if (Input.GetAxis("Mouse ScrollWheel") != 0)
{
_rectTransform.localScale += Vector3.one * Input.GetAxis("Mouse ScrollWheel")*2;
//设置最小缩放限制
if (_rectTransform.localScale.x <= 0.75f)
{
_rectTransform.localScale = new Vector3(0.75f, 0.75f, 0.75f);
}
}
}
//创建路径点Image
public void CreateImage()
{
//生成地图装饰物
for (int i = 0; i < navMesh.spawnedCubes.Count; i++)
{
GameObject bodyimg = GameObject.Instantiate(Resources.Load<GameObject>("bodyimg"), transform);
if (navMesh.spawnedCubes[i].tag == "Cube")
{
bodyimg.GetComponent<Image>().color = Color.yellow;
}
//都加起始位置,就是小地图 的左下角的位置(因为小地图一直在移动,所以用这个空对象作为起点)
float a = navMesh.spawnedCubes[i].transform.position.x / 100 * _rectTransform.sizeDelta.x + Startpoint.localPosition.x;
float b = navMesh.spawnedCubes[i].transform.position.z / 100 * _rectTransform.sizeDelta.y + Startpoint.localPosition.y;
bodyimg.transform.localPosition = new Vector2(a, b);
imageList.Add(bodyimg);
}
}
//删除路径点Image
public void DeletImage()
{
for (int i = 0; i < imageList.Count; i++)
{
Destroy(imageList[i].gameObject);
}
imageList.Clear();
}
public void OnPointerClick(PointerEventData eventData)
{
//mapImage 的标签
if (eventData.pointerPressRaycast.gameObject.tag == "Map")
{
var isClick =
RectTransformUtility.ScreenPointToLocalPointInRectangle(_rectTransform, eventData.position, null,
out var point);
float x = point.x / _rectTransform.sizeDelta.x * 100;
float y = point.y / _rectTransform.sizeDelta.y * 100;
var endpos = player.position + new Vector3(x, 0, y);
nav.SetDestination(endpos);
//点击小地图控制人物移动
navMesh.isGeneratingCubes = true;
}
}
}
角色挂载
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.AI;
public class NavMeshManager : MonoBehaviour
{
public SmallMap map;
public NavMeshAgent agent; // 角色的 NavMeshAgent
public GameObject cubePrefab; // 用于生成的 Cube 预制件
public float cubeSpacing = 2f; // Cube 之间的距离
public List<GameObject> spawnedCubes = new List<GameObject>();
public bool isGeneratingCubes = false;
void Update()
{
//有这个可以点击地图移动,让小地图动
//if (Input.GetMouseButtonDown(0))
//{
// Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition);
// if (Physics.Raycast(ray, out RaycastHit hit))
// {
// // 设置导航目标点
// agent.SetDestination(hit.point);
// isGeneratingCubes = true;
// }
//}
if (isGeneratingCubes && agent.hasPath && agent.remainingDistance > agent.stoppingDistance)
{
// 清除之前生成的所有 Cube
ClearCubes();
// 生成路径上的 Cube
GenerateCubesAlongPath(agent.path);
isGeneratingCubes = false;
}
}
private void GenerateCubesAlongPath(NavMeshPath path)
{
if (path.corners.Length < 2)
{
return;
}
Vector3 previousCorner = path.corners[0];
float distanceSinceLastCube = 0f;
for (int i = 1; i < path.corners.Length; i++)
{
Vector3 corner = path.corners[i];
float segmentLength = Vector3.Distance(previousCorner, corner);
while (distanceSinceLastCube < segmentLength)
{
Vector3 direction = (corner - previousCorner).normalized;
Vector3 cubePosition = previousCorner + direction * distanceSinceLastCube;
GameObject cube = Instantiate(cubePrefab, cubePosition, Quaternion.identity);
spawnedCubes.Add(cube);
distanceSinceLastCube += cubeSpacing;
}
distanceSinceLastCube -= segmentLength;
previousCorner = corner;
}
}
//清除生成的代表路径点的Cube
private void ClearCubes()
{
foreach (var cube in spawnedCubes)
{
Destroy(cube);
}
spawnedCubes.Clear();
}
private void OnTriggerEnter(Collider other)
{
if (other.gameObject.CompareTag("Cube"))
{
//碰撞就刷新
map.DeletImage();
Destroy(other.gameObject);
spawnedCubes.Remove(other.gameObject);
map.CreateImage();
}
}
}
预制体预览
水
路径点Image
路径点预制体
角色预制体
标签:void,地图,rectTransform,点击,mesh,new,using,导航,public From: https://blog.csdn.net/djrjnfjdjejb/article/details/140038103