首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> .NET 網頁程式設計 >> 關於.NET

WPF 資源系統完整指南:二進制/邏輯資源、Static/DynamicResource、ResourceDictionary 合併與本地化換膚實戰

     編輯:關於.NET

WPF 資源雙軌制:二進制資源 vs 邏輯資源

維度二進制資源邏輯資源
本質圖片、音訊、字型、松散檔案.NET 物件(Brush、Style、Template、ViewModel 等)
建置動作Resource (嵌入組件) / Content (松散檔)無,直接在 XAML Resources 區塊宣告
引用方式Pack URI(pack://application:,,,/Images/logo.png){StaticResource key} / {DynamicResource key}
本地化衛星組件ResourceDictionary 切換

建議:UI 圖示、啟動畫面用 Resource;大型媒體、頻繁更新檔案用 Content;避免 EmbeddedResource(WPF Pack URI 無法直接存取)。

Pack URI 快速參考

Images/logo.png                    // 專案內 Resource/Content 相對路徑
/SubFolder/Images/logo.png         // 專案根目錄相對路徑
pack://application:,,,/MyLib;component/Images/logo.png  // 參考組件 Resource
pack://siteoforigin:,,,/Images/logo.png  // 部署根目錄 Content (不打包進組件)
file:///C:/Data/logo.png           // 絕對檔案系統路徑

邏輯資源:StaticResource vs DynamicResource 抉擇指南

特性StaticResourceDynamicResource
解析時機載入 XAML 時一次性查找每次存取屬性時即時查找
前向引用不支援(資源必須在前面定義)支援(資源可在後面定義)
運行時更新不反映自動反映(ResourceDictionary 內容變更)
效能極佳(單次查找)稍高(每次查找走邏輯樹)
適用目標任何屬性、非 DependencyProperty僅 DependencyProperty
系統資源不可用必要({DynamicResource {x:Static SystemColors.WindowBrushKey}})

決策口訣:預設用 StaticResource;需運行時換膚、引用系統資源、前向引用時改 DynamicResource。

資源查找順序:從元素到系統的層層遞進

StaticResource:元素 Resources → 邏輯樹父元素 Resources → App/Window/Page Resources → 系統資源。
DynamicResource:元素 Resources → 邏輯樹父元素 → App Resources → 當前主題 Theme Resources → 系統資源。

程式碼存取:element.Resources["key"]、element.FindResource("key")(找不到拋例外)、element.TryFindResource("key")(回傳 null)。

ResourceDictionary 合併:模組化與換膚的核心機制

<Window.Resources>
  <ResourceDictionary>
    <ResourceDictionary.MergedDictionaries>
      <ResourceDictionary Source="Themes/LightBrushes.xaml"/>
      <ResourceDictionary Source="Common/SharedStyles.xaml"/>
    </ResourceDictionary.MergedDictionaries>
    <!-- 本視窗專用覆寫 -->
    <SolidColorBrush x:Key="AccentBrush" Color="Orange"/>
  </ResourceDictionary>
</Window.Resources>

合併順序決定優先權:後合併者勝出。執行時動態切換:

var dict = Application.LoadComponent(new Uri("Themes/DarkBrushes.xaml", UriKind.Relative)) as ResourceDictionary;
App.Current.Resources.MergedDictionaries.Clear();
App.Current.Resources.MergedDictionaries.Add(dict);  // 瞬間全域換膚

本地化實戰:四步建立多語言切換

  1. 建立語言字典:Resources/en-US.xaml、Resources/zh-TW.xaml,鍵值相同,值為當地語系字串。
  2. App.xaml 合併預設字典:<ResourceDictionary Source="Resources/en-US.xaml"/>。
  3. 啟動時載入當前文化字典並置頂:
    protected override void OnStartup(StartupEventArgs e) {
        base.OnStartup(e);
        var culture = CultureInfo.CurrentUICulture.Name;  // 如 "zh-TW"
        var dict = Application.LoadComponent(new Uri($"Resources/{culture}.xaml", UriKind.Relative)) as ResourceDictionary;
        if (dict != null) {
            Resources.MergedDictionaries.Clear();
            Resources.MergedDictionaries.Add(dict);  // 後加入者優先,覆蓋預設
        }
    }
    
  4. XAML 繫結字串資源:<TextBlock Text="{StaticResource Title_Home}"/>。

測試切換:Thread.CurrentThread.CurrentUICulture = new CultureInfo("zh-TW"); 重啟 App 即見中文介面。

隱性鍵樣式:針對型別的全域預設外觀

<Style TargetType="{x:Type Button}">  <!-- 無 x:Key,TargetType 即為隱性鍵 -->
  <Setter Property="Background">
    <Setter.Value><LinearGradientBrush StartPoint="0,0" EndPoint="0,1">
      <GradientStop Offset="0" Color="AliceBlue"/>
      <GradientStop Offset="1" Color="Salmon"/>
    </LinearGradientBrush></Setter.Value>
  </Setter>
  <Setter Property="FontSize" Value="14"/>
</Style>

範圍內所有 Button 自動套用,除非显式設定 Style={x:Null} 或另覆寫 Style。配合 BasedOn 可建立樣式繼承鏈。

跨組件共享邏輯資源:ComponentResourceKey

類別庫定義:

public static class MyResources {
    public static readonly ComponentResourceKey AccentBrushKey =
        new ComponentResourceKey(typeof(MyResources), "AccentBrush");
}

資源字典:<SolidColorBrush x:Key="{ComponentResourceKey TypeInTargetAssembly={x:Type local:MyResources}, ResourceId=AccentBrush}" Color="Teal"/>
消費端引用:<Button Background="{DynamicResource {x:Static local:MyResources.AccentBrushKey}}"/>

x:Shared="False":打破單例,每次引用建立新實例

<Button x:Key="btnTemplate" x:Shared="False" Content="範本按鈕"/>
<StackPanel>
  <StaticResource ResourceKey="btnTemplate"/>  <!-- 實例 A -->
  <StaticResource ResourceKey="btnTemplate"/>  <!-- 實例 B,獨立可修改 -->
</StackPanel>

適用於需在多處使用但需獨立狀態的視覺元素(如彈出式選單模板)。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved