WPF 中的 Pack URI(記下備忘)

  • 4014
  • 0
  • 2013-12-09

摘要:WPF 中的 Pack URI(記下備忘)

Pack URI 用法,從 msdn 抄過來記下備查。

[補充]

下面這種寫法是只參考 MyNameSpace 的 dll 的寫法:

<Image Source="pack://application:,,,/MyNameSpace;component/Images/abc.ico"/>

下面這種寫法就一定要把 MyNameSpace 的專案加入方案才能使用:

<Image Source="/MyNameSpace;component/Images/bbb.ico">

==============================

http://msdn.microsoft.com/zh-tw/library/aa970069(v=vs.110).aspx

==============================

WPF 中的 Pack URI

.NET Framework 4.5
 
本主題尚未接受評分 為這個主題評分
 

 

在 Windows Presentation Foundation (WPF) 中,統一資源識別元 (URI) 可透過許多方式識別及載入檔案,包括:

  • 指定應用程式第一次啟動時所顯示的使用者介面 (UI)。

  • 載入影像。

  • 巡覽至頁面。

  • 載入不可執行的資料檔案。

此外,URI 也可用來識別及載入來自各種位置的檔案,包括:

  • 目前的組件 (Assembly)。

  • 受參考的組件。

  • 相對於組件的位置。

  • 應用程式的來源網站。

為了提供一致的機制,供使用者從這些位置識別及載入這些檔案類型,WPF 利用了「Pack URI 配置」(Pack URI Scheme) 的擴充性。 本主題提供這種配置的概觀,內容涵蓋如何針對各種案例建構 Pack URI,並討論絕對和相對 URI 以及 URI 解析,最後再說明如何從標記和程式碼使用 URI。

 

本主題包含下列章節。

Pack URI 配置可供開放式封裝慣例 (OPC) 規格使用,以描述用來組織及識別內容的模型。 這個模型的主要項目包括封裝 (Package) 和組件 (Part),其中「封裝」(Package) 是一個或多個「組件」(Part) 的邏輯容器 (Container)。 下圖說明這個概念。

套件和部分圖表

為了識別組件,OPC 規格利用 RFC 2396 (Uniform Resource Identifiers (URI): Generic Syntax) 來定義 Pack URI 配置。

URI 指定的配置是由其前置字元所定義;http、ftp 和 file 都是已知的範例。 Pack URI 配置使用 "Pack" 做為其配置,其中包含兩個元件:授權和路徑。 Pack URI 的格式如下:

pack://authority/path

authority (授權) 指定包含組件之封裝的類型,而 path (路徑) 則指定組件在封裝內的位置。

下圖說明這個概念:

套件、授權和路徑之間的關聯性

封裝和組件類似於應用程式和檔案,而其中應用程式 (封裝) 可以包含一個或多個檔案 (組件),包括:

  • 編譯成本機組件 (Assembly) 的資源檔。

  • 編譯成受參考組件 (Referenced Assembly) 的資源檔。

  • 編譯成參考組件 (Referencing Assembly) 的資源檔。

  • 內容檔。

  • 來源網站檔。

為了存取這些檔案類型,WPF 支援兩種授權:application:/// 和 siteoforigin:///。 application:/// 授權可識別編譯時期已知的應用程式資料檔案,包括資源檔和內容檔。 siteoforigin:/// 授權可識別來源網站檔。 下圖顯示每個授權的範圍。

封裝 URI 圖表
注意事項 注意事項

Pack URI 的授權單位元件是內嵌的 URI,會指向封裝且必須符合 RFC 2396。 此外,"/" 字元必須取代為 "," 字元,且保留字元如 "%" 和 "?" 必須逸出。 如需詳細資訊,請參閱 OPC。

下列各節說明如何使用這兩種授權並結合適當的路徑來建構 Pack URI,以用於識別資源檔、內容檔和來源網站檔。

資源檔會設定為 MSBuild Resource 項目,並且編譯成組件。 WPF 支援建構可用來識別資源檔的 Pack URI,不論該資源檔是編譯成本機組件,還是編譯成從本機組件參考的組件。

Aa970069.collapse_all(zh-tw,VS.110).gif本機組件資源檔

