Optimization 如何使大型2d tilemap更易于在Unity中加载

Optimization 如何使大型2d tilemap更易于在Unity中加载,optimization,2d,render,game-engine,unity5,Optimization,2d,Render,Game Engine,Unity5,我正在Unity游戏引擎中创建一个小游戏,游戏的地图是从2d tilemap生成的。tilemap包含如此多的瓷砖,但是,对于像手机这样的设备来说,很难将它们全部渲染出来,因此帧速率会下降。地图是完全静态的,因为游戏中唯一移动的东西是一个主角精灵和跟随它的相机。贴图本身没有移动的对象,它非常简单,必须有一种方法只渲染它所需的部分,或者只渲染一次贴图。我在研究这个主题时发现,也许一个好方法是使用Unity mesh类将tilemap转换为网格。我不知道如何使用2d tilemap实现这一点,我也不

我正在Unity游戏引擎中创建一个小游戏,游戏的地图是从2d tilemap生成的。tilemap包含如此多的瓷砖,但是,对于像手机这样的设备来说,很难将它们全部渲染出来,因此帧速率会下降。地图是完全静态的,因为游戏中唯一移动的东西是一个主角精灵和跟随它的相机。贴图本身没有移动的对象,它非常简单,必须有一种方法只渲染它所需的部分,或者只渲染一次贴图。我在研究这个主题时发现,也许一个好方法是使用Unity mesh类将tilemap转换为网格。我不知道如何使用2d tilemap实现这一点,我也不知道它对渲染时间有何好处,但如果有人能为我指出渲染大型2d tilemap的正确方向,那将是非常棒的。谢谢

瓷砖系统: 为了使平铺贴图正常工作,我将每个单独的平铺作为预设放置在我的预设文件夹中,并更改了2d长方体碰撞器和缩放大小的属性。我将瓷砖的每个预制体属性化为RGB比例上的特定颜色,然后导入一个png文件,该文件具有我想要的预制体的相应颜色,如下所示:

然后,我编写了一个脚本,将每个预置放置在其相关颜色所在的位置。一块瓷砖的外观如下所示:

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

public class Map : MonoBehaviour {

    private int levelWidth;
    private int levelHeight;

    public Transform block13;

    private Color[] tileColors;

    public Color block13Color;

    public Texture2D levelTexture;

    public PlayerMobility playerMobility;

    // Use this for initialization
    void Start () {
        levelWidth = levelTexture.width;
        levelHeight = levelTexture.height;
        loadLevel ();
    }

    // Update is called once per frame
    void Update () {

    }

    void loadLevel(){
        tileColors = new Color[levelWidth * levelHeight];
        tileColors = levelTexture.GetPixels ();

        for (int y = 0; y < levelHeight; y++) {
            for (int x = 0; x < levelWidth; x++) {
//              if (tileColors [x + y * levelWidth] == block13Color) {
//                  Instantiate(block13, new Vector3(x, y), Quaternion.identity);
//              }
//              
            }
        }
    }
}
使用系统集合;
使用System.Collections.Generic;
使用UnityEngine;
公共类地图:单一行为{
私有内部水平宽度;
私人内部水平高度;
公共交通13号区块;
私人颜色[]瓷砖颜色;
公共色块13色;
公共纹理2d层次纹理;
公共玩家移动性玩家移动性;
//用于初始化
无效开始(){
levelWidth=levelTexture.width;
levelHeight=levelTexture.height;
加载级别();
}
//每帧调用一次更新
无效更新(){
}
void loadLevel(){
tileColors=新颜色[levelWidth*levelHeight];
tileColors=levelTexture.GetPixels();
对于(int y=0;y
当与所有代码一起使用时,这会产生一个类似于此的映射(为了节省空间,我取出了其他预置的所有代码)


您可以实例化相机范围内的磁贴,并销毁不在相机范围内的磁贴。有几种方法可以做到这一点。但首先要确保消耗资源的实际上是大量的瓷砖,而不是其他东西

一种方法是为每个磁贴创建一个空的父游戏对象(右键单击“层次”>创建空)

然后将脚本附加到此父级。此脚本具有对摄影机的引用(如果需要帮助,请告诉我),并计算摄影机与摄影机之间的距离,如果距离小于某个值,则实例化平铺,否则将销毁实例(如果有)

它必须在更新函数中执行此操作,以检查每帧的距离,或者您可以使用“协同路由”来执行较少的检查(更高效)

另一种方法是将脚本附加到具有所有平铺实例的阵列的摄影机,并以相同的方式检查它们与摄影机的距离。如果只有一个大平铺贴图,则可以执行此操作,因为如果有多个大平铺贴图,则很难重复使用此脚本

您还可以计算平铺和角色精灵(而不是相机)之间的距离。选择更方便的


完成上述操作后,您仍然会得到帧下降,您可以放大相机,以在其范围内包含较少的平铺,但您必须重新计算距离。

哇,回答得很好,非常感谢!不过,我对脚本中引用相机的内容有点迷茫。请您再解释一下,好吗?我如何连接e将游戏对象添加到每个互动程序中?您可以创建一个公共游戏对象变量
public gameObject MyCamera;
这很好…要将互动程序连接到空游戏对象,只需在层次结构中拖动其名称并将其放置在空游戏对象上。他们会看到它旁边有一个箭头,如上面答案中的图像。因此基本上您可以你是说为每个单独的磁贴创建一个这样的游戏对象,然后为每个磁贴的游戏对象创建一个脚本,如果游戏对象不在相机的视野内,它会破坏游戏对象?是的,是这样的脚本,你制作一次,然后对每个磁贴重复使用。但我不确定是否有“快速”的问题"为每个互动程序创建父游戏对象的方法。您需要父对象,因为父对象必须销毁其子对象。如果您将脚本直接附加到对象并使其销毁自身,它如何重新创建自身?它不能…。否则,只需使用另一种解决方案,即摄影机脚本。无需为父对象,脚本将自动创建只能在相机上使用。键入:
然后你会看到家长旁边有一个箭头…