Ingen beskrivning
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

Axis.cs 29KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867
  1. using System;
  2. using System.Collections.Generic;
  3. using UnityEngine;
  4. namespace XCharts.Runtime
  5. {
  6. /// <summary>
  7. /// The axis in rectangular coordinate.
  8. /// |直角坐标系的坐标轴组件。
  9. /// </summary>
  10. [System.Serializable]
  11. public class Axis : MainComponent
  12. {
  13. /// <summary>
  14. /// the type of axis.
  15. /// |坐标轴类型。
  16. /// </summary>
  17. public enum AxisType
  18. {
  19. /// <summary>
  20. /// Numerical axis, suitable for continuous data.
  21. /// |数值轴。适用于连续数据。
  22. /// </summary>
  23. Value,
  24. /// <summary>
  25. /// Category axis, suitable for discrete category data. Data should only be set via data for this type.
  26. /// |类目轴。适用于离散的类目数据,为该类型时必须通过 data 设置类目数据。serie的数据第0维数据对应坐标轴data的index。
  27. /// </summary>
  28. Category,
  29. /// <summary>
  30. /// Log axis, suitable for log data.
  31. /// |对数轴。适用于对数数据。
  32. /// </summary>
  33. Log,
  34. /// <summary>
  35. /// Time axis, suitable for continuous time series data.
  36. /// |时间轴。适用于连续的时序数据。
  37. /// </summary>
  38. Time
  39. }
  40. /// <summary>
  41. /// the type of axis min and max value.
  42. /// |坐标轴最大最小刻度显示类型。
  43. /// </summary>
  44. public enum AxisMinMaxType
  45. {
  46. /// <summary>
  47. /// 0 - maximum.
  48. /// |0-最大值。
  49. /// </summary>
  50. Default,
  51. /// <summary>
  52. /// minimum - maximum.
  53. /// |最小值-最大值。
  54. /// </summary>
  55. MinMax,
  56. /// <summary>
  57. /// Customize the minimum and maximum.
  58. /// |自定义最小值最大值。
  59. /// </summary>
  60. Custom
  61. }
  62. /// <summary>
  63. /// the position of axis in grid.
  64. /// |坐标轴在Grid中的位置
  65. /// </summary>
  66. public enum AxisPosition
  67. {
  68. Left,
  69. Right,
  70. Bottom,
  71. Top
  72. }
  73. [SerializeField] protected bool m_Show = true;
  74. [SerializeField] protected Axis.AxisType m_Type;
  75. [SerializeField] protected Axis.AxisMinMaxType m_MinMaxType;
  76. [SerializeField] protected int m_GridIndex;
  77. [SerializeField] protected int m_PolarIndex;
  78. [SerializeField] protected int m_ParallelIndex;
  79. [SerializeField] protected Axis.AxisPosition m_Position;
  80. [SerializeField] protected float m_Offset;
  81. [SerializeField] protected double m_Min;
  82. [SerializeField] protected double m_Max;
  83. [SerializeField] protected int m_SplitNumber = 0;
  84. [SerializeField] protected double m_Interval = 0;
  85. [SerializeField] protected bool m_BoundaryGap = true;
  86. [SerializeField] protected int m_MaxCache = 0;
  87. [SerializeField] protected float m_LogBase = 10;
  88. [SerializeField] protected bool m_LogBaseE = false;
  89. [SerializeField] protected double m_CeilRate = 0;
  90. [SerializeField] protected bool m_Inverse = false;
  91. [SerializeField] private bool m_Clockwise = true;
  92. [SerializeField] private bool m_InsertDataToHead;
  93. [SerializeField] protected List<Sprite> m_Icons = new List<Sprite>();
  94. [SerializeField] protected List<string> m_Data = new List<string>();
  95. [SerializeField] protected AxisLine m_AxisLine = AxisLine.defaultAxisLine;
  96. [SerializeField] protected AxisName m_AxisName = AxisName.defaultAxisName;
  97. [SerializeField] protected AxisTick m_AxisTick = AxisTick.defaultTick;
  98. [SerializeField] protected AxisLabel m_AxisLabel = AxisLabel.defaultAxisLabel;
  99. [SerializeField] protected AxisSplitLine m_SplitLine = AxisSplitLine.defaultSplitLine;
  100. [SerializeField] protected AxisSplitArea m_SplitArea = AxisSplitArea.defaultSplitArea;
  101. [SerializeField][Since("v3.2.0")] protected AxisMinorTick m_MinorTick = AxisMinorTick.defaultMinorTick;
  102. [SerializeField][Since("v3.2.0")] protected AxisMinorSplitLine m_MinorSplitLine = AxisMinorSplitLine.defaultMinorSplitLine;
  103. [SerializeField][Since("v3.4.0")] protected LabelStyle m_IndicatorLabel = new LabelStyle() { numericFormatter = "f2" };
  104. public AxisContext context = new AxisContext();
  105. /// <summary>
  106. /// Whether to show axis.
  107. /// |是否显示坐标轴。
  108. /// </summary>
  109. public bool show
  110. {
  111. get { return m_Show; }
  112. set { if (PropertyUtil.SetStruct(ref m_Show, value)) SetAllDirty(); }
  113. }
  114. /// <summary>
  115. /// the type of axis.
  116. /// |坐标轴类型。
  117. /// </summary>
  118. public AxisType type
  119. {
  120. get { return m_Type; }
  121. set { if (PropertyUtil.SetStruct(ref m_Type, value)) SetAllDirty(); }
  122. }
  123. /// <summary>
  124. /// the type of axis minmax.
  125. /// |坐标轴刻度最大最小值显示类型。
  126. /// </summary>
  127. public AxisMinMaxType minMaxType
  128. {
  129. get { return m_MinMaxType; }
  130. set { if (PropertyUtil.SetStruct(ref m_MinMaxType, value)) SetAllDirty(); }
  131. }
  132. /// <summary>
  133. /// The index of the grid on which the axis are located, by default, is in the first grid.
  134. /// |坐标轴所在的 grid 的索引,默认位于第一个 grid。
  135. /// </summary>
  136. public int gridIndex
  137. {
  138. get { return m_GridIndex; }
  139. set { if (PropertyUtil.SetStruct(ref m_GridIndex, value)) SetAllDirty(); }
  140. }
  141. /// <summary>
  142. /// The index of the polar on which the axis are located, by default, is in the first polar.
  143. /// |坐标轴所在的 ploar 的索引,默认位于第一个 polar。
  144. /// </summary>
  145. public int polarIndex
  146. {
  147. get { return m_PolarIndex; }
  148. set { if (PropertyUtil.SetStruct(ref m_PolarIndex, value)) SetAllDirty(); }
  149. }
  150. /// <summary>
  151. /// The index of the parallel on which the axis are located, by default, is in the first parallel.
  152. /// |坐标轴所在的 parallel 的索引,默认位于第一个 parallel。
  153. /// </summary>
  154. public int parallelIndex
  155. {
  156. get { return m_ParallelIndex; }
  157. set { if (PropertyUtil.SetStruct(ref m_ParallelIndex, value)) SetAllDirty(); }
  158. }
  159. /// <summary>
  160. /// the position of axis in grid.
  161. /// |坐标轴在Grid中的位置。
  162. /// </summary>
  163. public AxisPosition position
  164. {
  165. get { return m_Position; }
  166. set { if (PropertyUtil.SetStruct(ref m_Position, value)) SetAllDirty(); }
  167. }
  168. /// <summary>
  169. /// the offset of axis from the default position. Useful when the same position has multiple axes.
  170. /// |坐标轴相对默认位置的偏移。在相同position有多个坐标轴时有用。
  171. /// </summary>
  172. public float offset
  173. {
  174. get { return m_Offset; }
  175. set { if (PropertyUtil.SetStruct(ref m_Offset, value)) SetAllDirty(); }
  176. }
  177. /// <summary>
  178. /// The minimun value of axis.Valid when `minMaxType` is `Custom`
  179. /// |设定的坐标轴刻度最小值,当minMaxType为Custom时有效。
  180. /// </summary>
  181. public double min
  182. {
  183. get { return m_Min; }
  184. set { if (PropertyUtil.SetStruct(ref m_Min, value)) SetAllDirty(); }
  185. }
  186. /// <summary>
  187. /// The maximum value of axis.Valid when `minMaxType` is `Custom`
  188. /// |设定的坐标轴刻度最大值,当minMaxType为Custom时有效。
  189. /// </summary>
  190. public double max
  191. {
  192. get { return m_Max; }
  193. set { if (PropertyUtil.SetStruct(ref m_Max, value)) SetAllDirty(); }
  194. }
  195. /// <summary>
  196. /// Number of segments that the axis is split into.
  197. /// |坐标轴的期望的分割段数。默认为0表示自动分割。
  198. /// </summary>
  199. public int splitNumber
  200. {
  201. get { return m_SplitNumber; }
  202. set { if (PropertyUtil.SetStruct(ref m_SplitNumber, value)) SetAllDirty(); }
  203. }
  204. /// <summary>
  205. /// Compulsively set segmentation interval for axis.This is unavailable for category axis.
  206. /// |强制设置坐标轴分割间隔。无法在类目轴中使用。
  207. /// </summary>
  208. public double interval
  209. {
  210. get { return m_Interval; }
  211. set { if (PropertyUtil.SetStruct(ref m_Interval, value)) SetAllDirty(); }
  212. }
  213. /// <summary>
  214. /// The boundary gap on both sides of a coordinate axis, which is valid only for category axis with type: 'Category'.
  215. /// |坐标轴两边是否留白。只对类目轴有效。
  216. /// </summary>
  217. public bool boundaryGap
  218. {
  219. get { return IsCategory() ? m_BoundaryGap : false; }
  220. set { if (PropertyUtil.SetStruct(ref m_BoundaryGap, value)) SetAllDirty(); }
  221. }
  222. /// <summary>
  223. /// Base of logarithm, which is valid only for numeric axes with type: 'Log'.
  224. /// |对数轴的底数,只在对数轴(type:'Log')中有效。
  225. /// </summary>
  226. public float logBase
  227. {
  228. get { return m_LogBase; }
  229. set
  230. {
  231. if (value <= 0 || value == 1) value = 10;
  232. if (PropertyUtil.SetStruct(ref m_LogBase, value)) SetAllDirty();
  233. }
  234. }
  235. /// <summary>
  236. /// On the log axis, if base e is the natural number, and is true, logBase fails.
  237. /// |对数轴是否以自然数 e 为底数,为 true 时 logBase 失效。
  238. /// </summary>
  239. public bool logBaseE
  240. {
  241. get { return m_LogBaseE; }
  242. set { if (PropertyUtil.SetStruct(ref m_LogBaseE, value)) SetAllDirty(); }
  243. }
  244. /// <summary>
  245. /// The max number of axis data cache.
  246. /// |The first data will be remove when the size of axis data is larger then maxCache.
  247. /// |可缓存的最大数据量。默认为0没有限制,大于0时超过指定值会移除旧数据再插入新数据。
  248. /// </summary>
  249. public int maxCache
  250. {
  251. get { return m_MaxCache; }
  252. set { if (PropertyUtil.SetStruct(ref m_MaxCache, value < 0 ? 0 : value)) SetAllDirty(); }
  253. }
  254. /// <summary>
  255. /// The ratio of maximum and minimum values rounded upward. The default is 0, which is automatically calculated.
  256. /// |最大最小值向上取整的倍率。默认为0时自动计算。
  257. /// </summary>
  258. public double ceilRate
  259. {
  260. get { return m_CeilRate; }
  261. set { if (PropertyUtil.SetStruct(ref m_CeilRate, value < 0 ? 0 : value)) SetAllDirty(); }
  262. }
  263. /// <summary>
  264. /// Whether the axis are reversed or not. Invalid in `Category` axis.
  265. /// |是否反向坐标轴。在类目轴中无效。
  266. /// </summary>
  267. public bool inverse
  268. {
  269. get { return m_Inverse; }
  270. set { if (m_Type == AxisType.Value && PropertyUtil.SetStruct(ref m_Inverse, value)) SetAllDirty(); }
  271. }
  272. /// <summary>
  273. /// Whether the positive position of axis is in clockwise. True for clockwise by default.
  274. /// |刻度增长是否按顺时针,默认顺时针。
  275. /// </summary>
  276. public bool clockwise
  277. {
  278. get { return m_Clockwise; }
  279. set { if (PropertyUtil.SetStruct(ref m_Clockwise, value)) SetAllDirty(); }
  280. }
  281. /// <summary>
  282. /// Category data, available in type: 'Category' axis.
  283. /// |类目数据,在类目轴(type: 'category')中有效。
  284. /// </summary>
  285. public List<string> data
  286. {
  287. get { return m_Data; }
  288. set { if (value != null) { m_Data = value; SetAllDirty(); } }
  289. }
  290. /// <summary>
  291. /// 类目数据对应的图标。
  292. /// </summary>
  293. public List<Sprite> icons
  294. {
  295. get { return m_Icons; }
  296. set { if (value != null) { m_Icons = value; SetAllDirty(); } }
  297. }
  298. /// <summary>
  299. /// axis Line.
  300. /// |坐标轴轴线。
  301. /// </summary>
  302. public AxisLine axisLine
  303. {
  304. get { return m_AxisLine; }
  305. set { if (value != null) { m_AxisLine = value; SetVerticesDirty(); } }
  306. }
  307. /// <summary>
  308. /// axis name.
  309. /// |坐标轴名称。
  310. /// </summary>
  311. public AxisName axisName
  312. {
  313. get { return m_AxisName; }
  314. set { if (value != null) { m_AxisName = value; SetComponentDirty(); } }
  315. }
  316. /// <summary>
  317. /// axis tick.
  318. /// |坐标轴刻度。
  319. /// </summary>
  320. public AxisTick axisTick
  321. {
  322. get { return m_AxisTick; }
  323. set { if (value != null) { m_AxisTick = value; SetVerticesDirty(); } }
  324. }
  325. /// <summary>
  326. /// axis label.
  327. /// |坐标轴刻度标签。
  328. /// </summary>
  329. public AxisLabel axisLabel
  330. {
  331. get { return m_AxisLabel; }
  332. set { if (value != null) { m_AxisLabel = value; SetComponentDirty(); } }
  333. }
  334. /// <summary>
  335. /// axis split line.
  336. /// |坐标轴分割线。
  337. /// </summary>
  338. public AxisSplitLine splitLine
  339. {
  340. get { return m_SplitLine; }
  341. set { if (value != null) { m_SplitLine = value; SetVerticesDirty(); } }
  342. }
  343. /// <summary>
  344. /// axis split area.
  345. /// |坐标轴分割区域。
  346. /// </summary>
  347. public AxisSplitArea splitArea
  348. {
  349. get { return m_SplitArea; }
  350. set { if (value != null) { m_SplitArea = value; SetVerticesDirty(); } }
  351. }
  352. /// <summary>
  353. /// axis minor tick.
  354. /// |坐标轴次刻度。
  355. /// </summary>
  356. public AxisMinorTick minorTick
  357. {
  358. get { return m_MinorTick; }
  359. set { if (value != null) { m_MinorTick = value; SetVerticesDirty(); } }
  360. }
  361. /// <summary>
  362. /// axis minor split line.
  363. /// |坐标轴次分割线。
  364. /// </summary>
  365. public AxisMinorSplitLine minorSplitLine
  366. {
  367. get { return m_MinorSplitLine; }
  368. set { if (value != null) { m_MinorSplitLine = value; SetVerticesDirty(); } }
  369. }
  370. /// <summary>
  371. /// Style of axis tooltip indicator label.
  372. /// |指示器文本的样式。Tooltip为Cross时使用。
  373. /// </summary>
  374. public LabelStyle indicatorLabel
  375. {
  376. get { return m_IndicatorLabel; }
  377. set { if (value != null) { m_IndicatorLabel = value; SetComponentDirty(); } }
  378. }
  379. /// <summary>
  380. /// Whether to add new data at the head or at the end of the list.
  381. /// |添加新数据时是在列表的头部还是尾部加入。
  382. /// </summary>
  383. public bool insertDataToHead
  384. {
  385. get { return m_InsertDataToHead; }
  386. set { if (PropertyUtil.SetStruct(ref m_InsertDataToHead, value)) SetAllDirty(); }
  387. }
  388. public override bool vertsDirty
  389. {
  390. get
  391. {
  392. return m_VertsDirty ||
  393. axisLine.anyDirty ||
  394. axisTick.anyDirty ||
  395. splitLine.anyDirty ||
  396. splitArea.anyDirty ||
  397. minorTick.anyDirty ||
  398. minorSplitLine.anyDirty;
  399. }
  400. }
  401. public override bool componentDirty
  402. {
  403. get
  404. {
  405. return m_ComponentDirty ||
  406. axisName.anyDirty ||
  407. axisLabel.anyDirty ||
  408. indicatorLabel.anyDirty;
  409. }
  410. }
  411. public override void ClearComponentDirty()
  412. {
  413. base.ClearComponentDirty();
  414. axisName.ClearComponentDirty();
  415. axisLabel.ClearComponentDirty();
  416. indicatorLabel.ClearComponentDirty();
  417. }
  418. public override void ClearVerticesDirty()
  419. {
  420. base.ClearVerticesDirty();
  421. axisLabel.ClearVerticesDirty();
  422. axisLine.ClearVerticesDirty();
  423. axisTick.ClearVerticesDirty();
  424. splitLine.ClearVerticesDirty();
  425. splitArea.ClearVerticesDirty();
  426. minorTick.ClearVerticesDirty();
  427. minorSplitLine.ClearVerticesDirty();
  428. indicatorLabel.ClearComponentDirty();
  429. }
  430. public override void SetComponentDirty()
  431. {
  432. context.isNeedUpdateFilterData = true;
  433. base.SetComponentDirty();
  434. }
  435. public Axis Clone()
  436. {
  437. var axis = new Axis();
  438. axis.show = show;
  439. axis.type = type;
  440. axis.gridIndex = 0;
  441. axis.minMaxType = minMaxType;
  442. axis.min = min;
  443. axis.max = max;
  444. axis.splitNumber = splitNumber;
  445. axis.interval = interval;
  446. axis.boundaryGap = boundaryGap;
  447. axis.maxCache = maxCache;
  448. axis.logBase = logBase;
  449. axis.logBaseE = logBaseE;
  450. axis.ceilRate = ceilRate;
  451. axis.insertDataToHead = insertDataToHead;
  452. axis.axisLine = axisLine.Clone();
  453. axis.axisName = axisName.Clone();
  454. axis.axisTick = axisTick.Clone();
  455. axis.axisLabel = axisLabel.Clone();
  456. axis.splitLine = splitLine.Clone();
  457. axis.splitArea = splitArea.Clone();
  458. axis.minorTick = minorTick.Clone();
  459. axis.minorSplitLine = minorSplitLine.Clone();
  460. axis.indicatorLabel = indicatorLabel.Clone();
  461. axis.icons = new List<Sprite>();
  462. axis.data = new List<string>();
  463. ChartHelper.CopyList(axis.data, data);
  464. return axis;
  465. }
  466. public void Copy(Axis axis)
  467. {
  468. show = axis.show;
  469. type = axis.type;
  470. minMaxType = axis.minMaxType;
  471. gridIndex = axis.gridIndex;
  472. min = axis.min;
  473. max = axis.max;
  474. splitNumber = axis.splitNumber;
  475. interval = axis.interval;
  476. boundaryGap = axis.boundaryGap;
  477. maxCache = axis.maxCache;
  478. logBase = axis.logBase;
  479. logBaseE = axis.logBaseE;
  480. ceilRate = axis.ceilRate;
  481. insertDataToHead = axis.insertDataToHead;
  482. axisLine.Copy(axis.axisLine);
  483. axisName.Copy(axis.axisName);
  484. axisTick.Copy(axis.axisTick);
  485. axisLabel.Copy(axis.axisLabel);
  486. splitLine.Copy(axis.splitLine);
  487. splitArea.Copy(axis.splitArea);
  488. minorTick.Copy(axis.minorTick);
  489. minorSplitLine.Copy(axis.minorSplitLine);
  490. indicatorLabel.Copy(axis.indicatorLabel);
  491. ChartHelper.CopyList(data, axis.data);
  492. ChartHelper.CopyList<Sprite>(icons, axis.icons);
  493. }
  494. /// <summary>
  495. /// 清空类目数据
  496. /// </summary>
  497. public override void ClearData()
  498. {
  499. m_Data.Clear();
  500. m_Icons.Clear();
  501. context.Clear();
  502. SetAllDirty();
  503. }
  504. /// <summary>
  505. /// 是否为类目轴。
  506. /// </summary>
  507. /// <returns></returns>
  508. public bool IsCategory()
  509. {
  510. return m_Type == AxisType.Category;
  511. }
  512. /// <summary>
  513. /// 是否为数值轴。
  514. /// </summary>
  515. /// <returns></returns>
  516. public bool IsValue()
  517. {
  518. return m_Type == AxisType.Value;
  519. }
  520. /// <summary>
  521. /// 是否为对数轴。
  522. /// </summary>
  523. /// <returns></returns>
  524. public bool IsLog()
  525. {
  526. return m_Type == AxisType.Log;
  527. }
  528. /// <summary>
  529. /// 是否为时间轴。
  530. /// </summary>
  531. public bool IsTime()
  532. {
  533. return m_Type == AxisType.Time;
  534. }
  535. public bool IsLeft()
  536. {
  537. return m_Position == AxisPosition.Left;
  538. }
  539. public bool IsRight()
  540. {
  541. return m_Position == AxisPosition.Right;
  542. }
  543. public bool IsTop()
  544. {
  545. return m_Position == AxisPosition.Top;
  546. }
  547. public bool IsBottom()
  548. {
  549. return m_Position == AxisPosition.Bottom;
  550. }
  551. public bool IsNeedShowLabel(int index, int total = 0)
  552. {
  553. if (total == 0)
  554. {
  555. total = context.labelValueList.Count;
  556. }
  557. return axisLabel.IsNeedShowLabel(index, total);
  558. }
  559. public void SetNeedUpdateFilterData()
  560. {
  561. context.isNeedUpdateFilterData = true;
  562. }
  563. /// <summary>
  564. /// 添加一个类目到类目数据列表
  565. /// </summary>
  566. /// <param name="category"></param>
  567. public void AddData(string category)
  568. {
  569. if (maxCache > 0)
  570. {
  571. while (m_Data.Count >= maxCache)
  572. {
  573. RemoveData(m_InsertDataToHead ? m_Data.Count - 1 : 0);
  574. }
  575. }
  576. if (m_InsertDataToHead)
  577. m_Data.Insert(0, category);
  578. else
  579. m_Data.Add(category);
  580. SetAllDirty();
  581. }
  582. public void RemoveData(int dataIndex)
  583. {
  584. context.isNeedUpdateFilterData = true;
  585. m_Data.RemoveAt(dataIndex);
  586. }
  587. /// <summary>
  588. /// 更新类目数据
  589. /// </summary>
  590. /// <param name="index"></param>
  591. /// <param name="category"></param>
  592. public void UpdateData(int index, string category)
  593. {
  594. if (index >= 0 && index < m_Data.Count)
  595. {
  596. m_Data[index] = category;
  597. SetComponentDirty();
  598. }
  599. }
  600. /// <summary>
  601. /// 添加图标
  602. /// </summary>
  603. /// <param name="icon"></param>
  604. public void AddIcon(Sprite icon)
  605. {
  606. if (maxCache > 0)
  607. {
  608. while (m_Icons.Count > maxCache)
  609. {
  610. m_Icons.RemoveAt(m_InsertDataToHead ? m_Icons.Count - 1 : 0);
  611. }
  612. }
  613. if (m_InsertDataToHead) m_Icons.Insert(0, icon);
  614. else m_Icons.Add(icon);
  615. SetAllDirty();
  616. }
  617. /// <summary>
  618. /// 更新图标
  619. /// </summary>
  620. /// <param name="index"></param>
  621. /// <param name="icon"></param>
  622. public void UpdateIcon(int index, Sprite icon)
  623. {
  624. if (index >= 0 && index < m_Icons.Count)
  625. {
  626. m_Icons[index] = icon;
  627. SetComponentDirty();
  628. }
  629. }
  630. /// <summary>
  631. /// 获得指定索引的类目数据
  632. /// </summary>
  633. /// <param name="index"></param>
  634. /// <returns></returns>
  635. public string GetData(int index)
  636. {
  637. if (index >= 0 && index < m_Data.Count)
  638. return m_Data[index];
  639. else
  640. return null;
  641. }
  642. /// <summary>
  643. /// 获得在dataZoom范围内指定索引的类目数据
  644. /// </summary>
  645. /// <param name="index">类目数据索引</param>
  646. /// <param name="dataZoom">区域缩放</param>
  647. /// <returns></returns>
  648. public string GetData(int index, DataZoom dataZoom)
  649. {
  650. var showData = GetDataList(dataZoom);
  651. if (index >= 0 && index < showData.Count)
  652. return showData[index];
  653. else
  654. return "";
  655. }
  656. public Sprite GetIcon(int index)
  657. {
  658. if (index >= 0 && index < m_Icons.Count)
  659. return m_Icons[index];
  660. else
  661. return null;
  662. }
  663. /// <summary>
  664. /// 获得值在坐标轴上的距离
  665. /// </summary>
  666. /// <param name="value"></param>
  667. /// <param name="axisLength"></param>
  668. /// <returns></returns>
  669. public float GetDistance(double value, float axisLength)
  670. {
  671. if (context.minMaxRange == 0)
  672. return 0;
  673. if (IsCategory() && boundaryGap)
  674. {
  675. var each = axisLength / data.Count;
  676. return (float) (each * (value + 0.5f));
  677. }
  678. else
  679. {
  680. return axisLength * (float) ((value - context.minValue) / context.minMaxRange);
  681. }
  682. }
  683. public float GetValueLength(double value, float axisLength)
  684. {
  685. if (context.minMaxRange > 0)
  686. {
  687. return axisLength * ((float) (value / context.minMaxRange));
  688. }
  689. else
  690. {
  691. return 0;
  692. }
  693. }
  694. /// <summary>
  695. /// 获得指定区域缩放的类目数据列表
  696. /// </summary>
  697. /// <param name="dataZoom">区域缩放</param>
  698. /// <returns></returns>
  699. internal List<string> GetDataList(DataZoom dataZoom)
  700. {
  701. if (dataZoom != null && dataZoom.enable && dataZoom.IsContainsAxis(this))
  702. {
  703. UpdateFilterData(dataZoom);
  704. return context.filterData;
  705. }
  706. else
  707. {
  708. return m_Data.Count > 0 ? m_Data : context.runtimeData;
  709. }
  710. }
  711. internal List<string> GetDataList()
  712. {
  713. return m_Data.Count > 0 ? m_Data : context.runtimeData;
  714. }
  715. /// <summary>
  716. /// 更新dataZoom对应的类目数据列表
  717. /// </summary>
  718. /// <param name="dataZoom"></param>
  719. internal void UpdateFilterData(DataZoom dataZoom)
  720. {
  721. if (dataZoom != null && dataZoom.enable && dataZoom.IsContainsAxis(this))
  722. {
  723. var data = GetDataList();
  724. context.UpdateFilterData(data, dataZoom);
  725. }
  726. }
  727. /// <summary>
  728. /// 获得类目数据个数
  729. /// </summary>
  730. /// <param name="dataZoom"></param>
  731. /// <returns></returns>
  732. internal int GetDataCount(DataZoom dataZoom)
  733. {
  734. return IsCategory() ? GetDataList(dataZoom).Count : 0;
  735. }
  736. /// <summary>
  737. /// 更新刻度标签文字
  738. /// </summary>
  739. /// <param name="dataZoom"></param>
  740. internal void UpdateLabelText(float coordinateWidth, DataZoom dataZoom, bool forcePercent)
  741. {
  742. for (int i = 0; i < context.labelObjectList.Count; i++)
  743. {
  744. if (context.labelObjectList[i] != null)
  745. {
  746. var text = AxisHelper.GetLabelName(this, coordinateWidth, i, context.minValue, context.maxValue, dataZoom, forcePercent);
  747. context.labelObjectList[i].SetText(text);
  748. }
  749. }
  750. }
  751. internal Vector3 GetLabelObjectPosition(int index)
  752. {
  753. if (context.labelObjectList != null && index < context.labelObjectList.Count)
  754. return context.labelObjectList[index].GetPosition();
  755. else
  756. return Vector3.zero;
  757. }
  758. internal void UpdateMinMaxValue(double minValue, double maxValue)
  759. {
  760. context.minValue = minValue;
  761. context.maxValue = maxValue;
  762. double tempRange = maxValue - minValue;
  763. if (context.minMaxRange != tempRange)
  764. {
  765. context.minMaxRange = tempRange;
  766. if (type == Axis.AxisType.Value && interval > 0)
  767. {
  768. SetComponentDirty();
  769. }
  770. }
  771. }
  772. public float GetLogValue(double value)
  773. {
  774. if (value <= 0 || value == 1)
  775. return 0;
  776. else
  777. return logBaseE ? (float) Math.Log(value) : (float) Math.Log(value, logBase);
  778. }
  779. public double GetLogMinIndex()
  780. {
  781. return logBaseE ?
  782. Math.Log(context.minValue) :
  783. Math.Log(context.minValue, logBase);
  784. }
  785. public double GetLogMaxIndex()
  786. {
  787. return logBaseE ?
  788. Math.Log(context.maxValue) :
  789. Math.Log(context.maxValue, logBase);
  790. }
  791. public double GetLabelValue(int index)
  792. {
  793. if (index < 0)
  794. return context.minValue;
  795. else if (index > context.labelValueList.Count - 1)
  796. return context.maxValue;
  797. else
  798. return context.labelValueList[index];
  799. }
  800. public double GetLastLabelValue()
  801. {
  802. if (context.labelValueList.Count > 0)
  803. return context.labelValueList[context.labelValueList.Count - 1];
  804. else
  805. return 0;
  806. }
  807. public void UpdateZeroOffset(float axisLength)
  808. {
  809. context.offset = context.minValue > 0 || context.minMaxRange == 0 ?
  810. 0 :
  811. (context.maxValue < 0 ?
  812. axisLength :
  813. (float) (Math.Abs(context.minValue) * (axisLength /
  814. (Math.Abs(context.minValue) + Math.Abs(context.maxValue))))
  815. );
  816. }
  817. }
  818. }