当前位置:   article > 正文

Unity中实现UI渐变_unity ui渐变色

unity ui渐变色

一:效果演示


二:使用


GradientDir:渐变方向
ColorArray:颜色数组


三:实现原理

通过添加顶点并设置顶点数据实现渐变,注意颜色数组数量越多顶点和三角形数量也会增加
UGUI源码解析——BaseMeshEffect


四:代码实现

  1. using System.Collections.Generic;
  2. using UnityEngine;
  3. using UnityEngine.UI;
  4. /*
  5. Text顶点索引顺序
  6. 5-0 ---- 1
  7. | \ |
  8. | \ |
  9. | \ |
  10. | \ |
  11. 4-----3-2
  12. */
  13. /// <summary>
  14. /// 渐变
  15. /// </summary>
  16. [DisallowMultipleComponent]
  17. [AddComponentMenu("LFramework/UI/Effects/Gradient", 1)]
  18. public class Gradient : BaseMeshEffect
  19. {
  20. protected Gradient()
  21. {
  22. }
  23. /// <summary>
  24. /// 渐变方向
  25. /// </summary>
  26. public enum EGradientDir
  27. {
  28. TopToBottom,
  29. BottomToTop,
  30. LeftToRight,
  31. RightToLeft,
  32. }
  33. /// <summary>
  34. /// 渐变方向
  35. /// </summary>
  36. [SerializeField]
  37. EGradientDir m_GradientDir = EGradientDir.TopToBottom;
  38. public EGradientDir GradientDir
  39. {
  40. get
  41. {
  42. return m_GradientDir;
  43. }
  44. set
  45. {
  46. m_GradientDir = value;
  47. graphic.SetVerticesDirty();
  48. }
  49. }
  50. //颜色数组
  51. [SerializeField]
  52. Color32[] m_ColorArray = new Color32[2] { Color.black, Color.white };
  53. public Color32[] ColorArray
  54. {
  55. get
  56. {
  57. return m_ColorArray;
  58. }
  59. set
  60. {
  61. m_ColorArray = value;
  62. graphic.SetVerticesDirty();
  63. }
  64. }
  65. //顶点缓存
  66. List<UIVertex> m_VertexCache = new List<UIVertex>();
  67. //绘制使用的顶点列表
  68. List<UIVertex> m_VertexList = new List<UIVertex>();
  69. public override void ModifyMesh(VertexHelper vh)
  70. {
  71. if (!IsActive())
  72. {
  73. return;
  74. }
  75. vh.GetUIVertexStream(m_VertexCache);
  76. switch (m_GradientDir)
  77. {
  78. case EGradientDir.TopToBottom:
  79. ApplyGradient_TopToBottom(m_VertexCache);
  80. break;
  81. case EGradientDir.BottomToTop:
  82. ApplyGradient_BottomToTop(m_VertexCache);
  83. break;
  84. case EGradientDir.LeftToRight:
  85. ApplyGradient_LeftToRight(m_VertexCache);
  86. break;
  87. case EGradientDir.RightToLeft:
  88. ApplyGradient_RightToLeft(m_VertexCache);
  89. break;
  90. default:
  91. break;
  92. }
  93. vh.Clear();
  94. vh.AddUIVertexTriangleStream(m_VertexList);
  95. m_VertexCache.Clear();
  96. m_VertexList.Clear();
  97. }
  98. void ApplyGradient_TopToBottom(List<UIVertex> vertexCache)
  99. {
  100. if (vertexCache.Count == 0)
  101. {
  102. return;
  103. }
  104. if (m_ColorArray.Length < 2)
  105. {
  106. return;
  107. }
  108. int vertexCountPer = 6;//每一个文字的顶点数
  109. int vertexCount = vertexCache.Count;
  110. int colorCount = m_ColorArray.Length;
  111. for (int n = 0; n < vertexCount / 6; n++)
  112. {
  113. UIVertex lastVertexLB = new UIVertex();
  114. UIVertex lastVertexRB = new UIVertex();
  115. for (int i = 0; i < colorCount - 1; i++)
  116. {
  117. UIVertex vertexRT;
  118. UIVertex vertexLT;
  119. UIVertex vertexRB;
  120. UIVertex vertexLB;
  121. //左上角和右上角
  122. if (i == 0)
  123. {
  124. vertexLT = CalcVertex(vertexCache[n * vertexCountPer + 0], m_ColorArray[i]);
  125. vertexRT = CalcVertex(vertexCache[n * vertexCountPer + 1], m_ColorArray[i]);
  126. }
  127. else
  128. {
  129. vertexLT = lastVertexLB;
  130. vertexRT = lastVertexRB;
  131. }
  132. //左下角和右下角
  133. if (i == colorCount - 2)
  134. {
  135. vertexLB = CalcVertex(vertexCache[n * vertexCountPer + 4], m_ColorArray[i + 1]);
  136. vertexRB = CalcVertex(vertexCache[n * vertexCountPer + 2], m_ColorArray[i + 1]);
  137. }
  138. else
  139. {
  140. vertexLB = CalcVertex(vertexCache[n * vertexCountPer + 4], vertexCache[n * vertexCountPer + 0],
  141. (colorCount - i - 2) * 1f / (colorCount - 1), m_ColorArray[i + 1]);
  142. vertexRB = CalcVertex(vertexCache[n * vertexCountPer + 2], vertexCache[n * vertexCountPer + 1],
  143. (colorCount - i - 2) * 1f / (colorCount - 1), m_ColorArray[i + 1]);
  144. }
  145. lastVertexLB = vertexLB;
  146. lastVertexRB = vertexRB;
  147. m_VertexList.Add(vertexLT);
  148. m_VertexList.Add(vertexRT);
  149. m_VertexList.Add(vertexRB);
  150. m_VertexList.Add(vertexRB);
  151. m_VertexList.Add(vertexLB);
  152. m_VertexList.Add(vertexLT);
  153. }
  154. }
  155. }
  156. void ApplyGradient_BottomToTop(List<UIVertex> vertexCache)
  157. {
  158. if (vertexCache.Count == 0)
  159. {
  160. return;
  161. }
  162. if (m_ColorArray.Length < 2)
  163. {
  164. return;
  165. }
  166. int vertexCountPer = 6;//每一个文字的顶点数
  167. int vertexCount = vertexCache.Count;
  168. int colorCount = m_ColorArray.Length;
  169. for (int n = 0; n < vertexCount / 6; n++)
  170. {
  171. UIVertex lastVertexLT = new UIVertex();
  172. UIVertex lastVertexRT = new UIVertex();
  173. for (int i = 0; i < colorCount - 1; i++)
  174. {
  175. UIVertex vertexRT;
  176. UIVertex vertexLT;
  177. UIVertex vertexRB;
  178. UIVertex vertexLB;
  179. //左下角和右下角
  180. if (i == 0)
  181. {
  182. vertexLB = CalcVertex(vertexCache[n * vertexCountPer + 4], m_ColorArray[i]);
  183. vertexRB = CalcVertex(vertexCache[n * vertexCountPer + 2], m_ColorArray[i]);
  184. }
  185. else
  186. {
  187. vertexLB = lastVertexLT;
  188. vertexRB = lastVertexRT;
  189. }
  190. //左上角和右上角
  191. if (i == colorCount - 2)
  192. {
  193. vertexLT = CalcVertex(vertexCache[n * vertexCountPer + 0], m_ColorArray[i + 1]);
  194. vertexRT = CalcVertex(vertexCache[n * vertexCountPer + 1], m_ColorArray[i + 1]);
  195. }
  196. else
  197. {
  198. vertexLT = CalcVertex(vertexCache[n * vertexCountPer + 0], vertexCache[n * vertexCountPer + 4],
  199. (colorCount - i - 2) * 1f / (colorCount - 1), m_ColorArray[i + 1]);
  200. vertexRT = CalcVertex(vertexCache[n * vertexCountPer + 1], vertexCache[n * vertexCountPer + 2],
  201. (colorCount - i - 2) * 1f / (colorCount - 1), m_ColorArray[i + 1]);
  202. }
  203. lastVertexLT = vertexLT;
  204. lastVertexRT = vertexRT;
  205. m_VertexList.Add(vertexLT);
  206. m_VertexList.Add(vertexRT);
  207. m_VertexList.Add(vertexRB);
  208. m_VertexList.Add(vertexRB);
  209. m_VertexList.Add(vertexLB);
  210. m_VertexList.Add(vertexLT);
  211. }
  212. }
  213. }
  214. void ApplyGradient_LeftToRight(List<UIVertex> vertexCache)
  215. {
  216. if (vertexCache.Count == 0)
  217. {
  218. return;
  219. }
  220. if (m_ColorArray.Length < 2)
  221. {
  222. return;
  223. }
  224. int vertexCountPer = 6;//每一个文字的顶点数
  225. int vertexCount = vertexCache.Count;
  226. int colorCount = m_ColorArray.Length;
  227. for (int n = 0; n < vertexCount / 6; n++)
  228. {
  229. UIVertex lastVertexRT = new UIVertex();
  230. UIVertex lastVertexRB = new UIVertex();
  231. for (int i = 0; i < colorCount - 1; i++)
  232. {
  233. UIVertex vertexRT;
  234. UIVertex vertexLT;
  235. UIVertex vertexRB;
  236. UIVertex vertexLB;
  237. //左上角和左下角
  238. if (i == 0)
  239. {
  240. vertexLT = CalcVertex(vertexCache[n * vertexCountPer + 0], m_ColorArray[i]);
  241. vertexLB = CalcVertex(vertexCache[n * vertexCountPer + 4], m_ColorArray[i]);
  242. }
  243. else
  244. {
  245. vertexLT = lastVertexRT;
  246. vertexLB = lastVertexRB;
  247. }
  248. //右上角和右下角
  249. if (i == colorCount - 2)
  250. {
  251. vertexRT = CalcVertex(vertexCache[n * vertexCountPer + 1], m_ColorArray[i + 1]);
  252. vertexRB = CalcVertex(vertexCache[n * vertexCountPer + 2], m_ColorArray[i + 1]);
  253. }
  254. else
  255. {
  256. vertexRT = CalcVertex(vertexCache[n * vertexCountPer + 1], vertexCache[n * vertexCountPer + 0],
  257. (colorCount - i - 2) * 1f / (colorCount - 1), m_ColorArray[i + 1]);
  258. vertexRB = CalcVertex(vertexCache[n * vertexCountPer + 2], vertexCache[n * vertexCountPer + 4],
  259. (colorCount - i - 2) * 1f / (colorCount - 1), m_ColorArray[i + 1]);
  260. }
  261. lastVertexRT = vertexRT;
  262. lastVertexRB = vertexRB;
  263. m_VertexList.Add(vertexLT);
  264. m_VertexList.Add(vertexRT);
  265. m_VertexList.Add(vertexRB);
  266. m_VertexList.Add(vertexRB);
  267. m_VertexList.Add(vertexLB);
  268. m_VertexList.Add(vertexLT);
  269. }
  270. }
  271. }
  272. void ApplyGradient_RightToLeft(List<UIVertex> vertexCache)
  273. {
  274. if (vertexCache.Count == 0)
  275. {
  276. return;
  277. }
  278. if (m_ColorArray.Length < 2)
  279. {
  280. return;
  281. }
  282. int vertexCountPer = 6;//每一个文字的顶点数
  283. int vertexCount = vertexCache.Count;
  284. int colorCount = m_ColorArray.Length;
  285. for (int n = 0; n < vertexCount / 6; n++)
  286. {
  287. UIVertex lastVertexLT = new UIVertex();
  288. UIVertex lastVertexLB = new UIVertex();
  289. for (int i = 0; i < colorCount - 1; i++)
  290. {
  291. UIVertex vertexRT;
  292. UIVertex vertexLT;
  293. UIVertex vertexRB;
  294. UIVertex vertexLB;
  295. //右上角和右下角
  296. if (i == 0)
  297. {
  298. vertexRT = CalcVertex(vertexCache[n * vertexCountPer + 1], m_ColorArray[i]);
  299. vertexRB = CalcVertex(vertexCache[n * vertexCountPer + 2], m_ColorArray[i]);
  300. }
  301. else
  302. {
  303. vertexRT = lastVertexLT;
  304. vertexRB = lastVertexLB;
  305. }
  306. //左上角和左下角
  307. if (i == colorCount - 2)
  308. {
  309. vertexLT = CalcVertex(vertexCache[n * vertexCountPer + 0], m_ColorArray[i + 1]);
  310. vertexLB = CalcVertex(vertexCache[n * vertexCountPer + 4], m_ColorArray[i + 1]);
  311. }
  312. else
  313. {
  314. vertexLT = CalcVertex(vertexCache[n * vertexCountPer + 0], vertexCache[n * vertexCountPer + 1],
  315. (colorCount - i - 2) * 1f / (colorCount - 1), m_ColorArray[i + 1]);
  316. vertexLB = CalcVertex(vertexCache[n * vertexCountPer + 4], vertexCache[n * vertexCountPer + 2],
  317. (colorCount - i - 2) * 1f / (colorCount - 1), m_ColorArray[i + 1]);
  318. }
  319. lastVertexLT = vertexLT;
  320. lastVertexLB = vertexLB;
  321. m_VertexList.Add(vertexLT);
  322. m_VertexList.Add(vertexRT);
  323. m_VertexList.Add(vertexRB);
  324. m_VertexList.Add(vertexRB);
  325. m_VertexList.Add(vertexLB);
  326. m_VertexList.Add(vertexLT);
  327. }
  328. }
  329. }
  330. /// <summary>
  331. /// 计算顶点数据(只计算颜色)
  332. /// </summary>
  333. UIVertex CalcVertex(UIVertex vertex, Color32 color)
  334. {
  335. vertex.color = color;
  336. return vertex;
  337. }
  338. /// <summary>
  339. /// 计算顶点数据
  340. /// </summary>
  341. UIVertex CalcVertex(UIVertex vertexA, UIVertex vertexB, float ratio, Color32 color)
  342. {
  343. UIVertex vertexTemp = new UIVertex();
  344. vertexTemp.position = (vertexB.position - vertexA.position) * ratio + vertexA.position;
  345. vertexTemp.color = color;
  346. vertexTemp.normal = (vertexB.normal - vertexA.normal) * ratio + vertexA.normal;
  347. vertexTemp.tangent = (vertexB.tangent - vertexA.tangent) * ratio + vertexA.tangent;
  348. vertexTemp.uv0 = (vertexB.uv0 - vertexA.uv0) * ratio + vertexA.uv0;
  349. vertexTemp.uv1 = (vertexB.uv1 - vertexA.uv1) * ratio + vertexA.uv1;
  350. return vertexTemp;
  351. }
  352. }

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/2023面试高手/article/detail/107203
推荐阅读
相关标签
  

闽ICP备14008679号