Я хочу, чтобы мое приложение.NET C# имело форму, но не было формой.
То, когда я обычно запускаю приложение форм окон, оно похоже на форму, является ведущим устройством всего остального, что следует:
static void Main()
{
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new Form1());
}
Вместо этого я хотел бы запустить свою программу, которая затем может показать форму, но не является самой формой. Другими словами, я не хочу главный контроллер applicatin быть формой, я хотел бы, чтобы он вместо этого был невидимым логическим контейнером, который имеет возможность показать формы, но не является самой формой.
Я не уверен, ставлю ли я вопрос ясным способом, но я хотел бы услышать мысли.
Довольно часто создается отдельный компонент Bootstrapper, который можно переместить отображение основной формы в:
using System;
using System.Windows.Forms;
namespace Example
{
internal static class Program
{
[STAThread]
private static void Main()
{
new Bootstrapper().Run();
}
}
public class Bootstrapper
{
public void Run()
{
// [Application initialization here]
ShowView();
}
private static void ShowView()
{
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new Form1());
}
}
}
Вы можете просто использовать Application.Run()
для запуска цикла сообщений. Но вам нужно будет сделать что-то , чтобы прослушать ввод - возможно, системный трей и т. Д.
Создайте приложение как консольное приложение, а затем вызовите Application.Run, как сказал Марк, когда вам понадобится форма.
Как Mark_Gravell упоминалось, Application.Run() блокируется до закрытия Формы1. Вы можете открыть свои формы в отдельном потоке, но этот поток будет в основном использоваться формой. И когда вы хотите, чтобы exe-файл вышел, вам придется вручную убить каждый поток. См. следующий код. (Окно консоли не создается. Я получил это, создав приложение WinForms по умолчанию и изменив класс Program)
using System;
using System.Collections.Generic;
using System.Linq;
using System.Windows.Forms;
using System.Threading;
namespace WindowsFormsApplication1
{
static class Program
{
static List<Thread> threads = new List<Thread>();
/// <summary>
/// The main entry point for the application.
/// </summary>
[STAThread]
static void Main()
{
for (int i = 0; i < 10; i++)
{
StartThread();
System.Threading.Thread.Sleep(500);
}
//kill each thread so the app will exit, otherwise, the app won't close
//until all forms are manually closed...
threads.ForEach(t => t.Abort());
}
static void StartThread()
{
Thread t = new Thread(ShowForm);
threads.Add(t);
t.Start();
}
static void ShowForm()
{
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new Form1());
}
}
}
Вместо этого вы можете использовать ApplicationContext. Это дает вам необходимый цикл сообщений, который будет поддерживать форму, как только вы решите ее создать. Сделайте свой класс Program похожим на это:
static class Program {
[STAThread]
static void Main() {
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
AppContext = new ApplicationContext();
Application.Run(AppContext);
}
public static void Quit() {
AppContext.ExitThread();
}
public static ApplicationContext AppContext;
}
Помните, что приложение не закроется автоматически, когда вы закроете последнее окно. Требуется явный вызов ExitThread.
Вы также можете создать свой собственный ApplicationContext
static void Main()
{
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(AppController.Instance);
}
И внутри AppController.cs
namespace MyApplication
{
public class AppController
{
static AppController _AppController;
public LoginWIndow LoginWIndow;
//Constructor
public void AppController()
{
//Do what you will here, Start login form, bind events, w.e :)
if(true) //Your check
{
ShowLoginWindow();
}
}
public void ShowLoginWindow()
{
LoginWIndow = new LoginWIndow();
LoginWIndow.ClosedForm += new FormClosedEventHander(ExitApplication);
LoginWIndow.Show();
}
public void ExitApplication(Object Sender, FormClosedEventArgs Args)
{
//Some shutdown login Logic, then
Application.Exit();
}
static AppController Instance
{
get
{
if(_AppController == null)
{
_AppController = new AppController();
}
return _AppController;
}
}
}
}