我有一个文本框,我想将所选项目的数量限制为 MaxSelection。期望的行为是一旦选择了 MaxSelection 项目,任何进一步的选择都将被忽略。(因此这个问题不同于“在 vb.net 的列表框中限制选择”)。
我有一个用于尝试完成此操作的列表框的 SelectedIndexChanged 事件的事件处理程序。如果用户使用 Ctrl 键单击选择第 (MaxSelection+1) 项,则选择恢复为先前的选择。
问题是当用户选择一个项目,然后按住 Shift 键单击列表下方的项目,即 MaxSelection+1 项目在列表下方。在这种情况下,会引发多个 SelectedIndexChanged 事件:一个用于 Shift-click 事件,该事件选择被 Shift-clicked 的项目,一个用于选择原始选择和 Shift-clicked 选择之间的所有项目。这些事件中的第一个允许用户选择按住 Shift 键单击的项目(这在技术上是正确的),然后第二个事件将选择恢复为第一个事件之后的选择(这将是最初选择的项目和 Shift -单击的项目)。所需要的是代码会将选择恢复为第一个事件之前的选择(这只是最初选择的项目)。
有没有办法在 Shift 单击之前保留选择?
谢谢,罗伯
这是 SelectedIndexChanged 事件处理程序:
void ChildSelectionChanged(object sender, EventArgs e)
{
ListBox listBox = sender as ListBox;
//If the number of selected items is greater than the number the user is allowed to select
if ((this.MaxSelection != null) && (listBox.SelectedItems.Count > this.MaxSelection))
{
//Prevent this method from running while reverting the selection
listBox.SelectedIndexChanged -= ChildSelectionChanged;
//Revert the selection to the previous selection
try
{
for (int index = 0; index < listBox.Items.Count; index++)
{
if (listBox.SelectedIndices.Contains(index) && !this.previousSelection.Contains(index))
{
listBox.SetSelected(index, false);
}
}
}
finally
{
//Re-enable this method as an event handler for the selection change event
listBox.SelectedIndexChanged += ChildSelectionChanged;
}
}
else
{
//Store the current selection
this.previousSelection.Clear();
foreach (int selectedIndex in listBox.SelectedIndices)
{
this.previousSelection.Add(selectedIndex);
}
//Let any interested code know the selection has changed.
//(We do not do this in the case where the selection would put
//the selected count above max since we revert the selection;
//there is no net effect in that case.)
RaiseSelectionChangedEvent();
}
}