編譯成本機組件之資源檔的 Pack URI 使用下列授權和路徑:

  • 授權:application:///。

  • 路徑:資源檔的名稱,包括其路徑 (相對於本機組件專案資料夾根目錄)。

下列範例顯示 XAML 資源檔的 Pack URI;其中的資源檔位於本機組件之專案資料夾的根目錄中。

pack://application:,,,/ResourceFile.xaml

下列範例顯示 XAML 資源檔的 Pack URI;其中的資源檔位於本機組件之專案資料夾的子資料夾中。

pack://application:,,,/Subfolder/ResourceFile.xaml

Aa970069.collapse_all(zh-tw,VS.110).gif受參考的組件資源檔

編譯成受參考組件之資源檔的 Pack URI 使用下列授權和路徑:

  • 授權:application:///。

  • 路徑:編譯成受參考組件之資源檔的名稱。 此路徑必須符合下列格式:

    AssemblyShortName[;Version][;PublicKey];component/Path

    • AssemblyShortName:受參考組件的簡短名稱。

    • ;Version [選擇項]:包含資源檔案的受參考組件版本。 載入兩個以上簡短名稱相同的受參考組件時,就會使用這個項目。

    • ;PublicKey [選擇項]:用來簽署受參考組件的公開金鑰 (Public Key)。 載入兩個以上簡短名稱相同的受參考組件時,就會使用這個項目。

    • ;component:指定被參考的組件其參考來源是本機組件。

    • /Path:資源檔的名稱,包括其路徑 (相對於受參考組件之專案資料夾根目錄)。

下列範例顯示 XAML 資源檔的 Pack URI;其中的資源檔位於受參考組件之專案資料夾的根目錄中。

pack://application:,,,/ReferencedAssembly;component/ResourceFile.xaml

下列範例顯示 XAML 資源檔的 Pack URI;其中的資源檔位於受參考組件之專案資料夾的子資料夾中。

pack://application:,,,/ReferencedAssembly;component/Subfolder/ResourceFile.xaml

下列範例顯示 XAML 資源檔的 Pack URI;其中的資源檔位於受參考之特定版本組件其專案資料夾的根資料夾中。

pack://application:,,,/ReferencedAssembly;v1.0.0.1;component/ResourceFile.xaml

請注意,受參考組件資源檔的 Pack URI 語法只能與 application:/// 授權搭配使用。 例如,WPF 不支援下列語法。

pack://siteoforigin:,,,/SomeAssembly;component/ResourceFile.xaml

內容檔的 Pack URI 使用下列授權和路徑:

  • 授權:application:///。

  • 路徑:內容檔的名稱,包括其路徑 (相對於應用程式主要可執行組件的系統位置)。

下列範例顯示 XAML 內容檔的 Pack URI;其中的內容檔位於與可執行組件相同的資料夾中。

pack://application:,,,/ContentFile.xaml

下列範例顯示 XAML 內容檔的 Pack URI;其中的內容檔位於應用程式之可執行組件的相對子資料夾中。

pack://application:,,,/Subfolder/ContentFile.xaml

注意事項 注意事項

您不能巡覽至 HTML 內容檔。 URI 配置只支援巡覽至位於來源網站的 HTML 檔案。

來源網站的 Pack URI 使用下列授權和路徑:

  • 授權:siteoforigin:///。

  • 路徑:來源網路檔的名稱,包括其路徑 (相對於可執行組件的啟動位置)。

下列範例顯示 XAML 來源網站檔的 Pack URI;其中的來源網站檔儲存在可執行組件的啟動位置中。

pack://siteoforigin:,,,/SiteOfOriginFile.xaml

下列範例顯示 XAML 來源網站檔的 Pack URI;其中的來源網站檔儲存在應用程式可執行組件啟動位置的相對子資料夾中。

pack://siteoforigin:,,,/Subfolder/SiteOfOriginFile.xaml

設定為 MSBuild Page 項目的 XAML 檔案編譯成組件的方式與資源檔相同。 因此,MSBuild Page 項目可以使用資源檔的 Pack URI 來識別。

通常設定成 MSBuild Page 項目的 XAML 檔案具有下列其中一個根項目 (Root Element):

完整的 Pack URI 包括配置、授權和路徑,而且會被視為絕對 Pack URI。 為了簡化程式開發人員的工作,XAML 項目通常允許您使用只包含路徑的相對 Pack URI 來設定適當的屬性 (Attribute)。

