Old 06-18-2017, 04:54 AM   #1
Human being with feelings
Join Date: Nov 2015
Posts: 376
Default Execute action and return immediately

I am executing some reaper actions that pop up a dialog box and I spent a considerable amount of time writing code to interact with that dialog box from an external app. It works.

I then tried to put that code in a lua script and quickly realized that it won't work because Main_OnCommandEx is synchronous/blocking, probably due to the modal dialog window.

Basically, I do


But MyApp needs to be ran while the dialog is up, but this doesn't occur because the Main_OnCommandEx does not return until the dialog is closed ;/

I cannot reverse the order for several reasons. The major one is Exec is blocking(I use io.popen, which blocks. Even if it didn't, would create some serious synchronizing issues). If I could get a non blocking Exec I might be able to get it to work, but it will be tricky.

While I doubt it is possible, my suggestion is for reaper to allow one to run Main_OnCommandEx assynchronously. Either by adding another command such as Main_OnCommandExAsync or passing a flag. to know when the command is finished running, one can query to see. (by simply running the command in it's own thread, which should be easy to do, a few lines of code, this can be accomplished).

Does anyone have any ideas how to solve this?

heres the Exec function I'm using

function Exec(cmd, raw)
raw = raw or true
local f = assert(io.popen(cmd, 'r'))
local s = assert(f:read('*a'))
if raw then return s end
s = string.gsub(s, '^%s+', '')
s = string.gsub(s, '%s+$', '')
s = string.gsub(s, '[\n\r]+', ' ')
return s

For a test case, you can do:

reaper.ShowConsoleMsg("This should pop up right after the save as dialog box opens from above, not after it closes!")

Last edited by Airal; 06-18-2017 at 05:02 AM.
Airal is offline   Reply With Quote
Old 06-18-2017, 01:54 PM   #2
Human being with feelings
cfillion's Avatar
Join Date: May 2015
Location: Québec, Canada
Posts: 1,210

Two ideas, both requiring launching your external program before the action (and fixing the "several reasons"):
  1. Use your system's shell's features to run a command in the background. With sh/bash/zsh/etc it's:
    os.execute('sleep 42 &')
    (Tested on macOS, should work on Linux too, no idea on Windows.)
  2. Make your process fork so that the original one finishes immediately, not blocking the script.
An asynchronous way to open modal windows is probably impossible since it's all done in the same thread.

Last edited by cfillion; 06-18-2017 at 03:04 PM.
cfillion is offline   Reply With Quote
Old 06-18-2017, 03:32 PM   #3
Human being with feelings
Join Date: Nov 2015
Posts: 376

I had to create a CreateProcess wrapper and use cmd /c start to run a batch file that had the stuff I needed to execute. I PITA. My point was that reaper could allow for an os.execute to run asynchronously, which essentially implements what I have done.
Airal is offline   Reply With Quote

Thread Tools
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off

Forum Jump

All times are GMT -7. The time now is 01:45 PM.

Powered by vBulletin® Version 3.8.11
Copyright ©2000 - 2017, vBulletin Solutions Inc.