2009-08-12 9 views
5

Mam FlowDocument, który różni się wysokością ze względu na ItemsControl w BlockUIContainer. W niektórych przypadkach ItemsControl wykracza poza wysokość strony. Czy istnieje sposób na skalowanie FlowDocument do strony (8,5 "X 11") tuż przed drukowaniem, jeśli jest to konieczne?WPF FlowDocument Scale to Fit Page

Od teraz, FlowDocument nazwie „doc” oraz sposób drukowania używam jest:

private void Print_Click(object sender, RoutedEventArgs e) 
    { 

     PrintDialog pd = new PrintDialog(); 
     doc.PageHeight = pd.PrintableAreaHeight; 
     doc.PageWidth = pd.PrintableAreaWidth; 
     doc.ColumnGap = 0; 
     doc.ColumnWidth = pd.PrintableAreaWidth; 
     IDocumentPaginatorSource dps = doc; 
     pd.PrintDocument(dps.DocumentPaginator, "Sheet"); 
    } 
+0

Czy znalazłeś rozwiązanie tego problemu? –

+0

Nie, nadal nie mam. Musiałem załatwić i umieścić wrappanel wewnątrz kontroli przedmiotów, czego właśnie chciałem uniknąć od samego początku. – Johnathan1

Odpowiedz

3

Wiem, że to trochę późno, ale tutaj jest rozwiązanie wymyśliłem.

Najpierw tworzymy opakowanie, które wygeneruje dla nas strony dokumentu. Każda strona będzie miała zastosowaną transformację skali przed jej zwrotem.

public class FittedDocumentPaginator : DocumentPaginator 
{ 
    public DocumentPaginator Base { get; private set; } 
    public double Scale { get; private set; } 
    private readonly ScaleTransform _sTransform; 

    public FittedDocumentPaginator(DocumentPaginator baseDp, double scale) 
    { 
     if (baseDp == null) 
      throw new ArgumentNullException("baseDp"); 

     Base = baseDp; 
     Scale = scale; 
     _sTransform = new ScaleTransform(scale, scale); 
    } 

    public override DocumentPage GetPage(int pageNumber) 
    { 
     var page = Base.GetPage(pageNumber); 
     ((ContainerVisual)page.Visual).Transform = _sTransform; 

     return page; 
    } 

    public override bool IsPageCountValid 
    { 
     get { return Base.IsPageCountValid; } 
    } 

    public override int PageCount 
    { 
     get { return Base.PageCount; } 
    } 

    public override Size PageSize 
    { 
     get { return Base.PageSize; } 
     set { Base.PageSize = value; } 
    } 

    public override IDocumentPaginatorSource Source 
    { 
     get { return Base.Source; } 
    } 
} 

Używanie go jest dość prosta:

private void PrintDocument(PrintDialog pd, FlowDocument document, double scale, string title) 
    { 
     DocumentPaginator dp = ((IDocumentPaginatorSource)document).DocumentPaginator; 
     FittedDocumentPaginator fdp = new FittedDocumentPaginator(dp, scale); 

     pd.PrintDocument(fdp, title); 
    } 

Jeśli jesteś zainteresowany, tutaj jest jak ustaliliśmy skalę. W naszym przypadku dokument został rozszerzony poza szerokość strony, ale można go łatwo zmodyfikować w celu dostosowania do wysokości strony.

private void Print(FlowDocument document, string title, double documentWidth) 
    { 
     var pd = new PrintDialog(); 

     if (pd.ShowDialog() == true) 
     { 
      // Set the printing margins. 
      Thickness pageMargins = document.PagePadding; 
      document.PagePadding = new Thickness(15.0); 

      // In our case, the document's width is NaN so we have to navigate the visual tree to get the ActualWidth, which is represented by 'documentWidth'. 
      double scale = documentWidth/pd.PrintableAreaWidth; 

      if (scale < 1.0) 
      { 
       // The report fits on the page just fine. Don't scale. 
       scale = 1.0; 
      } 

      double invScale = 1/scale; 

      document.PageHeight = pd.PrintableAreaHeight * scale; 
      document.PageWidth = pd.PrintableAreaWidth * scale; 

      DocumentPaginator dp = ((IDocumentPaginatorSource)document).DocumentPaginator; 
      FittedDocumentPaginator fdp = new FittedDocumentPaginator(dp, invScale); 

      pd.PrintDocument(fdp, title); 

      // Restore the original values so the GUI isn't altered. 
      document.PageHeight = Double.NaN; 
      document.PageWidth = Double.NaN; 
      document.PagePadding = pageMargins; 
     } 
    }