Добавяне на формуляри. Взаимодействие между формите

Въпреки факта, че моето мнение за microsoft визуално студиовсе пак понякога трябва да направите нещо по въпроса. Ако се примирим с факта, че в този случай пишем всъщност не в C ++, а в така наречения C ++ / CLI , работата с обичайните визуални компоненти няма да бъде толкова различна от същата Borland среди. Но може да създаде проблеми в сравнение с Builder.Нека разгледаме 3 типични ситуации на работа с приложение, съдържащо повече от една форма.Примерната среда е безплатна Visual C++ 2010 Express, предполага се, че основната форма има име по подразбиране Form1.

Пример за конструиране и програмно извикване на формуляр

Този код може да се изпълни например чрез натискане на бутон в главната форма Form1.

Form^form2 = gcnew Form(); Бутон^бутон2 = gcnewButton(); бутон2->Текст = L"OK"; бутон2->Местоположение = Точка(10,10); form2->Текст = L"Моят прозорец"; form2->HelpButton = true; form2->FormBorderStyle = System::Windows::Forms::FormBorderStyle::FixedDialog; form2->StartPosition = FormStartPosition::CenterScreen; form2->Controls->Add(button2); form2->ShowDialog();

За да добавите манипулатор на кликване за програмно генерирания бутон2, просто напишете преди последния ред код:

Button2->Click += gcnew System::EventHandler(this, &Form1::button2_Click);

Преди методът form2->ShowDialog() или form2->Show() да бъде извикан;

В същото време кодът на манипулатора се поставя в текущия модул Form1.h:

Частно: System::Void button2_Click(System::Object^ sender, System::EventArgs^ e) ( MessageBox::Show("Here"); )

Извикайте друга форма от основната форма

В менюто изберете Проект - Добавяне на нов елемент - Форма - име Form2

Нека добавим оператор

#include "Form2.h"

преди първото пространство от имена във Form1.h (тоест в самото начало на файла).

Нека включим указател към екземпляра на класа в публичната секция на класа Form1:

Form2^F2;

Нека добавим кода, където трябва да създадем и извикаме втората форма:

F2=gcnew Form2(); F2->Покажи();

За програмно изтриване на втората форма кодът е подходящ

Изтриване на F2;

Трябва да се отбележи, че указателят съхранява адреса само на една форма, тази, която е създадена последна. Ако сме създали последователно няколко форми с този код, само последната ще бъде изтрита. Като алтернатива опитайте набор от форми, описани по-долу.

Нека опишем необходимите данни във формуляра клас Form1 (тук името и пространството от имена на проекта Tabulator, ако е необходимо, заменете със собствените си):

static const int MAX_FORMS = 100; // Максимална сумаформи int FormCount; // Формуляр на брояч масив ^F2; //Показател към масив от форми

След това инициализираме данните за събитието Load на главния формуляр:

FormCount=0; F2 = gcnew масив (MAX_FORM);

След това внедряваме кода, за да създадем следващия формуляр

Ако (FormCount покажи (); ) else MessageBox::Show("Твърде много форми!");

и премахването му:

Ако (FormCount) ( изтриване на F2; FormCount--; )

Ако искаме да създаваме дъщерни форми не отделно, а вътре в родителската форма, тогава в свойствата на Form1 трябва да посочим, че е "предшественик" (задайте свойство IsMdiParent = true), и преди да покажем дъщерната форма с F2 ->Show() оператор, маркирайте го като дъщерен Form1:

F2->MdiParent = това;

Извикване на метод на родителска форма от дъщерна форма

Едва ли можем да минем без включването на .cpp файлове, което не е лошо - писането на код в .h файлове на правилния C "shnik обикновено се счупва :)

Нека разбием процеса стъпка по стъпка.

1) Има 2 форми - Form1 и Form2, на Form1 са Button (button1, ще отвори втората форма) и Label (label1, тук ще променим текста). На Form2 - button1 , при щракване върху който текстът в label1 ще се промени.

2) Тъй като трябва да имаме достъп до втория от първия формуляр и от втория до първия, ще възникне проблемът с кръстосаните препратки (когато Form1.h препраща към Form2.h , което от своя страна отново препраща към Form1.h). За да избегнем това, ще преместим кода на първия формуляр (Form1), който ще има достъп до втория формуляр (Form2), от .h файла в .cpp файла. По този начин трябва да създадете файл Form1.cpp.

