locked
How to export multiple Crystal Reports into one pdf format ? RRS feed

  • Question

  • User-1123701243 posted

    Hi all

    I have a crystal report document called "crdReport1"

    Dim crdReport1 As New ReportDocument
    
    crdReport1.Load(Server.MapPath("~/Reports/rptSales.rpt"))
    
    dim oStream As MemoryStream = crdReport1.ExportToStream(ExportFormatType.PortableDocFormat)
        Response.Clear()
        Response.Buffer = True
        Response.ContentType = "application/pdf"
        Response.BinaryWrite(oStream.ToArray())
        Response.End()
    

    This way It works fine.

    I have another report Called "crdReport2" , I need to display it along with "crdReport1" in a single Report, showing combined pages from both reports.

    I used the the code below but it didn't work:

    Dim crdReport1 As New ReportDocument
    Dim crdReport2 As New ReportDocument
    
    crdReport1.Load(Server.MapPath("~/Reports/rptSales.rpt"))
    crdReport2.Load(Server.MapPath("~/Reports/rptPurchaces.rpt"))
    
    dim st1 As MemoryStream = crdReport1.ExportToStream(ExportFormatType.PortableDocFormat)
    dim st2 As MemoryStream = crdReport2.ExportToStream(ExportFormatType.PortableDocFormat)
        Response.Clear()
        Response.Buffer = True
        Response.ContentType = "application/pdf"
        st2.CopyTo(st1)
        Response.BinaryWrite(st1.ToArray())
        Response.End()

    It shows the first Report only.

    Any Idea. I don't to create pdf files into server.

    Thanx in advance

    Saturday, July 29, 2017 7:02 PM

All replies

  • User1970566204 posted

    I don't to create pdf files into server.

    so, 

    1) create one [empty] Report and create two  details section or Required

    2) drag & drop all existing reports into this section [as sub-report]

    3) pass the all requried data & parameters  (

    cryRpt.Subreports[0].SetDataSource(YOURDATA);

    Monday, July 31, 2017 10:21 AM
  • User-1123701243 posted

    Thank you asyed4u.

    But In my case the number of reports is not fixed. It varies at run time. Sometimes , it could be 1,2,3,..... ,20

    Thats why I can't use the subreport.

    I guess merging streams it ideal in my case but It didn't work fine.

    Tuesday, August 1, 2017 2:15 PM
  • User1970566204 posted

    Hi,

    working  sample  [ c# , using vs 2015 cm]-    [as per your point ..... no more files .in server]

    1)  crystalreports added to sample-project named as "CrystalReport1.rpt , CrystalReport2.rpt"  [ simple design]

    2)  Required Files :  ( merging streams) itext lib :  https://www.nuget.org/packages/iTextSharp   ( command ::  Install-Package iTextSharp -Version 5.5.11)

    3) Required Namespace  

    using System;
    using System.IO;
    using System.Collections.Generic;
    
    using CrystalDecisions.CrystalReports.Engine;
    using CrystalDecisions.Shared;
    
    using iTextSharp.text;
    using iTextSharp.text.pdf;

    Step  1:  Reference code 

            //reploace this event to your related event .......
    protected void Page_Load(object sender, EventArgs e) { //hold the more than one report outputs [bytes] List<byte[]> files = new List<byte[]>(); //for testing purpose LOOP used, //u can change as per your requirement and your report name for (int i = 1; i <= 2; i++) { ReportDocument crdReport1 = new ReportDocument(); //put your related report names..... crdReport1.Load(Server.MapPath(string.Format("CrystalReport{0}.rpt", i))); Stream stream1 = crdReport1.ExportToStream(ExportFormatType.PortableDocFormat); //prepare the "bytes" from "stream" files.Add(PrepareBytes(stream1)); //finally the result added to LIST } Response.Clear(); Response.Buffer = true; Response.ContentType = "application/pdf"; //merge the all reports & show the reports Response.BinaryWrite(MergeReports(files).ToArray()); Response.End(); }

    Step  2:  Reference code  (credits :: https://stackoverflow.com/a/221941 )

     //prepare the report bytes
            private byte[] PrepareBytes(Stream stream)
            {          
                using (MemoryStream ms = new MemoryStream())
                {
                    byte[] buffer = new byte[stream.Length];
                    int read;
                    while ((read = stream.Read(buffer, 0, buffer.Length)) > 0)
                    {
                        ms.Write(buffer, 0, read);
                    }
                   return ms.ToArray();
                }           
            }

    Step  3:  Reference code   ( credits ::  https://stackoverflow.com/a/6780582 )

    //Merge the reports 
            private MemoryStream MergeReports(List<byte[]> files)
            {
                if (files.Count > 1)
                {
                    PdfReader pdfFile;
                    Document doc;
                    PdfWriter pCopy;
                    MemoryStream msOutput = new MemoryStream();
    
                    pdfFile = new PdfReader(files[0]);
    
                    doc = new Document();
                    pCopy = new PdfSmartCopy(doc, msOutput);
    
                    doc.Open();
    
                    for (int k = 0; k < files.Count; k++)
                    {
                        pdfFile = new PdfReader(files[k]);
                        for (int i = 1; i < pdfFile.NumberOfPages + 1; i++)
                        {
                            ((PdfSmartCopy)pCopy).AddPage(pCopy.GetImportedPage(pdfFile, i));
                        }
                        pCopy.FreeReader(pdfFile);
                    }
    
                    pdfFile.Close();
                    pCopy.Close();
                    doc.Close();
    
                    return msOutput;
                }
                else if (files.Count == 1)
                {
                    return new MemoryStream(files[0]);
                }
    
                return null;
            }

     

    so, you can change the logic in step : 1  ( as per you reports )

    Wednesday, August 2, 2017 9:23 AM