c# - UWP 打印预览仅在第一页显示空白页
问题描述
我们目前正在尝试执行一个功能,该功能将在 gridview 中打印图像(StorageFile
存储在模型中。)
我们成功地做到了,但我们遇到了一个我无法弄清楚原因的问题:预览的第一页,而且只有预览!,总是空白。打印(或另存为 PDF)时,它可以完美运行。
出于某种原因,打印预览的加载速度似乎比PrintGenerator.xaml
页面中设置的图像快(我们根据需要使用它来放置图像。)
有人有过吗?我尝试了所有我能想到的谷歌搜索,但没有人遇到过这样的问题。
代码:
MainPage.xaml.cs
(仅相关行)
private void PrintPages_Click(object sender, RoutedEventArgs e)
{
if (CurrentPages.Count == 0)
{
ShowError(title: "No pages to print", msg: "Please add at least one page to allow printing.");
return;
}
// Name: "PrintPages"
AppBarButton barButton = (AppBarButton)sender;
barButton.IsEnabled = false;
PrintImages();
barButton.IsEnabled = true;
}
private async void PrintImages()
{
bottomLoader.Visibility = Visibility.Visible;
if (PrintManager.IsSupported())
{
try
{
await PrintManager.ShowPrintUIAsync();
}
catch (Exception e)
{
ShowError(title: "Printing not supported", msg: "Sorry, printing is not supported on this device.\n" + e.Message);
}
}
else
{
ShowError(title: "Printing not supported", msg: "Sorry, printing is not supported on this device.");
}
bottomLoader.Visibility = Visibility.Collapsed;
}
private PrintManager printManager = PrintManager.GetForCurrentView();
private PrintDocument printDocument = new PrintDocument();
private IPrintDocumentSource printSource;
private List<PrintGenerator> PrintPagePreviews = new List<PrintGenerator>();
private event EventHandler PreviewPagesCreated;
private void RegisterForPrint()
{
printManager.PrintTaskRequested += PrintStart;
printSource = printDocument.DocumentSource;
printDocument.Paginate += PrintPaginate;
printDocument.GetPreviewPage += PrintPreview;
printDocument.AddPages += PrintAddPages;
}
private void PrintStart(PrintManager sender, PrintTaskRequestedEventArgs e)
{
PrintTask task = null;
task = e.Request.CreatePrintTask("Print", sourceRequestedArgs => {
IList<string> displayedOptions = task.Options.DisplayedOptions;
displayedOptions.Clear();
displayedOptions.Add(StandardPrintTaskOptions.Copies);
displayedOptions.Add(StandardPrintTaskOptions.Orientation);
displayedOptions.Add(StandardPrintTaskOptions.MediaSize);
displayedOptions.Add(StandardPrintTaskOptions.Collation);
displayedOptions.Add(StandardPrintTaskOptions.Duplex);
task.Options.MediaSize = PrintMediaSize.NorthAmericaLetter;
task.Options.PrintQuality = PrintQuality.High;
task.IsPreviewEnabled = false;
task.Completed += PrintCompleted;
sourceRequestedArgs.SetSource(printSource);
});
}
private void PrintPaginate(object sender, PaginateEventArgs e)
{
lock (PrintPagePreviews)
{
PrintPagePreviews.Clear();
PrintPageDescription pageDescription = e.PrintTaskOptions.GetPageDescription(0);
foreach (AppPage fileToPrint in CurrentPages)
{
PrintGenerator page = PrintCreatePage(fileToPrint, pageDescription);
PrintPagePreviews.Add(page);
}
if (PreviewPagesCreated != null)
{
PreviewPagesCreated.Invoke(PrintPagePreviews, null);
}
printDocument.SetPreviewPageCount(PrintPagePreviews.Count, PreviewPageCountType.Intermediate);
}
}
private void PrintAddPages(object sender, AddPagesEventArgs e)
{
foreach (PrintGenerator pagePreview in PrintPagePreviews)
{
printDocument.AddPage(pagePreview);
}
printDocument.AddPagesComplete();
}
private PrintGenerator PrintCreatePage(AppPage pageFile, PrintPageDescription pageDescription)
{
PrintGenerator page = new PrintGenerator(pageFile.ImageFile);
Image img = (Image)page.FindName("ImgPreview");
page.Width = pageDescription.PageSize.Width;
page.Height = pageDescription.PageSize.Height;
double marginWidth = (pageDescription.PageSize.Width - pageDescription.ImageableRect.Width);
double marginHeight = (pageDescription.PageSize.Height - pageDescription.ImageableRect.Height);
img.Width = page.Width - marginWidth;
img.Height = page.Height - marginHeight;
img.Margin = new Thickness()
{
Top = pageDescription.ImageableRect.Top,
Left = pageDescription.ImageableRect.Left
};
page.InvalidateMeasure();
page.UpdateLayout();
return page;
}
private void PrintPreview(object sender, GetPreviewPageEventArgs e)
{
PrintGenerator printPreview = PrintPagePreviews[e.PageNumber - 1];
printPreview.UpdateLayout();
printDocument.SetPreviewPage(e.PageNumber, printPreview);
}
private void PrintCompleted(PrintTask sender, PrintTaskCompletedEventArgs e)
{
if (e.Completion == PrintTaskCompletion.Failed)
{
ShowError(title: "Printing error", msg: "Sorry, failed to print.");
}
else if (e.Completion == PrintTaskCompletion.Submitted)
{
ShowError(title: "Printing success", msg: "Success, task sent to printer.");
}
}
PrintGenerator.xaml
<Page
x:Class="COG_ScanDesk.PrintGenerator"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="using:COG_ScanDesk"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
<Grid>
<Image x:Name="ImgPreview" HorizontalAlignment="Left" Margin="0" VerticalAlignment="Top" Stretch="Uniform" />
</Grid>
</Page>
PrintGenerator.xaml.cs
public PrintGenerator(StorageFile file)
{
this.InitializeComponent();
LoadImage(file);
}
private async void LoadImage(StorageFile file)
{
var image = new BitmapImage();
using (var stream = await file.OpenStreamForReadAsync())
{
await image.SetSourceAsync(stream.AsRandomAccessStream());
}
this.ImgPreview.Source = image;
}
解决方案
出于某种原因,打印预览的加载速度似乎比在 PrintGenerator.xaml 页面中设置的图像要快(我们根据需要使用它来放置图像。)
LoadImage
事后处理,对于这种情况,我们建议您像官方代码示例PrintPreview
一样重新构建布局,如果您确实想使用上面的代码进行打印预览,您可以像下面这样进行任务延迟。PrintPreview
private async void PrintPreview(object sender, GetPreviewPageEventArgs e)
{
PrintGenerator printPreview = PrintPagePreviews[e.PageNumber - 1];
await Task.Delay(500);
printDocument.SetPreviewPage(e.PageNumber, printPreview);
}
推荐阅读
- javascript - Python Selenium javascript 错误:不支持 shape=rectangle
- c - __builtin_object_size 总是返回 -1
- python - 在 matplotlib 中手动定义比例
- ruby-on-rails - 从表格中的价格中删除美元符号和逗号
- entity-framework - 在 .NET Core 3.1 中使用 AutoMapper、WebApplicationFactory、Entity Framework 和 DTO 进行集成测试
- javascript - 如何使用 Jest 测试不同的屏幕宽度
- database - 如何使用 vb.net 创建 AutoBackup SQL 数据库?
- python - 如何检查我的子进程是否仍在正常运行?
- reactjs - 如何使用 react-jsonschema-form 禁用附加属性的标签?
- java - 包 sun.net.www.protocol.https 在模块 java.base 中声明,它不会导出它