3939from qdarkstyle import DarkPalette
4040# import qdarkgraystyle
4141import trio
42- from outcome import Error
42+ from outcome import Error , Outcome
4343
4444from .._daemon import maybe_open_pikerd , _tractor_kwargs
4545from ..log import get_logger
7373
7474
7575def run_qtractor (
76+
7677 func : Callable ,
7778 args : Tuple ,
7879 main_widget : QtGui .QWidget ,
80+
7981 tractor_kwargs : Dict [str , Any ] = {},
8082 window_type : QtGui .QMainWindow = None ,
81- ) -> None :
83+
84+ ) -> int :
85+
8286 # avoids annoying message when entering debugger from qt loop
8387 pyqtRemoveInputHook ()
8488
@@ -119,7 +123,7 @@ def run_sync_soon_threadsafe(fn):
119123 event .fn = fn
120124 app .postEvent (reenter , event )
121125
122- def done_callback (outcome ) :
126+ def done_callback (outcome : Outcome ) -> Outcome :
123127
124128 if isinstance (outcome , Error ):
125129 exc = outcome .error
@@ -131,8 +135,11 @@ def done_callback(outcome):
131135 else :
132136 traceback .print_exception (type (exc ), exc , exc .__traceback__ )
133137
138+ # tear down Qt when ``trio`` completes
134139 app .quit ()
135140
141+ return outcome
142+
136143 # load dark theme
137144 stylesheet = qdarkstyle .load_stylesheet (
138145 qt_api = 'pyqt5' ,
@@ -164,13 +171,25 @@ def done_callback(outcome):
164171 # override tractor's defaults
165172 tractor_kwargs .update (_tractor_kwargs )
166173
174+ # setup a root scope to be cancelled on Qt exit
175+ root_trio_cs = trio .CancelScope ()
176+ app .lastWindowClosed .connect (root_trio_cs .cancel )
177+
167178 # define tractor entrypoint
168179 async def main ():
169180
170- async with maybe_open_pikerd (
171- ** tractor_kwargs ,
172- ):
173- await func (* ((instance ,) + args ))
181+ nonlocal root_trio_cs
182+
183+ with root_trio_cs as rcs :
184+
185+ async with maybe_open_pikerd (
186+ ** tractor_kwargs ,
187+ ):
188+ return await func (* ((instance ,) + args ))
189+
190+ if rcs .cancelled_caught :
191+ print ('Terminated' )
192+ return
174193
175194 # guest mode entry
176195 trio .lowlevel .start_guest_run (
@@ -185,4 +204,6 @@ async def main():
185204
186205 # actually render to screen
187206 window .show ()
188- app .exec_ ()
207+
208+ return_code : int = app .exec_ ()
209+ return return_code
0 commit comments