Вы можете использовать класс Panel в качестве отправной точки.Просто наследуйте от него.
Вы захотите загрузить свой индикатор выполнения либо в верхней части панели, либо в качестве ее первого члена.Вы можете использовать стиль Marquee на индикаторе выполнения, если вы не хотите его обновлять;в противном случае вы можете увеличивать индикатор выполнения при добавлении элементов управления на панель.
Если вы используете стиль Marquee, вы в значительной степени сделали это.Если вы хотите, чтобы фактический индикатор выполнения заполнялся от 0 до 100%, вам понадобятся некоторые дополнительные возможности.
Вот сложная часть: обновления компонента пользовательского интерфейса должны выполняться в потоке пользовательского интерфейса.Но вы не можете запустить все в потоке пользовательского интерфейса, потому что поток пользовательского интерфейса не будет обрабатывать события (такие как обновление индикатора выполнения), пока не завершится добавление элементов управления.
Вам нужен метод, который будетнести ответственность за добавление элементов управления в Panel, чтобы вы могли обновлять пользовательский интерфейс по мере его появления.Есть много способов сделать это;возможно, самый простой способ - просто сделать:
Thread thread = new Thread(MyControlAddingMethod);
thread.Start();
Ваш метод добавления элементов управления должен маршалировать вызовы методов пользовательского интерфейса до потока пользовательского интерфейса.Вот как это сделать:
void MyControlAddingMethod()
{
myPanel.BeginInvoke(m => { myPanel.Controls.Add(myControl); ++myProgressBar.Value;});
//or
myPanel.BeginInvoke(MyFunctionThatDoesTheSameAsTheLambdaStatementAbove);
}