3) Декларирайте публичен метод Set във Form1.h, така че да можете да промените текста на label1 (кодът може да бъде написан в края на файла, след #pragma endregion):

Public: void Set(String^ text) ( label1->Text = text; )

4) Във файла Form2.h включваме Form1.h (в началото):

#include "Form1.h"

и създайте конструктор, който ще приеме и съхрани препратка към първата форма за по-късна употреба:

Form2(Form1^ parent) ( InitializeComponent(); parentForm = parent; ) //можете да добавите връзка точно отдолу: private: Form1^ parentForm;

5) При щракване върху бутона във Form2, ще извикаме метода Set на родителския формуляр:

Частно: System::Void button1_Click(System::Object^ sender, System::EventArgs^ e) ( parentForm->Set("hello from form2"); parentForm->Show(); this->Hide(); )

6) Остава в първата форма да се направи отварянето на втората форма. За да направите това, прехвърлете манипулатора за щракване върху бутон от Form1.h към Form1.cpp и оставете само неговата декларация в .h файла.

От админ.

Изучаването на C# е бавно. но продължава правилно. Съвсем наскоро аз
даде пример как да отворите друга от една форма в Visual C#. По принцип всичко е просто.

Днес се появи следната задача: стартирайте модална форма от основната форма на приложението, тази форма, когато е затворена, трябва да прехвърли всички данни (текст, стойности на свойства и т.н.) към контролите на основната форма. Не е възможно този проблем да се реши по начина, описан в предишната публикация за формулярите. в този случай ние просто създаваме нов обект на формуляр с нови стойности за всички свойства. За щастие C # има прекрасен събирач на боклук ... Но въпросът не е в колектора, а в това как да отворите дъщерна форма в C # и след това да се върнете към основната от нея?

Като начало нека зададем първоначалните (първоначалните) данни.

Така. Имаме основния формуляр за кандидатстване:

Този формуляр също съдържа текстово поле с име TBDialog и бутон при щракване, върху който трябва:

  1. Предайте стойността на свойството Text от TBDialog към TBMain;
  2. Затворете fDialog;

Сега разгледайте целия процес на работа в ред.

Първо, винаги трябва да помните, че по подразбиране на всички свойства, променливи и методи в C# е присвоен модификатор частен- следователно, за да стигнем от втората форма до контролата на първата, трябва да настроим модификатора на TBMain публиченсам по себе си. За да направите това, изберете елемента TBMain в конструктора на формуляр, отидете в прозореца със свойства и промяна на стойността на имота Модификатори с частенНа публичен.

Сега TBMain ще се вижда в други обекти. Продължаваме напред. За да отворим формата в модален режим, трябва да използваме една от двете опции за метода ShowDialog():

public DialogResult ShowDialog() ; public DialogResult ShowDialog(собственик на IWin32Window);

В първия случай методът показва формата като модален диалогов прозорец с текущия активен прозорец, зададен като собственик, а във втория случай можем независимо да посочим коя форма ще стане собственик на нашия модален прозорец.

Например, нека използваме втория вариант на метода ShowDialog() и да покажем втората форма модално. За да направите това, ние пишем следното:

Тук отново използвах ключовата дума това , който сочи към текущия обект, т.е. задайте главната форма като собственик ( fГлавен). Сега преминаваме директно към решаването на нашия проблем и отговаряме на въпроса: как да предам стойност от една форма в друга?Всеки контрол има чудесно свойство Собственик - което сочи към родителя:

Сега можете да стартирате проекта и да се уверите, че текстът от TextBox на дъщерния формуляр е перфектно прехвърлен в TextBox на първия. За всеки случай публикувам изходния код на проекта, разгледан в примера.

Понякога трябва да се обърнете към елементите на една форма от друга по време на изпълнение на програмата. Например, има форма Form1, от която отваряме друга Form2 и сега, работейки във формата Form2, трябва да имаме достъп до елементите на родителската форма Form1. Намерих няколко начина да направя това.

1-ви начин. Предаване на препратка към публична променлива.

