Как конструктор Winforms создает мою форму? - PullRequest
4 голосов
/ 16 мая 2009

Я разрабатываю свой собственный дизайнер WinForms. Он должен иметь возможность загружать существующие типы пользовательских форм. Одна из проблем, с которыми я сталкиваюсь, это формы без ctor по умолчанию: мой код в настоящее время создает экземпляр формы, прежде чем он сможет загрузить ее в конструктор, для чего требуется ctor по умолчанию.

OTOH, VS2008 умеет загружать такие формы. Я считаю, что на самом деле это не создает экземпляр моей формы (как отмечено в этот вопрос ): даже ctors по умолчанию не выполняются. И он действительно не выполняет InitializeComponent (). Я только что добавил окно сообщения в эту функцию, и оно не отображается.

Похоже, он динамически имитирует пользовательский тип формы и выполняет только те части кода в InitializeComponent, которые он считает уместными.

Кто-нибудь знает, где я могу найти больше информации о том, как работает дизайнер VS.

ТИА.

Примечание: я нашел этот связанный вопрос без удовлетворительных ответов

РЕДАКТИРОВАТЬ: Дополнительная информация: Стив указывает мне на CodeDom, что очень интересно. Однако моя проблема в том, что типы, которые мне нужно загрузить в конструктор, уже скомпилированы, а не доступны в виде исходного кода. Я не могу найти способ применить десериализацию CodeDom к скомпилированному коду.

Ответы [ 2 ]

13 голосов
/ 16 мая 2009

Нашел здесь :

При открытии новой Windows Проект приложения в VS, вы видите пустая форма называется Form1 в дизайне Посмотреть. Теперь вы не построили Проект пока, так как же дизайнер возможность создать экземпляр Form1 и показать это? Ну дизайнер не действительно инстанцирование Form1 на всех. Это создает экземпляр базы класс Form1, т.е. System.Windows.Forms.Form. С базовые знания объектно-ориентированного программирования, вы обнаружите, что это интуитивно имеет смысл. Когда вы Проектируя Form1, вы начинаете с Базовый класс, Форма и настроить его. Это именно то, что дизайнер поможет вам сделать.

Теперь предположим, что вы добавили кучу контролирует форму и закрыл дизайнер. Когда вы снова откроете дизайнер, управление все еще там. Тем не менее, базовый класс Form не имеет этих элементов управления на нем, так если дизайнер не работает конструктор Form1, как он показал элементы управления? Дизайнер делает это десериализацией кода в InitializeComponent. Каждый язык что дизайнер поддерживает CodeDomProvider, который несет ответственность для обеспечения парсера, который анализирует код в InitializeComponent и создает представление CodeDom Это. Затем дизайнер вызывает набор CodeDomSerializer для десериализации этого в фактический контроль (или в более широком смысле, Компоненты), которые он может добавить к Форма разработки. Теперь я замял по многим деталям в этом описание, но дело здесь конструктор этой Form1 и InitializeComponent никогда не бывает на самом деле вызывается. Вместо этого дизайнер разбирает заявления в InitializeComponent выяснить, что контролирует создать экземпляр и добавить в форму.


Выше показано, как конструктор Windows Forms в Visual Studio загружает форму. Если вы ищете способ создания экземпляра формы, у которой нет конструктора по умолчанию и по-прежнему имеют доступ к содержащимся компонентам / элементам управления, я не знаю решения. Единственный известный мне метод, позволяющий обойти отсутствие конструктора по умолчанию, - это FormatterServices.GetUninitializedObject , но будьте осторожны ...

Потому что новый экземпляр объекта инициализируется в ноль и нет конструкторы запускаются, объект может не представляет государство, которое считается как действительный для этого объекта.

У меня тоже есть приложение, которое требует создания скомпилированных форм, но я всегда использовал Activator.CreateInstance и требовал, чтобы другие разработчики включали, по крайней мере, частный конструктор по умолчанию, если они хотят, чтобы их форма была доступна в моем приложение. Поскольку мы владеем всей кодовой базой, и все знают о требованиях, это не проблема, и у нас это хорошо работает.

0 голосов
/ 16 мая 2009

В дополнение к ответу Стива, если вы добавите новую форму Windows в проект, но сделаете ее абстрактной, вы все равно сможете открыть ее в конструкторе. Однако, если вы добавите другую форму и получите ее из первой (абстрактной) формы, вы получите ошибку при попытке открыть форму в конструкторе.

...