0

I've generated a single long string of invoices formatted as required. I now need to print them out on a printer with one invoice displayed per page.

I've looked at these tutorials/help as well as some code I was:

https://msdn.microsoft.com/en-us/library/cwbe712d%28v=vs.110%29.aspx

https://social.msdn.microsoft.com/Forums/en-US/93e54c4f-fd07-4b60-9922-102439292f52/c-printing-a-string-to-printer?forum=csharplanguage

I've primarily followed the second one.

What I've ended up with is (Working VS C# project with a single form with a single button):

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Drawing.Printing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace TestPrint
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private string stringToPrint = "Hello\r\nWorld\r\n\r\n<<< Page >>>World\r\nHello";

        private void button1_Click(object sender, EventArgs e)
        {

            //  Convert string to strings
            string[] seperatingChars = { "<<< Page >>>" };
            string[] printString = stringToPrint.Split(seperatingChars, System.StringSplitOptions.RemoveEmptyEntries);

            //  Connect to the printer
            PrintDocument printDocument1 = new PrintDocument();     // Stream to the printer

            //  Send to printer (reference: https://social.msdn.microsoft.com/Forums/en-US/93e54c4f-fd07-4b60-9922-102439292f52/c-printing-a-string-to-printer?forum=csharplanguage)
            foreach (string s in printString)
            {
                printDocument1.PrintPage += delegate (object sender1, PrintPageEventArgs e1)
                {
                    e1.Graphics.DrawString(s, new Font("Times New Roman", 12), new SolidBrush(Color.Black),
                    new RectangleF(0, 0, printDocument1.DefaultPageSettings.PrintableArea.Width,
                    printDocument1.DefaultPageSettings.PrintableArea.Height));
                };
                try
                {
                    printDocument1.Print();
                    printDocument1.Dispose();
                }
                catch (Exception ex)
                {
                    throw new Exception("Exception Occured While Printing", ex);
                }
            }
        }
    }
}

I break the long string into it's parts that I want printed to each individual page and then sent that to the printer. This works fine for the first invoice/page but after that it just adds each page on to image of the first (I added the printDocument1.Dispose(); to try and sort that but that didn't work).

What I want to know is how can I print the string as a single string while keeping one invoice per page.

EDIT: How do I generate the string as multi-page image for the printer?

  • Have you tried putting the PrintDocument printDocument1 = new PrintDocument(); inside the foreach loop? – Dr. Stitch Apr 13 '16 at 06:48
  • That worked. I'm still getting it as an output of multiple files (printing to PDF not a printer) and I would like it to go to a single file. It won't make any difference when printing to a printer of course but it makes a difference in time when printing to a file - if it can be done with what I have. –  Apr 13 '16 at 07:20
  • So you just want to print the strings to one file? Then you need to generate the document before sending it to the printer. At the moment, you're generating the document at the point of printing. Sounds like you need to take your `printDocument1.Print();` out the for loop and do something else inside of there and then finally call your `printDocument1.Print();` – Draken Apr 13 '16 at 07:24
  • Yes, I think that would be a better way to do it but how do I generate it first? –  Apr 13 '16 at 07:35

2 Answers2

0

EDIT: complete solution.

 public partial class Form1 : Form
    {
        //string to print
        private string stringToPrint = "Hello\r\nWorld\r\n\r\n<<< Page >>>World\r\nHello";
        //list of strings/pages
        private List<string> pageData = new List<string>();
        //enumerator for iteration thru "pages"
        private IEnumerator pageEnumerator;
        //print document
        PrintDocument printDocument1;

        public Form1()
        {
            InitializeComponent();

        }

        private void button1_Click(object sender, EventArgs e)
        {

            //  Connect to the printer
            printDocument1 = new PrintDocument();
            //handle events
            printDocument1.BeginPrint += new PrintEventHandler(BeginPrint);
            printDocument1.PrintPage += new PrintPageEventHandler(PrintPage);


            try
            {
                //do print
                printDocument1.Print();
                printDocument1.Dispose();
            }
            catch (Exception ex)
            {
                throw new Exception("Exception Occured While Printing", ex);
            }

        }

        void BeginPrint(object sender, PrintEventArgs e)
        {
            //  Convert string to strings
            string[] seperatingChars = { "<<< Page >>>" };

            //generate some dummy strings to print
            pageData = stringToPrint.Split(seperatingChars, System.StringSplitOptions.RemoveEmptyEntries).ToList();

            // get enumerator for dummy strings
            pageEnumerator = pageData.GetEnumerator();

            //position to first string to print (i.e. first page)
            pageEnumerator.MoveNext(); 
        }

        private void PrintPage(object sender, PrintPageEventArgs e)
        {
            //define font, brush, and print area
            Font font = new Font("Times New Roman", 12);
            Brush brush = Brushes.Black;
            RectangleF area = new RectangleF(0, 0, printDocument1.DefaultPageSettings.PrintableArea.Width,
                    printDocument1.DefaultPageSettings.PrintableArea.Height);

            //print current page
            e.Graphics.DrawString(pageEnumerator.Current.ToString(), font, brush, area);

            // advance enumerator to determine if we have more pages.
            e.HasMorePages = pageEnumerator.MoveNext();

        }


    }
Nino
  • 6,931
  • 2
  • 27
  • 42
  • Um, yes, sorry. `HasMorePages` is never set to `false`, so it tries to print forever. Take a look at this solution, looks like it could help in your case: http://stackoverflow.com/questions/10608938/form-feed-in-c-sharp-printing – Nino Apr 13 '16 at 07:44
  • Ok, I've edited my response with solution. It is based on [this answer](http://stackoverflow.com/questions/10608938/form-feed-in-c-sharp-printing). Document is prepared in begin print event. – Nino Apr 13 '16 at 08:48
-3

From what I can see, this line is causing the problem that you described:

printDocument1.PrintPage += delegate(object sender1,
PrintPageEventArgs e1)

Try changing it to:

printDocument1.PrintPage = delegate(object sender1,
PrintPageEventArgs e1)
StepUp
  • 36,391
  • 15
  • 88
  • 148
8934904
  • 16
  • 2
  • Removing the + from the += gives me an error on the PrintPage and it won't compile. –  Apr 13 '16 at 07:12
  • They're using that to subscribe to an event, that's standard C# notation and won't be causing the issue – Draken Apr 13 '16 at 07:15
  • thats not an issue, is how you subscribe events. Please delete this false answer – acostela Apr 13 '16 at 12:12