例如,以本機組件中資源檔的下列絕對 Pack URI 為例:

pack://application:,,,/ResourceFile.xaml

指向此資源檔的相對 Pack URI 如下:

/ResourceFile.xaml

注意事項 注意事項

因為來源網站檔與組件無關,所以這些檔案只能以絕對 Pack URI 來參考。

根據預設,相對 Pack URI 應該與內含參考之標記或程式碼的位置相對。 不過,如果使用前置反斜線,則相對 Pack URI 參考則應該是相對於應用程式的根目錄。 例如,以下列專案結構為例:

App.xaml

Page2.xaml

\SubFolder

  + Page1.xaml

  + Page2.xaml

如果 Page1.xaml 包含參考 Root\SubFolder\Page2.xaml 的 URI,則此參考可以使用下列相對 Pack URI。

Page2.xaml

如果 Page1.xaml 包含參考 Root\Page2.xaml 的 URI,此參考便可使用下列相對 Pack URI。

/Page2.xaml

Pack URI 的格式使得不同檔案類型的 Pack URI 看起來可能完全相同。 例如,若以下列絕對 Pack URI 為例:

pack://application:,,,/ResourceOrContentFile.xaml

這個絕對 Pack URI 可以參考至本機組件中的資源檔或內容檔。 同樣的情況也適用於下列相對 URI:

/ResourceOrContentFile.xaml

為了判斷 Pack URI 所參考的檔案類型,WPF 會使用下列啟發方式解析本機組件中資源檔以及內容檔的 URI:

  1. 探查符合 Pack URI 之 AssemblyAssociatedContentFileAttribute 屬性的組件中繼資料 (Metadata)。

  2. 如果找到 AssemblyAssociatedContentFileAttribute 屬性,Pack URI 的路徑就會參考到內容檔。

  3. 如果找不到 AssemblyAssociatedContentFileAttribute 屬性,則請探查編譯成本機組件的已設定資源檔。

  4. 如果找到符合 Pack URI 路徑的資源檔,Pack URI 的路徑就會參考到資源檔。

  5. 如果找不到資源,內部建立的 Uri 便無效。

URI 解析不適用於參考下列項目的 URI:

  • 受參考組件中的內容檔:WPF 不支援這些檔案類型。

  • 受參考組件中的內嵌檔案:識別這些檔案的 URI 是唯一的,因為它們同時包含了受參考組件的名稱和 ;component 後置字元。

  • 來源網站檔:識別這些檔案的 URI 是唯一的,因為它們是包含 siteoforigin:/// 授權之 Pack URI 唯一可以識別的檔案。

Pack URI 解析可以接受的一種簡化方式是讓程式碼在某種程度上不受資源檔和內容檔的位置影響。 例如,如果您將本機組件中的資源檔重新設定為內容檔,該資源的 Pack URI 將維持不變,就像使用 Pack URI 的程式碼一樣。

許多 WPF 類別都實作可以使用 Pack URI 設定的屬性,包括:

這些屬性都可以從標記和程式碼設定。 本節示範兩者的基本建構,然後再顯示常見案例的範例。

Aa970069.collapse_all(zh-tw,VS.110).gif在標記中使用 Pack URI

在標記中指定 Pack URI 的方式是使用 Pack URI 設定屬性的項目。 例如:

<element attribute="pack://application:,,,/File.xaml" />

表 1 說明可以在標記中指定的各種絕對 Pack URI。

表 1:標記中的絕對 Pack URI

 

檔案

絕對 Pack URI

資源檔 - 本機組件

"pack://application:,,,/ResourceFile.xaml"

子資料夾中的資源檔 - 本機組件

"pack://application:,,,/Subfolder/ResourceFile.xaml"

資源檔 - 參考的組件

"pack://application:,,,/ReferencedAssembly;component/ResourceFile.xaml"

子資料夾中的資源檔 - 參考的組件

"pack://application:,,,/ReferencedAssembly;component/Subfolder/ResourceFile.xaml"

已建立版本之受參考組件中的資源檔

"pack://application:,,,/ReferencedAssembly;v1.0.0.0;component/ResourceFile.xaml"

