Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/272.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 项目更新后的列表框排序,items.SortDescriptions绑定InotifyProperty是否已更改?_C#_Wpf_Sorting - Fatal编程技术网

C# 项目更新后的列表框排序,items.SortDescriptions绑定InotifyProperty是否已更改?

C# 项目更新后的列表框排序,items.SortDescriptions绑定InotifyProperty是否已更改?,c#,wpf,sorting,C#,Wpf,Sorting,继续之前的大问题更新: Items.SortDescription是否在INotifyPropertyChanged事件中被激发 根据另一个问题的代码:,我解决了使用Items.Refres()来降低执行速度的问题 但在我开始对项目进行排序后,问题再次出现 正如我在另一个主题中所说的,我需要刷新每个已更改用户的状态,但需要重新分组列表框中已更改的项 如果我循环调用函数Clear()并重新添加SortDescriptions,就会丢失输入,比如鼠标和键盘问题 一些代码: 线程计时器: vo

继续之前的大问题更新: Items.SortDescription是否在INotifyPropertyChanged事件中被激发

根据另一个问题的代码:,我解决了使用Items.Refres()来降低执行速度的问题

但在我开始对项目进行排序后,问题再次出现

正如我在另一个主题中所说的,我需要刷新每个已更改用户的状态,但需要重新分组列表框中已更改的项

如果我循环调用函数Clear()并重新添加SortDescriptions,就会丢失输入,比如鼠标和键盘问题

一些代码:

线程计时器:

    void StatusUpdater(object sender, EventArgs e)
    {
        ContactData[] contacts = ((Contacts)contactList.Resources["Contacts"]).ToArray<ContactData>();
        XDocument doc = XDocument.Load("http://localhost/contact/xml/status.php");
        foreach (XElement node in doc.Descendants("update"))
        {
            var item = contacts.Where(i => i.UserID.ToString() == node.Element("UserID").Value);
            ContactData[] its = item.ToArray();
            if (its.Length > 0)
            {
                its[0].UpdateFromXML(node);
            }
        }
        Dispatcher.Invoke(DispatcherPriority.Normal, new Action( () => { contactList.SortAndGroup(); } ));
    }
项目来源:

