10

ほとんどのウィンドウの派生元となる基本ウィンドウ クラスを作成中です。明らかに、これに対する最善の解決策は、別のクラスとそれに適用されるスタイルでした。

問題は、<Style ../>私が持っている が にあるときに適用されないことですApp.Resources。つまり、外部ResourceDictionaryで定義されていて のリソースにマージされてApp.xamlいるか、ローカル ディクショナリにマージまたはインラインで配置されている場合App.Resourcesです。<Style ../>ただし、 は に配置されたときに適用されますThemes/Generic.xaml

この問題は、ベース ウィンドウで何も特別なことをしなくても実証できますDefaultStyleKeyProperty。.

以下はThemeWindow

public class ThemeWindow : Window
{
    static ThemeWindow()
    {
        DefaultStyleKeyProperty.OverrideMetadata(typeof(ThemeWindow), new FrameworkPropertyMetadata(typeof(ThemeWindow)));
    }
}

<Style ../>これは私が適用しようとしている非常に単純なものです(Window背景が赤くなり、それ以上のものはありません):

<Style TargetType="{x:Type testing:ThemeWindow}">
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="{x:Type testing:ThemeWindow}">
                <Grid>
                    <Grid.Background>
                        <SolidColorBrush Color="Red"/>
                    </Grid.Background>
                    <AdornerDecorator>
                        <ContentPresenter />
                    </AdornerDecorator>
                </Grid>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>

MainWindowを使用する は、ThemeWindow単純に次の XAML です。

<testing:ThemeWindow x:Class="Testing.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:testing="clr-namespace:Testing"
        Title="MainWindow" Height="350" Width="525">
    <Grid>
        <Button Content="Button" HorizontalAlignment="Left" Margin="125,83,0,0" VerticalAlignment="Top" Width="75"/>
    </Grid>
</testing:ThemeWindow>

さて、述べたようにStyle、それを独自のに配置し、次のResourceDictionaryように含めると:

<App.Resources>
    <ResourceDictionary>
        <ResourceDictionary.MergedDictionaries>
            <ResourceDictionary Source="/Themes/ThemeWindow.xaml" />
        </ResourceDictionary.MergedDictionaries>
    </ResourceDictionary>
</App.Resources>

.. それは動作しません。スタイルを に直接インライン化するApp.Resourcesと、機能しません。

動作していることがわかる唯一の状況は、 ResourceDictionaryxamlを呼び出して、アプリケーションのディレクトリにGeneric.xaml配置することです。Themes/

なぜこれが起こっているのか、私は正確に疑問に思っています。

私の唯一の理論は、WPF がコントロール タイプを検出すると、 に向かい、そのタイプのThemesすべての をスキャンしてから、ResourceDictionaryフォールバックしGeneric.xamlてロードするというものです。<Style />ただし、マージされた が利用可能な場合にロードされない理由は説明されていませんResourceDictionary。明らかな理由から、 を に配置すると機能することに注意してください。MergedDictionaryGeneric.xaml

それが私がしなければならないことである場合、私はにマージResourceDictionaryGeneric.xamlなければならないことに完全に問題ありません。なぜこのようにする必要があるのか​​について、技術的な詳細に取り掛かりたいと思います。

これが機能しない/機能するスクリーンショット: 壊れた画像 作業イメージ

4

2 に答える 2

3

app.xaml でスタイルを設定できる簡単な回避策があります。

次のように app.xaml でスタイルを定義します。

<Style x:Key="{x:Type testing:ThemeWindow}" TargetType="{x:Type testing:ThemeWindow}">

そして、ThemWindow を次のように変更します。

public class ThemeWindow : Window
{
    static ThemeWindow()
    {
        StyleProperty.OverrideMetadata(typeof(ThemeWindow), new FrameworkPropertyMetadata(GetDefautlStyle()));
    }

    private static Style GetDefautlStyle()
    {
        if (defaultStyle == null)
        {
            defaultStyle = Application.Current.FindResource(typeof(ThemeWindow)) as Style;
        }
        return defaultStyle;
    }

    private static Style defaultStyle = null;
}

質問を実際に解決するわけではありませんが、必要なものを達成することができます!

編集: DefaultStyleKey参照を見ると、それがテーマ スタイル ルックアップに使用されていることが明確に述べられています。これは、app.xaml やその他の辞書で見つからない理由を説明しています。テーマ辞書のみを検索します。そのため、テーマ ディクショナリでスタイルを定義するか、上記の例のように Style プロパティを直接使用する必要があります。

于 2013-01-17T16:40:45.067 に答える
0

stackoverflow で既に説明されている次のソリューションを回避します。アプリケーションのロード時にロード コンポーネントを追加する必要があります。

ソリューションを参照

于 2013-01-17T17:26:50.987 に答える