Вывести управление Winforms на передний план
существуют ли какие-либо другие методы вывода элемента управления на передний план, кроме управления.BringToFront()? У меня есть серия меток на пользовательском элементе управления, и когда я пытаюсь вывести один из них на передний план, он не работает. Я даже прошелся по всем элементам управления и отправил их назад, за исключением того, который меня интересует, и это ничего не меняет.
вот метод, в котором метка добавляется в пользовательский элемент управления
private void AddUserLabel()
{
UserLabel field = new UserLabel();
++fieldNumber;
field.Name = "field" + fieldNumber.ToString();
field.Top = field.FieldTop + fieldNumber;
field.Left = field.FieldLeft + fieldNumber;
field.Height = field.FieldHeight;
field.Width = field.FieldWidth;
field.RotationAngle = field.FieldRotation;
field.Barcode = field.BarCoded;
field.HumanReadable = field.HumanReadable;
field.Text = field.FieldText;
field.ForeColor = Color.Black;
field.MouseDown += new MouseEventHandler(label_MouseDown);
field.MouseUp += new MouseEventHandler(label_MouseUp);
field.MouseMove += new MouseEventHandler(label_MouseMove);
userContainer.Controls.Add(field);
SendLabelsToBack(); //Send All labels to back
userContainer.Controls[field.FieldName].BringToFront();
}
вот метод, который отправляет все из них в спину.
private void SendLabelsToBack()
{
foreach (UserLabel lbl in userContainer.Controls)
{
lbl.SendToBack();
}
}
5 ответов
Да, есть другой способ. The Controls.SetChildIndex()
также изменяет Z-порядок. Тот, у которого индекс 0, находится сверху. Но ничего не покупает,BringToFront()
использует этот метод.
код SendLabelsToBack()
метод, как указано, не может работать, он также отправит метку, добавленную в спину. Но ваше следующее заявление исправит это снова.
хорошо, это не работает, что означает BringToFront()
метод не выполняется. Посмотрите в окне вывода для уведомления "первый шанс исключения". Как написано, Ваш SendLabelsToBack()
вызовет исключение, если пользовательский элемент управления содержит любой элемент управления, кроме UserLabel. Кроме того, установите точку останова после the BringToFront()
вызовите и проверьте значение userContainer.Controls[0].Name
, когда он ломается.
Z-индекс элементов управления на контейнер.
Если вы вызываете BringToFront на элементе управления, который находится внутри контейнера (например,Panel
), Он не принесет контейнер к фронту.
Таким образом элемент управления будет идти только перед другими элементами управления в этом контейнере.
чтобы увидеть, в каких контейнерах находятся элементы управления, можно использовать панель контур документа в меню Вид.
редактировать: ваш userContainer
управление, вероятно, находится за a другой контроль.
ты пробовал Invalidate()
после BringToFront()
? BringToFront не вызывает событие Paint
попробуйте это:
private void SendLabelsToBack()
{
foreach (UserLabel lbl in userContainer.Controls)
{
lbl.SendToBack();
lbl.Invalidate();
}
}
Я думаю, вам просто нужно изменить последнюю строку:
userContainer.Controls[field.FieldName].BringToFront();
для этого:
userContainer.Controls[field.Name].BringToFront();
когда вы используете строку в качестве индексатора для коллекции элементов управления, он идет Name
свойство элемента управления (не FieldName
свойства).
поскольку вы просто пытаетесь привести самый последний добавленный элемент управления к вершине, это также будет работать:
userContainer.Controls[userContainer.Controls.Count - 1].BringToFront();
по моему опыту похоже, что windows помещает все элементы управления, принадлежащие одному графическому контейнеру (панель, групповое поле...etc) в коллекции программного обеспечения. Коллекция упорядочена по дочернему индексу, который является свойством каждого элемента управления в этом контейнере. Фокус в том, что дети с одним и тем же индексом могут и существуют. В этом случае окна будут рисовать этих детей, упорядоченных относительно других, но между ними он будет рисовать их в обратном порядке, они были добавлены в контейнер.
короче говоря: для одного контейнера-вам нужно убедиться, что элементы управления имеют разные индексы, изменяя все, а не только некоторые индексы, когда вы хотите изменить Z-порядок. Например:
foreach (Control newControl in TopControl.Controls)
{
TopControl.Controls.SetChildIndex(newControl,indexlogic(newControl));
}
здесь indexLogic(newControl )
ваш метод расчета индекса конкретного элемента управления.