Пространство от имена WindowsApplication1 ( публичен частичен клас Form1: Формуляр ( публичен Form1() ( InitializeComponent(); ) private void button1_Click(изпращач на обект, EventArgs e) ( Form2 frm = new Form2(); frm.but1 = this.button1; // пас връзка към бутона във Form2 frm.ShowDialog(); ) ) )

Във Form2 променливата, към която е предадена връзката, сега ще съответства на button1 от Form1

Пространство от имена WindowsApplication1 ( public частичен клас Form2: Form ( public Button but1; // тази променлива ще съдържа препратка към бутона button1 от Form1 public Form2() ( InitializeComponent(); ) private void button1_Click(object sender, EventArgs e) ( but1 . Text = "test"; // промяна на текста на бутона button1 на Form1 ) ) )

2-ри начин. Предаване на връзка към дъщерен формуляр.

Същността е приблизително същата, след това в 1-ви метод. Когато отваряме формата Form2, ние предаваме в нея връзка към елемента, който планираме да променим по-късно.

Пространство от имена WindowsApplication1 ( публичен частичен клас Form1: Формуляр ( публичен Form1() ( InitializeComponent(); ) private void button1_Click(object sender, EventArgs e) ( Form2 frm = new Form2(this.button1); // предаване на връзка към бутон към формуляр Form2 frm.ShowDialog(); ) ) )

Сега във Form2 трябва да създадете променлива, която ще съдържа връзка към този бутон и чрез нея ще имаме достъп до бутона на Form1 (редове 5,7,9 и 15).

Пространство от имена WindowsApplication1 ( public частичен клас Form2: Form ( private Button but1; // тази променлива ще съдържа препратка към бутона button1 от Form1 public Form2(Button but) // получава препратка към бутона в променливата but ( but1 = but ; // сега but1 ще бъде връзка към button1 InitializeComponent(); ) private void button1_Click(object sender, EventArgs e) ( but1.Text = "test"; // промяна на текста на бутона button1 на Form1 ) ) )

3-ти начин. Достъп до цялата родителска форма.

За да направим това, трябва да направим промени в няколко файла, но в същото време ще имаме достъп до всички елементи на родителската форма и не е необходимо да подаваме връзка към всеки елемент, както при първия метод.

Етап 1.Във файл Program.csсъздайте публична променлива f1 (ред 5).

Пространство на имената WindowsApplication1 ( статичен клас Program ( public static Form1 f1; // променлива, която ще съдържа препратка към Form1 static void Main() ( Application.EnableVisualStyles(); Application.SetCompatibleTextRenderingDefault(false); Application.Run(new Form1() ) ;)))

Стъпка 2Ние отваряме Form1.Designer.csи в него за елементите, които ще трябва да бъдат достъпни от друга форма, ние променяме частенНа публичен. Например, нека направим бутона button1 достъпен за промени във Form1.

Public System.Windows.Forms.Button button1; // променено частно на публично

Стъпка 3. Когато създаваме формуляра Form1, присвояваме на променливата f1 препратка към този формуляр (ред 7)

Пространство от имена WindowsApplication1 ( public частичен клас Form1: Form ( public Form1() ( Program.f1 = this; // сега f1 ще бъде препратка към формуляр Form1 InitializeComponent(); ) private void button1_Click(object sender, EventArgs e) ( Form2 frm = нов Form2(); frm.ShowDialog(); ) ) )

Стъпка 4Сега, от абсолютно всяка форма или от всеки клас, можете да получите достъп до елемента button1, разположен на Form1 по следния начин: Program.f1.button1. Например, нека един бутон във Form2 промени текста на бутона на Form1:

Пространство на имената WindowsApplication1 ( public частичен клас Form2: Form ( public Form2() ( InitializeComponent(); ) private void button1_Click(object sender, EventArgs e) ( Program.f1.button1.Text = "test"; // Промяна на текста на бутон за форма Form1 ) ) )

Въпросът, който се обсъжда в тази статия, е по-скоро свързан с темата за архитектурата на приложението, а не с конкретния разглеждан проблем. Прехвърлянето на данни от една форма в друга не е никак трудно. За да направите това, достатъчно е да отворите контролата, чиито данни искаме да получим, тоест да я маркирате с модификатора public. Освен това е възможен и друг вариант. Например, в първата форма, ние създаваме обект от втората форма, като предаваме препратка към себе си към конструктора, тоест като предаваме от първата форма към втората форма препратка към първата
SecondForm secondForm = нов SecondForm(this);
Естествено, преди да направите това, трябва да се погрижите за създаването на претоварване на втория конструктор на формуляри.

И този метод е доста често срещан. Въпреки това, със своята простота, той носи много потенциални проблеми, основният от които е нарушение на принципа на капсулиране. С една дума, втората форма не трябва да знае нищо за съществуването на първата и още повече не трябва да може да й влияе.

Решението на този проблем е съвсем просто. Да преминем директно към кода. В дизайнера създаваме основния формуляр (той ще се стартира при стартиране на приложението). Да сложим един текстово поле, етикетИ бутон.

При натискане на бутона се отваря втората форма и текстът от текстовото поле на основната форма се прехвърля в текстовото поле на втората форма. Първоначално втората форма изглежда така:

Подобно на първия, той има същите контроли. Не ни трябва повече. Входната точка на приложението стартира главния формуляр:

Използване на системата; използване на System.Collections.Generic; използване на System.Linq; използване на System.Windows.Forms; пространство от имена From1FormTo2 ( статичен клас Program ( // Основната входна точка за приложението. static void Main() ( Application.EnableVisualStyles(); Application.SetCompatibleTextRenderingDefault(false); Application.Run(new MainForm()); ) ) )

Основният код на формуляра изглежда така:

Използване на системата; използване на System.Collections.Generic; използване на System.ComponentModel; използване на System.Data; използване на System.Drawing; използване на System.Linq; използване на System.Text; използване на System.Windows.Forms; пространство от имена From1FormTo2 ( публичен частичен клас MainForm: Form ( //втора форма SecondForm secondForm; //конструктор public MainForm() ( InitializeComponent(); ) //обработчик на събития за трансфер на данни //от главната форма към втората частна void btn_mainForm_Click(object подател, EventArgs e) ( secondForm = new SecondForm(tb_mainForm.Text.Trim()); secondForm.ShowDialog(); if (secondForm.DialogResult == DialogResult.OK) tb_mainForm.Text = secondForm.ReturnData(); ) ) )

Съответно, не забравяйте да свържете бутона към събитието Кликнете. Тук, в основния клас на формуляра, има поле SecondForm secondForm A, което представлява втория обект с форма. Когато щракнете върху бутона „Изпращане“, се създава втора форма (извиква се претовареният конструктор, ще го създадем по-късно) и се стартира от метода ShowDialog(). В този случай този метод ни подхожда. Освен това след това задължително ще проверим дали не сме затворили втория формуляр, а сме кликнали върху неговия бутон. Ако във втория формуляр е щракнат бутон, тогава първият формуляр трябва да получи данни от втория. Това става чрез извикване на метода Връщане на данни ()във втората форма.

Сега най-интересната част е кодът на втората форма:

Използване на системата; използване на System.Collections.Generic; използване на System.ComponentModel; използване на System.Data; използване на System.Drawing; използване на System.Linq; използване на System.Text; използване на System.Windows.Forms; пространство от имена From1FormTo2 ( публичен частичен клас SecondForm: Form ( //претоварен конструктор public SecondForm(string data) ( InitializeComponent(); tb_secondForm.Text = data; ) //обработчик на събитие за трансфер на данни //от втория формуляр към главния формуляр private void btn_secondForm_Click (изпращач на обект, EventArgs e) ( this.DialogResult = DialogResult.OK; ) //публичен метод за достъп //до текстовото поле на този формуляр публичен низ ReturnData() ( return (tb_secondForm.Text.Trim()); ) ) )

Както можете да видите, има едно претоварване на конструктора, който приема тип низ. Не забравяйте, че се опитваме да предадем текст от TextBox. В конструктора компонентите са планирани да бъдат инициализирани и текстът на текстовото поле е зададен на стойността, предадена от първия формуляр. След това се абонирайте за събитието Кликнетеза бутона на втората форма създадохме манипулатор btn_secondForm_Click, който симулира работата на бутона "Ok" на всеки диалогов прозорец. Така с щракване върху бутона „Изпращане“ (на втората форма) изпълняваме условието

(secondForm .DialogResult == DialogResult .OK)

Първата форма, следователно, извикване на метода secondForm.ReturnData(), задаваме текстовото поле на първата форма на стойността на текстовото поле на втората форма.

работа този методМисля, че няма нужда от допълнително обяснение. Той просто връща текста от едно текстово поле, като същевременно го запазва лично.

В резултат на това прехвърлихме данни във втората форма от първата и от втората към първата, без да нарушаваме принципите на капсулиране.

Опитайте да въведете текста "aaa" в текстовото поле на първия формуляр и щракнете върху бутона. В отворената втора форма ще видите този текст в нейното текстово поле. Опитайте да промените текста на "aaa ppp" и щракнете върху бутона. Ще видите как след затваряне на втората форма даден текстще се покаже в текстовото поле на главния формуляр.

Сега мисля, че ще извършвате по-правилно прехвърляне на данни между формуляри. В следващата статия ще говорим за това как в приложенията на ASP.NET.

Последна актуализация: 31.10.2015г

За да добавите друга форма към проекта, щракнете върху името на проекта в прозореца на Solution Explorer (Solution Explorer) Кликнете с десния бутонмишката и изберете Add(Add)->Windows Form...

Нека дадем име на новата форма, например, Form2.cs:

И така, добавихме втора форма към проекта. Сега нека се опитаме да реализираме взаимодействието между двете форми. Да кажем, че първата форма ще извика втората форма, когато се щракне върху бутона. Първо, нека добавим бутон към първия формуляр Form1 и щракнете двукратно върху бутона, за да отидете до файла с код. И така, ще влезем в манипулатора на събития при щракване върху бутон, който се създава по подразбиране след двойно щракване върху бутона:

Private void button1_Click(изпращач на обект, EventArgs e) ( )

Сега нека добавим към него кода за повикване на втората форма. Нашата втора форма се нарича Form2, така че първо създаваме обект от този клас и след това извикваме метода Show, за да го покажем на екрана:

Private void button1_Click(object sender, EventArgs e) ( Form2 newForm = new Form2(); newForm.Show(); )

Сега нека направим обратното - така че втората форма да повлияе на първата. Докато втората форма не знае за съществуването на първата. За да коригирате това, трябва по някакъв начин да прехвърлите информация за първия формуляр към втория формуляр. За целта ще използваме предаване на връзка към формата в конструктора.

Така че нека да преминем към втората форма и да преминем към нейния код - щракнете с десния бутон върху формата и изберете Преглед на кода (Преглед на кода). Докато е празен и съдържа само конструктор. Тъй като C# поддържа претоварване на методи, можем да създадем множество методи и конструктори с различни параметри и да извикаме един от тях в зависимост от ситуацията. И така, нека променим кодовия файл на втората форма на следното:

Използване на системата; използване на System.Collections.Generic; използване на System.ComponentModel; използване на System.Data; използване на System.Drawing; използване на System.Linq; използване на System.Text; използване на System.Threading.Tasks; използване на System.Windows.Forms; пространство от имена HelloApp ( публичен частичен клас Form2: Form ( публичен Form2() ( InitializeComponent(); ) публичен Form2(Form1 f) ( InitializeComponent(); f.BackColor = Color.Yellow; ) ) )

Всъщност ние току-що добавихме нов публичен конструктор Form2(Form1 f) тук, в който получаваме първата форма и задаваме нейния фон на жълто. Сега нека да отидем на кода на първата форма, където извикахме втората форма и да я променим на следното:

Private void button1_Click(object sender, EventArgs e) ( Form2 newForm = new Form2(this); newForm.Show(); )

Защото в този случай ключова думатова представлява препратка към текущия обект - обект Form1, след което при създаване на втория формуляр, той ще го получи (връзката) и ще управлява първия формуляр чрез него.

Сега, след като щракнете върху бутона, ще създадем втора форма, която веднага ще промени цвета на първата форма.

Можем също да създаваме обекти за текущата форма:

Private void button1_Click(object sender, EventArgs e) ( Form1 newForm1 = new Form1(); newForm1.Show(); Form2 newForm2 = new Form2(newForm1); newForm2.Show(); )

Когато работите с множество форми, имайте предвид, че една от тях е основната – която се стартира първа във файла Program.cs. Ако имаме куп формуляри, отворени едновременно, тогава, когато основният се затвори, цялото приложение се затваря, а с него и всички останали форми.



Зареждане...
Връх