Solved

Force method to wait until variable has a value

Posted on 2008-10-06
17
4,933 Views
Last Modified: 2013-12-17
I have a windows form that is using the web browswer control.  I have a method that opens a page in the web browser control.  When the web browser control is finished loading the page, it looks for and saves a value found in the html of the loaded page.  My method that navigates the web browser control needs to wait until the value is found before it can do anything.  I tried accomplishing this several ways.  One way was to pause the thread but that stops everything, including the web browser control so that it never finishes loading the page and thus never finds and saves my value.  See example ...

string myValue = null;

private void GoToPage()
{          webBrowser.Navigate("http://page.htm", ref empty, ref empty, ref empty, ref empty);
            while (myValue == null)
            {       System.Threading.Thread.Sleep(1000); //the value has not been found yet
            }
            MessageBox.Show(myValue);
}

private void webBrowser_DocumentComplete(n/a)
{            myValue = "example";
}


0
Comment
Question by:GaryRasmussen
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
  • 10
  • 3
  • 2
  • +2
17 Comments
 
LVL 26

Expert Comment

by:Anurag Thakur
ID: 22655453
dont use the threading.sleep because your are asking your main processing thread to sleep
instead either user a timer which checks for the value after some time interval or use a while loop just to kill some time so that the value myValue is filled
0
 
LVL 1

Author Comment

by:GaryRasmussen
ID: 22655469
can you offer an example of how to use the timer control in my application?  I don't quite understand how it works.

Thanks!
0
 
LVL 1

Author Comment

by:GaryRasmussen
ID: 22655506
This is so simple in javascript using setInterval and having the function just continue to call itself until the condition is met and then just return the value to the method that called the function.
0
Guide to Performance: Optimization & Monitoring

Nowadays, monitoring is a mixture of tools, systems, and codes—making it a very complex process. And with this complexity, comes variables for failure. Get DZone’s new Guide to Performance to learn how to proactively find these variables and solve them before a disruption occurs.

 
LVL 55

Expert Comment

by:Jaime Olivares
ID: 22655529
why not just do what you want at DocumentComplete method ?
0
 
LVL 1

Author Comment

by:GaryRasmussen
ID: 22655552
The method that loads the pape into the control will be opening a file and then looping several pages, saving the value found each time.

Get the page
Find the value
Save the value
Go to the next page
0
 
LVL 1

Author Comment

by:GaryRasmussen
ID: 22655638
This seems like it would work but it doesn't ...

do
{     //this is one way to wait but there ought to be a better way?
}
while(myValue == null);
                  
MessageBox.Show(myValue);
0
 
LVL 16

Expert Comment

by:CuteBug
ID: 22655660
Use System.Threading.ManualResetEvent.


ManualResetEvent myManualEvent = new ManualResetEvent(false);
 
private void GoToPage()
{          webBrowser.Navigate("http://page.htm", ref empty, ref empty, ref empty, ref empty);
           myManualEvent.WaitOne(); 
           MessageBox.Show(myValue);
}
 
private void webBrowser_DocumentComplete(n/a)
{            myValue = "example";
             myManualEvent.Set();
}

Open in new window

0
 
LVL 1

Author Comment

by:GaryRasmussen
ID: 22655755
wow, when I see stuff like this I realize I don't know jack.  I have never heard of this.  Thank you!!

While this works, there is something very strange happening.  After I click the button to call the GoToPage method, nothing ever happens unless I click on the application tab in the task bar several times.  I would not have even noticed it but it seems like the ap freezes and I was trying to right-mouse click on the application tab so that I could close the application?  Almost like the ap lost focus or forgot that it was waiting for something.

If you click the button to call the GoToPage method, the browser never goes to the page.  Nothing happens and I waited for up to 3 minutes.  But as soon as you click the application tab several times, the browser goes to the web page and the message box pops up the value as it should.  A left mouse click will not do anything.  You have to right-mouse click the tab 3 times to make it work.  I know, wierd.  I have no other code in this form.
0
 
LVL 16

Expert Comment

by:CuteBug
ID: 22656294
This is because of the Sleep method you are calling.

Once you use the ManualResetEvent and remove the Sleep method, it should work fine.
0
 
LVL 1

Author Comment

