正如我读到的:http://msdn.microsoft.com/en-us/library/cc903952(VS.95).aspx,特别是标有"使用ResourceDictionary的前向引用"的部分:
来自任何给定资源字典的静态资源引用必须引用已在资源引用之前以词法方式定义的资源.静态资源引用无法解析转发引用.因此,如果使用静态资源引用,则必须设计资源字典结构,以便在每个相应资源字典的开头或附近定义用于进一步按资源使用的资源.
这是否意味着我无法在App.xaml中执行此类操作:
<Application.Resources>
<ResourceDictionary>
<ResourceDictionary.MergedDictionaries>
<ResourceDictionary Source="Assets/Colors.xaml"/>
<ResourceDictionary Source="Assets/Brushes.xaml"/>
</ResourceDictionary.MergedDictionaries>
</ResourceDictionary>
</Application.Resources>
Run Code Online (Sandbox Code Playgroud)
其中Brushes.xaml包含SolidColorBrush,LinearColorBrush等,引用Colors.xaml中定义的颜色的定义?
例如
<SolidColorBrush x:Key="OrangeRedBrush" Color="{StaticResource AppOrangeRed}"/>
Run Code Online (Sandbox Code Playgroud)
?
我在Colors.xaml中定义我的颜色,如:
<Color x:Key="AppOrangeRed">#FFBF3C1F</Color>
Run Code Online (Sandbox Code Playgroud)
我收到一个运行时错误,指出它无法找到具有键'AppOrangeRed'的资源.
组织颜色和画笔的最佳实践是什么,以便可以重复使用(在适当的情况下,我理解颜色是结构和画笔是参考对象,在http://weblogs.manas.com.ar/spalladino/2009/中解释03/02/silverlight-xaml-guidelines /)
谢谢Rob
我正在尝试创建一个应用选项卡,其中每个选项卡都有一个按钮区域和一个视图区域.
现在每个选项卡在布局中基本上具有相同的布局,我希望能够重用相同的布局,这样我就不必在很多地方进行更改(这只是不好的编程).我可以使用资源或样式完成此操作.
如果可能,请提供灯光代码示例.
编辑:我已经决定添加一个我正在尝试做的例子,因为我还没有得到它.
在每个TabItem下我试图重新创建这个网格(它有点复杂,但你明白了):
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="200"/>
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<Border Margin="10"
BorderBrush="{StaticResource MediumColorBrush}"
CornerRadius="10"
BorderThickness="2"
Grid.Row="0">
<!-- First content goes here -->
</Border>
<Border Margin="10"
BorderBrush="{StaticResource MediumColorBrush}"
CornerRadius="10"
BorderThickness="2"
Grid.Row="1">
<!-- Second content goes here -->
</Border>
</Grid>
Run Code Online (Sandbox Code Playgroud)
你也可以看到2个边框是一样的.现在我需要将一些内容占位符放在我的评论所在的位置.我不想在资源字典中声明这个Grid布局,然后在我使用它的地方将单独的内容放入每个边框.
我可能有很多TabItems,所以重复这段代码不是一个好主意,每个Tab页面将在2个占位符中有不同的内容.
我可以用了
<ContentPresenter Content="{Binding}" />
Run Code Online (Sandbox Code Playgroud)
只有1个内容的东西,当会有更多内容时会发生什么.
我有以下,很容易重现问题:我正在创建一个使用其他文件资源的xaml应用程序.要做的就是创建一个MergedDictionaries-tag来合并本地和全局资源,如下所示:
<Window>
<Window.Resources>
<ResourceDictionary>
<ResourceDictionary.MergedDictionaries>
<ResourceDictionary Source="path.to.xaml.file"/>
<ResourceDictionary>
<Style TargetType="{x:Type Border}" x:Key="TypeBlock">
</Style>
<Style TargetType="{x:Type Border}" x:Key="SetBlock">
</Style>
</ResourceDictionary>
</ResourceDictionary.MergedDictionaries>
</ResourceDictionary>
</Window.Resources>
....
</Window>
Run Code Online (Sandbox Code Playgroud)
如果运行它,这段代码会崩溃:
Item has already been added. Key in dictionary: 'System.Windows.Controls.Border' Key being added: 'System.Windows.Controls.Border'
Run Code Online (Sandbox Code Playgroud)
如果我们删除MergedDictionaries-tag,代码将按预期运行:
<Window>
<Window.Resources>
<Style TargetType="{x:Type Border}" x:Key="TypeBlock">
</Style>
<Style TargetType="{x:Type Border}" x:Key="SetBlock">
</Style>
</Window.Resources>
</Window>
Run Code Online (Sandbox Code Playgroud)
我不明白为什么它在我们使用Merged Resources时抛出异常.当然,修复现在很容易(将资源调到较低的水平).很高兴知道这是否是"正常"行为......
我有一个WPF 4.0应用程序,它在菜单命令之类的东西中使用了一些自定义的16x16图标.我想(现在)有两组图标,默认的Vista/7-ish和一些XP-ish.我想要的是让当前的操作系统确定使用哪些图标.
现在,我已经在主题资源字典(即Aero.NormalColor.xaml等)中定义了指向特定PNG资源的BitmapImage资源.
<!-- Aero.NormalColor.xaml -->
<BitmapImage x:Key="IconSave" UriSource="/MyWPFApp;component/Resources/Icons16/Aero/disk.png"/>
<!-- Luna.NormalColor.xaml -->
<BitmapImage x:Key="IconSave" UriSource="/MyWPFApp;component/Resources/Icons16/Luna/disk.png"/>
Run Code Online (Sandbox Code Playgroud)
在我的应用中想要显示图标的任何地方都将Image/Icon的source属性设置为StaticResource到其中一个BitmapImages.
<Image Source="{StaticResource IconSave}"/>
Run Code Online (Sandbox Code Playgroud)
我们的想法是,由于WPF根据当前的操作系统和主题自动加载主题词典,因此只会加载一组BitmapImage资源,并且图标会神奇地成为合适的图标.
但是,这不起作用,我在运行时遇到了可怕的"无法找到资源"异常.我的预感是,这是因为主题文件只搜索自定义控件,Image不是.
Blend 4对这些没有任何问题,但它已经定义了其特殊的DesignTimeResources.xaml文件,并在Aero.NormalColor.xaml上进行了合并.VS2010扼流圈,但它也没有使用像DesignData文件这样的东西,所以我并不感到惊讶.我目前还有一个单独的资源字典文件(MainSkin.xaml),它被合并到Application资源中.引用样式等在运行时可以正常工作.
我是在正确的轨道上,只是有一些轻微的错误?我是否需要做一些完全不同的事情才能获得理想的效果,如果有,那该怎么办?
如何在运行时更改WPF静态资源的值?
我有以下资源
<UserControl.Resources>
<sys:String x:Key="LengthFormat">#.# mm</sys:String>
<sys:String x:Key="AreaFormat">#.# mm²</sys:String>
<sys:String x:Key="InertiaFormat">#.# mm?</sys:String>
</UserControl.Resources>
Run Code Online (Sandbox Code Playgroud)
一些文字块参考
<TextBlock Grid.Row="2" Grid.Column="1"
Text="{Binding Path=Breadth, StringFormat={StaticResource ResourceKey=LengthFormat}}" />
Run Code Online (Sandbox Code Playgroud)
然后根据要绑定到控件的对象,我想改变格式.我在控件中设置了如下属性:
public string LengthFormat
{
set
{
this.Resources["LengthFormat"] = value;
}
}
public string AreaFormat
{
set
{
this.Resources["AreaFormat"] = value;
}
}
public string InertiaFormat
{
set
{
this.Resources["InertiaFormat"] = value;
}
}
Run Code Online (Sandbox Code Playgroud)
然后在绑定之前我设置每个字符串.
但它不起作用,有人建议whynot?
干杯
编辑:当使用标准.NET ResourceDictionary时也会出现此问题,并且似乎是在控件或数据模板中使用资源字典的问题.
我有一个自定义资源字典遵循共享资源实例的常见方法.
http://softnotes.wordpress.com/2011/04/05/shared-resourcedictionary-for-silverlight/ http://www.wpftutorial.net/MergedDictionaryPerformance.html
public class SharedResourceDictionary : ResourceDictionary
{
static readonly Dictionary<Uri, WeakReference<ResourceDictionary>> SharedDictionaries = new Dictionary<Uri, WeakReference<ResourceDictionary>>();
Uri _sourceUri;
public new Uri Source
{
get
{
// Behave like standard resource dictionary for IDE...
if (VisualStudio.IsInDesignMode)
return base.Source;
return this._sourceUri;
}
set
{
// Behave like standard resource dictionary for IDE...
if (VisualStudio.IsInDesignMode)
{
base.Source = value;
return;
}
this._sourceUri = value;
WeakReference<ResourceDictionary> cached;
if (SharedDictionaries.TryGetValue(value, out cached))
{
ResourceDictionary rd;
if (cached.TryGetTarget(out rd))
{
this.MergedDictionaries.Add(rd);
return; …Run Code Online (Sandbox Code Playgroud) 有没有办法获得特定WPF资源的价值变化的通知?
我们需要在WPF应用程序中动态调整内容字体大小...对于WPF控件,我们设置Control.FontSize为动态资源,字体自动调整大小.不幸的是,我们还有一个嵌入式winforms控件,其字体大小不能这样设置.我们的想法是订阅在每个资源值更改时触发的事件,并实现winforms控件的自定义刷新.有什么建议吗?
先感谢您!
假设我的 Application.xaml 中有一些 ResourceDictionary 定义如下:
<Application>
<Application.Resources>
<ResourceDictionary>
<ResourceDictionary.MergedDictionaries>
<ResourceDictionary x:Name="brushResources"/>
<ResourceDictionary x:Name="graphicsResources"/>
</ResourceDictionary.MergedDictionaries>
</ResourceDictionary>
</Application.Resources>
</Application>
Run Code Online (Sandbox Code Playgroud)
我本以为我可以简单地访问后面代码中的字典,如下所示:
brushResources.MergedDictionaries.Add(someNewBrushes)
graphicsResources.MergedDictionaries.Add(someNewGraphics)
Run Code Online (Sandbox Code Playgroud)
但事实似乎并非如此,这是处理 ResourceDictionary 的错误方法吗?我真的很喜欢使用 MEF 动态加载资源的能力,但这对我来说似乎是一个绊脚石。
编辑
修复了示例代码以显示字典实际上位于 MergedDictionaries 中
我有一个在XAML文件中定义的矢量图像
Image.xaml
<Canvas xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" x:Name="appbar_power" Width="76" Height="76" Clip="F1 M 0,0L 76,0L 76,76L 0,76L 0,0">
<Path Width="38" Height="41.1667" Canvas.Left="19" Canvas.Top="17.4167" Stretch="Fill" Fill="#FFFFFFFF" Data="F1 M 36.4167,36.4167L 36.4167,17.4167L 41.1667,17.4167L 41.1667,36.4167L 36.4167,36.4167 Z M 57,39.5833C 57,50.0767 48.4934,58.5833 38,58.5833C 27.5066,58.5833 19,50.0767 19,39.5833C 19,30.7301 25.0552,23.2911 33.25,21.1819L 33.25,27.8374C 28.6079,29.7165 25.3333,34.2675 25.3333,39.5833C 25.3333,46.5789 31.0044,52.25 38,52.25C 44.9956,52.25 50.6667,46.5789 50.6667,39.5833C 50.6667,34.8949 48.1194,30.8014 44.3333,28.6113L 44.3333,21.6645C 51.7129,24.2728 57,31.3106 57,39.5833 Z "/>
</Canvas>
Run Code Online (Sandbox Code Playgroud)
如果我修改此图像的XAML代码(例如Path的Fill属性),则会立即在Visual Studio 2015的"设计"窗口中显示更改.
现在我想创建一个引用此图像的ResourceDictionary.我将xaml代码直接包含在ResourceDictionary中,但在这种情况下我失去了预览的能力(Visual Studio中没有设计窗口,我得到"MyResourceDictionary.xaml无法在设计视图中编辑").
MyResourceDictionary.xaml
<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="clr-namespace:Project.XamlResources">
<Canvas x:Key="appbar_power" x:Name="appbar_power" Width="76" Height="76" Clip="F1 M …Run Code Online (Sandbox Code Playgroud) 我正在构建一个使用ResourceDictionaries其他程序集的应用程序,但在使用字体时遇到了问题。
有一个名为MyFontAssembly的程序集将字体以及对它们的引用存储为ResourceDictionary. 它的结构如下:
MyFontAssembly
- FontDictionary.xaml - (stores references to fonts)
- Fonts
- FontA.ttf
- FontB.ttf
...
Run Code Online (Sandbox Code Playgroud)
还有另一个程序集用于存储ResourceDictionaries样式控件,它称为MyStylesAssembly。然后将 MyStylesAssembly 中的 ResourceDictionaries 合并到应用程序的 App.xaml 中,以提供可重用的样式。
问题是我的样式确实识别字体资源(代码没有崩溃,因为它无法通过其键找到资源),但看起来没有应用存储为 ttf 文件的字体。
我在我的FontDictionary.xaml.
<FontFamily x:Key="MyFontKey">Fonts/#MyFontName</FontFamily>
<FontFamily x:Key="MyFontKey">pack://application:,,,/MyFontAssemblyName;Component/Fonts/#MyFontName</FontFamily>
<FontFamily x:Key="MyFontKey">/MyFontAssemblyName;Component/Fonts/#MyFontName</FontFamily>
<FontFamily x:Key="MyFontKey">pack://application:,,,/Fonts/#MyFontName</FontFamily>
Run Code Online (Sandbox Code Playgroud)
笔记:
<FontFamily x:Key="MyFontKey">Fonts/#MyFontName</FontFamily>在具有相同结构的单个 exe 项目中使用实现,一切都很好,当我在重构期间将实现拆分为几个程序集时出现问题,就像我描述的那样。MyFontAssembly已MyStylesAssembly正确合并。我在这里只是用那个名字来称呼它,在实际代码中,它还有一些ResourceDictionaries由MyStylesAssembly. 问题似乎只是<FontFamily>标签无法识别 ttf 文件。MyFontAssembly并且MyStylesAssembly是类型的项目ClassLibrary并且不包含除 in …