初心
一开始的时候是想在一张图上进行涂鸦,经过寻找,在unity中,可以通过GL图形库,来绘制线条,以达到涂鸦的效果。
代码实现
简单的添加了改变线条颜色和线条粗细的功能,在一定程度上可以撤销操作和断点绘制
ps:装13的英文注释请忽略
using UnityEngine;
using System.Collections;
using System.Collections.Generic;
public class DrawLineByCursor: MonoBehaviour
{
// the line's Material
private Material m_LineMaterial;
public Material LineMaterial
{
get { return m_LineMaterial; }
}
// MousePosition Data
private List<List<Vector3>> m_LineInfo;
// the line's Width
public int m_Width = 1;
public Color LineColor = Color.black;
// MouseButtonUp Count
private int currentID;
// Use this for initialization
void Start ()
{
currentID = 0;
// Create List
m_LineInfo = new List<List<Vector3>>();
}
// Update is called once per frame
void Update ()
{
// the Left mouseButton Up stop recording the mousePosition to this list
if (Input.GetMouseButtonUp(0))
{
currentID += 1;
}
// the left mouseButton Down create new mousePosition list
if (Input.GetMouseButtonDown(0))
{
List<Vector3> tmp = new List<Vector3>();
m_LineInfo.Add(tmp);
}
if (Input.GetMouseButton(0))
{
m_LineInfo[currentID].Add(Input.mousePosition);
}
if (Input.GetKeyDown(KeyCode.C))
ClearAll();
if (Input.GetKeyDown(KeyCode.Z))
Undo();
}
// Draw Line by system
void OnPostRender()
{
// create the line's shader
if (m_LineMaterial == null)
CreateLineShader();
// set the Ortho
GL.LoadOrtho();
// filtration the material
m_LineMaterial.SetPass(0);
// strat Draw line
GL.Begin(GL.LINES);
// Get the need draw line Count
int size = m_LineInfo.Count;
if (size != 0)
{
// draw line one by one
for (int i = 0; i < size; ++i)
{
for (int j = 0; j < m_LineInfo[i].Count - 1; ++j)
{
Vector3 start = m_LineInfo[i][j];
Vector3 end = m_LineInfo[i][j + 1];
GL.Color(LineColor);
DrawLine(start.x, start.y, start.z, end.x, end.y, end.z, m_Width);
}
}
}
GL.End();
}
// DrawLine procedure
void DrawLine(float x1, float y1, float z1, float x2, float y2, float z2, int width)
{
for (int i = 0; i < width; ++i)
{
int iTmp = width / 2;
// Draw current line
GL.Vertex3(x1 / Screen.width, y1 / Screen.height, z1);
GL.Vertex3(x2 / Screen.width, y2 / Screen.height, z2);
// Draw Left
if (i % 2 == 0)
{
for (int j = -iTmp; j < iTmp; ++j)
{
GL.Vertex3((x1 - (i / 2)) / Screen.width, (y1 + j) / Screen.height, z1);
GL.Vertex3((x2 - (i / 2)) / Screen.width, (y2 + j) / Screen.height, z2);
}
}
// Draw Right
else
{
for (int j = -iTmp; j < iTmp; ++j)
{
GL.Vertex3((x1 + (i / 2)) / Screen.width, (y1 + j) / Screen.height, z1);
GL.Vertex3((x2 + (i / 2)) / Screen.width, (y2 + j) / Screen.height, z2);
}
}
}
}
// Create LineShader
private void CreateLineShader()
{
Shader shader = Shader.Find("Hidden/Internal-Colored");
m_LineMaterial = new Material(shader);
m_LineMaterial.hideFlags = HideFlags.HideAndDontSave;
m_LineMaterial.SetInt("_SrcBlend", (int)UnityEngine.Rendering.BlendMode.SrcAlpha);
m_LineMaterial.SetInt("_DstBlend",(int)UnityEngine.Rendering.BlendMode.OneMinusSrcAlpha);
m_LineMaterial.SetInt("_Cull",(int)UnityEngine.Rendering.CullMode.Off);
m_LineMaterial.SetInt("_ZWrite", 0);
}
// ClearAll
public void ClearAll()
{
m_LineInfo.Clear();
currentID = 0;
}
// Undo
public void Undo()
{
if (currentID > 0)
currentID--;
m_LineInfo.RemoveAt(currentID);
}
}
附注
在使用过程中,尝试使用unity创建完成的材质球,发现无法改变线条的颜色,所以动态创建了材质,如果有大神知道如何使用通过unity创建的材质球,烦请指点