2009-03-29 8 views
9

In <Window.Resources> ho definito stile seguente:È possibile impostare uno stile in XAML che influenzi selettivamente i controlli?

<Style x:Key="textBlockStyle" TargetType="TextBlock"> 
     <Setter Property="Margin" Value="5,0,5,0"/> 
    </Style> 

ho definito alcuni griglia dove ho quattro TextBlocks:

<WrapPanel> 
     <TextBlock Style="{StaticResource textBlockStyle}">Server</TextBlock> 
     <TextBlock Style="{StaticResource textBlockStyle}">IP</TextBlock> 
     <TextBlock Style="{StaticResource textBlockStyle}">Port</TextBlock> 
     <TextBlock Style="{StaticResource textBlockStyle}">Status</TextBlock> 
    </WrapPanel> 

Problema: Ho necessario fare riferimento alla textBlockStyle quattro volte.

Domanda: È possibile impostare tale stile una sola volta in WrapPanel o altrove senza ripetere il riferimento allo stile?

Forse qualcosa di simile:

<WrapPanel Style="{StaticResource textBlockStyle}"> 
     <TextBlock>Server</TextBlock> 
     <TextBlock>IP</TextBlock> 
     <TextBlock>Port</TextBlock> 
     <TextBlock>Status</TextBlock> 
    </WrapPanel> 

io non sono alla ricerca di una soluzione globale! È possibile eliminare la proprietà x:Key="textBlockStyle", ma ciò influirebbe sullo aTextBlocks nella finestra. Ho bisogno di un meccanismo più selettivo, ma senza quella brutta duplicazione del codice.

risposta

17

Hai diverse opzioni, presentate qui in base alla loro scalabilità.

Opzione 1: definire lo stile senza una chiave a un livello inferiore

Si può attaccare la risorsa a livello WrapPanel in modo che esso riguarda solo i controlli all'interno che WrapPanel:

<WrapPanel> 
    <WrapPanel.Resources> 
     <Style TargetType="TextBlock"> 
      <Setter Property="Margin" Value="5,0,5,0"/> 
     </Style> 
    </WrapPanel.Resources> 

    <!-- TextBlocks here --> 
</WrapPanel> 

Avviso la mancanza di chiave. Questo Style si applica a tutti gli TextBlock s all'interno dello WrapPanel.

Opzione 2: definire lo stile con una chiave e di nuovo senza ad un livello inferiore

Se si definisce il Style a un livello superiore con una chiave, si può quindi definire un altro Style ad un livello inferiore, senza una chiave, e la base che Style al livello più alta:

<Window> 
    <Window.Resources> 
     <Style TargetType="TextBlock" x:Key="textBlockStyle"> 
      <Setter Property="Margin" Value="5,0,5,0"/> 
     </Style> 
    </Window.Resources> 

    <WrapPanel> 
     <WrapPanel.Resources> 
      <Style TargetType="TextBlock" BasedOn="{StaticResource textBlockStyle"/> 
     </WrapPanel.Resources> 

     <!-- TextBlocks here --> 
    </WrapPanel> 
</Window> 

Ciò comporta un Style essendo applicato automaticamente TextBlock s dentro l'WrapPanel, ma non al di fuori di esso. Inoltre, non si duplicano i dettagli dello Style - sono memorizzati ad un livello superiore.

Opzione 3: Posizionare i stili in un ResourceDictionary e selettivamente fondono lo

Infine, è possibile inserire i tuoi Style s in un separato ResourceDictionary e selettivamente fondersi quel dizionario in Resources collezione di un controllo:

<!-- TextBlockStyles.xaml --> 
<ResourceDictionary> 
    <Style TargetType="TextBlock"> 
     <Setter Property="Margin" Value="5,0,5,0"/> 
    </Style> 
</ResourceDictionary> 

<!-- Window.xaml --> 
<Window> 
    <WrapPanel> 
     <WrapPanel.Resources> 
      <ResourceDictionary> 
       <ResourceDictionary.MergedDictionaries> 
        <ResourceDictionary Source="TextBlockStyles.xaml"/> 
       </ResourceDictionary.MergedDictionaries> 
      </ResourceDictionary> 
     </WrapPanel.Resources> 
    </WrapPanel> 
</Window> 

<!-- Alternative Window.xaml if you have only one RD to merge in --> 
<Window> 
    <WrapPanel> 
     <WrapPanel.Resources> 
      <ResourceDictionary Source="TextBlockStyles.xaml"/> 
     </WrapPanel.Resources> 
    </WrapPanel> 
</Window> 

Ora è possibile impostare il numero di insiemi di stili definito in dizionari separati come desiderato, quindi applicarli in modo selettivo all'albero degli elementi.

+0

Di solito preferisco l'opzione 2 se ho lo stile già definito e lo uso altrove, altrimenti l'opzione 1. Per quello che vale. Grande risposta Kent. –

2

sì, puoi farlo. Hai quasi l'idea giusta. lo si fa in questo modo ....

<WrapPanel> 
< WrapPanel. Resources > 
<Style TargetType="{x:Type TextBlock}"> 
     <Setter Property="Margin" Value="5,0,5,0"/> 
    </Style> 
</WrapPanel.Resources/> 
     <TextBlock Server</TextBlock> 
     <TextBlock >IP</TextBlock> 
     <TextBlock >Port</TextBlock> 
     <TextBlock >Status</TextBlock> 
    </WrapPanel> 

utilizzando il {x: tipo} sintassi non avete bisogno la x: chiave, sarà impostare lo stile per tutti i TextBlocks nella WrapPanel. se vuoi gli stili diff, puoi comunque usare la chiave x: ed esplicitamente impostare lo stile sul blocco di testo.

Problemi correlati