如何从ObservableCollection获取特定参数?修复Xamarin.Forms杂货清单应用删除商品时总价计算错误问题
解决杂货清单应用的删除价格计算错误与商品ID系统实现
首先,先解决你最头疼的总价扣除错误问题——其实核心原因很简单:你现在删除时用的是ViewModel里绑定输入框的Price值,而不是被删除商品自己的价格!
第一步:修复删除时的总价计算逻辑
找到你ViewModel中的RemoveTodoItem方法,把扣除总价的代码改成使用被删除商品自身的Price属性:
void RemoveTodoItem(object o) { TodoItem todoItemBeingRemoved = o as TodoItem; // 加个空判断,避免意外报错 if (todoItemBeingRemoved != null) { TodoItems.Remove(todoItemBeingRemoved); // 这里改成用被删商品的价格,而不是输入框的Price TotalPrice -= todoItemBeingRemoved.Price; } }
这样修改后,点击删除西兰花时,就会从总价里减去它自己的6.5,而不是输入框里的3了!
第二步:给每个商品添加唯一ID(可选但推荐)
你现在通过CommandParameter="{Binding .}"已经能把要删除的商品对象直接传到删除方法里,其实已经能准确识别目标商品,但添加ID会让数据更规范,后续如果要做数据持久化(比如存数据库)或者更复杂的操作会更方便。
方案1:自动生成全局唯一ID(最简单)
修改你的TodoItem类,添加一个Guid类型的ID属性——Guid是系统自动生成的唯一字符串,不会重复:
public class TodoItem { // 新增唯一ID属性 public Guid Id { get; set; } public string ToDoText { get; set; } public bool Complete { get; set; } public double Price { get; set; } public TodoItem(string toDoText, bool complete, double price) { // 创建商品时自动生成唯一ID Id = Guid.NewGuid(); ToDoText = toDoText; Complete = complete; Price = price; } }
方案2:自增数字ID(适合喜欢整数标识的场景)
如果你偏好数字ID,可以在ViewModel里加一个计数器,每次添加商品时自动递增:
- 先修改
TodoItem类的构造函数,添加ID参数:
public class TodoItem { public int Id { get; set; } public string ToDoText { get; set; } public bool Complete { get; set; } public double Price { get; set; } public TodoItem(int id, string toDoText, bool complete, double price) { Id = id; ToDoText = toDoText; Complete = complete; Price = price; } }
- 在ViewModel里添加计数器,并修改
AddTodoItem方法:
public class TodoListViewModel : INotifyPropertyChanged { // 自增计数器,从1开始 private int _nextItemId = 1; // ... 其他原有代码不变 ... void AddTodoItem() { // 传入自增的ID TodoItems.Add(new TodoItem(_nextItemId++, NewTodoInputValue, false, Price)); TotalPrice += Price; } }
额外小优化(提升用户体验)
- 添加商品后清空输入框:避免下次添加时默认使用之前的输入内容:
void AddTodoItem() { // 简单验证,防止添加空名称或负价格的商品 if (!string.IsNullOrWhiteSpace(NewTodoInputValue) && Price >= 0) { TodoItems.Add(new TodoItem(NewTodoInputValue, false, Price)); TotalPrice += Price; // 清空输入框并通知UI更新 NewTodoInputValue = string.Empty; Price = 0; OnPropertyChanged(nameof(NewTodoInputValue)); OnPropertyChanged(nameof(Price)); } }
- 修正TotalPrice的属性通知:你当前的
TotalPrice属性里错误通知了Price的变化,应该改为通知自身:
public double TotalPrice { get => name; set { if (name == value) { return; } name = value; // 新增这个通知,规范属性变更通知逻辑 OnPropertyChanged(nameof(TotalPrice)); OnPropertyChanged(nameof(DisplayName)); } }
这样改完,你的删除价格计算就正常了,商品ID系统也能正常工作,应用体验也会更流畅!
内容的提问来源于stack exchange,提问作者Sexy Scorch
相关产品推荐
相关产品推荐

