2 * Copyright (C) 2013 FooProject
\r
3 * * This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by
\r
4 * the Free Software Foundation; either version 3 of the License, or (at your option) any later version.
\r
6 * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
\r
7 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
\r
9 You should have received a copy of the GNU General Public License along with this program. If not, see <http://www.gnu.org/licenses/>.
\r
12 using Windows.Graphics.Display;
\r
13 using Windows.Graphics.Printing;
\r
14 using System.Runtime.InteropServices;
\r
16 using FooEditEngine.Metro;
\r
18 namespace FooEditEngine
\r
23 public sealed class ParseCommandEventArgs
\r
28 public int PageNumber;
\r
30 /// ページ範囲内で許容されている最大の番号
\r
32 public int MaxPageNumber;
\r
36 public string Original;
\r
40 /// <param name="nowPage">印刷中のページ番号</param>
\r
41 /// <param name="maxPage">印刷すべき最大のページ番号</param>
\r
42 /// <param name="org">処理前の文字列</param>
\r
43 public ParseCommandEventArgs(int nowPage, int maxPage, string org)
\r
45 this.PageNumber = nowPage;
\r
46 this.MaxPageNumber = maxPage;
\r
47 this.Original = org;
\r
54 /// <param name="sender">送信元のクラス</param>
\r
55 /// <param name="e">イベントデータ</param>
\r
56 /// <returns>処理後の文字列</returns>
\r
57 public delegate string ParseCommandHandler(object sender, ParseCommandEventArgs e);
\r
60 sealed class PrintableViewFactory
\r
62 Windows.UI.Color foreground, comment, keyword1, keyword2, literal, url;
\r
66 LineBreakMethod lineBreakMethod;
\r
67 int lineBreakCharCount, tabCount;
\r
69 IHilighter hilighter;
\r
72 public PrintableViewFactory(FooTextBox textbox,Padding padding)
\r
74 this.foreground = textbox.Foreground;
\r
75 this.comment = textbox.Comment;
\r
76 this.keyword1 = textbox.Keyword1;
\r
77 this.keyword2 = textbox.Keyword2;
\r
78 this.literal = textbox.Literal;
\r
79 this.url = textbox.URL;
\r
80 this.fontName = textbox.FontFamily.Source;
\r
81 this.fontSize = textbox.FontSize;
\r
82 this.tabCount = textbox.TabChars;
\r
83 this.document = new Document(textbox.Document);
\r
84 this.lineBreakMethod = textbox.LineBreakMethod;
\r
85 this.lineBreakCharCount = textbox.LineBreakCharCount;
\r
86 this.drawLineNumber = textbox.DrawLineNumber;
\r
87 this.urlMark = textbox.MarkURL;
\r
88 this.hilighter = textbox.Hilighter;
\r
89 this.displayDpi = DisplayInformation.GetForCurrentView().LogicalDpi;
\r
90 this.padding = padding;
\r
91 this.EnableHilight = true;
\r
93 public D2DRenderBase CreateRender(PrintPageDescription pagedesc, IPrintDocumentPackageTarget docPackageTarget)
\r
95 D2DRenderBase render;
\r
96 Size size = new Size(pagedesc.ImageableRect.Width, pagedesc.ImageableRect.Height);
\r
97 render = new D2DPrintRender(this.fontName, this.fontSize, size, Math.Min(pagedesc.DpiX, pagedesc.DpiY), docPackageTarget);
\r
98 render.Foreground = this.foreground;
\r
99 render.Comment = this.comment;
\r
100 render.Keyword1 = this.keyword1;
\r
101 render.Keyword2 = this.keyword2;
\r
102 render.Literal = this.literal;
\r
103 render.Url = this.url;
\r
106 public D2DPrintPreviewRender CreateRender(PrintPageDescription pagedesc)
\r
108 D2DPrintPreviewRender render;
\r
109 Size size = new Size(pagedesc.ImageableRect.Width, pagedesc.ImageableRect.Height);
\r
110 render = new D2DPrintPreviewRender(this.fontName, this.fontSize, size, this.displayDpi);
\r
111 render.Foreground = this.foreground;
\r
112 render.Comment = this.comment;
\r
113 render.Keyword1 = this.keyword1;
\r
114 render.Keyword2 = this.keyword2;
\r
115 render.Literal = this.literal;
\r
116 render.Url = this.url;
\r
119 public PrintableView CreateView(PrintPageDescription pagedesc, D2DRenderBase render, string header, string footer)
\r
121 PrintableView view = new PrintableView(this.document, (IPrintableTextRender)render,padding);
\r
122 view.TabStops = this.tabCount;
\r
123 view.LineBreak = this.lineBreakMethod == LineBreakMethod.None ? LineBreakMethod.PageBound : this.lineBreakMethod;
\r
124 view.LineBreakCharCount = this.lineBreakCharCount;
\r
125 view.DrawLineNumber = this.drawLineNumber;
\r
126 view.Header = header;
\r
127 view.Footer = footer;
\r
128 view.UrlMark = this.urlMark;
\r
129 view.PageBound = new Rectangle(pagedesc.ImageableRect.X, pagedesc.ImageableRect.Y, pagedesc.ImageableRect.Width, pagedesc.ImageableRect.Height);
\r
130 view.Hilighter = this.EnableHilight ? this.hilighter : null;
\r
131 view.PerfomLayouts();
\r
136 public bool drawLineNumber
\r
142 public bool EnableHilight
\r
149 sealed class DocumentSource : IPrintDocumentPageSource, IPrintPreviewPageCollection, IPrintDocumentSource,IPrintPreviewSource
\r
151 IPrintPreviewDxgiPackageTarget dxgiPreviewTarget;
\r
152 bool paginateCalled = false;
\r
154 PrintableViewFactory factory;
\r
155 D2DPrintPreviewRender previewRender;
\r
156 PrintableView previewView;
\r
157 int maxPreviePageCount;
\r
159 public ParseCommandHandler ParseHF;
\r
160 public string Header = string.Empty;
\r
161 public string Fotter = string.Empty;
\r
163 public DocumentSource(FooTextBox textbox,Padding padding)
\r
165 this.factory = new PrintableViewFactory(textbox, padding);
\r
168 internal enum SyntaxHilightApplibility
\r
174 [DisplayPrintOptionResourceID("SyntaxHilight")]
\r
175 internal SyntaxHilightApplibility EnableHilight
\r
179 return this.factory.EnableHilight ? SyntaxHilightApplibility.Apply : SyntaxHilightApplibility.NoApply;
\r
183 this.factory.EnableHilight = value == SyntaxHilightApplibility.Apply;
\r
187 internal enum LineNumberVisiblity
\r
193 [DisplayPrintOptionResourceID("ShowLineNumber")]
\r
194 internal LineNumberVisiblity ShowLineNumber
\r
198 return this.factory.drawLineNumber ? LineNumberVisiblity.Visible : LineNumberVisiblity.Hidden;
\r
202 this.factory.drawLineNumber = value == LineNumberVisiblity.Visible;
\r
206 public void GetPreviewPageCollection(IPrintDocumentPackageTarget docPackageTarget, out IPrintPreviewPageCollection docPageCollection)
\r
208 Guid guid = new Guid(PreviewPackageIds.IID_PREVIEWPACKAGETARGET_DXGI);
\r
210 docPackageTarget.GetPackageTarget(guid, guid, out target);
\r
211 this.dxgiPreviewTarget = (IPrintPreviewDxgiPackageTarget)Marshal.GetObjectForIUnknown(target);
\r
212 docPageCollection = (IPrintPreviewPageCollection)this;
\r
215 public void MakeDocument(object printTaskOptions, IPrintDocumentPackageTarget docPackageTarget)
\r
217 PrintTaskOptions options = (PrintTaskOptions)printTaskOptions;
\r
218 PrintPageDescription pagedesc = options.GetPageDescription(1);
\r
220 D2DRenderBase render = this.factory.CreateRender(pagedesc, docPackageTarget);
\r
221 PrintableView view = this.factory.CreateView(pagedesc, render, this.Header, this.Fotter);
\r
223 bool result = false;
\r
224 int currentPage = 0;
\r
228 if(!string.IsNullOrEmpty(this.Header))
\r
229 view.Header = this.ParseHF(this, new ParseCommandEventArgs(currentPage, this.maxPreviePageCount, this.Header));
\r
230 if (!string.IsNullOrEmpty(this.Fotter))
\r
231 view.Footer = this.ParseHF(this, new ParseCommandEventArgs(currentPage, this.maxPreviePageCount, this.Fotter));
\r
233 render.BeginDraw();
\r
234 view.Draw(view.PageBound);
\r
236 result = view.TryPageDown();
\r
244 public void Paginate(uint currentJobPage, object printTaskOptions)
\r
246 PrintTaskOptions options = (PrintTaskOptions)printTaskOptions;
\r
247 PrintPageDescription pagedesc = options.GetPageDescription(currentJobPage);
\r
249 this.imageRect = new Size(pagedesc.ImageableRect.Width, pagedesc.ImageableRect.Height);
\r
251 this.previewRender = this.factory.CreateRender(pagedesc);
\r
252 this.previewView = this.factory.CreateView(pagedesc, this.previewRender, this.Header, this.Fotter);
\r
255 while (!this.previewView.TryPageDown())
\r
258 this.dxgiPreviewTarget.SetJobPageCount(PageCountType.FinalPageCount, (uint)maxPage);
\r
260 this.dxgiPreviewTarget.InvalidatePreview();
\r
262 this.maxPreviePageCount = maxPage;
\r
264 this.paginateCalled = true;
\r
267 public void InvalidatePreview()
\r
269 this.dxgiPreviewTarget.InvalidatePreview();
\r
272 public void MakePage(uint desiredJobPage, float width, float height)
\r
274 if (width <= 0 || height <= 0)
\r
275 throw new COMException("", 0x70057/*E_INVALIDARG*/);
\r
276 if (!this.paginateCalled)
\r
278 if (desiredJobPage == 0xFFFFFFFF)
\r
279 desiredJobPage = 1;
\r
281 this.previewView.TryScroll(0, 0); //元に戻さないとページ番号が変わった時に正しく動作しない
\r
283 for (int i = 1; i < desiredJobPage; i++)
\r
284 this.previewView.TryPageDown();
\r
286 if (!string.IsNullOrEmpty(this.Header))
\r
287 this.previewView.Header = this.ParseHF(this, new ParseCommandEventArgs((int)desiredJobPage, this.maxPreviePageCount, this.Header));
\r
288 if (!string.IsNullOrEmpty(this.Fotter))
\r
289 this.previewView.Footer = this.ParseHF(this, new ParseCommandEventArgs((int)desiredJobPage, this.maxPreviePageCount, this.Fotter));
\r
291 this.previewRender.Resize(width, height);
\r
292 this.previewRender.SetScale((float)(this.previewView.PageBound.Width / width)); //BeginDraw()で倍率が1に戻る
\r
294 this.previewRender.BeginDraw();
\r
295 this.previewView.Draw(this.previewView.PageBound);
\r
296 this.previewRender.EndDraw(this.dxgiPreviewTarget,desiredJobPage);
\r
299 public void Dispose()
\r
301 if (this.previewView != null)
\r
302 this.previewView.Dispose();
\r
303 if (this.previewRender != null)
\r
304 this.previewRender.Dispose();
\r