none
在Winform中刷新ListView及DataGridView时如何让滚动条定位到用户选择的行? RRS feed

  • 问题

  • 我们程序使用多线程不停的刷新数据,当用户选择某行数据时,由于界面又重新回到第一行了,我使用Items[index].Selected/Checked/Focused=true;都无法定位到选择行,为此我们只能延长刷新时间,但如果数据较多时就很难选定要编辑的行了,请各位高手指点一下,小弟不胜感激,谢谢!
    2009年12月10日 2:04

答案

  • 你好!
         你这样试试:
    dataGridView1.Rows[index].Selected   =   true;                

    dataGridView1.FirstDisplayedScrollingRowIndex   =   index;
    周雪峰
    2009年12月10日 2:16
    版主
  •     首先在单击单元格时获得当前行的索引  

          int index;//当前行索引
            private void dataGridView1_CellClick(object sender, DataGridViewCellEventArgs e)
            {
                index = this.dataGridView1.CurrentRow.Index;
            }


    然后在你刷新数据的方法中调用以下,就可实现定位
          this.dataGridView1.DataSource = ds.Tables[0];
                dataGridView1.Rows[index].Selected = true;       
                this.dataGridView1.FirstDisplayedScrollingRowIndex = index;
    努力+方法=成功
    2009年12月10日 2:32
  • ListView可以这样来实现:
                listView1.Items[3].Selected = true;
                listView1.EnsureVisible(3);
    希望对你有帮助!
    周雪峰
    • 已标记为答案 YiChun Chen 2009年12月11日 9:55
    2009年12月11日 4:34
    版主

