2013-06-17 1 views
3

내 요구 사항은 10 페이지 (말)가있는 xps 문서를 만드는 것입니다. 다음 코드를 사용하여 xps 문서를 만듭니다. 이것을 봐주세요.xps에서 고정 문서에 여러 fpages를 추가하는 방법은 무엇입니까?

// Create the new document 
     XpsDocument xd = new XpsDocument("D:\\9780545325653.xps", FileAccess.ReadWrite); 

     IXpsFixedDocumentSequenceWriter xdSW = xd.AddFixedDocumentSequence(); 

     IXpsFixedDocumentWriter xdW = xdSW.AddFixedDocument(); 

     IXpsFixedPageWriter xpW = xdW.AddFixedPage(); 

      fontURI = AddFontResourceToFixedPage(xpW, @"D:\arial.ttf"); 

      image = AddJpegImageResourceToFixedPage(xpW, @"D:\Single content\20_1.jpg"); 

      StringBuilder pageContents = new StringBuilder(); 

      pageContents.Append(ReadFile(@"D:\Single content\20.fpage\20.fpage", i)); 

      xmlWriter = xpW.XmlWriter; 
      xmlWriter.WriteRaw(pageContents.ToString());    
     } 
     xmlWriter.Close(); 
     xpW.Commit(); 

     // Commit the fixed document 
     xdW.Commit(); 
     // Commite the fixed document sequence writer 
     xdSW.Commit(); 
     // Commit the XPS document itself 
     xd.Close(); 

    } 

    private static string AddFontResourceToFixedPage(IXpsFixedPageWriter pageWriter, String fontFileName) 
    { 
     string fontUri = ""; 
     using (XpsFont font = pageWriter.AddFont(false)) 
     { 
      using (Stream dstFontStream = font.GetStream()) 
      using (Stream srcFontStream = File.OpenRead(fontFileName)) 
      { 
       CopyStream(srcFontStream, dstFontStream); 

       // commit font resource to the package file 
       font.Commit(); 
      } 
      fontUri = font.Uri.ToString(); 
     } 
     return fontUri; 
    } 

    private static Int32 CopyStream(Stream srcStream, Stream dstStream) 
    { 
     const int size = 64 * 1024; // copy using 64K buffers 
     byte[] localBuffer = new byte[size]; 
     int bytesRead; 
     Int32 bytesMoved = 0; 

     // reset stream pointers 
     srcStream.Seek(0, SeekOrigin.Begin); 
     dstStream.Seek(0, SeekOrigin.Begin); 

     // stream position is advanced automatically by stream object 
     while ((bytesRead = srcStream.Read(localBuffer, 0, size)) > 0) 
     { 
      dstStream.Write(localBuffer, 0, bytesRead); 
      bytesMoved += bytesRead; 
     } 
     return bytesMoved; 
    } 

    private static string ReadFile(string filePath,int i) 
    { 

     FileStream fs = new FileStream(filePath, FileMode.Open, FileAccess.ReadWrite); 

     StringBuilder sb = new StringBuilder(); 
     using (StreamReader sr = new StreamReader(fs)) 
     { 
      String line; 
      // Read and display lines from the file until the end of 
      // the file is reached. 
      while ((line = sr.ReadLine()) != null) 
      { 
       sb.AppendLine(line); 
      } 
     } 
     string allines = sb.ToString(); 

     //allines = allines.Replace("FontUri=\"/Resources/f7728e4c-2606-4fcb-b963-d2d3f52b013b.odttf\"", "FontUri=\"" + fontURI + "\" "); 

     //XmlReader xmlReader = XmlReader.Create(fs, new XmlReaderSettings() { IgnoreComments = true }); 

     XMLSerializer serializer = new XMLSerializer(); 

     FixedPage fp = (FixedPage)serializer.DeSerialize(allines, typeof(FixedPage)); 

     foreach (Glyphs glyph in fp.lstGlyphs) 
     { 
      glyph.FontUri = fontURI; 
     } 

     fp.Path.PathFill.ImageBrush.ImageSource = image; 

     fs.Close(); 

     string fpageString = serializer.Serialize(fp); 



     return fpageString; 
    } 

    private static string AddJpegImageResourceToFixedPage(IXpsFixedPageWriter pageWriter, String imgFileName) 
    { 
     XpsImage image = pageWriter.AddImage("image/jpeg"); 
     using (Stream dstImageStream = image.GetStream()) 
     using (Stream srcImageStream = File.OpenRead(imgFileName)) 
     { 
      CopyStream(srcImageStream, dstImageStream); // commit image resource to the package file 
      //image.Commit(); 
     } 

     return image.Uri.ToString(); 

    } 

표시되는 경우 단일 이미지 및 단일 fpage를 전달하여 xps 문서를 만들었을 것입니다. 여러 페이지가있는 xps 문서를 만들려면 여러 fpages 목록 및 이미지 목록을 전달하고 싶습니다 ..?

답변

4

당신은 가장 격렬하게 어려운 방식으로 이것을하고 있습니다. 나는 게으른 남자의 길을 선택하는 것이 좋습니다.

XpsDocument가 0보다 많거나 많음을 포함하는 FixedDocuments을 포함하는 FixedDocumentSequence에있는 래퍼임을 깨닫습니다. FixedPages. XML을 작성하지 않고도이 모든 유형을 생성, 조작 및 결합 할 수 있습니다.

정말로해야 할 일은 필요한 콘텐츠가있는 FixedPage를 만드는 것입니다. 다음은 그 예입니다.

static FixedPage CreateFixedPage(Uri imageSource) 
{ 
    FixedPage fp = new FixedPage(); 
    fp.Width = 320; 
    fp.Height = 240; 
    Grid g = new Grid(); 
    g.HorizontalAlignment = System.Windows.HorizontalAlignment.Center; 
    g.VerticalAlignment = System.Windows.VerticalAlignment.Center; 
    fp.Children.Add(g); 
    Image img = new Image 
    { 
     UriSource = imageSource, 
    }; 
    g.Children.Add(image); 
    return fp; 
} 

이것은 모두 WPF입니다. 주어진 Uri에서로드 된 이미지가 포함 된 Grid를 루트로 갖는 FixedPage를 만듭니다. 이미지는 그리드의 사용 가능한 공간을 채우기 위해 늘어납니다. 또는 원하는대로 할 수 있습니다. 템플릿을 UserControl로 생성하고, 텍스트를 그 자체 내에 배치합니다.

다음으로 고정 된 페이지 묶음을 XpsDocument에 추가하면됩니다. 믿을 수 없을만큼 힘들어하므로주의 깊게 읽으십시오.

public void WriteAllPages(XpsDocument document, IEnumerable<FixedPage> pages) 
{ 

    var writer = XpsDocument.CreateXpsDocumentWriter(document); 
    foreach(var page in pages) 
     writer.Write(page); 
} 

그리고 그게 전부입니다. 페이지를 만들어 문서에 추가하십시오. 끝난.

+0

+1 엄청나게 어려운 일을 거부하여 시간을 절약 해주었습니다. :) – WiiMaxx

+0

writer.Write (page)는 "Writer Writer가 작성되어 더 이상의 쓰기 요청을 처리 할 수 ​​없습니다." – wischi

+0

@wischi : 아니요. 프로토 타입에 최소 재 작성을 작성하고 다시 발생하는지 확인하십시오. 그렇다면 repro의 코드를 사용하여 질문하십시오. 그렇지 않은 경우 플러시 또는 닫기 또는 처분과 같이 작가에게 잘못된 행동을하고있는 것입니다. – Will

관련 문제