public class Contacts : ObservableCollection<ContactData>, INotifyPropertyChanged
{
    private ContactData.States _state = ContactData.States.Online | ContactData.States.Busy;
    public new event PropertyChangedEventHandler PropertyChanged;
    public ContactData.States Filter 
    { 
        get { return _state; } 
        set 
        { 
            _state = value;
            NotifyPropertyChanged("Filter");
            NotifyPropertyChanged("FilteredItems");
        } 
    }
    public IEnumerable<ContactData> FilteredItems
    {
        get { return Items.Where(o => o.State == _state || (_state & o.State) == o.State).ToArray(); }
    }
    public Contacts()
    {
        XDocument doc = XDocument.Load("http://localhost/contact/xml/contactlist.php");
        foreach (ContactData data in ContactData.ParseXML(doc)) Add(data);
    }
    public void NotifyPropertyChanged(string propertyName)
    {
        if (PropertyChanged != null)
        {
            PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
        }
    } 
}
公共类联系人:ObservableCollection,INotifyPropertyChanged
{
私有ContactData.States _state=ContactData.States.Online | ContactData.States.Busy;
公共新事件属性ChangedEventHandler属性Changed;
公共联系人数据。状态筛选器
{ 
获取{return\u state;}
设置
{ 
_状态=值;
NotifyPropertyChanged(“过滤器”);
NotifyPropertyChanged(“FilteredItems”);
} 
}
公共IEnumerable FilteredItems
{
获取{return Items.Where(o=>o.State==_State | | |(_State&o.State)==o.State).ToArray()}
}
公众接触()
{
XDocument doc=XDocument.Load(“http://localhost/contact/xml/contactlist.php");
foreach(ContactData.ParseXML(doc)中的ContactData数据)添加(数据);
}
public void NotifyPropertyChanged(字符串propertyName)
{
if(PropertyChanged!=null)
{
PropertyChanged(这是新的PropertyChangedEventArgs(propertyName));
}
} 
}
源数据类:

public class ContactData : INotifyPropertyChanged
{
    public enum States { Online = 1, Away = 2, Busy = 4, Offline = 128 }
    public event PropertyChangedEventHandler PropertyChanged;
    public int UserID 
    {
        get { return int.Parse(Data["UserID"]); }
        set { Data["UserID"] = value.ToString(); NotifyPropertyChanged("UserID"); }
    }
    public States State 
    {
        get { return (Data.Keys.Contains("State")) ? (States)Enum.Parse(typeof(States), Data["State"]) : States.Offline; }
        set 
        { 
            Data["State"] = value.ToString();
            NotifyStateChanged();
        }
    }
    public Dictionary<string, string> Data { get; set; }
    public void Set(string name, string value) 
    {
        if (Data.Keys.Contains(name)) Data[name] = value;
        else Data.Add(name, value);
        NotifyPropertyChanged("Data");
    }
    public Color ColorState { get { return UserStateToColorState(State); } }
    public Brush BrushState { get { return new SolidColorBrush(ColorState); } }
    public string FullName { get { return Data["Name"] + ' ' + Data["Surname"]; } }

    public System.Windows.Media.Imaging.BitmapImage Avatar
    {
        get 
        {
            return Utilities.Stream.Base64ToBitmapImage(Data["Avatar"]); 
        }
        set 
        { 
            Data["Avatar"] = Utilities.Stream.BitmapImageToBase64( value ); 
            NotifyPropertyChanged("Avatar"); 
        }
    }

    public ContactData() {}
    public override string ToString()
    {
        try { return FullName; }
        catch (Exception e) { Console.WriteLine(e.Message); return base.ToString(); }
    }
    Color UserStateToColorState(States state)
    {
        switch (state)
        {
            case States.Online: return Colors.LightGreen;
            case States.Away: return Colors.Orange;
            case States.Busy: return Colors.Red;
            case States.Offline: default: return Colors.Gray;
        }
    }

    public void UpdateFromXML(XElement xEntry)
    {
        var result = xEntry.Elements().ToDictionary(e => e.Name.ToString(), e => e.Value);
        foreach (string key in result.Keys) if (key != "UserID")
        {
            if (Data.Keys.Contains(key)) Data[key] = result[key];
            else Data.Add(key, result[key]);
            char[] property = key.ToCharArray();
            property[0] = char.ToUpper(property[0]);
            NotifyPropertyChanged(new string(property));
        }
    }

    public void NotifyStateChanged()
    {
        if (PropertyChanged != null)
        {
            PropertyChanged(this, new PropertyChangedEventArgs("State"));
            PropertyChanged(this, new PropertyChangedEventArgs("ColorState"));
            PropertyChanged(this, new PropertyChangedEventArgs("BrushState"));
        }
    }

    public void NotifyPropertyChanged(string propertyName)
    {
        if (PropertyChanged != null)
        {
            if (this.GetType().GetProperty(propertyName) != null)
            {
                if (propertyName != "State")
                    PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
                else NotifyStateChanged();
            }
        }
    }

    public static ContactData[] ParseXML(XDocument xmlDocument)
    {
        var result = from entry in xmlDocument.Descendants("contact")
        select new ContactData { Data = entry.Elements().ToDictionary(e => e.Name.ToString(), e => e.Value) };
        return result.ToArray<ContactData>();
    }
}
公共类联系人数据:INotifyPropertyChanged
{
公共枚举状态{Online=1,Away=2,Busy=4,Offline=128}
公共事件属性更改事件处理程序属性更改;
公共int用户标识
{
获取{return int.Parse(数据[“UserID]”);}
设置{Data[“UserID”]=value.ToString();NotifyPropertyChanged(“UserID”);}
}
公共国家
{
获取{return(Data.Keys.Contains(“State”)?(States)Enum.Parse(typeof(States),Data[“State”]):States.Offline;}
设置
{ 
数据[“状态”]=value.ToString();
NotifyStateChanged();
}
}
公共字典数据{get;set;}
公共无效集(字符串名称、字符串值)
{
如果(Data.Keys.Contains(name))数据[name]=值;
其他数据。添加(名称、值);
NotifyPropertyChanged(“数据”);
}
公共颜色颜色状态{get{return UserStateToColorState(State);}
公共画笔笔刷状态{get{返回新的SolidColorBrush(ColorState);}
公共字符串全名{get{返回数据[“名称”]+''+数据[“姓氏”];}
public System.Windows.Media.Imaging.BitmapImage头像
{
得到
{
返回Utilities.Stream.Base64ToBitmapImage(数据[“化身]);
}
设置
{ 
Data[“Avatar”]=Utilities.Stream.BitmapImageToBase64(值);
NotifyPropertyChanged(“化身”);
}
}
公共联系人数据(){}
公共重写字符串ToString()
{
请尝试{返回全名;}
catch(异常e){Console.WriteLine(e.Message);返回base.ToString();}
}
颜色用户状态到颜色状态(状态状态)
{
开关(状态)
{
案例状态。联机:返回颜色。浅绿色;
案例状态。离开:返回颜色。橙色;
案例状态。忙:返回颜色。红色;
案例状态。脱机:默认:返回颜色。灰色;
}
}
公共void UpdateFromXML(XElement xEntry)
{
var result=xEntry.Elements().ToDictionary(e=>e.Name.ToString(),e=>e.Value);
foreach(result.Keys中的字符串键)if(key!=“UserID”)
{
如果(Data.Keys.Contains(key))Data[key]=结果[key];
添加(键,结果[键]);
char[]属性=key.ToCharArray();
属性[0]=char.ToUpper(属性[0]);
NotifyPropertyChanged(新字符串(属性));
}
}
public void NotifyStateChanged()
{
if(PropertyChanged!=null)
{
PropertyChanged(即新PropertyChangedEventArgs(“州”);
PropertyChanged(这是新PropertyChangedEventArgs(“ColorState”);
PropertyChanged(即新PropertyChangedEventArgs(“BrushState”);
}
}
public void NotifyPropertyChanged(字符串propertyName)
{
if(PropertyChanged!=null)
{
if(this.GetType().GetProperty(propertyName)!=null)
{
如果(propertyName!=“状态”)
PropertyChanged(这是新的PropertyChangedEventArgs(propertyName));
else NotifyStateChanged();
}
}
}
公共静态联系人数据[]解析XML(XDocument xmlDocument)
{
var result=来自xmlDocument.subjects(“联系人”)中的条目
选择new ContactData{Data=entry.Elements().ToDictionary(e=>e.Name.ToString(),e=>e.Value)};
返回result.ToArray();
}
}

不确定您的问题是什么,但您可能需要在添加GroupDescription之前添加此项

MyListBox.Items.GroupDescriptions.Clear();
现在,您添加了更有意义的周期性评论。为什么不绑定到PagedCollectionView而不是向控件分派排序

       PagedCollectionView itemListView = new PagedCollectionView(contacts);

        // Set the DataPager and ListBox to the same data source.
       itemListView.SortDescriptions.Clear();
       itemListView.SortDescriptions.Add(new SortDescription("State", ListSortDirection.Ascending));
       MyListBox.ItemsSource=itemListView;

不完全确定您的问题是什么,但您可能需要在添加GroupDescription之前添加此项

MyListBox.Items.GroupDescriptions.Clear();
现在,您添加了更有意义的周期性评论。为什么不绑定到PagedCollectionView而不是向控件分派排序

       PagedCollectionView itemListView = new PagedCollectionView(contacts);

        // Set the DataPager and ListBox to the same data source.
       itemListView.SortDescriptions.Clear();
       itemListView.SortDescriptions.Add(new SortDescription("State", ListSortDirection.Ascending));
       MyListBox.ItemsSource=itemListView;

像您这样使用GroupDescriptions是列表框最快的方式,除非您想自己实现控件。你是不是碰到体育课了
        while (IsStatusUpdateRunnig)
        {
            ContactData[] contacts = ((ContactData[])View.SourceCollection);//MyListBox.ItemsSource);
            XDocument doc = XDocument.Load("http://localhost/contact/xml/status.php");
            foreach (XElement node in doc.Descendants("update"))
            {
                ContactData[] its = contacts.Where(i => i.UserID.ToString() == node.Element("UserID").Value).ToArray();
                if (its.Length > 0)
                {
                    its[0].UpdateFromXML(node);
                    Dispatcher.Invoke(new Action(() => { View.EditItem(its[0]); }));
                }
            }
            Dispatcher.Invoke(new Action(() => { View.CommitEdit(); }));
            System.Threading.Thread.Sleep(2000);
        }