全部回复

  • 你好!
         你这样试试:
    dataGridView1.Rows[index].Selected   =   true;                

    dataGridView1.FirstDisplayedScrollingRowIndex   =   index;
    周雪峰
    2009年12月10日 2:16
    版主
  •     首先在单击单元格时获得当前行的索引  

          int index;//当前行索引
            private void dataGridView1_CellClick(object sender, DataGridViewCellEventArgs e)
            {
                index = this.dataGridView1.CurrentRow.Index;
            }


    然后在你刷新数据的方法中调用以下,就可实现定位
          this.dataGridView1.DataSource = ds.Tables[0];
                dataGridView1.Rows[index].Selected = true;       
                this.dataGridView1.FirstDisplayedScrollingRowIndex = index;
    努力+方法=成功
    2009年12月10日 2:32
  • 非常谢谢两位的回答,DataGridView使用上述方法,可以解决上述问题。但是现在我们的程序用的是ListView显示数据,由于程序涉及到硬件,比较复杂,我不敢轻易改动,有没有关于ListView的解决方法呢?谢谢。

    2009年12月11日 4:04
  • ListView可以这样来实现:
                listView1.Items[3].Selected = true;
                listView1.EnsureVisible(3);
    希望对你有帮助!
    周雪峰
    • 已标记为答案 YiChun Chen 2009年12月11日 9:55
    2009年12月11日 4:34
    版主
  •  

         

    namespace ScrollOffset
    {
        partial class Form1
        {
            /// <summary>
            /// 必需的设计器变量。
            /// </summary>
            private System.ComponentModel.IContainer components = null;
    
            /// <summary>
            /// 清理所有正在使用的资源。
            /// </summary>
            /// <param name="disposing">如果应释放托管资源,为 true;否则为 false。</param>
            protected override void Dispose(bool disposing)
            {
                if (disposing && (components != null))
                {
                    components.Dispose();
                }
                base.Dispose(disposing);
            }
    
            #region Windows 窗体设计器生成的代码
    
            /// <summary>
            /// 设计器支持所需的方法 - 不要
            /// 使用代码编辑器修改此方法的内容。
            /// </summary>
            private void InitializeComponent()
            {
                this.listView1 = new System.Windows.Forms.ListView();
                this.columnHeader1 = new System.Windows.Forms.ColumnHeader();
                this.columnHeader2 = new System.Windows.Forms.ColumnHeader();
                this.dataGridView1 = new System.Windows.Forms.DataGridView();
                this.linkLabel1 = new System.Windows.Forms.LinkLabel();
                this.linkLabel2 = new System.Windows.Forms.LinkLabel();
                ((System.ComponentModel.ISupportInitialize)(this.dataGridView1)).BeginInit();
                this.SuspendLayout();
                // 
                // listView1
                // 
                this.listView1.Columns.AddRange(new System.Windows.Forms.ColumnHeader[] {
                this.columnHeader1,
                this.columnHeader2});
                this.listView1.FullRowSelect = true;
                this.listView1.Location = new System.Drawing.Point(12, 40);
                this.listView1.Name = "listView1";
                this.listView1.Size = new System.Drawing.Size(286, 210);
                this.listView1.TabIndex = 0;
                this.listView1.UseCompatibleStateImageBehavior = false;
                this.listView1.View = System.Windows.Forms.View.Details;
                this.listView1.ItemChecked += new System.Windows.Forms.ItemCheckedEventHandler(this.listView1_ItemChecked);
                // 
                // columnHeader1
                // 
                this.columnHeader1.Text = "#";
                // 
                // columnHeader2
                // 
                this.columnHeader2.Text = "Text";
                // 
                // dataGridView1
                // 
                this.dataGridView1.ColumnHeadersHeightSizeMode = System.Windows.Forms.DataGridViewColumnHeadersHeightSizeMode.AutoSize;
                this.dataGridView1.Location = new System.Drawing.Point(332, 40);
                this.dataGridView1.Name = "dataGridView1";
                this.dataGridView1.RowTemplate.Height = 23;
                this.dataGridView1.Size = new System.Drawing.Size(319, 210);
                this.dataGridView1.TabIndex = 1;
                this.dataGridView1.CellClick += new System.Windows.Forms.DataGridViewCellEventHandler(this.dataGridView1_CellClick);
                // 
                // linkLabel1
                // 
                this.linkLabel1.AutoSize = true;
                this.linkLabel1.Location = new System.Drawing.Point(12, 9);
                this.linkLabel1.Name = "linkLabel1";
                this.linkLabel1.Size = new System.Drawing.Size(29, 12);
                this.linkLabel1.TabIndex = 2;
                this.linkLabel1.TabStop = true;
                this.linkLabel1.Text = "开始";
                this.linkLabel1.LinkClicked += new System.Windows.Forms.LinkLabelLinkClickedEventHandler(this.linkLabel1_LinkClicked);
                // 
                // linkLabel2
                // 
                this.linkLabel2.AutoSize = true;
                this.linkLabel2.Location = new System.Drawing.Point(57, 9);
                this.linkLabel2.Name = "linkLabel2";
                this.linkLabel2.Size = new System.Drawing.Size(29, 12);
                this.linkLabel2.TabIndex = 3;
                this.linkLabel2.TabStop = true;
                this.linkLabel2.Text = "结束";
                this.linkLabel2.LinkClicked += new System.Windows.Forms.LinkLabelLinkClickedEventHandler(this.linkLabel2_LinkClicked);
                // 
                // Form1
                // 
                this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 12F);
                this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
                this.ClientSize = new System.Drawing.Size(678, 262);
                this.Controls.Add(this.linkLabel2);
                this.Controls.Add(this.linkLabel1);
                this.Controls.Add(this.dataGridView1);
                this.Controls.Add(this.listView1);
                this.Name = "Form1";
                this.Text = "Form1";
                this.Load += new System.EventHandler(this.Form1_Load);
                ((System.ComponentModel.ISupportInitialize)(this.dataGridView1)).EndInit();
                this.ResumeLayout(false);
                this.PerformLayout();
    
            }
    
            #endregion
    
            private System.Windows.Forms.ListView listView1;
            private System.Windows.Forms.DataGridView dataGridView1;
            private System.Windows.Forms.LinkLabel linkLabel1;
            private System.Windows.Forms.LinkLabel linkLabel2;
            private System.Windows.Forms.ColumnHeader columnHeader1;
            private System.Windows.Forms.ColumnHeader columnHeader2;
    
    
        }
    }
    
    using System;
    using System.Threading;
    using System.Collections.Generic;
    using System.ComponentModel;
    using System.Data;
    using System.Drawing;
    using System.Text;
    using System.Windows.Forms;
    
    namespace ScrollOffset
    {
        public partial class Form1 : Form
        {
            Thread RefreshThread;
            DataTable datas = new DataTable();
            int row1 = 0; int row2 = 0;
            public Form1()
            {
                InitializeComponent();
            }
    
            private void Form1_Load(object sender, EventArgs e)
            {
                Getdata();
            }
    
            private void Getdata()
            {
                datas = new DataTable();
                datas.Columns.Add("#");
                datas.Columns.Add("Text");
                for (int count = 1; count <= 100; count++)
                {
                    datas.Rows.Add(count.ToString(), "data----" + count.ToString());
                }
            }
    
            private void BeginReshData()
            {
                datas = new DataTable();
                MethodInvoker mi = new MethodInvoker(SetData);
                while (true)
                {
                    this.BeginInvoke(mi);
                    Thread.Sleep(2000);
                }
            }
    
            private void SetData()
            {
                Getdata();
                dataGridView1.DataSource = datas;
                dataGridView1.FirstDisplayedScrollingRowIndex = row2;
                dataGridView1.Rows[row2].Selected = true;
                if (row1 >= 0 && row2 < listView1.Items.Count)
                    listView1.BeginUpdate();
                listView1.Items.Clear();
                foreach (DataRow dr in datas.Rows)
                {
                    ListViewItem lv = new ListViewItem();
                    lv.Text = dr[0].ToString();
                    lv.SubItems.Add(dr[1].ToString());
                    listView1.Items.Add(lv);
                }
                listView1.EndUpdate();
                if (listView1.SelectedItems.Count > 0 && row1 < listView1.SelectedItems.Count)
                {
                    listView1.Focus();
                    listView1.SelectedItems[row1].Checked = true;
                    listView1.SelectedItems[row1].Focused = true;
                    listView1.SelectedItems[row1].Selected = true;
    
                    listView1.EnsureVisible(row1);
                }
            }
    
            private void listView1_SelectedIndexChanged(object sender, EventArgs e)
            {
    
                if (listView1.SelectedItems.Count > 0)
                {
                    row1 = listView1.SelectedItems[0].Index;
                }
    
            }
    
            private void linkLabel1_LinkClicked(object sender, LinkLabelLinkClickedEventArgs e)
            {
                //for (int i = 0; i < 1000; i++)
                //{
                //    Application.DoEvents();
                //}
                RefreshThread = new Thread(new ThreadStart(this.BeginReshData));
                RefreshThread.IsBackground = true;
                RefreshThread.Start();
            }
    
            private void linkLabel2_LinkClicked(object sender, LinkLabelLinkClickedEventArgs e)
            {
                if (RefreshThread != null)
                {
                    try
                    {
                        RefreshThread.Abort();
                    }
                    catch { }
                }
    
            }
    
            private void dataGridView1_CellClick(object sender, DataGridViewCellEventArgs e)
            {
                if (listView1.SelectedItems.Count >= 0)
                {
                    row2 = e.RowIndex;
                }
            }
    
            private void listView1_ItemChecked(object sender, ItemCheckedEventArgs e)
            {
                if (listView1.SelectedItems.Count >= 0)
                {
                    ListViewItem lv = e.Item;
                    lv.Selected = true;
                 
                }
            }
        }
    }
    请帮忙看一下,ListView为什么不能选定,谢谢!



    2009年12月11日 5:25
  • 尝试把HideSelection属性设置为false
    周雪峰
    2009年12月11日 5:38
    版主