C#从工作目录设置壁纸遇FileNotFoundException问题求助
问题原因与解决方案
为什么XAML能用但C#报错?
XAML与C#的路径解析逻辑完全不同:
- 在WPF的XAML中,
"/Saitama.png"是应用根目录的相对路径,默认指向程序输出目录下的文件,或对应嵌入资源的Pack URI,因此能正常加载。 - 但在C#代码中,
@"/Saitama.png"会被解析为绝对路径的根目录(即C:\Saitama.png),这显然不是你存放图片的位置,所以抛出FileNotFoundException。
实现相对路径调用的两种方法
方法1:基于程序输出目录拼接路径
如果图片是作为文件随程序发布的,先确保图片的复制到输出目录属性设置正确:
- 右键项目中的图片文件 → 属性
- 将「复制到输出目录」设为「如果较新则复制」或「始终复制」
然后在代码中获取程序运行目录,拼接相对路径:
// 获取程序的基目录(通常是输出目录) string baseDir = AppDomain.CurrentDomain.BaseDirectory; // 拼接图片相对路径(直接写文件名即可,不要加开头的/) string imagePath = Path.Combine(baseDir, "Saitama.png"); // 调用设置壁纸方法 Wallpaper.Set(imagePath);
也可以用Directory.GetCurrentDirectory()替代AppDomain.CurrentDomain.BaseDirectory,前者偏向当前工作目录,后者更稳定指向程序安装/输出目录。
方法2:嵌入资源方式(无需单独携带图片文件)
如果不想把图片作为独立文件发布,可以将其设为嵌入资源:
- 右键图片文件 → 属性
- 将「生成操作」设为「嵌入的资源」
然后通过读取嵌入资源流,保存为临时文件后再设置壁纸(系统设置壁纸的API只能识别本地文件路径):
using System.Reflection; using System.IO; // 资源命名格式:「项目命名空间.图片路径」,比如项目叫MyWallpaperApp,图片在根目录就是"MyWallpaperApp.Saitama.png" string resourceName = "你的项目命名空间.Saitama.png"; using (Stream resourceStream = Assembly.GetExecutingAssembly().GetManifestResourceStream(resourceName)) { if (resourceStream == null) throw new FileNotFoundException("未找到嵌入的图片资源", resourceName); // 创建临时文件路径 string tempFilePath = Path.Combine(Path.GetTempPath(), "TempWallpaper.png"); using (FileStream fs = new FileStream(tempFilePath, FileMode.Create, FileAccess.Write)) { resourceStream.CopyTo(fs); } // 设置壁纸 Wallpaper.Set(tempFilePath); // 可选:设置完成后延迟删除临时文件(避免系统占用文件导致删除失败) Task.Delay(2000).ContinueWith(t => { try { File.Delete(tempFilePath); } catch { /* 忽略删除失败的情况 */ } }); }
关键注意点
- 不要在C#中使用
@"/Saitama.png"这种开头带斜杠的路径,这不是相对路径,而是绝对根路径。 - 无论哪种方式,都要确保程序有读取对应路径文件的权限,避免将图片放在需要管理员权限的目录下。
内容的提问来源于stack exchange,提问作者001Sarper
相关产品推荐
相关产品推荐

