Domanda

Ho un assembly della libreria di classi C # (2008 / .NET 3.5) che supporta WPF (basato su questo articolo ).
Ho creato diverse finestre e ora sto provando a creare un set di stile comune per loro. Tuttavia, poiché si tratta di una libreria di classi (anziché di un'app WPF), non ho un app.xaml (e il suo contenuto Application & amp; Application.Resources corrispondenti) in cui archiviare questi stili per l'accesso globale.

Quindi: Come posso creare una serie di definizioni di stile di livello superiore che verranno visualizzate da tutti i file xaml nell'assieme, dato che non ho app.xaml ( vedi sopra) ? E / o è possibile aggiungere un'app.xaml funzionante a una libreria di classi?

Cordiali saluti, ho provato a creare un ResourceDictionary in un file ResourceDictionary.xaml e includerlo in ogni finestra all'interno di un " Window.Resources " bloccare. Ciò si è rivelato per risolvere lo stile dei pulsanti, ecc ... ma non per la finestra chiusa. Posso mettere Style = " {StaticResource MyWindowStyle} " nel blocco di apertura di Window, e si compila e si presenta bene nella finestra di VS Design, ma durante il runtime effettivo ottengo un'eccezione di analisi (MyWindowStyle impossibile trovare; suppongo che Visual Studio veda il dizionario incluso dopo la riga in questione, ma il CRL esegue le operazioni in modo più sequenziale e quindi non ha ancora caricato ResourceDictionary).


Grazie per le idee, ma ancora niente da fare ... apparentemente una libreria di classi NON supporta implicitamente l'uso di generic.xaml. Ho aggiunto generic.xaml al mio progetto di libreria di classi e ho impostato la sua azione Build su " Resource " ;. Contiene:

<ResourceDictionary 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
    <Style TargetType="{x:Type Window}" x:Key="MyWindow">
        <Setter Property="Background" Value="Black"/>
    </Style>
</ResourceDictionary>

La finestra xaml che voglio avere usa il tema è simile a questa:

<Window x:Class="MyAssembly.ConfigureGenericButtons"
    x:ClassModifier="internal"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Style="{StaticResource MyWindow}"
    Title="ConfigureGenericButtons">
...Buttons, etc...
</Window>

Sebbene la finestra VS Design non mostri la finestra usando lo stile MyWindow (ovvero sfondo nero), si compila bene e si avvia. Tuttavia, quando l'app che contiene questa libreria di classi effettua una chiamata che causa la visualizzazione di questa finestra, ottengo una XamlParseException:

  

Impossibile trovare la risorsa denominata '{MyWindow}'.

Ho anche provato a tralasciare il parametro Style, per vedere se la finestra avrebbe usato lo stile di default (e ho provato che entrambi con x: Key in generic.xaml incluso e senza). Nessun errore, ma non è stato visualizzato neanche nulla definito in generic.xaml.

Sto facendo qualcosa di sbagliato qui, o qualsiasi altra idea su come si potrebbe consentire l'uso di stili personalizzati comuni su una finestra (cioè, non è necessario definire gli stili in ogni xaml di Windows) - con l'avvertenza che questo NON è un'applicazione?

È stato utile?

Soluzione

Prova ad aggiungere

Style={DynamicResource MyStyle}

In questo caso non è possibile utilizzare uno StaticResource.

Altri suggerimenti

Sembra un lavoro a tema.

  1. Aggiungi un /themes/generic.xaml ResourceDictionary al tuo progetto.
  2. Aggiungi quanto segue a AssemblyInfo.cs: [assembly: ThemeInfo (ResourceDictionaryLocation.None, ResourceDictionaryLocation.SourceAssembly)]
  3. profitto!

Tutte le risorse aggiunte al generico verranno utilizzate da tutti i controlli. Inoltre puoi creare temi specifici per il profilo (Luna, Aero ecc.) Includendo un file ResourceDictionary con il nome del tema corretto nella directory themes .

Ecco un link per maggiori informazioni: Crea e applica temi personalizzati

Se non si dispone di un app.xaml, è comunque possibile caricarlo nelle risorse a livello di moltiplicazione, ma è necessario scrivere codice (non xaml) per farlo, simile a questo ...

void LoadIt()
{
     ResourceDictionary MyResourceDictionary = new ResourceDictionary();
     MyResourceDictionary.Source = new Uri("MyResources.xaml", UriKind.Relative);
     App.Current.Resources.MergedDictionaries.Add(  MyResourceDictionary )
}

controlla questo sito per un esempio: http: // ascendedguard .com / 2007/08 / uno-di-belle-funzioni-about-WPF-è-how.html

Dr. WPF (o la persona precedentemente nota come Dr. WPF) ha un grande post sull'argomento.

Ecco un estratto dal post in cui creano l'oggetto Applicazione e aggiungono risorse:

if (Application.Current == null)
{
    // create the Application object
    new Application();

    // merge in your application resources
    Application.Current.Resources.MergedDictionaries.Add(
        Application.LoadComponent(
            new Uri("MyLibrary;component/Resources/MyResourceDictionary.xaml",
            UriKind.Relative)) as ResourceDictionary);
}

Dato che il mio assembly è ospitato tramite interop, ho dovuto aggiungere l'impostazione ShutdownMode come segue e l'arresto al termine:

new Application() { ShutdownMode = ShutdownMode.OnExplicitShutdown };

Ha funzionato come un fascino.

se lo carichi in Window.Resource, il dizionario è disponibile solo per i figli di quella finestra. Devi averlo disponibile per la finestra e i suoi figli.

Prova a caricarlo nel tuo file app.xaml. Ciò dovrebbe renderlo una risorsa a livello di applicazione, non una risorsa a livello di finestra.

Quindi, dopo aver trascorso molto tempo, ho finalmente capito. Ecco come:

  1. Nella libreria dei controlli WPF, aggiungi una nuova cartella denominata themes .
  2. All'interno della cartella themes , aggiungi un dizionario di risorse denominato generic.xaml .
  3. All'interno di generic.xaml , aggiungi la tua risorsa utilizzando la sintassi seguente:

    <SolidColorBrush x:Key="{ComponentResourceKey {x:Type local:UserControl1}, MyEllipseBrush}" Color="Blue" />
    
  4. Nel tuo controllo, utilizza la sintassi seguente per accedere a questa risorsa:

    Background="{StaticResource {ComponentResourceKey {x:Type local:UserControl1}, MyEllipseBrush}}"
    

Cose da notare:

  1. I passaggi 1 e 2 vengono normalmente eseguiti automaticamente da Visual Studio quando si crea una nuova libreria di controlli WPF.
  2. Non capisco completamente lo scopo del primo parametro di ComponentResourceKey , ma è obbligatorio. Utilizzare il nome del controllo che utilizzerà questa risorsa.
  3. Il progettista di Visual Studio non è stato in grado di individuare la risorsa nel mio caso. Potrebbe essere un problema di cache, non sono sicuro. In fase di esecuzione, tuttavia, funziona perfettamente.
  4. Puoi leggere maggiori dettagli su questa sintassi in questo articolo MSDN .

Spero che questo renda alcune vite più facili.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top