by:GaryRasmussen
ID: 22657024
I am not using the sleep method.  In fact, my code looks almost identical to your example.  I will attach my form (the cs and resx file in zip format).  There are only 2 small methods.

Thank you,
0
 
LVL 13

Expert Comment

by:joechina
ID: 22660205
Use System.Threading.ManualResetEvent would not help here because the document complete event is still run by the same thread as GoToPage().

Why not just move all the code behind
 webBrowser.Navigate("http://page.htm", ref empty, ref empty, ref empty, ref empty);

Into
Document complete event handler?
0
 
LVL 1

Author Comment

by:GaryRasmussen
ID: 22661293
Because there are several other things happening here that I left out so that we could stay focused on what the question is.  The web browser control is used for other functions before actually getting to this area where I need a wait mechanism like logging into a site and also selecting/submitting  parameters for building a download request.  Plus I have this chicken/egg thing going on ...

The method that loads the page into the control does so based on a looked up value.  So it gets say a ProductID from the first row of a file of 500 products...

- Use the ProductID to build the URL and go to that page ine the browser
- The page finishes loading
- A particular value is found on the page (this has to happen after the page  is fully loaded)
- The value is saved to the same row as the ProductID (would be nice if this could just be returned to the method that loaded the control with the web page so that the file read/write would be cleaner.

This waiting is a common problem and since I am new to Windows Forms, I am really suprised this one hasn't been solved yet.  I come from a web application background where a situation like this would be easily solved using a javascript function that recursively called itself with a setInterval until the value was scraped and then just returned it back to whatever called it.

And why doesn't a while loop work in this situation?  I swear I have tried every logical way to do this simple wait and none of them work correctly.  I thought this stupid application was going to take me an afternoon, not 3 days.  Geez
0
 
LVL 1

Accepted Solution

by:
GaryRasmussen earned 0 total points
ID: 22661634
I solved this one on my own.  Thanks to everyone that tried to help.  I will add my solution here for some other poor sap like me :)


bool pageLoaded = false;
 
private void GoToPage()
{	webBrowser.Navigate("http://page.htm");
	do
	{	System.Windows.Forms.Application.DoEvents();
	}
	while(! pageLoaded);
	
	myValue = "example";
	pageLoaded = false;
}
 
private void webBrowser_DocumentComplete(n/a)
{	myValue = "example";
	pageLoaded = true;
}

Open in new window

0
 
LVL 13

Expert Comment

by:joechina
ID: 22661696
Ok, in this case, your GoToPage() should run in a different thread.

So, use the code provided by cutebug,  change the code where you call GoToPage() to
(new Thread(new ThreadStart(GoToPage))).Start();
0
 
LVL 1

Author Comment

by:GaryRasmussen
ID: 22661760
Is there a reason I should change it since it is working now?  With the solution I posted, I don't need to keep a public variable, I can just keep it all inside the GoToPage.

Thanks!
0
 
LVL 13

Expert Comment

by:joechina
ID: 22662370
I had not seen your post before I posted my last one.
Your solution is fine but takes a little more CPU resourse.
0
 
LVL 1

Author Comment

by:GaryRasmussen
ID: 22662619
ok great and thanks to all of you who took the time to try and help me.
0

Featured Post

Free Tool: ZipGrep

ZipGrep is a utility that can list and search zip (.war, .ear, .jar, etc) archives for text patterns, without the need to extract the archive's contents.

One of a set of tools we're offering as a way to say thank you for being a part of the community.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

In my previous two articles we discussed Binary Serialization (http://www.experts-exchange.com/A_4362.html) and XML Serialization (http://www.experts-exchange.com/A_4425.html). In this article we will try to know more about SOAP (Simple Object Acces…
The article shows the basic steps of integrating an HTML theme template into an ASP.NET MVC project
With Secure Portal Encryption, the recipient is sent a link to their email address directing them to the email laundry delivery page. From there, the recipient will be required to enter a user name and password to enter the page. Once the recipient …
In a recent question (https://www.experts-exchange.com/questions/29004105/Run-AutoHotkey-script-directly-from-Notepad.html) here at Experts Exchange, a member asked how to run an AutoHotkey script (.AHK) directly from Notepad++ (aka NPP). This video…

740 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question