WPF类库中的程序集级/根级样式
WPF类库中的程序集级/根级样式
我有一个支持WPF的C#(2008/.NET 3.5)类库程序集(基于这篇文章)。我创建了几个窗口,现在想为它们创建一个共同的样式集。然而,由于它是一个类库(而不是WPF应用程序),我没有一个app.xaml(和它包含的Application和相应的Application.Resources)来存储这些样式以供全局访问。
所以:在没有app.xaml的情况下,我如何创建一个顶级的样式定义集,让所有xaml文件都能看到?或者是否可能将一个可工作的app.xaml添加到类库中?
顺便说一下,我尝试在ResourceDictionary.xaml文件中创建一个ResourceDictionary,并在每个窗口中使用"Window.Resources"块进行包含。结果解决了按钮等的样式问题,但对于包含的窗口却没有效果。我可以在窗口的开头块中添加Style="{StaticResource MyWindowStyle}"
,它可以正常编译并在VS Design窗口中显示,但在实际运行时却出现解析异常(无法找到MyWindowStyle;我猜测Visual Studio在该行之后看到了包含的字典,但CRL按顺序执行操作,因此尚未加载ResourceDictionary)。
谢谢你们的建议,但仍然不起作用...显然类库并不隐式支持generic.xaml的使用。我在类库项目中添加了generic.xaml,并将其Build Action设置为"Resource"。它包含:
我想要使用这个主题的窗口xaml如下所示:
...Buttons, etc...
尽管VS Design窗口没有显示窗口使用MyWindow样式(即黑色背景),但它可以正常编译并启动。然而,当包含此类库的应用程序调用导致此窗口显示的调用时,我会得到一个XamlParseException:
无法找到名为'{MyWindow}'的资源。
我还尝试省略Style参数,看看窗口是否会默认使用样式(我尝试过在generic.xaml中包含x:Key和不包含x:Key)。没有错误,但在generic.xaml中定义的任何内容也没有显示出来。
我在这里做错了吗?或者还有其他想法可以让一个窗口使用通用的自定义样式(即不需要在每个窗口的xaml中定义样式)- 前提是这不是一个应用程序?
在WPF类库中,如果没有app.xaml文件,你仍然可以将其加载到应用程序级别的资源中,但是你需要编写代码(而不是xaml)来完成,类似于以下代码:
void LoadIt() { ResourceDictionary MyResourceDictionary = new ResourceDictionary(); MyResourceDictionary.Source = new Uri("MyResources.xaml", UriKind.Relative); App.Current.Resources.MergedDictionaries.Add(MyResourceDictionary); }
你可以通过访问http://ascendedguard.com/2007/08/one-of-nice-features-about-wpf-is-how.html查看一个示例。
在WPF中,app.xaml是一个很常见的文件,它通常用于定义应用程序级别的样式和资源。然而,在某些情况下,可能没有app.xaml文件,这可能会导致一些困惑和问题。
解决这个问题的方法是通过编写代码来手动加载资源字典。在上面的代码示例中,我们创建了一个ResourceDictionary对象,并将其Source属性设置为一个xaml文件的URI。然后,我们将这个资源字典添加到App.Current.Resources.MergedDictionaries中,这样它就可以在应用程序中使用了。
通过这种方式,我们可以在没有app.xaml文件的情况下仍然使用类库级别的样式和资源。这对于将类库作为独立的模块使用非常有用,并且可以帮助我们更好地组织和重用代码。
问题的出现原因:
使用WPF类库时,我们希望能够在整个程序集或根级别上应用样式,以便所有控件都能使用这些样式。然而,WPF默认情况下不支持这种全局样式的应用。
解决方法:
1. 在项目中添加一个名为"generic.xaml"的ResourceDictionary文件,路径为"/themes/generic.xaml"。
2. 在AssemblyInfo.cs文件中添加以下代码:
[assembly: ThemeInfo(ResourceDictionaryLocation.None, ResourceDictionaryLocation.SourceAssembly)]
3. 将所需的样式资源添加到generic.xaml中,这些样式将被所有控件使用。
4. 如果需要特定的主题(如Luna、Aero等),可以在"themes"目录中包含带有正确主题名称的ResourceDictionary文件。
这样,我们就可以在WPF类库中使用全局样式了。更多信息可以参考链接:Create and apply custom themes。
另外,网友提到的链接stackoverflow.com/questions/404019/…可能是问题发起者对回答的回应。
在回答中还提到了关于"/themes/generic.xaml"是一个标准的问题,回答者表示是的,这是一个标准的路径。详细信息可以参考链接:msdn.microsoft.com/en-us/library/…。同时还指出了一个错误,正确的路径应为"/themes/generic.xaml"(注意最后一个字母是a)。