现象:

  打印时候程序直接崩溃。调试时出现下列异常。

异常信息:

  中文:System.ArgumentException : 路径中有非法字符。

  英文: System.ArgumentException' occurred in mscorlib.dll  Additional information: Illegal characters in path

堆栈信息:

Stack Trace:=
   at System.IO.Path.CheckInvalidPathChars(String path)
   at System.IO.Path.Combine(String path1, String path2)
   at Microsoft.Internal.GDIExporter.BuildFontList(String fontdir)
   at Microsoft.Internal.GDIExporter.CGDIDevice.CheckFont(GlyphTypeface typeface, String name)
   at Microsoft.Internal.GDIExporter.CGDIRenderTarget.CreateFontW(GlyphRun pGlyphRun, Double fontSize, Double scaleY)
   at Microsoft.Internal.GDIExporter.CGDIRenderTarget.RenderTextThroughGDI(GlyphRun pGlyphRun, Brush pBrush)
   at Microsoft.Internal.GDIExporter.CGDIRenderTarget.DrawGlyphRun(Brush pBrush, GlyphRun glyphRun)
   at Microsoft.Internal.AlphaFlattener.BrushProxyDecomposer.Microsoft.Internal..AlphaFlattener.IProxyDrawingContext.DrawGlyphs(GlyphRun glyphrun, Geometry clip, Matrix trans, BrushProxy foreground)
   at Microsoft.Internal.AlphaFlattener.PrimitiveRenderer.DrawGlyphs(GlyphRun glyphrun, Rect bounds, Matrix trans, String desp)
   at Microsoft.Internal.AlphaFlattener.Flattener.AlphaRender(Primitive primitive, List` overlapping, Int32 overlapHasTransparency, Boolean disjoint, String desp)
   at Microsoft.Internal.AlphaFlattener.Flattener.AlphaFlatten(IProxyDrawingContext dc, Boolean disjoint)
   at Microsoft.Internal.AlphaFlattener.Flattener.Convert(Primitive tree, ILegacyDevice dc, Double width, Double height, Double dpix, Double dpiy, Nullable` quality)
   at Microsoft.Internal.AlphaFlattener.MetroDevice0.FlushPage(ILegacyDevice sink, Double width, Double height, Nullable` outputQuality)
   at Microsoft.Internal.AlphaFlattener.MetroToGdiConverter.FlushPage()
   at System.Windows.Xps.Serialization.NgcSerializationManager.EndPage()
   at System.Windows.Xps.Serialization.NgcFixedPageSerializer.SerializeObject(Object serializedObject)
   at System.Windows.Xps.Serialization.NgcDocumentPageSerializer.SerializeObject(Object serializedObject)
   at System.Windows.Xps.Serialization.NgcDocumentPaginatorSerializer.SerializeObject(Object serializedObject)
   at System.Windows.Xps.Serialization.NgcSerializationManager.SaveAsXaml(Object serializedObject)
   at System.Windows.Xps.XpsDocumentWriter.SaveAsXaml(Object serializedObject, Boolean isSync)
   at System.Windows.Xps.XpsDocumentWriter.Write(DocumentPaginator documentPaginator)
   at System.Windows.Controls.PrintDialog.PrintDocument(DocumentPaginator documentPaginator, String description)

原因:

  在注册表 HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Fonts 中存的是字体名称及其文件位置的列表。但这些文件位置中有非法字符中有非法字符。在执行Path.Combine方法时,出现异常。

解决方案:

  重新处理注册表。

代码:

    public class FontsClearup
{
/// <summary>
/// 获取系统文件位置
/// </summary>
[MethodImpl(MethodImplOptions.ForwardRef), SecurityCritical, SuppressUnmanagedCodeSecurity, DllImport("shell32.dll", CharSet = CharSet.Unicode)]
internal static extern int SHGetSpecialFolderPathW(IntPtr hwndOwner, StringBuilder lpszPath, int nFolder, int fCreate); /// <summary>
/// 获取字体文件夹
/// </summary>
/// <returns></returns>
private static string GetFontDir()
{
var lpszPath = new StringBuilder();
return SHGetSpecialFolderPathW(IntPtr.Zero, lpszPath, , ) != ? lpszPath.ToString().ToUpperInvariant() : null;
} public const string FontsRegistryPath =
@"HKEY_LOCAL_MACHINE\Software\Microsoft\Windows NT\CurrentVersion\Fonts";
public const string FontsLocalMachineRegistryPath =
@"Software\Microsoft\Windows NT\CurrentVersion\Fonts"; /// <summary>
/// 获取所有字体信息
/// </summary>
/// <returns></returns>
public static IEnumerable<FontInfo> ScanAllRegistryFonts()
{
var fontNames = new List<FontInfo>();
new RegistryPermission(RegistryPermissionAccess.Read, FontsRegistryPath).Assert();
try
{
var fontDirPath = GetFontDir();
using (var key = Registry.LocalMachine.OpenSubKey(FontsLocalMachineRegistryPath))
{
if (key == null)
{
return Enumerable.Empty<FontInfo>();
}
var valueNames = key.GetValueNames();
foreach (var valueName in valueNames)
{
var fontName = key.GetValue(valueName).ToString();
var fontInfo = new FontInfo
{
Name = valueName,
RegistryKeyPath = key.ToString(),
Value = fontName
};
try
{
var systemFontUri = new Uri(fontName, UriKind.RelativeOrAbsolute);
if (!systemFontUri.IsAbsoluteUri)
{
new Uri(Path.Combine(fontDirPath, fontName));
}
}
catch
{
fontInfo.IsCorrupt = true;
}
fontNames.Add(fontInfo);
}
key.Close();
key.Flush();
}
}
catch (Exception exception)
{
Console.WriteLine(exception);
}
finally
{
CodeAccessPermission.RevertAssert();
}
return fontNames;
} /// <summary>
/// 获取所有异常字体信息
/// </summary>
/// <returns></returns>
public static IEnumerable<FontInfo> GetAllCorruptFonts()
{
var fonts = ScanAllRegistryFonts();
return fonts.Where(f => f.IsCorrupt);
} /// <summary>
/// 整理字体信息
/// </summary>
/// <param name="p_corruptFonts"></param>
public static void FixRegistryFonts(IEnumerable<FontInfo> p_corruptFonts = null)
{
IEnumerable<FontInfo> corruptFonts = p_corruptFonts;
if (corruptFonts == null)
{
corruptFonts = GetAllCorruptFonts();
} new RegistryPermission(RegistryPermissionAccess.Write, FontsRegistryPath).Assert();
try
{
using (var key = Registry.LocalMachine.OpenSubKey(FontsLocalMachineRegistryPath, true))
{
if (key == null) return;
foreach (var corruptFont in corruptFonts)
{
if (!corruptFont.IsCorrupt) continue;
var fixedFontName = RemoveInvalidCharsFormFontName(corruptFont.Value);
key.SetValue(corruptFont.Name, fixedFontName, RegistryValueKind.String);
}
key.Close();
key.Flush();
}
}
catch (Exception exception)
{
Console.WriteLine(exception.Message);
}
finally
{
CodeAccessPermission.RevertAssert();
ScanAllRegistryFonts();
}
} private static string RemoveInvalidCharsFormFontName(string fontName)
{
var invalidChars = Path.GetInvalidPathChars();
var fontCharList = fontName.ToCharArray().ToList();
fontCharList.RemoveAll(c => invalidChars.Contains(c));
return new string(fontCharList.ToArray());
}
} public class FontInfo
{
public string RegistryKeyPath { get; set; }
public bool IsCorrupt { get; set; }
public string Name { get; set; }
public string Value { get; set; } }

执行:FontsClearup.FixRegistryFonts();

其实方法的用法见注释。

参考:http://www.dnsingh.com/MyBlog/?tag=/GDIExporter.BuildFontList

WPF 打印崩溃问题( 异常:Illegal characters in path/路径中有非法字符)的更多相关文章

  1. 【已解决】unity4.2.0f4 导出Android工程报错:Error building Player: ArgumentException: Illegal characters in path. [unity导出android工程 报错,路径含有非法字符]

    使用unity3D开发的一个客户端,需要导出为Android工程,然后接入一些第三方android SDK. unity版本 操作系统为: OS 名称: Microsoft Windows 7 旗舰版 ...

  2. VS2017 v15.8.0 Task ExpandPriContent failed. Illegal characters in path

    昨天更新了VS到最新版本v15.8.0,但是编译UWP出现了操蛋的bug. 谷歌一下,vs社区已经有答案了. 打开.csproj文件,在节点 <PropertyGroup> 里面,加上一行 ...

  3. URLDecoder异常Illegal hex characters in escape (%)

    URLDecoder对参数进行解码时候,代码如: URLDecoder.decode(param,"utf-8"); 有时候会出现类似如下的错误: URLDecoder异常Ille ...

  4. 引擎崩溃、异常、警告、BUG与提示总结及解决方法

    http://www.58player.com/blog-635-128.html [Unity3D]引擎崩溃.异常.警告.BUG与提示总结及解决方法   此贴会持续更新,都是项目中常会遇到的问题,总 ...

  5. WPF打印票据

    最近工作的内容是有关于WPF的,整体开发没有什么难度,主要是在打印上因为没有任何经验,犯了一些难,不过还好,解决起来也不是很费劲. WPF打印票据或者是打印普通纸张区别不大,只是说打印票据要把需要打的 ...

  6. WPF 打印实例

    原文:WPF 打印实例      在WPF 中可以通过PrintDialog 类方便的实现应用程序打印功能,本文将使用一个简单实例进行演示.首先在VS中编辑一个图形(如下图所示).      将需要打 ...

  7. 【Bug】解决 SpringBoot Artifact contains illegal characters 错误

    解决 SpringBoot  Artifact contains illegal characters错误 错误原因:Artifact包含非法字符(大写字母) 解决方法:将Artifact名称改成小写 ...

  8. IDEA中新建SpringBoot项目时提示:Artifact contains illegal characters

    场景 一步一步教你在IEDA中快速搭建SpringBoot项目: https://blog.csdn.net/BADAO_LIUMANG_QIZHI/article/details/87688277 ...

  9. Linux curl遇到错误curl: (3) Illegal characters found in URL

    服务器上执行一个脚本,在linux新建的sh,把本地编辑器的内容粘贴到文件里. 结果执行的时候报错了. 问题就是 curl:(3)Illegal characters found in URL 看着一 ...

随机推荐

  1. MySQL语句相关

    一.增加 1.基本 2.集合 3.组合 二.删除 1.基本 2.集合 3.组合 1.一个表的查询结果作为另一个表的插入字段之一 <insert id="方法" paramet ...

  2. 在winsshd 中添加id_rsa.pub 实现Windows 服务器主机自动信任Linux 客户端

    文章一. 生成密钥: 在Linux主机(ssh客户端),通过ssh-keygen在建立SSH keys# ssh-keygen -t rsa (连续三次回车,即在本地生成了公钥和私钥,不设置密码)将在 ...

  3. ECMAScript5新特性之isFrozen、freeze

    对象被冻结后: 1 不能添加属性. 2 不能删除属性. 3 不能修改属性.(赋值) 4 不能修改属性描述符.(会抛异常) var fruit = { name : '苹果', desc : '红富士' ...

  4. 判断RadioButtonList是否选中

    RadioButtonList有很多指示用户选择项的属性,如SelectedIndex 当该属性 = -1时表示用户没选择项SelectedItem  当该属性为null时也表示用户没选择项

  5. URL去重

    import socket dictlist ={}; def ReadHost(): hosts = []; obn = open('d:/sss.txt', 'rb'); for line in ...

  6. 初学Hadoop之图解MapReduce与WordCount示例分析

    Hadoop的框架最核心的设计就是:HDFS和MapReduce.HDFS为海量的数据提供了存储,MapReduce则为海量的数据提供了计算. HDFS是Google File System(GFS) ...

  7. mysql5.5以上开启慢查询

    在my.ini配置文件中添加: [mysqld] #开启慢查询 slow_query_log = on #慢查询时间 long_query_time = 0.5 #记录没有使用索引的查询 log_qu ...

  8. TPshop学习

    笔记大纲: tpshop目录结构 功能模块 函数库 重要配置 助手函数 插件 模板 1.TPshop目录结构 目录结构(来自官方视频截图) 看这个图,目录结构一目了然.下面要讲的内容也是根据这个图展开 ...

  9. PAT 1054 求平均值 (20)(代码+思路+测试用例)

    1054 求平均值 (20)(20 分) 本题的基本要求非常简单:给定N个实数,计算它们的平均值.但复杂的是有些输入数据可能是非法的.一个"合法"的输入是[-1000,1000]区 ...

  10. BZOJ1222 [HNOI2001]产品加工 - 动态规划- 背包

    题解 怎么看都不像是个背包,直到我看了题解→_→, 第一次碰到这么奇怪的背包= = 定一个滚动数组$F_i$, $i$表示机器$a$用了$i$的时间, $F_i$表示机器$b$用了$F_i$的时间, ...