內容檔

"pack://application:,,,/ContentFile.xaml"

子資料夾中的內容檔

"pack://application:,,,/Subfolder/ContentFile.xaml"

來源網站檔

"pack://siteoforigin:,,,/SOOFile.xaml"

子資料夾中的來源網站檔

"pack://siteoforigin:,,,/Subfolder/SOOFile.xaml"

表 2 說明可以在標記中指定的各種相對 Pack URI。

表 2:標記中的相對 Pack URI

 

檔案

相對 Pack URI

本機組件中的資源檔

"/ResourceFile.xaml"

本機組件子資料夾中的資源檔

"/Subfolder/ResourceFile.xaml"

受參考組件中的資源檔

"/ReferencedAssembly;component/ResourceFile.xaml"

子資料夾中的資源檔 - 參考的組件

"/ReferencedAssembly;component/Subfolder/ResourceFile.xaml"

內容檔

"/ContentFile.xaml"

子資料夾中的內容檔

"/Subfolder/ContentFile.xaml"

Aa970069.collapse_all(zh-tw,VS.110).gif在程式碼中使用 Pack URI

在程式碼中指定 Pack URI 的方式是執行個體化 Uri 類別,並將 Pack URI 當做參數傳遞至建構函式 (Constructor)。 這點在下列範例中示範。

 
Uri uri = new Uri("pack://application:,,,/File.xaml");

依預設,Uri 類別會將 Pack URI 視為絕對路徑。 因此,使用相對 Pack URI 建立 Uri 類別的執行個體 (Instance) 時,將會引發例外狀況 (Exception)。

 
Uri uri = new Uri("/File.xaml");

但幸好 Uri 類別建構函式的 Uri(String, UriKind) 多載可接受型別 UriKind 的參數,使您可以指定 Pack URI 是絕對還是相對路徑。

 
// Absolute URI (default)
Uri absoluteUri = new Uri("pack://application:,,,/File.xaml", UriKind.Absolute);
// Relative URI
Uri relativeUri = new Uri("/File.xaml", UriKind.Relative);

當您確定提供的 Pack URI 是絕對或相對路徑時,只能指定 Absolute 或 Relative 如果您不知道使用的 Pack URI 類型 (例如在使用者於執行階段中輸入 Pack URI 時),請改用 RelativeOrAbsolute

 
// Relative or Absolute URI provided by user via a text box
TextBox userProvidedUriTextBox = new TextBox();
Uri uri = new Uri(userProvidedUriTextBox.Text, UriKind.RelativeOrAbsolute);

表 3 說明可以使用 System.Uri 在程式碼中指定的各種絕對 Pack URI。

表 3:程式碼中的絕對 Pack URI

 

檔案

絕對 Pack URI

資源檔 - 本機組件

Uri uri = new Uri("pack://application:,,,/ResourceFile.xaml", UriKind.Absolute);

子資料夾中的資源檔 - 本機組件

Uri uri = new Uri("pack://application:,,,/Subfolder/ResourceFile.xaml", UriKind.Absolute);

資源檔 - 參考的組件

Uri uri = new Uri("pack://application:,,,/ReferencedAssembly;component/ResourceFile.xaml", UriKind.Absolute);

子資料夾中的資源檔 - 參考的組件

Uri uri = new Uri("pack://application:,,,/ReferencedAssembly;component/Subfolder/ResourceFile.xaml", UriKind.Absolute);

已建立版本之受參考組件中的資源檔

Uri uri = new Uri("pack://application:,,,/ReferencedAssembly;v1.0.0.0;component/ResourceFile.xaml", UriKind.Absolute);

內容檔

Uri uri = new Uri("pack://application:,,,/ContentFile.xaml", UriKind.Absolute);

子資料夾中的內容檔

Uri uri = new Uri("pack://application:,,,/Subfolder/ContentFile.xaml", UriKind.Absolute);

來源網站檔

Uri uri = new Uri("pack://siteoforigin:,,,/SOOFile.xaml", UriKind.Absolute);

子資料夾中的來源網站檔

Uri uri = new Uri("pack://siteoforigin:,,,/Subfolder/SOOFile.xaml", UriKind.Absolute);

表 4 說明可以使用 System.Uri 在程式碼中指定的各種相對 Pack URI。

