PreparedPagePostprocessor.cs 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190
  1. using System;
  2. using System.Collections.Generic;
  3. using System.Collections;
  4. namespace FastReport.Preview
  5. {
  6. internal class PreparedPagePosprocessor
  7. {
  8. private Dictionary<string, List<TextObjectBase>> duplicates;
  9. private Dictionary<int, Base> bands;
  10. int iBand;
  11. private void ProcessDuplicates(TextObjectBase obj)
  12. {
  13. if (duplicates.ContainsKey(obj.Name))
  14. {
  15. List<TextObjectBase> list = duplicates[obj.Name];
  16. TextObjectBase lastObj = list[list.Count - 1];
  17. bool isDuplicate = true;
  18. // compare Text
  19. if (obj.Text != lastObj.Text)
  20. isDuplicate = false;
  21. else
  22. {
  23. float lastObjBottom = (lastObj.Parent as ReportComponentBase).Bottom;
  24. float objTop = (obj.Parent as ReportComponentBase).Top;
  25. if (Math.Abs(objTop - lastObjBottom) > 0.5f)
  26. isDuplicate = false;
  27. }
  28. if (isDuplicate)
  29. {
  30. list.Add(obj);
  31. }
  32. else
  33. {
  34. // close duplicates
  35. CloseDuplicates(list);
  36. // add new obj
  37. list.Clear();
  38. list.Add(obj);
  39. }
  40. }
  41. else
  42. {
  43. List<TextObjectBase> list = new List<TextObjectBase>();
  44. list.Add(obj);
  45. duplicates.Add(obj.Name, list);
  46. }
  47. }
  48. private void CloseDuplicates()
  49. {
  50. foreach (List<TextObjectBase> list in duplicates.Values)
  51. {
  52. CloseDuplicates(list);
  53. }
  54. }
  55. private void CloseDuplicates(List<TextObjectBase> list)
  56. {
  57. if (list.Count == 0)
  58. return;
  59. Duplicates duplicates = list[0].Duplicates;
  60. switch (duplicates)
  61. {
  62. case Duplicates.Clear:
  63. CloseDuplicatesClear(list);
  64. break;
  65. case Duplicates.Hide:
  66. CloseDuplicatesHide(list);
  67. break;
  68. case Duplicates.Merge:
  69. CloseDuplicatesMerge(list);
  70. break;
  71. }
  72. }
  73. private void CloseDuplicatesClear(List<TextObjectBase> list)
  74. {
  75. for (int i = 0; i < list.Count; i++)
  76. {
  77. if (i > 0)
  78. list[i].Text = "";
  79. }
  80. }
  81. private void CloseDuplicatesHide(List<TextObjectBase> list)
  82. {
  83. for (int i = 0; i < list.Count; i++)
  84. {
  85. if (i > 0)
  86. list[i].Dispose();
  87. }
  88. }
  89. private void CloseDuplicatesMerge(List<TextObjectBase> list)
  90. {
  91. float top = list[0].AbsTop;
  92. // dispose all objects except the last one
  93. for (int i = 0; i < list.Count - 1; i++)
  94. {
  95. list[i].Dispose();
  96. }
  97. // stretch the last object
  98. TextObjectBase lastObj = list[list.Count - 1];
  99. float delta = lastObj.AbsTop - top;
  100. lastObj.Top -= delta;
  101. lastObj.Height += delta;
  102. }
  103. public void Postprocess(ReportPage page)
  104. {
  105. page.ExtractMacros();
  106. ObjectCollection allObjects = page.AllObjects;
  107. for (int i = 0; i < allObjects.Count; i++)
  108. {
  109. Base c = allObjects[i];
  110. if (c.Report == null)
  111. c.SetReport(page.Report);
  112. c.ExtractMacros();
  113. if (c is BandBase)
  114. (c as BandBase).UpdateWidth();
  115. if (c is TextObjectBase && (c as TextObjectBase).Duplicates != Duplicates.Show)
  116. {
  117. ProcessDuplicates(c as TextObjectBase);
  118. }
  119. }
  120. CloseDuplicates();
  121. }
  122. public PreparedPagePosprocessor()
  123. {
  124. duplicates = new Dictionary<string, List<TextObjectBase>>();
  125. bands = new Dictionary<int, Base>();
  126. iBand = 0;
  127. }
  128. public void PostprocessUnlimited(PreparedPage preparedPage, ReportPage page)
  129. {
  130. bool flag = false;
  131. int i = 0;
  132. foreach (Base b in preparedPage.GetPageItems(page, true))
  133. {
  134. foreach (Base c in b.AllObjects)
  135. if (c is TextObjectBase && (c as TextObjectBase).Duplicates != Duplicates.Show)
  136. {
  137. ProcessDuplicates(c as TextObjectBase);
  138. flag = true;//flag for keep in dictionary
  139. }
  140. i++;
  141. if (flag)
  142. {
  143. b.ExtractMacros();
  144. bands[i-1] = b;
  145. }
  146. else
  147. {
  148. b.Dispose();
  149. }
  150. }
  151. CloseDuplicates();
  152. }
  153. public Base PostProcessBandUnlimitedPage(Base band)
  154. {
  155. if(bands.ContainsKey(iBand))
  156. {
  157. Base replaceBand = bands[iBand];
  158. Base parent = band.Parent;
  159. band.Parent = null;
  160. replaceBand.Parent = parent;
  161. band.Dispose();
  162. iBand++;
  163. return replaceBand;
  164. }
  165. band.ExtractMacros();
  166. iBand++;
  167. return band;
  168. }
  169. }
  170. }