EInherjar
EInherjar

Reputation: 339

Passing data w/ constructor with main form

I have three forms, f1, f2, f3 we'll call them. I have a class Account, in which I store username, password, groups and path (files). F2 is the main form, and should interact with both other forms. F1 is the login form and F3 is the edit form. I use this in my program.cs to call the login form before other forms.

Form1 login = new Form1();
if (login.ShowDialog() == DialogResult.OK)
{
    Application.Run(new Form2());
}

To pass data between f2 and f3, I use a constructor with the account class. However, I would also like to pass data from f1 to f2, but if I use the same approach, I get no data interaction between the forms (data is null).

I edited the above code to this:

Form1 login = new Form1();
Account acc = new Account();
if (login.ShowDialog() == DialogResult.OK)
{
    Application.Run(new Form2(acc));
}

In the login form (f1), I pass some data to the Account class, so upon login button click this happens:

private void LoginButton_Click(object sender, EventArgs e)
{
    Account acc = new Account();
    //some code
    acc.Groups = "New group";
    //some more code
    DialogResult = DialogResult.OK;
}

Then, in the Form2.cs, I have the following code:

string groups = "";
public Form2(Account acc)
{
    InitializeComponent();
    groups = acc.Groups;
}

But whenever I run it like that, I never get any results in the main form (f2), acc.Groups is always null, and I do not know why exactly. I used the same approach with constructors to pull data from f2 to f3, and it worked fine, why doesn't this work? Is it because I use the wrong approach with the login form? What is the correct way to handle this?

Upvotes: 0

Views: 1515

Answers (3)

Mong Zhu
Mong Zhu

Reputation: 23732

the problem is that you create a new instance of Account in the LoginButton_Click event. and you never pass this instance to the form2!

Create a field in the Form1 class of type Account:

Account my_account;

And overload the constructor to take an account as parameter:

public Form1(Account acc)
{
    my_account = acc;
}

then reference in the click event the field my_account

private void LoginButton_Click(object sender, EventArgs e)
{
    //reference the class variable
    my_account.Groups = "New group";
    //some more code
    DialogResult = DialogResult.OK;
}

In the beginning you need to pass the starting instance of Account into the Form1 constructor so it can be filled with values:

Account acc = new Account();
Form1 login = new Form1(acc);

if (login.ShowDialog() == DialogResult.OK)
{
    Application.Run(new Form2(acc));
}

Explanation in detail:

When creating an instance of Account acc = new Account(); you get a unique object with a specific location in the memory. When you pass this object to the constructor of Form1 and assign it to the private field my_account you actually pass only the reference of acc. Meaning that you pass the location of it in memory. That means that when you do this: my_account = acc; in the constructor you make sure that my_account points to the same location as the acc object. When you manipulate values of my_account by assigning a string to Groups you actually manipulate the original acc object. After returning from Form1 you pass the acc object again as reference to the next constructor. So when you access in Form2 this object in groups = acc.Groups; you access the original location in memory that you have manipulated and to which you have assigned the string "New group".

In your posted code you created in Form1 an entire new object using Account acc = new Account(); which is again unique and independent of the object that you created in the very beginning. This object also is located on a different portion of memory as the first acc object. This is why the property Groups is null when you have tried to access it in Form2 I hope this is understanable

Upvotes: 1

Hieu Le
Hieu Le

Reputation: 1132

In Form1, declare

public Account Account { get; set; }

In Account, declare

 public Form1 Form1{ get; set; }

After created 2 objects login and acc :

Form1 login = new Form1();
Account acc = new Account();

Assign to each other

login.Account = acc;
acc.Form1 = login;

Upvotes: 0

kendzi
kendzi

Reputation: 331

I see you create new Account() in two places ( so you have more than one instance), but you don't pass account to form2 nowhere.

You can make Account static like Janes suggest in comment or make property to get account.

Upvotes: 0

Related Questions