Стиль проверки TextBox в WPF исчезает, когда мышь находится над фокусом или имеет фокус - PullRequest
1 голос
/ 06 октября 2010

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

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

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

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

Я попытался создать некоторые дополнительные датггеры для событий IsMouseOver, IsFocused и IsMouseCaptured (показанных ниже), но безрезультатно.

Я что-то упустил?

Статический конструктор (показывает, что я использую стиль TextBox:

    static ValidatorTextBox()
    {
        //Commenting this line out to use the default textbox style
        DefaultStyleKeyProperty.OverrideMetadata(typeof(ValidatorTextBox), new FrameworkPropertyMetadata(typeof(TextBox)));
    }

А вот мой стиль:

 <Style TargetType="{x:Type local:ValidatorTextBox}">
    <Style.Triggers>
        <DataTrigger Binding="{Binding RelativeSource={RelativeSource Self}, Path=IsValid}" Value="False">
            <Setter Property="BorderBrush" Value="Red" />
            <Setter Property="BorderThickness" Value="1" />
        </DataTrigger>
        <DataTrigger Binding="{Binding RelativeSource={RelativeSource Self}, Path=IsRequired}" Value="True">
            <Setter Property="Background" Value="AliceBlue" />
        </DataTrigger>
        <DataTrigger Binding="{Binding RelativeSource={RelativeSource Self}, Path=IsFocused}" Value="True">
            <Setter Property="BorderBrush" Value="{Binding RelativeSource={RelativeSource Self}, Path=BorderBrush}" />
        </DataTrigger>
        <DataTrigger Binding="{Binding RelativeSource={RelativeSource Self}, Path=IsMouseOver}" Value="True">
            <Setter Property="BorderBrush" Value="{Binding RelativeSource={RelativeSource Self}, Path=BorderBrush}" />
        </DataTrigger>
        <DataTrigger Binding="{Binding RelativeSource={RelativeSource Self}, Path=IsMouseCaptured}" Value="True">
            <Setter Property="BorderBrush" Value="{Binding RelativeSource={RelativeSource Self}, Path=BorderBrush}" />
        </DataTrigger>
    </Style.Triggers>
</Style>

1 Ответ

2 голосов
/ 06 октября 2010

Скорее всего, проблема вызвана шаблоном TextBox по умолчанию. В Aero (и я думаю, что аналогично в некоторых других темах) граница на самом деле представляет собой элемент управления Chrome, который изменяется при наведении мыши на определенный цвет. Поскольку это происходит внутри ControlTemplate, он переопределяет TemplateBinding, обычно используемый для извлечения набора BorderBrush в стиле элемента управления. Самым прямым решением было бы фактически скопировать ControlTemplate по умолчанию в стиль вашего пользовательского элемента управления по умолчанию и использовать простую границу с настраиваемыми триггерами, а не просто в содержащем стиле.

<Style TargetType="{x:Type local:ValidatorTextBox}">
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="{x:Type local:ValidatorTextBox}">
                <Border x:Name="Bd" BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}" Background="{TemplateBinding Background}" SnapsToDevicePixels="true" >
                    <ScrollViewer x:Name="PART_ContentHost" SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}"/>
                </Border>
                <ControlTemplate.Triggers>
                    <Trigger Property="IsValid" Value="False">
                        <Setter Property="Background" TargetName="Bd" Value="Red"/>
                    </Trigger>
                    <Trigger Property="IsEnabled" Value="false">
                        <Setter Property="Background" TargetName="Bd" Value="{DynamicResource {x:Static SystemColors.ControlBrushKey}}"/>
                        <Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.GrayTextBrushKey}}"/>
                    </Trigger>
                </ControlTemplate.Triggers>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...