Как я могу предоставить несколько условий для запуска данных в WPF?
Как я могу предоставить несколько условий для запуска данных в WPF?
Ответы:
Использовать тип MultiDataTrigger
<Style TargetType="ListBoxItem">
<Style.Triggers>
<DataTrigger Binding="{Binding Path=State}" Value="WA">
<Setter Property="Foreground" Value="Red" />
</DataTrigger>
<MultiDataTrigger>
<MultiDataTrigger.Conditions>
<Condition Binding="{Binding Path=Name}" Value="Portland" />
<Condition Binding="{Binding Path=State}" Value="OR" />
</MultiDataTrigger.Conditions>
<Setter Property="Background" Value="Cyan" />
</MultiDataTrigger>
</Style.Triggers>
</Style>
@jasonk - если вы хотите иметь "или", то отмените все условия, так как (A и B) <=> ~ (~ A или ~ B)
но если у вас есть значения, отличные от логических, попробуйте использовать преобразователи типов:
<MultiDataTrigger.Conditions>
<Condition Value="True">
<Condition.Binding>
<MultiBinding Converter="{StaticResource conditionConverter}">
<Binding Path="Name" />
<Binding Path="State" />
</MultiBinding>
</Condition.Binding>
<Setter Property="Background" Value="Cyan" />
</Condition>
</MultiDataTrigger.Conditions>
Вы можете использовать значения в методе Convert любым удобным для вас способом для создания условия, которое вам подходит.
conditionConverter
? Как мы указываем «Портленд» и «ИЛИ» в качестве двух наших or
вариантов в этом примере?
Чтобы уточнить ответ @ serine и проиллюстрировать работу с нетривиальным многозначным условием: мне нужно было показать наложение «затемнения» на элемент для логического условия NOT a AND (b OR NOT c)
.
Для справки, это вопрос с множественным выбором. Если пользователь выбирает неправильный ответ, он отключается (затемняется и не может быть выбран снова). Автоматизированный агент имеет возможность сосредоточиться на любом конкретном выборе, чтобы дать объяснение (граница выделена). Когда агент фокусируется на элементе, он не должен быть затемнен, даже если он отключен . Все предметы, которые не в фокусе, помечены как не сфокусированные и должны быть затемнены.
Логика для затемнения такова:
NOT IsFocused AND (IsDefocused OR NOT Enabled)
Чтобы реализовать эту логику, я сделал обобщение с IMultiValueConverter
именем (неловко), чтобы соответствовать моей логике
// 'P' represents a parenthesis
// ! a && ( b || ! c )
class NOT_a_AND_P_b_OR_NOT_c_P : IMultiValueConverter
{
// redacted [...] for brevity
public object Convert(object[] values, ...)
{
bool a = System.Convert.ToBoolean(values[0]);
bool b = System.Convert.ToBoolean(values[1]);
bool c = System.Convert.ToBoolean(values[2]);
return !a && (b || !c);
}
...
}
В XAML я использую это MultiDataTrigger
в <Style><Style.Triggers>
ресурс
<MultiDataTrigger>
<MultiDataTrigger.Conditions>
<!-- when the equation is TRUE ... -->
<Condition Value="True">
<Condition.Binding>
<MultiBinding Converter="{StaticResource NOT_a_AND_P_b_OR_NOT_c_P}">
<!-- NOT IsFocus AND ( IsDefocused OR NOT Enabled ) -->
<Binding Path="IsFocus"/>
<Binding Path="IsDefocused" />
<Binding Path="Enabled" />
</MultiBinding>
</Condition.Binding>
</Condition>
</MultiDataTrigger.Conditions>
<MultiDataTrigger.Setters>
<!-- ... show the 'dim-out' overlay -->
<Setter Property="Visibility" Value="Visible" />
</MultiDataTrigger.Setters>
</MultiDataTrigger>
И ради полноты, мой конвертер определен в ResourceDictionary
<ResourceDictionary xmlns:conv="clr-namespace:My.Converters" ...>
<conv:NOT_a_AND_P_b_OR_NOT_c_P x:Key="NOT_a_AND_P_b_OR_NOT_c_P" />
</ResourceDictionary>
ЭТОТ ОТВЕТ ТОЛЬКО ДЛЯ АНИМАЦИЙ.
Если вы хотите реализовать логику И, вы должны использовать MultiTrigger, вот пример:
Предположим, мы хотим выполнить некоторые действия, если свойство Text = "" (пустая строка) И IsKeyboardFocused = "False", тогда Ваш код должен выглядеть следующим образом:
<MultiTrigger>
<MultiTrigger.Conditions>
<Condition Property="Text" Value="" />
<Condition Property="IsKeyboardFocused" Value="False" />
</MultiTrigger.Conditions>
<MultiTrigger.EnterActions>
<!-- Your actions here -->
</MultiTrigger.EnterActions>
</MultiTrigger>
Если вы хотите реализовать логику ИЛИ, есть несколько способов, и это зависит от того, что вы пытаетесь сделать:
Первый вариант - использовать несколько триггеров.
Итак, предположим, что вы хотите что-то сделать, если либо Text = "" OR IsKeyboardFocused = "False",
то ваш код должен выглядеть примерно так:
<Trigger Property="IsEnabled" Value="false">
<Setter Property="Opacity" TargetName="border" Value="0.56"/>
</Trigger>
<Trigger Property="IsMouseOver" Value="true">
<Setter Property="BorderBrush" TargetName="border"
Value="{StaticResource TextBox.MouseOver.Border}"/>
</Trigger>
Но проблема в том, что будет делать , если я хочу сделать что - то , если любой текст не является нулевым или IsKeyboard = «True»? Это может быть достигнуто вторым подходом:
вспомните правило де Моргана, которое гласит! (! X &&! Y) = x || у.
Таким образом, мы будем использовать его для решения предыдущей проблемы, написав мульти-триггер, который срабатывает, когда Text = "" и IsKeyboard = "True", и мы выполним наши действия в EXIT ACTIONS , например:
<MultiTrigger>
<MultiTrigger.Conditions>
<Condition Property="Text" Value="" />
<Condition Property="IsKeyboardFocused" Value="False" />
</MultiTrigger.Conditions>
<MultiTrigger.ExitActions>
<!-- Do something here -->
</MultiTrigger.ExitActions>
</MultiTrigger>