Я ищу пример кода, как получить всех дочерних элементов родительского контроля.
Я понятия не имею, как это сделать.
foreach (Control control in Controls)
{
if (control.HasChildren)
{
??
}
}
Я ищу пример кода, как получить всех дочерних элементов родительского контроля.
Я понятия не имею, как это сделать.
foreach (Control control in Controls)
{
if (control.HasChildren)
{
??
}
}
Если вы хотите только непосредственных детей, используйте
...
var children = control.Controls.OfType<Control>();
...
Если вы хотите, чтобы все элементы управления из иерархии (т.е. все элементы в дереве находились под определенным элементом управления), используйте довольно простой рекурсивный метод данных:
private IEnumerable<Control> GetControlHierarchy(Control root)
{
var queue = new Queue<Control>();
queue.Enqueue(root);
do
{
var control = queue.Dequeue();
yield return control;
foreach (var child in control.Controls.OfType<Control>())
queue.Enqueue(child);
} while (queue.Count > 0);
}
Затем вы можете использовать что-то вроде этого в форме:
private void button1_Click(object sender, EventArgs e)
{
/// get all of the controls in the form hierarchy in a List<>
foreach (var control in GetControlHierarchy(this))
{
/// do something with this control
}
}
Элементы управления имеют коллекцию MyControl.Controls
, которую вы можете сделать foreach
.
Каждый элемент управления также имеет свойство Parent
, которое предоставляет родительский элемент управления.
Вы можете написать рекурсивный метод, если вам нужно спуститься на неизвестное количество уровней.
Может быть, это может быть полезно для кого-то:
public void GetControlsCollection(Control root,ref List<Control> AllControls, Func<Control,Control> filter)
{
foreach (Control child in root.Controls)
{
var childFiltered = filter(child);
if (childFiltered != null) AllControls.Add(child);
if (child.HasControls()) GetControlsCollection(child, ref AllControls, filter);
}
}
Это рекурсивная функция для сбора коллекции элементов управления с возможностью использования фильтра (для расширения по типу). И пример:
List<Control> resultControlList = new List<Control>();
GetControlsCollection(rootControl, ref resultControlList, new Func<Control,Control>(ctr => (ctr is DropDownList)? ctr:null ));
Он вернет все DropDownLists в rootControl и всех его дочерних
Наверное, слишком сложно, но используя Linq и некоторые идеи из вышеперечисленных/других мест:
public static IEnumerable<Control> GetAllChildren(this Control root) {
var q = new Queue<Control>(root.Controls.Cast<Control>());
while (q.Any()) {
var next = q.Dequeue();
next.Controls.Cast<Control>().ToList().ForEach(q.Enqueue);
yield return next;
}
}
Чтение некоторых из этих фрагментов кода заставляет меня хотеть пойти к дантисту вместо этого. Вот простой пример, и, как всегда, простой означает быстрее, намного быстрее (без инициализации коллекций, списков, очередей и прочего) и в качестве дополнительного бонуса: он работает!
bool found = true;
while (found)
{
found = false;
foreach (Control c in /*your_Parent.*/Controls)
if (c is Label)
{
/* your action; */
found = true; }
}
}