[MonoDevelop] One-shot dialogs from add-ins

Casey Marshall casey.s.marshall at gmail.com
Wed Mar 18 14:43:21 EDT 2009


On Mar 18, 2009, at 3:20 AM, Lluis Sanchez Gual wrote:

> El dt 17 de 03 de 2009 a les 15:06 -0700, en/na Casey Marshall va
> escriure:
>> I'm working on a version control addin for MonoDevelop 2.0 (beta 2),
>> and would like to have it pop up a simple dialog requesting the  
>> user's
>> password if needed. I'm able to make the dialog appear OK (I'm using
>> MessageService.GetPassword, but also tried creating a new Gtk.Dialog
>> myself), but I can't seem to be able to make it a "one shot" window  
>> --
>> only one instance of the window should appear, and if multiple VC
>> commands need to execute, they should all wait for the same dialog to
>> return.
>>
>> Is it possible to do this? I've tried three different approaches, and
>> none of them have worked.
>
> First of all you should take into account that MD may execute VS
> operations in a thread other than the main GUI thread, so you should
> make sure that the dialog is created in the GUI thread. MessageService
> will automatically do it for you, but if you create your own dialog,
> you'll have to take care of the thread transition.
>

Is Gtk.Application.Invoke the thing to use here? One frustrating thing  
is that there doesn't seem to be a way to tell if you're in the GUI  
thread or not, so you don't know if Application.Invoke will block  
(running in the GUI thread) or not (some other thread).

Because, I want to do this:

   Application.Invoke(delegate {
     run-dialog-and-get-result();
     signal-caller(); // only signal if not originally in GUI thread?
   });
   wait-to-be-signaled(); // only wait if not in GUI thread?
   use-result();

But there doesn't seem to be any good idiom for that, given my shallow  
understanding of GTK.

> To make the dialog "one shot", ensure that the dialog is modal
> (MessageService.GetPassword already is), and put a lock around the  
> code
> that shows the dialog. This should be enough.
>

Not so much; when Dialog.Run is called, Gtk# still recursively runs  
other things in the event loop, and more VC operations may be run. A  
lock won't do it in this case, since it's the same thread that owns  
the lock.

I came up with this:

   runningDialog = false

   ShowDialog() {
     while (runningDialog)
       Gtk.Main.Iteration();
     if (lastPassword != null)
       return lastPassword;
     runningDialog = true;
     // dialog setup, Run.
     lastPassword = passwd from dialog
     runningDialog = false;
     return passwd;
   }

Which *seems* to work OK, except when loading certain projects the  
TreeView showing the solution gets corrupted. I don't know if this is  
a side effect of my implementation, or a bug elsewhere.

Thanks.


More information about the Monodevelop-list mailing list