ResourceDictionary в отдельной сборке


245

У меня есть файлы словаря ресурсов (MenuTemplate.xaml, ButtonTemplate.xaml и т. Д.), Которые я хочу использовать в нескольких отдельных приложениях. Я мог бы добавить их в сборки приложений, но было бы лучше, если бы я скомпилировал эти ресурсы в одну сборку и чтобы мои приложения ссылались на него, верно?

После сборки сборки ресурса, как я могу ссылаться на нее в App.xaml моих приложений? В настоящее время я использую ResourceDictionary.MergedDictionaries для объединения отдельных файлов словаря. Если у меня есть их в сборке, как я могу ссылаться на них в xaml?


1
Это может быть излишним, но вы можете подготовить свои ресурсы для экспорта, используя метод, описанный здесь: alexfeinberg.wordpress.com/2015/08/16/… . Основным преимуществом этого является предотвращение проблем с загрузкой нескольких версий сборки ресурса в один домен приложения.
user195275

Ответы:


353

Проверьте синтаксис URI пакета . Вы хотите что-то вроде этого:

<ResourceDictionary Source="pack://application:,,,/YourAssembly;component/Subfolder/YourResourceFile.xaml"/>

1
Что если YourAssembly не содержится в пути приложения?
SaneDeveloper

@Engineer Spock: тогда CLR не найдет его без посторонней помощи (ничего общего с WPF). Либо добавьте пробные пути к вашему app.config , либо присоедините, AppDomain.AssemblyResolveчтобы помочь ему найти сборку.
Кент Бугаарт

1
Нужно ли добавлять пробный путь, если проект YourAssembly находится на том же уровне, что и проект приложения, который должен ссылаться на YourAssembly? Например, C: \ Solution \ AppProject \ и C: \ Solution \ YourAssemblyProject \
SaneDeveloper

1
@EngineerSpock: это отдельный вопрос, поэтому, пожалуйста, откройте его.
Кент Бугаарт

2
Этот ответ не имеет смысла. Чтобы следовать этому, нужно уже знать, как это сделать!
user1040323

97

Например, просто чтобы ответить на 15 секунд -

Скажем, у вас есть файл "styles.xaml" в библиотеке WPF с именем "common", и вы хотите использовать его из основного проекта приложения:

  1. Добавить ссылку из основного проекта в «общий» проект
  2. Ваш app.xaml должен содержать:

<Application.Resources>
    <ResourceDictionary>
        <ResourceDictionary.MergedDictionaries>
            <ResourceDictionary Source="pack://application:,,,/Common;component/styles.xaml"/>
        </ResourceDictionary.MergedDictionaries>
    </ResourceDictionary>
</Application.Resources>

ура


2
И как сделать ресурсы, определенные в styles.xaml, доступными через окно свойств Visual Studio 2010? Если я выбираю элемент и затем нажимаю «Применить ресурс» для его свойства «Фон», он показывает только SystemColors, а не те, которые определены в styles.xaml. Но если я сам наберу имя ресурса в XAML, оно будет работать, поэтому на него будут ссылаться правильно.
xr280xr

Просто хотел добавить, что если вы ссылаетесь на ResourceDictionary из UserControl, то вам нужно добавить ссылку на сборку в обоих местах: в UserControl и в проекте главного окна. В противном случае вы получите ошибку во время выполнения.
Андрей Гасилов,


16

Resource-Only DLL - вариант для вас. Но это не обязательно, если вы не хотите изменять ресурсы без перекомпиляции приложений. Иметь только один общий файл ResourceDictionary также вариант. Это зависит от того, как часто вы меняете ресурсы и т. Д.

<ResourceDictionary Source="pack://application:,,,/
     <MyAssembly>;component/<FolderStructureInAssembly>/<ResourceFile.xaml>"/>

MyAssembly - просто имя сборки без расширения

FolderStructureInAssembly - если ваши ресурсы находятся в папке, укажите структуру папок

Когда вы делаете это, лучше знать о siteOfOrigin .

WPF поддерживает два органа: application: /// и siteoforigin: ///. Application: /// Authority идентифицирует файлы данных приложения, которые известны во время компиляции, включая файлы ресурсов и содержимого. Атрибут siteoforigin: /// определяет сайт исходных файлов. Объем каждого органа показан на следующем рисунке.

введите описание изображения здесь



4

Использование XAML:

Если вы знаете другую assemblyструктуру и хотите использовать код resourcesin c # , используйте следующий код:

 ResourceDictionary dictionary = new ResourceDictionary();
 dictionary.Source = new Uri("pack://application:,,,/WpfControlLibrary1;Component/RD1.xaml", UriKind.Absolute);
 foreach (var item in dictionary.Values)
 {
    //operations
 }

Вывод: если мы хотим использовать ResourceDictionary RD1.xamlProject WpfControlLibrary1в StackOverflowAppпроекте.

Структура проектов :

Структура проектов

Ресурсный словарь: Ресурсный словарь

Вывод кода:

Вывод

PS: все ResourceDictionaryфайлы должны иметь Build Actionкак ' Resource' или ' Page'.

Используя C #:

Если кому-то нужно решение в чисто коде c #, тогда посмотрите мое решение.

Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.