ReactiveUI 使用 WhenAny 观察 Collection 并分配布尔值 PropertyHelper
ReactiveUI observing Collection with WhenAny and assigning boolean PropertyHelper
我有一个包含我想要观察的字符串的 ObservableCollection。当第一个索引发生变化时,我想更新一个 ObservableAsPropertyHelper 布尔变量,如果该索引处的字符串不为空且不为空,则将其设置为 true 。或者,将 Collection 转换为第二个包含 bool 的 ObservableCollection 的方法也可以。
这是我尝试过的:
public ObservableCollection<string> Difficulties { get; set; }
public extern bool Easy { [ObservableAsProperty] get; }
public Song()
{
this.WhenAny(x => x.Easy, x => x.GetValue()[0] != null && x.GetValue()[0}]!= "").ToPropertyEx(this, x => x.Easy);
}
我尝试了上面的代码,因为它适用于类似的示例:
[Reactive] public string Title { get; set; }
public extern bool Enabled { [ObservableAsProperty] get; }
public Song()
{
this.WhenAny(x => x.Title, x => x.GetValue() != null && x.GetValue() != "").ToPropertyEx(this, x => x.Enabled);
}
我对使用 Linq 表达式还很陌生,所以解决方案可能很简单(比我尝试过的东西要简单得多 -_-)
顺便说一句,我在 .net core 3.0 上使用 ReactiveUi.WPF 和 ReactiveUi.Fody。
WhenAnyValue
扩展方法通常用于您想观察视图模型属性变化的情况,并且在这方面非常出色。它并非设计用于可变集合,例如 ObservableCollection
或 ReadOnlyObservableCollection
。对于反应性集合,也可以使用 DynamicData library, see the related documentation page。最新的 ReactiveUI 版本依赖于 DynamicData,因此您不必安装任何额外的包。
TLDR;
如果您有 T
类型的 属性,则使用 WhenAnyValue
.
如果您有 ObservableCollection<T>
类型的 属性,请使用 ToObservableChangeSet
。
[ObservableAsProperty]
public bool Easy { get; }
public ObservableCollection<string> Difficulties { get; }
public Song()
{
Difficulties = new ObservableCollection<string>();
// Observe any changes in the observable collection.
// Note that the property has no public setters, so we
// assume the collection is mutated by using the Add(),
// Delete(), Clear() and other similar methods.
this.Difficulties
// Convert the collection to a stream of chunks,
// so we have IObservable<IChangeSet<TKey, TValue>>
// type also known as the DynamicData monad.
.ToObservableChangeSet(x => x)
// Each time the collection changes, we get
// all updated items at once.
.ToCollection()
// If the collection isn't empty, we access the
// first element and check if it is an empty string.
.Select(items =>
items.Any() &&
!string.IsNullOrWhiteSpace(items.First()))
// Then, we convert the boolean value to the
// property. When the first string in the
// collection isn't empty, Easy will be set
// to True, otherwise to False.
.ToPropertyEx(this, x => x.Easy);
}
请注意,如果您使用的是不可变数据集,例如有点像这样:
[Reactive] public IEnumerable<string> Difficulties { get; set; }
并且该数据集仅通过其 public setter 更新,那么您应该在此处使用 WhenAnyValue
扩展方法,因为声明为 IEnumerable<string>
的集合不是无法观察到:
this.WhenAnyValue(x => x.Difficulties)
.Select(items =>
items.Any() &&
!string.IsNullOrWhiteSpace(items.First()))
.ToPropertyEx(this, x => x.Easy);
我有一个包含我想要观察的字符串的 ObservableCollection。当第一个索引发生变化时,我想更新一个 ObservableAsPropertyHelper 布尔变量,如果该索引处的字符串不为空且不为空,则将其设置为 true 。或者,将 Collection 转换为第二个包含 bool 的 ObservableCollection 的方法也可以。
这是我尝试过的:
public ObservableCollection<string> Difficulties { get; set; }
public extern bool Easy { [ObservableAsProperty] get; }
public Song()
{
this.WhenAny(x => x.Easy, x => x.GetValue()[0] != null && x.GetValue()[0}]!= "").ToPropertyEx(this, x => x.Easy);
}
我尝试了上面的代码,因为它适用于类似的示例:
[Reactive] public string Title { get; set; }
public extern bool Enabled { [ObservableAsProperty] get; }
public Song()
{
this.WhenAny(x => x.Title, x => x.GetValue() != null && x.GetValue() != "").ToPropertyEx(this, x => x.Enabled);
}
我对使用 Linq 表达式还很陌生,所以解决方案可能很简单(比我尝试过的东西要简单得多 -_-)
顺便说一句,我在 .net core 3.0 上使用 ReactiveUi.WPF 和 ReactiveUi.Fody。
WhenAnyValue
扩展方法通常用于您想观察视图模型属性变化的情况,并且在这方面非常出色。它并非设计用于可变集合,例如 ObservableCollection
或 ReadOnlyObservableCollection
。对于反应性集合,也可以使用 DynamicData library, see the related documentation page。最新的 ReactiveUI 版本依赖于 DynamicData,因此您不必安装任何额外的包。
TLDR;
如果您有
T
类型的 属性,则使用WhenAnyValue
.如果您有
ObservableCollection<T>
类型的 属性,请使用ToObservableChangeSet
。
[ObservableAsProperty]
public bool Easy { get; }
public ObservableCollection<string> Difficulties { get; }
public Song()
{
Difficulties = new ObservableCollection<string>();
// Observe any changes in the observable collection.
// Note that the property has no public setters, so we
// assume the collection is mutated by using the Add(),
// Delete(), Clear() and other similar methods.
this.Difficulties
// Convert the collection to a stream of chunks,
// so we have IObservable<IChangeSet<TKey, TValue>>
// type also known as the DynamicData monad.
.ToObservableChangeSet(x => x)
// Each time the collection changes, we get
// all updated items at once.
.ToCollection()
// If the collection isn't empty, we access the
// first element and check if it is an empty string.
.Select(items =>
items.Any() &&
!string.IsNullOrWhiteSpace(items.First()))
// Then, we convert the boolean value to the
// property. When the first string in the
// collection isn't empty, Easy will be set
// to True, otherwise to False.
.ToPropertyEx(this, x => x.Easy);
}
请注意,如果您使用的是不可变数据集,例如有点像这样:
[Reactive] public IEnumerable<string> Difficulties { get; set; }
并且该数据集仅通过其 public setter 更新,那么您应该在此处使用 WhenAnyValue
扩展方法,因为声明为 IEnumerable<string>
的集合不是无法观察到:
this.WhenAnyValue(x => x.Difficulties)
.Select(items =>
items.Any() &&
!string.IsNullOrWhiteSpace(items.First()))
.ToPropertyEx(this, x => x.Easy);