ReportPrintDocument.cs 7.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198
  1. using System;
  2. using System.Collections.Generic;
  3. using System.Linq;
  4. using System.Web;
  5. using System.Drawing.Printing;
  6. using System.IO;
  7. using Microsoft.Reporting.WebForms;
  8. using System.Drawing.Imaging;
  9. using System.Drawing;
  10. using System.Collections.Specialized;
  11. using System.Text;
  12. using System.Globalization;
  13. namespace EmisTerminal
  14. {
  15. /// <summary>
  16. /// The ReportPrintDocument will print all of the pages of a ServerReport or LocalReport.
  17. /// The pages are rendered when the print document is constructed. Once constructed,
  18. /// call Print() on this class to begin printing.
  19. /// </summary>
  20. public class ReportPrintDocument : PrintDocument
  21. {
  22. private PageSettings m_pageSettings;
  23. private int m_currentPage;
  24. private List<Stream> m_pages = new List<Stream>();
  25. public ReportPrintDocument(ServerReport serverReport)
  26. : this((Report)serverReport)
  27. {
  28. RenderAllServerReportPages(serverReport);
  29. }
  30. public ReportPrintDocument(LocalReport localReport)
  31. : this((Report)localReport)
  32. {
  33. RenderAllLocalReportPages(localReport);
  34. }
  35. private ReportPrintDocument(Report report)
  36. {
  37. // Set the page settings to the default defined in the report
  38. ReportPageSettings reportPageSettings = report.GetDefaultPageSettings();
  39. // The page settings object will use the default printer unless
  40. // PageSettings.PrinterSettings is changed. This assumes there
  41. // is a default printer.
  42. m_pageSettings = new PageSettings();
  43. m_pageSettings.PaperSize = reportPageSettings.PaperSize;
  44. m_pageSettings.Margins = reportPageSettings.Margins;
  45. }
  46. protected override void Dispose(bool disposing)
  47. {
  48. base.Dispose(disposing);
  49. if (disposing)
  50. {
  51. foreach (Stream s in m_pages)
  52. {
  53. s.Dispose();
  54. }
  55. m_pages.Clear();
  56. }
  57. }
  58. protected override void OnBeginPrint(PrintEventArgs e)
  59. {
  60. base.OnBeginPrint(e);
  61. m_currentPage = 0;
  62. }
  63. protected override void OnPrintPage(PrintPageEventArgs e)
  64. {
  65. base.OnPrintPage(e);
  66. Stream pageToPrint = m_pages[m_currentPage];
  67. pageToPrint.Position = 0;
  68. // Load each page into a Metafile to draw it.
  69. using (Metafile pageMetaFile = new Metafile(pageToPrint))
  70. {
  71. Rectangle adjustedRect = new Rectangle(
  72. e.PageBounds.Left - (int)e.PageSettings.HardMarginX,
  73. e.PageBounds.Top - (int)e.PageSettings.HardMarginY,
  74. e.PageBounds.Width,
  75. e.PageBounds.Height);
  76. // Draw a white background for the report
  77. e.Graphics.FillRectangle(Brushes.White, adjustedRect);
  78. // Draw the report content
  79. e.Graphics.DrawImage(pageMetaFile, adjustedRect);
  80. // Prepare for next page. Make sure we haven't hit the end.
  81. m_currentPage++;
  82. e.HasMorePages = m_currentPage < m_pages.Count;
  83. }
  84. }
  85. protected override void OnQueryPageSettings(QueryPageSettingsEventArgs e)
  86. {
  87. e.PageSettings = (PageSettings)m_pageSettings.Clone();
  88. }
  89. private void RenderAllServerReportPages(ServerReport serverReport)
  90. {
  91. try
  92. {
  93. string deviceInfo = CreateEMFDeviceInfo();
  94. // Generating Image renderer pages one at a time can be expensive. In order
  95. // to generate page 2, the server would need to recalculate page 1 and throw it
  96. // away. Using PersistStreams causes the server to generate all the pages in
  97. // the background but return as soon as page 1 is complete.
  98. NameValueCollection firstPageParameters = new NameValueCollection();
  99. firstPageParameters.Add("rs:PersistStreams", "True");
  100. // GetNextStream returns the next page in the sequence from the background process
  101. // started by PersistStreams.
  102. NameValueCollection nonFirstPageParameters = new NameValueCollection();
  103. nonFirstPageParameters.Add("rs:GetNextStream", "True");
  104. string mimeType;
  105. string fileExtension;
  106. Stream pageStream = serverReport.Render("Image", deviceInfo, firstPageParameters, out mimeType, out fileExtension);
  107. // The server returns an empty stream when moving beyond the last page.
  108. while (pageStream.Length > 0)
  109. {
  110. m_pages.Add(pageStream);
  111. pageStream = serverReport.Render("Image", deviceInfo, nonFirstPageParameters, out mimeType, out fileExtension);
  112. }
  113. }
  114. catch (Exception e)
  115. {
  116. throw new Exception("possible missing information :: " + e.Message);
  117. }
  118. }
  119. private void RenderAllLocalReportPages(LocalReport localReport)
  120. {
  121. try
  122. {
  123. string deviceInfo = CreateEMFDeviceInfo();
  124. Warning[] warnings;
  125. localReport.Render("IMAGE", deviceInfo, LocalReportCreateStreamCallback, out warnings);
  126. }
  127. catch (Exception e)
  128. {
  129. throw new Exception("error :: " + e);
  130. }
  131. }
  132. private Stream LocalReportCreateStreamCallback(
  133. string name,
  134. string extension,
  135. Encoding encoding,
  136. string mimeType,
  137. bool willSeek)
  138. {
  139. MemoryStream stream = new MemoryStream();
  140. m_pages.Add(stream);
  141. return stream;
  142. }
  143. private string CreateEMFDeviceInfo()
  144. {
  145. PaperSize paperSize = m_pageSettings.PaperSize;
  146. Margins margins = m_pageSettings.Margins;
  147. // The device info string defines the page range to print as well as the size of the page.
  148. // A start and end page of 0 means generate all pages.
  149. return string.Format(
  150. CultureInfo.InvariantCulture,
  151. "<DeviceInfo><OutputFormat>emf</OutputFormat><StartPage>0</StartPage><EndPage>0</EndPage><MarginTop>{0}</MarginTop><MarginLeft>{1}</MarginLeft><MarginRight>{2}</MarginRight><MarginBottom>{3}</MarginBottom><PageHeight>{4}</PageHeight><PageWidth>{5}</PageWidth></DeviceInfo>",
  152. ToInches(margins.Top + 20),
  153. ToInches(margins.Left),
  154. ToInches(margins.Right),
  155. ToInches(margins.Bottom),
  156. ToInches(paperSize.Height),
  157. ToInches(paperSize.Width));
  158. }
  159. private static string ToInches(int hundrethsOfInch)
  160. {
  161. double inches = hundrethsOfInch / 100.0;
  162. return inches.ToString(CultureInfo.InvariantCulture) + "in";
  163. }
  164. }
  165. }