Accessing GUI from event handler - c#

When a byte from the serial port is received, it enters this handler correctly, but my label on the GUI does not change. Edit: Yes, it is in the same class as the GUI
Edit 2 The function declaration does not need to be 'static'...I merely copy-pasted an example from msdn
edit 3 It works after getting rid of the static decleration and using something like this.
Thanks for your help
private static void DataReceivedHandler(object sender, SerialDataReceivedEventArgs e)
{
Form1 gui = new Form1(); //main GUI
try
{
SerialPort sp = (SerialPort)sender;
string indata = sp.ReadExisting();
//gui.rxLabel.Text = indata;
gui.txLabel.Text = "testttingg";
}
.......

Why are you declaring a new instance of your form? Just use your form's txLabel
In c#:
this.txLabel.Text = "testing";
In vb.net:
Me.txLabel.Text = "testing"
In the sample code you posted you are creating a new instance / reference to your actual form. Use the existing instance, in addition, use this rather then a new instance.
I had to edit my question as I noticed you were using a static method.
Try this:
public static void DataReceivedHandler(object sender, SerialDataReceivedEventArgs e)
{
Form1 f = (Form1) sender;
f.textBox1.Text = "testing";
}
private void button1_Click(object sender, EventArgs e)
{
DataReceivedHandler(this, null);
}
Of course I am just calling DataReceivedHandler() from a button event, you can call it from your own event. Point being is you need to pass the current instance, this to the function. Once inside the function do not create a new instance of the form, just set a reference to the current form and use that reference to apply the settings to the property (txtBox or Label or whatever).

It appears you're instantiating a new instance of Form1, instead of accessing the existing form in memory.

Related

C# : Using statement and this keyword

While wanting to use using statement, I came across a scenario that I don't understand :
private void RoomMealHistory_Click(object sender, EventArgs e)
{
MealRoomPlanning fMealRoomPlanning = new MealRoomPlanning(true);
fMealRoomPlanning .MdiParent = this;
fMealRoomPlanning.Show();
}
This code works correctly and my window is a MdiChild.
However, the following code does not work :
private void RoomMealHistory_Click(object sender, EventArgs e)
{
using (MealRoomPlanning fMealRoomPlanning = new MealRoomPlanning(true))
{
MdiParent = this;
fMealRoomPlanning.Show();
}
}
ArgumentException: 'A form cannot be an MDI child and an MDI parent at the same time.
I also tried to replace this with this.ParentForm doesn't work anymore.
Is there a problem with the scope of this?
In your first snippet, you set the MdiParent-Property of fMealRoomPlanning.
In your second snippet, you set MdiParent of your own class instance (this.MdiParent).
You should set it on the object you are using:
private void RoomMealHistory_Click(object sender, EventArgs e)
{
using (MealRoomPlanning fMealRoomPlanning = new MealRoomPlanning(true))
{
fMealRoomPlanning.MdiParent = this;
fMealRoomPlanning.Show();
}
}
That's why many style-checks recommend using the this-Qualifier although it is redundant. This makes it more clear if you set a local, global or class variable.
Finally I have just understood that Using is not necessary for non-modal Form.
When a non modal form is closed, the Dispose will automatically be called by WinForms.
Unlike Forms opened with ShowDialog for which the Dispose is not called automatically.
Try changing MdiParent = this to fMealRoomPlanning.MdiParent = this
Try Changing the 2nd Code, After creating object for MealRoomPlanning class
change MdiParent = this; to fMealRoomPlanning.MdiParent = this;
private void RoomMealHistory_Click(object sender, EventArgs e)
{
using (MealRoomPlanning fMealRoomPlanning = new MealRoomPlanning(true))
{
fMealRoomPlanning.MdiParent = this;
fMealRoomPlanning.Show();
}
}

can't able to add value to textbox

I have a datacontrol.cs(UserControl), which is contain textbox1 and codebehind window having a method with parameter of currentvalue
public void bindvalue(float currentvalue)
{
textbox1.Clear();
textbox1.Text = currentvalue.ToString();
}
I have a Form, Here added the usercontrol in this form and which contains a Button
So when clicking button it pass a currentvalue by the way of method to the datacontrol class like that .
private void button_click(object sender, EventArgs e)
{
float currentvalue = 1500.00f;
datacontrol obj = new datacontrol();
obj.bindvalue(currentvalue);
}
Everything working fine to me. It pass the current value to the usercontrol class and there current value assigned/added to the textbox1.Text = currentvalue.ToString();. It doesn't shows any error . But finally the textbox doesn't shows any value.
I used breakpoint to check the functionality. It gave current value to the textbox. But strange!!!..
I can't predict whats wrong in my code.
Helps appreciated.:)
Your instance of datacontrol with required value (1500.00f) does not exist on your form. You are only delcaring it, passing value and forgetting about it.
If you have already added user control to form and want to call bindvalue method of existing control, you should do the following:
private void button_click(object sender, EventArgs e)
{
float currentvalue = 1500.00f;
this.dataControl1.bindvalue(currentvalue);
}
Note that dataControl1 is the name of your user control on the form, it can be different from dataControl1.
If you want to create new user control and call bindvalue, you should add new instance on the form:
private void button_click(object sender, EventArgs e)
{
float currentvalue = 1500.00f;
datacontrol obj = new datacontrol();
obj.bindvalue(currentvalue);
this.Controls.Add(obj);
}
If it is already dynamically added control on the form, declare a field of Form class, assign new instance of it control, when you want it, and call to it as it shows in the first example.
You need add instance of datacontrol to the form
datacontrol obj = new datacontrol();
obj.bindvalue(currentvalue);
Controls.Add(obj);
You can simply make a call to bindvalue method by using the tagename of your user control in button click event handler.
Suppose the tag name is 'datacontrol', then you should use the following lines of code to achieve your task:
protected void Button1_Click(object sender, EventArgs e)
{
float myvalue = 150.50f;
datacontrol1.BindValue(myvalue);
}
Regards, Aamir ( .Net developer)
Please marks this thread as answer if it solved what were looking for... thanks

