Есть ли в XAML директива условного компилятора для режима отладки? - PullRequest
59 голосов
/ 04 января 2012

Мне нужно что-то подобное для стилей в XAML:

<Application.Resources>

#if DEBUG
    <Style TargetType="{x:Type ToolTip}">
        <Setter Property="FontFamily" Value="Arial"/>
        <Setter Property="FlowDirection" Value="LeftToRight"/>
    </Style>
#else
    <Style TargetType="{x:Type ToolTip}">
        <Setter Property="FontFamily" Value="Tahoma"/>
        <Setter Property="FlowDirection" Value="RightToLeft"/>
    </Style>
#endif

</Application.Resources>

Ответы [ 4 ]

107 голосов
/ 13 ноября 2013

Мне недавно пришлось это сделать, и я был удивлен, насколько просто это было, когда я не мог легко найти какие-либо четкие примеры.Что я сделал, так это добавил в AssemblyInfo.cs следующее:

#if DEBUG
[assembly: XmlnsDefinition( "debug-mode", "Namespace" )]
#endif

Затем с помощью тега AlternateContent пространства имен разметки-совместимости выберите свой контент на основе наличия этого определения пространства имен:

<Window x:Class="Namespace.Class"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"

        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:d="debug-mode"

        Width="400" Height="400">

        ...

        <mc:AlternateContent>
            <mc:Choice Requires="d">
                <Style TargetType="{x:Type ToolTip}">
                    <Setter Property="FontFamily" Value="Arial"/>
                    <Setter Property="FlowDirection" Value="LeftToRight"/>
                </Style>
            </mc:Choice>
            <mc:Fallback>
                <Style TargetType="{x:Type ToolTip}">
                    <Setter Property="FontFamily" Value="Tahoma"/>
                    <Setter Property="FlowDirection" Value="RightToLeft"/>
                </Style>
            </mc:Fallback>
        </mc:AlternateContent>

        ...
</Window>

Теперь, когда определен DEBUG, также будет определен «режим отладки» и будет присутствовать пространство имен «d».Это заставляет тег AlternateContent выбирать первый блок кода.Если DEBUG не определен, будет использован блок кода Fallback.

Этот пример кода не был протестирован, но в основном это то же самое, что я использую в моем текущем проекте для условного отображения некоторых кнопок отладки.

Я видел сообщение в блоге с примером кода, в котором использовался тег «Ignorable», но он казался намного менее понятным и простым в использовании, чем этот метод.

2 голосов
/ 06 января 2012

Это невозможно в WPF / Silverlight / WP7.

В интересной заметке документ по стандартам ISO / IEC 29500 описывает, как это должно обрабатываться в документе XML, а XAML поддерживает один из элементов из этой спецификации mc:Ignorable, который нам делать такие вещи:

<Page xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
      xmlns:c="Comments"
      mc:Ignorable="c">
    <Button Content="Some Text"
            c:Content="Some other text" />
</Page>

чтобы закомментировать атрибуты. Я думаю, было бы здорово, если бы XAML однажды поддержал остальную часть спецификации, которая позволяет загружать альтернативный контент.

Атрибут mc:Ignorable используется Blend для поддержки функций времени разработки.

2 голосов
/ 04 января 2012

Вы можете использовать селектор шаблонов.Класс DataTemplateSelector - это то, что вы кодируете.С методом выбора шаблона, который вы переопределяете, вы можете поместить свои директивы препроцессора.

1 голос
/ 18 июня 2018

Мне кажется, что данные ответы не самые простые в использовании. Вот мое решение с использованием настраиваемого присоединяемого свойства зависимостей:

using namespace Utility{
    public static class DebugVisibility
    {
        public static readonly DependencyProperty IsVisibleProperty = DependencyProperty.RegisterAttached(
    "Debug", typeof(bool?), typeof(DebugVisibility), new PropertyMetadata(default(bool?), IsVisibleChangedCallback));

        private static void IsVisibleChangedCallback(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            var fe = d as FrameworkElement;
            if (fe == null)
                return;
#if DEBUG
            fe.Visibility = Visibility.Visible;
#else
            fe.Visibility = Visibility.Collapsed;
#endif
        }

        public static void SetIsVisible(DependencyObject element, bool? value)
        {
            element.SetValue(IsVisibleProperty, value);
        }

        public static bool? GetIsVisible(DependencyObject element)
        {
            return (bool?)element.GetValue(IsVisibleProperty);
        }
    }
}

и xaml будет использоваться так:

<window ... xmlns:Util="clr-namespace:MyNamespace.Utility" >
    <Label Util:DebugVisibility.IsVisible="True">
</window>

Я оставил это как бул на случай, если вы захотите добавить какую-то другую логику видимости. Это хороший простой переключатель, который можно привязать к любому элементу управления и присоединить к нему

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...