C#滚动ListView更新项目

时间:2015-08-06 22:58:17

标签: c# wpf

我有ListView

    <ListView x:Name="BlockList" Grid.Row="1" Grid.ColumnSpan="4" ItemsSource="{Binding Blocks}">
        <ListView.View>
            <GridView>
                <GridViewColumn Width="75" Header="Address" DisplayMemberBinding="{Binding Path=Address, Converter={StaticResource IntToHexConverter}}"/>
                <GridViewColumn Width="100" Header="Length" DisplayMemberBinding="{Binding Length}"/>
                <GridViewColumn Width="100" Header="Status" DisplayMemberBinding="{Binding Status}"/>
            </GridView>
        </ListView.View>
    </ListView>

显示ObservableCollection Blocks的地址,长度和状态。

public class Block : ObservableObject
{
    public enum BlockStatus
    {
        Unwritten,
        Written,
        Verified,
        Bad,
    }

    private UInt16 address;
    public UInt16 Address
    {
        get { return address; }
        set { address = value; NotifyPropertyChanged(); }
    }

    private byte[] data;
    public byte[] Data
    {
        get { return data; }
        set { data = value; NotifyPropertyChanged(); }
    }

    private BlockStatus status;
    public BlockStatus Status
    {
        get { return status; }
        set { status = value; NotifyPropertyChanged(); }
    }

    public UInt16 Length
    {
        get { return (UInt16)Data.Length; }
    }

    public Block(UInt16 address, byte[] data) : this(address, data, BlockStatus.Unwritten) { }

    public Block(UInt16 address, byte[] data, BlockStatus status)
    {
        this.Address = address;
        this.Data = data;
        this.Status = status;
    }
}

这些Blocks最初将以BlockStatus.Unwritten状态开始,最终为Written,然后为Verified。如果ListView发生变化,如何将Block滚动到Status

Example Window

1 个答案:

答案 0 :(得分:0)

有很多事情需要做。

1)您的Block需要实施INotifyPropertyChanged

public class Block : ObservableObject, INotifyPropertyChanged
{
    // Your existing members and code


    private BlockStatus _status;
    public BlockStatus Status
    {
        get { return _status; }
        set { _status = value; NotifyPropertyChanged("Status"); }
    }

    // INotifyPropertyChanged implementation
    public event PropertyChangedEventHandler PropertyChanged;
    protected void NotifyPropertyChanged(string propertyName)
    {
        if (PropertyChanged != null)
        {
            PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
        }
    }
}

2)您的ViewModel需要StatusChanged事件

public delegate void StatusChangedHandler(object sender, StatusChangedHandlerArgs args);
public event StatusChangedHandler StatusChanged;

// Put this class where it suits your project
public class StatusChangedHandlerArgs
{
    public Block.BlockStatus NewStatus { get; private set; }

    public StatusChangedHandlerArgs(Block.BlockStatus newStatus)
    {
        NewStatus = newStatus;
    }
}

3)Blocks中的ViewModel属性需要如下所示:

    private ObservableCollection<Block> _blocks;
    public ObservableCollection<Block> Blocks
    {
        get
        {
            return _blocks;
        }
        set
        {
            _blocks = value;
            if (_blocks != null)
            {
                foreach (var block in _blocks)
                {
                    block.PropertyChanged += block_PropertyChanged;
                }
            }
            NotifyPropertyChanged("Blocks");
        }
    }

   // The event handler for PropertyChanged 
    private void block_PropertyChanged(object sender, System.ComponentModel.PropertyChangedEventArgs e)
    {
        if (e.PropertyName != "Status" || StatusChanged == null)
        {
            return;
        }

        var block = sender as Block;
        if (block != null)
        {
            StatusChanged.Invoke(block, new StatusChangedHandlerArgs(block.Status));
        }
    }

4)最后,您的View(其中包含ViewModel的实例)应订阅后面代码中的StatusChanged事件。

   // Somewhere in the initializer or constructor for the page
   yourViewModel.StatusChanged += yourViewModel_StatusChanged;

   // The handler for StatusChanged
   private void yourViewModel_StatusChanged(object sender, StatusChangedHandlerArgs args)
    {
        var block = sender as Block;
        if (block != null)
        {
            BlockList.ScrollIntoView(block);
        }
    }