Pass parameter in an already opened form in C#

I want to pass a parameter to the textbox. I have the following code and it is passing the parameter but not the way I want.
My main form in already open and I want to pass the parameter from my search form. when I do with the code below it opens mt 1 more main form and the parameter is shown in there. I want to by able to show in the opened main form.
When I erase frmMain.Show(); nothing happens.
Main frmMain = new Main();
artikal = "TEST TEST";
frmMain.ed_artiakal.Text = artikal;
frmMain.Show();
any suggestions?
You have many variants to solve your problem.
Option 1
Define and use custom event.
Search form code:
public event EventHandler ArtikalTextChanged;
private void textBox1_TextChanged(object sender, EventArgs e)
{
if (ArtikalTextChanged != null)
ArtikalTextChanged(this, EventArgs.Empty);
}
Main form code:
private void button1_Click(object sender, EventArgs e)
{
Search search = new Search();
search.ArtikalTextChanged += OnArtikalTextChanged;
search.Show();
}
private void OnArtikalTextChanged(object sender, EventArgs e)
{
this.ed_artiakal.Text = (sender as Search).textBox1.Text;
}
Don't forget to make textBox1 of Search form public.
Option 2
Get instance of your main form in search form:
Search form code:
private void textBox1_TextChanged(object sender, EventArgs e)
{
var mainForm = Application.OpenForms.OfType<Main>().FirstOrDefault();
mainForm.ed_artiakal.Text = textBox1.Text;
}
Main form code:
private void button1_Click(object sender, EventArgs e)
{
Search search = new Search();
search.Show();
}
Don't forget to make ed_artiakal control public in your Main form.
Option 3
Share data between forms (recommend)
But if you application is large and you want to make it scaleable and flexible I recommend you to use data-binding technique to share data between forms without coupling them. You can read more at articles: http://msdn.microsoft.com/en-us/library/h974h4y2(v=vs.90).aspx
I have solved my problem in the following way.
On my Search Form I created a public string and when I showed the form I referenced to that string in my case GetItemCode.
The key here was to use ShowDialog() and not to use Show().
SEARCH FORM
Search frmSearch = new Search();
frmSearch.ShowDialog();
ed_artiakal.Text = frmSearch.GetItemCode;
MAIN FORM
public string GetItemCode
{
get { return Artikal; }
}
Now when I close the search form the value is shown in the TextBox on my main form.
Thanks for your answers and comments!

