views:

450

answers:

1

Hello,

I am building a Silverlight 4 application. This application is going to print the contents of an ItemsControl. This ItemsControl uses an ItemTemplate to render the items bound to the control. In all, I have 500 items that are bound to the control.

Oddly, when I attempt to print the ItemsControl, it seems to cut off after a certain point. I cannot tell when it gets cut off. I just know that it gets cut off. I have a hunch it has something to do with virtualization. However, I'm not sure how to overcome this. Currently, I'm printing the ItemsControl like such:

private void printHyperlink_Click(object sender, RoutedEventArgs e)
{
  PrintDocument printDocument = new PrintDocument();
  printDocument.BeginPrint += 
    new EventHandler<BeginPrintEventArgs>(printDocument_BeginPrint);
  printDocument.PrintPage += 
    new EventHandler<PrintPageEventArgs>(printDocument_PrintPage);
  printDocument.EndPrint += 
    new EventHandler<EndPrintEventArgs>(printDocument_EndPrint);

  printDocument.Print("My Items");
}

void printDocument_BeginPrint(object sender, BeginPrintEventArgs e)
{}

void printDocument_PrintPage(object sender, PrintPageEventArgs e)
{ e.PageVisual = myItemsControl; }

void printDocument_EndPrint(object sender, EndPrintEventArgs e)
{}

What am I doing wrong? How do I ensure that all of the items in my ItemsControl are printed as they are rendered?

+1  A: 

The printing APIs don't automatically paginate items in an ItemsControl for you. Furthermore, if you are printing something that is already in the visual tree, the result may get clipped to match what is being rendered in the window at the time of printing.

To print multiple pages, you'll need to:

  • Measure to figure out how many items to show on the page
  • Create visuals that only show the items you want on that page
  • Pass them into your "e.PageVisual"
  • Set e.HasMorePages to be true until you're on the last page

All in all, this can be a fair amount of work. If you're just trying to print an ItemsControl with an ItemTemplate, you'll have to do all of the work above. For slightly more sophisticated scenarios (e.g. adding page numbers, headers/footers, etc.), there's even more work to do.

That said, it's possible to build a library over the simple Silverlight printing APIs that does something like this. I recently blogged a control meant to address exactly this scenario (as well as some of the more sophisticated ones).

http://www.davidpoll.com/2010/04/16/making-printing-easier-in-silverlight-4/

David.Poll