最近碰到一個功能,需要將一張大圖切割成若干個小圖在拼成大圖。
首先定義一些基礎(chǔ)變量
//小圖的寬和高
public int m_iMinWidth;
public int m_iMinHeight;
//一行有多少個小圖
public int m_iMinPicRowCount;
//一列有多少個小圖
public int m_iMinPicColumnCount;
//需要切割的大圖
public Texture2D m_texPlayer;
//小圖數(shù)組
private Texture2D[,] m_texPlayers;
初始化一些變量
//初始化行數(shù)列數(shù)
m_iMinPicRowCount = 22;
m_iMinPicColumnCount = 12;
//根據(jù)行數(shù)和列數(shù)構(gòu)造儲存小圖的數(shù)組
m_texPlayers = new Texture2D[m_iMinPicRowCount, m_iMinPicRowCount];
核心方法 分割大圖,核心思想就是在大圖上去像素點賦值給小圖
//切圖
void DePackTexture(int i, int j)
{
//通過大圖寬高計算出每次切圖的大小
m_iMinHeight = m_texPlayer.height / m_iMinPicColumnCount;
m_iMinWidth = m_texPlayer.width / m_iMinPicRowCount;
int cur_x = i * m_iMinWidth;
int cur_y = j * m_iMinHeight;
Texture2D newTexture = new Texture2D(m_iMinWidth, m_iMinHeight);
for (int m = cur_y; m < cur_y + m_iMinHeight; m++)
{
for (int n = cur_x; n < cur_x + m_iMinWidth; n++)
{
//核心 通過從大圖拿到的像素點賦值給小圖
newTexture.SetPixel(n - cur_x, m - cur_y, m_texPlayer.GetPixel(n, m));
}
}
//Apply一下 更新貼圖
newTexture.Apply();
//儲存到數(shù)組
m_texPlayers[i, j] = newTexture;
}
有時候會碰到說大圖不能讀的情況,這是Unity為了節(jié)省性能默認(rèn)的為不可讀了,可以在設(shè)置中更改,也可以使用下面這個方法:
private Texture2D duplicateTexture(Texture2D source)
{
RenderTexture renderTex = RenderTexture.GetTemporary(
source.width,
source.height,
0,
RenderTextureFormat.Default,
RenderTextureReadWrite.Linear);
Graphics.Blit(source, renderTex);
RenderTexture previous = RenderTexture.active;
RenderTexture.active = renderTex;
Texture2D readableText = new Texture2D(source.width, source.height);
readableText.ReadPixels(new Rect(0, 0, renderTex.width, renderTex.height), 0, 0);
readableText.Apply();
RenderTexture.active = previous;
RenderTexture.ReleaseTemporary(renderTex);
return readableText;
}
調(diào)用下這個方法
m_texPlayer = duplicateTexture(m_texPlayer);
根據(jù)行列數(shù)分割大圖
//切割圖片
for (int i = 0; i < m_iMinPicRowCount; i++)
{
for (int j = 0; j < m_iMinPicColumnCount; j++)
{
DePackTexture(i, j);
}
}
最后創(chuàng)建下Quad看下效果
//創(chuàng)建Quad
void CreatQuad()
{
GameObject go = Resources.Load<GameObject>("Quad");
for (int i = 0; i < m_iMinPicRowCount; i++)
{
for (int j = 0; j < m_iMinPicColumnCount; j++)
{
GameObject g = Instantiate(go, new Vector3(i, j, 0), Quaternion.identity);
//將材質(zhì)賦給對應(yīng)的Quad
g.gameObject.GetComponent<MeshRenderer>().material.mainTexture = m_texPlayers[i, j];
}
}
}
效果展示

image.png
但是這樣會有一個問題,就是圖片之間有很明顯的縫隙感,這是由于創(chuàng)建的Texture2D大小并不能完美貼合所創(chuàng)建出來的Quad。
所以我們需要修改wrapMode,代碼如下:
newTexture.wrapMode = TextureWrapMode.Clamp;
運行效果如下:

image.png
是不是就很完美了。