есть класс Project (модель) с некиеми методами:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Xml.Serialization;
using System.Xml.Linq;
using System.IO;
using System.Xml;
using System.Collections.ObjectModel;
using System.ComponentModel;
namespace ReadAndVerify
{
[Serializable]
public class Project : INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged;
[XmlIgnore]
private static string pathToFile = @"..\..\Xml\Project.xml";
[XmlIgnore]
private string title;
[XmlIgnore]
private DateTime startDateForProject;
[XmlIgnore]
private DateTime finishDateForProject;
public string Title { get { return title; } set { title = value; RaisePropertyChanged("Title"); } }
[XmlElement("StartDate")]
public DateTime StartDateForProject { get { return startDateForProject; } set { startDateForProject = value; RaisePropertyChanged("StartDateForProject"); } }
[XmlElement("FinishDate")]
public DateTime FinishDateForProject { get { return finishDateForProject; } set { finishDateForProject = value; RaisePropertyChanged("FinishDateForProject"); } }
public Project() { }
public Project(string title,DateTime startDate, DateTime finishDate)
{
Title = title;
StartDateForProject = startDate;
FinishDateForProject = finishDate;
//DayOfProject = 10;
}
public static ObservableCollection<MyDictionary> getTheurrentPercentageOfTheDayOfProjectExecution(List<Project> projects)
{
ObservableCollection<MyDictionary> result = new ObservableCollection<MyDictionary>();
foreach (Project _project in projects)
{
// Сколько всего дней для проекта (100%)
int maxDate = _project.FinishDateForProject.Subtract(_project.StartDateForProject).Days;
// Сколько прошо дней (кол-во)
int curentDate = DateTime.Now.Subtract(_project.StartDateForProject).Days;
// Текущий процен пройденых дней
result.Add(new MyDictionary(_project.Title, curentDate * 100 / maxDate));
}
return result;
}
protected virtual void RaisePropertyChanged(PropertyChangedEventArgs e)
{
var handler = PropertyChanged;
if (handler != null) handler(this, e);
}
protected void RaisePropertyChanged(string propertyName)
{
RaisePropertyChanged(new PropertyChangedEventArgs(propertyName));
}
}
}
Во ViewModel есть переменная project, которая содержит в себе все проекты с xml файла (биндится DataGrit Mode = TwoWay) для редактирования данных каждого проекта. Отображение идет в другом окне через прогресс бары + текстблок отдельной переменной, которая заполняется методом getTheurrentPercentageOfTheDayOfProjectExecution() класса Project. Класс MyDictionary имеет реализацию интерфейса INotifyPropertyChanged. Key - это название проекта, Value- это процент прогресс бара.
Проблема: если я изменяю список проектов, и на кнопке сохранить вызываю заново метод getTheurrentPercentageOfTheDayOfProjectExecution, то почему прогресс бары и названия с коллекции ObservableCollection автоматом не подтягиваются? (Возможно что-то еще из кода понадобится...)
Вся ваша проблема в том, что вы пытаетесь повторно инициализировать уже привязанную и инициализированную коллекцию.
То есть если у нас есть
public ObservableCollection<string> TestData { get; set; } = new ObservableCollection<string>();
с привязкой <ListBox ItemsSource="{Binding TestData}"/>.
То если мы напишем TestData = new ObservableCollection<string>(); - наша привязка пропадет, ибо мы привязались к старой копии объекта.
Добавлять данные нужно через метод Add или его аналогу. Если у нас есть некий метод, который генерирует данные и возвращает новую коллекцию, то стоит пройтись по ней циклом, добавив так все данные в привязанную коллекцию. Пример:
foreach (var item in AddData())
TestData.Add(item);
Теперь что касается обновления. В MVVM (да и вообще в ООП) принято разбивать всю логику по своим классам, которые отвечают только за этот объект. Скажем есть у нас человек, делаем класс class Person{}. Человек имеет руки, ноги, голову, пусть это будут наши свойства (public Hand[] Hands {get; set;}, public Head Head {get; set;} ...). Также человек может выполнять какие то действия, например идти, это по сути тоже метод класса Person (public void Walk(int speed){...}). Как видите все это относится к человеку логично это все реализовывать именно в классе человека, а не относить скажем ходьбу к классу сердца. Также и у вас, вы делаете коллекцию неких объектов у которых есть своя логика, так почему бы не написать метод обновления внутри этой ViewModel?
Пример:
Делаем некий класс (VM):
public class TestData
{
public TestData(string name, int percent)
{
Name = name;
Percent = percent;
}
public string Name { get; set; }
public int Percent { get; set; }
public void Update() => Percent++;
}
Делаем коллекцию с тестовыми данными:
public ObservableCollection<TestData> TestCollection { get; set; } = new ObservableCollection<TestData>
{
new TestData("Item 1", 0),
new TestData("Item 2", 1),
new TestData("Item 3", 2),
new TestData("Item 4", 3)
};
Далее предположим, что мы ее привязали, все у нас работает. Надо теперь обновить данные, мы делаем следующее:
Если всю коллекцию, то:
foreach (var testData in TestCollection)
testData.Update();
Если один элемент:
TestCollection.FirstOrDefault(x => x.Name == "Item 3")?.Update();
Как видите мы нечего не передобавляем, мы работаем с тем, что уже имеем. Так что советую вам тоже попробовать это реализовать, отказавшись от каких то статичных методов...
Удачи в изучении WPF!
Основные этапы разработки сайта для стоматологической клиники
Продвижение своими сайтами как стратегия роста и независимости