Application with both GUI and continuously running elements

I am actually using a Mac, so I don’t know why I’d get those errors. Anyway, I downloaded your new example. Thanks for making it for me. It seems to run but I still get the error:

Error in TMutex::UnLock: thread -1610160352 tries to unlock unlocked mutex

I have version 5.24/00 of ROOT. There are two graph canvases, one above the other, and only the top one has anything in it when I click Draw. Is that what it’s supposed to do?

Thanks.

Hi,

[quote=“msj”]
Error in TMutex::UnLock: thread -1610160352 tries to unlock unlocked mutex [/quote]
I don’t have this error with svn trunk, so this has probably been fixed in more recent versions of ROOT.

[quote=“msj”]
I have version 5.24/00 of ROOT. There are two graph canvases, one above the other, and only the top one has anything in it when I click Draw. Is that what it’s supposed to do?[/quote]
Well, yes, it is based on the code you wrote:

[quote=“msj”]
Thanks very much for the example. I have been able to incorporate it into the application I am developing. The only trouble I am having is that I want to have 2 graphs. I have started out by adding a canvas called fEcanvas2 and defining it in a similar way to fEcanvas. However, when I do this, the plotting no longer works properly. I don’t understand what is wrong. Here is my modified code:[/quote]
Cheers, Bertrand.

Thanks for the new example. I have incorporated the thread into my program. Unfortunately, there is a segmentation fault caused by fThread->GetState(). This doesn’t end the overall program, but prints the error on the screen, and the graph doesn’t appear. Everything else I had in the program from before seems to work.

Do you know why this would happen? I think I have declared everything exactly as you have. Is it perhaps because my program is standalone?

Thanks.

Initialize fThread to 0 when creating your class and check for its validity before to access it:

   fThread = 0;
   [...]
   if (fThread && fThread->GetState() != TThread::kRunningState) {

If it still doesn’t work, please post your code.

Cheers, Bertrand.

I have a .cxx and an .h file. The class is defined in the .h file, with the function declarations, and some definitions. The rest of the definitions are in the .cxx file. Where should I put “fThread=0;”? Or would I need to put “MyMainFrame::fThread=0”? Thanks.

In the parent class constructor implementation (.cxx), as any other class member initialization should be done… For example:

//______________________________________________________________________ 
MyMainFrame::MyMainFrame(const TGWindow *p,UInt_t w,UInt_t h) 
   : TGMainFrame(p,w,h) 
{ 
   fThread = 0;
   ...

or:

//______________________________________________________________________ 
MyMainFrame::MyMainFrame(const TGWindow *p,UInt_t w,UInt_t h) 
   : TGMainFrame(p,w,h), fThread(0)
{ 
   ...

Now it seems to skip over that code entirely, as if fThread is not defined. Do I need to do anything else?

Edit: actually, forget that. I hadn’t put a couple of lines in that I needed. I’m still having a segmentation violation and I am figuring out exactly where it occurs.

Thanks.

I realized I had missed another line, so now I’m no longer getting a segmentation violation. However, it starts plotting as it’s supposed to, but when I click the buttons that take a while to execute, the plotting is suspended until they are finished. I want it to keep continuously plotting no matter what buttons are pressed. Is that possible? Right now I don’t see much difference between the present functionality and what it did when the timer was used. Am I missing something?

Thanks.

Well, I would say that if you have a time consuming operation taking all the CPU resource, it may block the graphics update (but the thread should not be blocked if it doesn’t make any graphics output). And maybe your code is not optimal for what you are trying to achieve… If you have time (and CPU) consuming loops, you can try to add gSystem->ProcessEvents() inside the loop to see if it makes any difference.
Then, if you need more help, please post your code, because it is impossible for me to guess what could be wrong in your code without seeing what you are doing…
Cheers, Bertrand.

Thanks so much for the help. That gSystem->ProcessEvents() line did the trick. All I have in the loop is a sleep command and a couple of other commands (not anything CPU intensive), but it seemed to stop everything. Now it works basically as I want and I can tweak it to make it perfect. I can’t promise I won’t have any more questions but I’m good for now. Thanks again.

Very good! And you’re welcome! :slight_smile:
Cheers, Bertrand.

Just one more question (for now): If I want to be able to start and stop the thread while the program is running, how can I do that?

Thanks.

Try the attached script. But note there are still some issues with stopping and restarting threads on non-Windows platforms (someone should be looking at this right now)

Cheers, Bertrand.
gui_thread.C (4.56 KB)

Thanks for the script. I was only missing one line. It works in Mac and Linux. I didn’t try it with Windows.

If I want to access the other nonstatic members of the class from inside the thread, is that possible, and how can it be done? Part of what I want to do in the thread is to query the connected device for some values and plot them, but it is not possible to declare the connection to the device as static.

Thanks.

Then take a look at this version, which is the same script, but without any static members.
– Bertrand.
gui_thread2.C (4.81 KB)

Thanks so much for this latest useful example. I got it working inside my program. One thing I have noticed is that even with gSystem->ProcessEvents(), if I do a Clear() on the canvas in the thread, the graph will not update while something else is happening, like a button has been clicked and it is executing the appropriate instructions. Is there a way around this? In my program, the thread fills an array and continuously updates a graph, but without the Clear() command, the axes accumulate (they don’t get erased every time). Is there another command which will clear the axes between plots and will not stop the updating? I have looked at the Draw() command but there doesn’t seem to be an option for erasing the axes. I can’t use “same” because the x-axis is time and it needs to be able to expand.

Thanks.

Hi,

I don’t really understand what is the problem. Could you send a running script (with comments) illustrating what is the exact issue?

Cheers, Bertrand.