表 4:程式碼中的相對 Pack URI

 

檔案

相對 Pack URI

資源檔 - 本機組件

Uri uri = new Uri("/ResourceFile.xaml", UriKind.Relative);

子資料夾中的資源檔 - 本機組件

Uri uri = new Uri("/Subfolder/ResourceFile.xaml", UriKind.Relative);

資源檔 - 參考的組件

Uri uri = new Uri("/ReferencedAssembly;component/ResourceFile.xaml", UriKind.Relative);

子資料夾中的資源檔 - 受參考的組件

Uri uri = new Uri("/ReferencedAssembly;component/Subfolder/ResourceFile.xaml", UriKind.Relative);

內容檔

Uri uri = new Uri("/ContentFile.xaml", UriKind.Relative);

子資料夾中的內容檔

Uri uri = new Uri("/Subfolder/ContentFile.xaml", UriKind.Relative);

Aa970069.collapse_all(zh-tw,VS.110).gif常見的 Pack URI 案例

前面各節已經討論如何建構 Pack URI 來識別資源、內容和來源網站等檔案。 在 WPF 中,這些建構有各種不同的使用方式,下列各節僅涵蓋幾個較常見的使用方式。

Aa970069.collapse_all(zh-tw,VS.110).gif指定應用程式啟動時所顯示的 UI

StartupUri 可指定 WPF 應用程式啟動時顯示的第一個 UI。 在獨立應用程式中,這個 UI 可能是視窗,如下列範例所示。

 
<Application
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    StartupUri="MainWindow.xaml" />


獨立應用程式 XAML 瀏覽器應用程式 (XBAP) 也可以指定頁面做為初始 UI,如下列範例所示。

 
<Application
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    StartupUri="HomePage.xaml" />


如果應用程式是獨立應用程式,而且使用 StartupUri 指定了頁面,WPF 將會開啟 NavigationWindow 來裝載該頁面。 若為 XBAP,此頁面會顯示在主瀏覽器中。

Aa970069.collapse_all(zh-tw,VS.110).gif巡覽至頁面

下列範例示範如何巡覽至頁面。

 
<Page
  xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
  WindowTitle="Page With Hyperlink"
  WindowWidth="250"
  WindowHeight="250">


...


<Hyperlink NavigateUri="UriOfPageToNavigateTo.xaml">
  Navigate to Another Page
</Hyperlink>


...


</Page>


如需 WPF 中各種巡覽方式的詳細資訊,請參閱巡覽概觀

Aa970069.collapse_all(zh-tw,VS.110).gif指定視窗圖示

下列範例示範如何使用 URI 指定視窗的圖示。

 
<Window
  xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
  xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
  x:Class="SDKSample.MainWindow"
	Icon="WPFIcon1.ico">
</Window>


如需詳細資訊,請參閱 Icon

Aa970069.collapse_all(zh-tw,VS.110).gif載入影像、音訊和視訊檔案

WPF 允許應用程式使用各種媒體類型,而且所有的媒體類型都可以使用 Pack URI 識別及載入,如下列各範例所示。

 
<MediaElement Stretch="Fill" LoadedBehavior="Play" Source="pack://siteoforigin:,,,/Media/bee.wmv" />


 
<MediaElement Stretch="Fill" LoadedBehavior="Play" Source="pack://siteoforigin:,,,/Media/ringin.wav" />


 
<Image Source="Images/Watermark.png" />


如需使用媒體內容的詳細資訊,請參閱 圖形和多媒體

Aa970069.collapse_all(zh-tw,VS.110).gif從來源網站載入資源字典

資源字典 (ResourceDictionary) 可用來支援應用程式佈景主題。 其中一種建立及管理佈景主題的方式是建立多個佈景主題,做為位於網站來源的資源字典, 如此您就可以新增及更新佈景主題,而不需要重新編譯及重新部署應用程式。 這些資源字典都可以使用 Pack URI 來識別及載入,如下列範例所示。

 
<Application
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    StartupUri="HomePage.xaml">
  <Application.Resources>
    <ResourceDictionary Source="pack://siteoforigin:,,,/PageTheme.xaml" />
  </Application.Resources>
</Application>


如需 WPF 中佈景主題的概觀,請參閱設定樣式和範本