Form.Show(): Cannot access a disposed object

I have been stuck with this for some time now. I can't open a new form on button click.
If i create and .Show() form in the start form constructor i will work. I dont get it! :-(
StartUp Form
public Form1()
{
InitializeComponent();
startmessage();
br = Logic.loadXML("theshiiiiiittt.xml");
br2 = br.Clone();
loadboxes();
//serializeTest();
t = new Thread(contactDBUpdate);
//t.IsBackground = true;
t.Start();
}
Button event:
private void resultButton_Click(object sender, EventArgs e)
{
ResultForm rf = new ResultForm(this);
rf.Show();
this.Enabled = false;
}
Hope this is enough.
In my case it was caused by the fact that i wanted to make my forms non-modal. So i changed them from form.ShowDialog(parentForm) to form.Show().
But that caused the ObjectDisposedException if i try to show a form a second time because somewhere in the code was this.Close();. Form.Close also disposes it.
MSDN:
When a form is closed, all resources created within the object are
closed and the form is disposed.
I just needed to change
this.Close();
to
this.Hide();
Found my code problem.
I took one more look at the Stack trace and found i a message "Icon".
this.Icon.Dispose();
Startupform had this line.
This code fixed my problem:
private void resultButton_Click(object sender, EventArgs e)
{
ResultForm rf = new ResultForm(this);
rf.Icon = this.Icon;
rf.Show();
this.Enabled = false;
}
Thanks for the helping hands...
The problem is that your form object loose the scope and is disposed off.
If you want to keep the dialog open, use Form.ShowDialog();
Try this:
private void resultButton_Click(object sender, EventArgs e)
{
using(ResultForm rf = new ResultForm(this))
{
rf.ShowDialog();
}
this.Enabled = false;
}
Wile Implementing singleton pattern on windows form I got this error too.
The solution is that you have to assign a null value to the static reference in
protected override void Dispose(bool disposing)
by putting simple line.
obj=null; //obj is the static reference in the class.

Some events dont work in Winform in C#

I am using YoutubeExtractor's dll.. videoDownloader_ProgressChanged and videoDownloader_DownloadFinished events are working in console application but in winform, it doesnt work.. I dont understand why..
private void btnStart_Click(object sender, EventArgs e)
{
string link = textBox1.Text;
start(link);
}
static void start(string link)
{
IEnumerable<VideoInfo> videoInfos = DownloadUrlResolver.GetDownloadUrls(link);
DownloadVideo(videoInfos);
}
private static void DownloadVideo(IEnumerable<VideoInfo> videoInfos)
{
VideoInfo video = videoInfos
.First(info => info.VideoFormat == VideoFormat.Standard360);
var videoDownloader = new VideoDownloader(video, Path.Combine("C:/Downloads", video.Title + video.VideoExtension));
videoDownloader.DownloadFinished += new EventHandler(videoDownloader_DownloadFinished);
videoDownloader.ProgressChanged += new EventHandler<ProgressEventArgs>(videoDownloader_ProgressChanged);
videoDownloader.Execute();
}
static void videoDownloader_ProgressChanged(object sender, ProgressEventArgs e)
{
//some code..
}
static void videoDownloader_DownloadFinished(object sender, EventArgs e)
{
//some code..
}
my second question is, I want to access a form control in a static videoDownloader_ProgressChanged event. e.ProgressPercentage paramter gives me percent of video downloaded. I want to show it in label. But I cant access label because of static event.. I tried to use delegate but nothing changed..
Please modify both Start() and DownloadVideo() routines to instance methods. Remove 'static' keyword from them and event handlers as well.
Thread off 'videoDownloader.Execute()' and BeginInvoke() in the changed/finished handlers.
Don't call methods that take forever, (in computer terms), in GUI event handlers. If it takes more than about 50ms, thread it off. Any net thingy, eg. something with 'YouTube' in it, will take longer than that just to establish a connection!

Categories

Resources