我有一个包含大约 100 个项目的 ListView。我从过去选择了一些项目,现在我需要向下滚动以找到另一个项目,但在那个时候 - 刷新发生并且它只是自动滚动回最后一个选定的项目。
如果我目前正在滚动,是否有可能将其关闭或最好不要滚动?
感谢您的回复:)
我不知道这是否会有所帮助,但这里的设置在添加和排序新项目时不会出现滚动回所选项目的问题。但是,我使用排序设置并且不调用排序或刷新。
创建一个新表单并将 ListView 和 Timer 放在那里。在 ListView 上仅更改这些属性。
现在添加以下代码
public Form1()
{
InitializeComponent();
for (int x = 0; x < 100; x++)
{
listView1.Items.Add("Item #" + x);
}
}
private int y = 10;
private void timer1_Tick(object sender, EventArgs e)
{
listView1.Items.Add("Item #" + y + "b");
y += 10;
}
现在,当您运行它时,您可以选择任何项目并在任何地方滚动,并且在添加新项目时它不会跳回到所选项目。但是,如果它添加的项目在上方,它将向下滚动一行……
也许这让你足够接近,你可以进一步使用它来获得你需要的东西。
但这是我能做的最好的事情,而无需以某种方式使用 Win32 API 对 ListView 控件进行子类化。
这是一种迂回的解决方案(可能有点晚),但它似乎有效。我在最近添加的项目上使用 EnsureVisible() 以进行自动滚动,这在 timer1_Tick 方法中调用。但是我使用了一个“inspectingList”标志,当你点击一个列表项时,它会阻止自动滚动发生。当焦点从列表视图移开时,滚动继续正常进行。
部分解决方案是 jross 所说的,即创建一个虚拟表单进行测试:
private void Form1_Load(object sender, EventArgs e)
{
listView1.Columns.Add("Scroll Control", 100);
for(int i = 0; i < 100; i++)
{
listView1.Items.Add(string.Format("Item #{0:000}", i));
}
timer1.Interval = 1000;
timer1.Start();
}
private int newItem = 10;
private bool inspectingList = false;
private void timer1_Tick(object sender, EventArgs e)
{
listView1.Items.Add(string.Format("Item #{0:000}", newItem));
newItem += 10;
if (!inspectingList)
{
listView1.Items[listView1.Items.Count - 1].EnsureVisible();
}
listView1.Refresh();
}
private void listView1_SelectedIndexChanged(object sender, EventArgs e)
{
inspectingList = true;
if (listView1.SelectedIndices.Count > 0)
{
listView1.Items[listView1.SelectedIndices[0]].EnsureVisible();
}
}
private void listView1_Leave(object sender, EventArgs e)
{
inspectingList = false;
}