Bonjour!
我的产品型号包含许多经典属性(代码,描述,价格含增值税,价格不含增值税,增值税)。对于我的例子,我只放了一些有趣的属性。
在这个模型中,我想添加价格计算。当任何金额变化时,计算其他属性(当增值税改变时,重新计算价格与增值税和价格无增值税,反之亦然)
我的例子:
public class Product : EditableObject
{
//VAT percentage propertie (ex: 20%)
private decimal _vat;
public decimal Vat
{
get { return _vat; }
set
{
_vat = value;
PriceWithVat = _priceWithoutVat * (1 + Vat / 100); //Vat changed, we recalculate Price WITH VAT propertie
PriceWithoutVat = _priceWithVat / (1 + Vat / 100); //Vat changed, we recalculate Price WITHOUT VAT propertie
NotifyOfPropertyChange(() => Vat);
}
}
//Product Price Without VAT
private decimal _priceWithoutVat;
public decimal PriceWithoutVat
{
get { return _priceWithoutVat; }
set
{
_priceWithoutVat = value;
PriceWithVat = _priceWithoutVat * (1 + Vat / 100); //PriceWithoutVat changed, we recalculate Price WITH VAT propertie
NotifyOfPropertyChange(() => PriceWithoutVat);
}
}
//Product Price WITH Vat
private decimal _priceWithVat;
public decimal PriceWithVat
{
get { return _priceWithVat; }
set
{
_priceWithVat = value;
PriceWithoutVat = _priceWithVat / (1 + Vat / 100); //PriceWithVat changed, we recalculate Price WITHOUT VAT propertie
NotifyOfPropertyChange(() => PriceWithVat);
}
}
}
有了这个,当任何价格变化时,我有无限循环和Stack Overflow。正常,因为当价格发生任何变化时,所有其他价格都会重新计算,并且他们会依次重新计算价格:)
您是否有解决方案在其中任何一个更改时自动重新计算我的3个金额?
答案 0 :(得分:1)
不要将计算属性设为读写。相反,为只读计算属性引用适当的PropertyChanged
,例如:
public decimal Price
{
get { return _price; }
set
{
if (_price != value)
{
_price = value;
NotifyOfPropertyChange(() => Price);
NotifyOfPropertyChange(() => PriceWithVat);
}
}
}
public decimal Vat
{
get { return _vat; }
set
{
if (_vat != value)
{
_vat = value;
NotifyOfPropertyChange(() => Vat);
NotifyOfPropertyChange(() => PriceWithVat);
}
}
}
public decimal PriceWithVat
{
get { return _price / (1 + _vat / 100); }
}
由于它们是计算的属性,因此您无法直接设置其值。另一方面,为他们提升PropertyChanged
足以从UI重新读取他们的值。
<强>更新强>
根据您的评论(即使这是非常奇怪的要求),您可以通过更新支持字段值来实现您想要的效果。请注意,您不得在此处调用属性设置器以避免StackoverflowException
:
private void UpdatePriceWithVat()
{
_priceWithVat = _price * (1 + _vat / 100);
NotifyOfPropertyChange(() => PriceWithVat);
}
private void UpdatePrice()
{
_price = _priceWithVat / (1 + _vat / 100);
NotifyOfPropertyChange(() => Price);
}
public decimal Price
{
get { return _price; }
set
{
if (_price != value)
{
_price = value;
NotifyOfPropertyChange(() => Price);
UpdatePriceWithVat();
}
}
}
public decimal Vat
{
get { return _vat; }
set
{
if (_vat != value)
{
_vat = value;
NotifyOfPropertyChange(() => Vat);
UpdatePriceWithVat();
}
}
}
public decimal PriceWithVat
{
get { return _priceWithVat; }
set
{
if (_priceWithVat != value)
{
_priceWithVat = value;
NotifyOfPropertyChange(() => PriceWithVat);
UpdatePrice();
}
}
}
两个注释: