No internet connection
  1. Home
  2. How to

Pro Tools Bounce Script

By Lou Teti @Lou_Teti
    2026-02-06 03:17:35.664Z

    Hi,

    I have something that I'd like to do, but I'm really not even sure if it's possible. First I'll quickly explain what I do now for context. In my template, I already have all the mix and stem tracks I might need to bounce already created at the bottom of the session. They all have the proper buss already routed to the input. This way if I have to make say, a full mix and a dialog stem, I can just enable those two tracks, select the busses in the bounce window and offline bounce. Then I just drag the newly created files up to the tracks I already have made. Now I can punch in changes if I ever need to. The problem with this is that every session changes and even in some cases I need to make different sets of stems for the same project. Which is a little annoying going through the bounce drop down menu for every stem. I know that you can save your bounce settings and recall them, but I was hoping to do something even simpler...

    What I want to be able to do is to select only the bounce tracks that I need stems for in my edit window and have sound flow run a script that will recognize the buss es that are set as the input of the tracks, open the bounce window, select those busses, run an offline bounce, place them on new tracks in the edit window at selection, then move the newly created stem to the correct bounce track and delete the new tracks that were created. Simply selecting the bounce tracks needed from my edit widow and clicking a button would be much simpler than digging through the dropdown menu of busses in the bounce window and manually moving files.

    Can anyone imagine a way to do this?

    If this is not possible, a slightly less complicated version might be to select the busses you need from the bounce window and bounce as normal, but after the stems are made and placed on a new track in the edit window, change the input of the new track to be the buss that was bounced.

    I wasn't sure if something like this was possible in bounce factory, but the little bit of time I spent with it, I couldn't really find anything that would reproduce this. Seems like that's more about automating multiple passes. I have things set up where I can bounce everything in one pass, but would like some automation to make it less clicking.

    Anyhow, thanks in advance for any help with this!

    Lou

    • 10 replies

    There are 10 replies. Estimated reading time: 28 minutes

    1. In reply toLou_Teti:
      Matt Friedman @Matt_Friedman
        2026-02-06 16:29:27.838Z

        Why aren't you doing Track Bounce? It sounds like you're doing everything that would warrant Track Bouncing rather than old-school bus bouncing, i.e. you stated you're "selecting the bounce tracks needed"

        I ONLY do track bouncing. It's so much simpler and more straight forward, and way easier to implement Soundflow workflows and automations with a Track Bouncing strategy - just select the tracks and initiate the Track Bounce.

        I get that some have reasons for still bouncing via the Mix Bounce window, but from your post it sounds like you could simplify your workflow by using Track Bounce instead.

        For example, I have a Batch-Track-Bounce script (published in the store) that lets you select multiple Pro Tools sessions, trigger the script, and it will open each session 1-by-1, track bounce the designated tracks within a designated timeline selection, optionally import the bounced audio back into the session, optionally export those imported tracks to a brand new stand-alone session, do a save-as on the open session and move on to the next, all while you enjoy time with your family or a coffee. It's meant for film, TV and video game score-mix workflows, and has completely eliminated the tedious time consuming process of printing stems for the dozens upon dozens of cues that need to be rapidly stemmed out and delivered. (But it's only for track bounces)

        1. LLou Teti @Lou_Teti
            2026-02-06 16:51:52.208Z

            Hi Matt,

            Thanks so much for your reply. Yes, this script you have in the store sounds great for me as well as I primarily work in Film & TV. Bouncing and popping them into a new session sounds AMAZING as certain networks require individual PT sessions of the stems. So I'll definitely check that out.

            However, I'm not sure why I don't know the answer to this as I've sat in front of PT basically every day for 25 years, but what is "track bounce"? I think I've only really known that there's like record in real time to the track or use the bounce window (option command b) for offline bouncing. Is there some other way to bounce a track in offline that I just don't know about?

            Going to check out Batch-Track-Bounce script now! Thanks again.

            Lou

            1. Matt Friedman @Matt_Friedman
                2026-02-06 16:55:06.279Z

                Track Bounce is the same thing in theory as regular bouncing. But it bounces the tracks selected (I think it's under the Tracks menu). It basically bounces the track, so whatever that track is outputting is what it bounces, and it names the bounced file after the track, though you can add a Prefix. Doesn't matter if the tracks are audio, auxes or folders either. What you hear is what you get.

                1. LLou Teti @Lou_Teti
                    2026-02-06 17:25:21.981Z

                    Wow, I'm not going to lie, that kind of blows my mind. I had NO IDEA that was there. Ha! I have a template setup that lets me bounce any permutation of mixes and stems that I might need for a project in a single offline pass. So I can bounce like both versions of 5.1 & stereo mix, along with 5.1 dialog, stereo dialog, mono dialog all at one time. So I'd love to keep my workflow so that I can do all my stems in one pass. I think to use track bounce for this would require a major reworking of the template because I use sends off of busses to fold down the different channel configurations. So my stems are more built around the busses I guess, than the output of a track. I guess I would need to add more tracks to my template to take place of the busses. I'll have to think about this a little bit to see if there's a way for me to rework things so that I can do any set of stems I can imagine in one pass. Also, just a quick experiment I did with track bounce, it seems like maybe I can't bounce more than one track at a time.

                    Again, really apprecaite your help here. I think I have some stuff to explore and think about for a bit.

                    1. BBrandon Jiaconia @Brandon_Jiaconia
                        2026-02-06 17:57:42.714Z

                        I have a similar set up - my busses/print tracks are different from project to project and my offline bounce script would often not be setup for them. My solution was to find my print tracks by color (which are always the same in my template), then set up and offline bounce based on the inputs of those print tracks. I dont know why Ive never considered track bouncing, it avoids problems with the bounce window, I'm going to take Matts suggestion and look into it - thanks Matt !
                        Here's a quick screen cap of it
                        https://youtu.be/O_9a-U2Y3Gg
                        It's by no means perfect, but has been useful for sure.

                        sf.ui.useSfx();
                        
                        //
                        // Helper Functions
                        //
                        
                        /**
                         * Ensures a button is in the "Selected" state.
                         * 
                         * @param {Object} button - The button element to check and enable.
                         */
                        function ensureButtonEnabled(button) {
                            if (button.value.invalidate().value !== 'Selected') {
                                button.elementClick();
                            }
                        }
                        
                        //
                        // Setup & Prep
                        //
                        
                        // Suspend all groups
                        sf.ui.proTools.mainWindow.groupListPopupButton.popupMenuSelect({
                            menuPath: ["Suspend All Groups"],
                            targetValue: "Enable"
                        });
                        
                        // Enable link and tab buttons
                        const linkBtn = sf.ui.proTools.mainWindow.cursorToolCluster.buttons
                            .whoseTitle.is('Link Timeline and Edit Selection').first;
                        const timeBtn = sf.ui.proTools.mainWindow.cursorToolCluster.buttons
                            .whoseTitle.is('Link Track and Edit Selection').first;
                        const tabBtn = sf.ui.proTools.mainWindow.cursorToolCluster.buttons
                            .whoseTitle.is('Tab to Transients').first;
                        
                        ensureButtonEnabled(linkBtn);
                        ensureButtonEnabled(timeBtn);
                        ensureButtonEnabled(tabBtn);
                        
                        sf.ui.proTools.appActivateMainWindow();
                        sf.app.proTools.invalidate();
                        
                        // Save the original timeline selection
                        const originalSelection = sf.app.proTools.getTimelineSelection();
                        
                        //
                        // Find Stem Tracks by Color
                        //
                        
                        const targetColor = "#ffbc000d";
                        
                        // Get all visible tracks
                        const visibleTracks = sf.app.proTools.tracks.invalidate().allItems
                            .filter(track => !track.isHidden);
                        
                        // Filter tracks that match the target color
                        const matchingTracks = visibleTracks.filter(track => track.color === targetColor);
                        
                        // Get stem names
                        const matchingTrackNames = matchingTracks.map(track => track.name);
                        
                        const firstStemName = matchingTrackNames[0];
                        const lastStemName = matchingTrackNames[matchingTrackNames.length - 1];
                        
                        // Define bounce sources
                        const mixSources = matchingTrackNames.map(name => ["bus", `${name} (Stereo)`]);
                        
                        // Select last stem track
                        sf.app.proTools.selectTracksByName({
                            trackNames: [lastStemName]
                        });
                        
                        //
                        // Open Bounce Window
                        //
                        
                        sf.ui.proTools.appActivateMainWindow();
                        
                        // Open bounce window
                        sf.ui.proTools.sfx.getMenuItem('File', 'Bounce Mix...').elementClick();
                        
                        // Wait for bounce window
                        const bounceWindow = sf.ui.proTools.sfx.windows.whoseTitle.is("Bounce Mix").first;
                        bounceWindow.elementWaitFor();
                        
                        //
                        // Bounce Settings
                        //
                        
                        const locationGroup = bounceWindow.groups.whoseTitle.is("Location").first;
                        const importAfterBounceCbx = locationGroup.checkBoxes.whoseTitle.is("Import After Bounce").first;
                        
                        //  unique filename with timestamp
                        const timestamp = new Date().getTime();
                        const uniqueFileName = `t${timestamp}`;
                        
                        bounceWindow.textFields.first.elementSetTextAreaValue({
                            value: uniqueFileName
                        });
                        
                        // Set file type to WAV
                        if (bounceWindow.popupButtons.first.value.value !== 'WAV (BWF)') {
                            try {
                                bounceWindow.popupButtons.first.popupMenuSelect({ menuPath: ['WAV (BWF)'] });
                            } catch (err) {
                                bounceWindow.buttons.whoseTitle.is("Cancel").first.elementClick();
                                throw new Error("Failed to set file type to WAV");
                            }
                        }
                        
                        // Ensure "Import After Bounce" is enabled
                        importAfterBounceCbx.checkboxSet({ targetValue: "Disable" });
                        
                        //
                        // Adjust Source Count
                        //
                        
                        // Count existing sources
                        let existingSources = bounceWindow.buttons.whoseTitle.is("Move row").allItems.length;
                        
                        // If no Move Row buttons exist then there is only one existing source
                        if (existingSources === 0) existingSources = 1;
                        
                        // Determine how many sources to add or delete
                        const sourceDifference = mixSources.length - existingSources;
                        
                        if (sourceDifference > 0) {
                            // Add sources
                            for (let i = 0; i < sourceDifference; i++) {
                                bounceWindow.invalidate();
                                const addButton = bounceWindow.buttons.whoseTitle.is("Add row").first;
                                addButton.elementClick();
                                sf.wait({ intervalMs: 200 });
                            }
                        } else if (sourceDifference < 0) {
                            // Remove sources
                            const rowsToRemove = Math.abs(sourceDifference);
                            
                            for (let i = 0; i < rowsToRemove; i++) {
                                const removeButton = bounceWindow.buttons.whoseTitle.is("Remove row").first;
                                removeButton.elementClick();
                                sf.wait({ intervalMs: 100 });
                            }
                        }
                        
                        // Verify 
                        sf.waitFor({
                            callback: () => {
                                bounceWindow.invalidate();
                                let currentSources = bounceWindow.buttons.whoseTitle.is("Move row").allItems.length;
                                if (currentSources === 0) currentSources = 1;
                                return currentSources === mixSources.length;
                            },
                            timeout: 5000
                        }, 'Failed to adjust source count to match mixSources');
                        
                        sf.wait({ intervalMs: 300 });
                        
                        //
                        // Set Bounce Sources
                        //
                        
                        mixSources.forEach((path, index) => {
                            bounceWindow.invalidate();
                            const popupButton = bounceWindow.popupButtons.allItems[index + 1];
                            
                            popupButton.popupMenuSelect({
                                menuSelector: menuItems => menuItems.find(menuItem => {
                                    return menuItem.path.length === path.length &&
                                           menuItem.path.every((segment, i) => segment === path[i]);
                                })
                            });
                            
                            sf.wait({ intervalMs: 300 });
                        });
                        
                        // Set bounce location to session folder
                        bounceWindow.groups.whoseTitle.is("Location").first
                            .radioButtons.whoseTitle.is("Session Folder:").first
                            .elementClick();
                        
                        //
                        // Bounce
                        //
                        
                        bounceWindow.buttons.whoseTitle.is("Bounce").first.elementClick();
                        
                        // Wait for bounce to complete
                        const dlg = sf.ui.proTools.confirmationDialog;
                        
                        sf.waitFor({
                            callback: () => {
                                dlg.invalidate();
                                return !dlg.children.whoseRole.is('AXStaticText')
                                    .whoseValue.is("Bouncing...").first.exists;
                            },
                            timeout: -1
                        }, 'Failed waiting for bounce dialog to leave');
                        
                        sf.wait({ intervalMs: 1500 });
                        
                        //
                        // Import and Paste
                        //
                        
                        // Get session path and audio files folder
                        const sessionPath = sf.app.proTools.getSessionPath().sessionPath;
                        const sessionFolder = sessionPath.split('/').slice(0, -1).join('/');
                        const audioFilesFolder = `${sessionFolder}/Audio Files`;
                        
                        // Spot each bounced file to its corresponding track
                        matchingTrackNames.forEach((trackName, index) => {
                            const stemFileName = `${uniqueFileName}-${index + 1}.wav`;
                            const stemFilePath = `${audioFilesFolder}/${stemFileName}`;
                            
                            // Copy file to clipboard
                            sf.file.copyToClipboard({ path: stemFilePath });
                            
                            // Select the target track
                            sf.app.proTools.selectTracksByName({
                                trackNames: [trackName]
                            });
                            
                            // Spot the file from clipboard
                            sf.ui.proTools.spotFileFromClipboard({
                                sourceSampleStart: Number(0),
                            });
                            sf.wait({ intervalMs: 200 });
                        });
                        
                        //
                        // Final Cleanup
                        //
                        
                        // Enable Tab To Transient
                        sf.ui.proTools.menuClick({
                            menuPath: ["Options", "Tab to Transient"],
                            targetValue: "Enable"
                        });
                        
                        // Select first stem track
                        sf.app.proTools.selectTracksByName({
                            trackNames: [firstStemName]
                        });
                        

                        This is made for my template so its looking for red tracks with hex color #ffbc000d to use as the sources. You can log all of your track colors with this to get the hex code you'd need for it to work with your template

                        sf.ui.proTools.appActivateMainWindow();
                        sf.ui.proTools.mainWindow.invalidate();
                        
                        const visibleTracks = sf.app.proTools.tracks.invalidate().allItems
                            .filter(track => !track.isHidden);
                        
                        // Log color and name of each track
                        visibleTracks.forEach(track => {
                            log(`${track.name} → color: ${track.color}`);
                        });
                        
                        

                        then you'd put that hexcode in place of the targetColor in the script

                        const targetColor = "#ffbc000d";
                        
                        1. LLou Teti @Lou_Teti
                            2026-02-06 18:32:50.431Z

                            Hey Brandon,

                            Thanks so much this is great. I'm going to give it a shot. I would love to figure out how to tweak this code so that it just uses selected tracks rather than track color. I have all possible stems in my template and their all red as well. But they're all hidden and disabled by default. I just enable the ones I need for the task and bounce those. So would be very slick to just be able to select only those and bounce away.

                            Thanks so much for sharing this. You're helping my dreams become reality! Ha.

                            Lou

                            1. BBrandon Jiaconia @Brandon_Jiaconia
                                2026-02-06 19:31:55.766Z

                                hey Lou - This works with the selected stereo tracks, Id need to do some re-working for your 5.1 stems - there may also be things specific to my template/workflow you dont need in the script.. ie switching tab to transient on etc.. :

                                sf.ui.useSfx();
                                
                                //
                                // Helper Functions
                                //
                                
                                /**
                                 * Ensures a button is in the "Selected" state.
                                 * 
                                 * @param {Object} button - The button element to check and enable.
                                 */
                                function ensureButtonEnabled(button) {
                                    if (button.value.invalidate().value !== 'Selected') {
                                        button.elementClick();
                                    }
                                }
                                
                                //
                                // Setup & Prep
                                //
                                
                                // Suspend all groups
                                sf.ui.proTools.mainWindow.groupListPopupButton.popupMenuSelect({
                                    menuPath: ["Suspend All Groups"],
                                    targetValue: "Enable"
                                });
                                
                                // Enable link and tab buttons
                                const linkBtn = sf.ui.proTools.mainWindow.cursorToolCluster.buttons
                                    .whoseTitle.is('Link Timeline and Edit Selection').first;
                                const timeBtn = sf.ui.proTools.mainWindow.cursorToolCluster.buttons
                                    .whoseTitle.is('Link Track and Edit Selection').first;
                                const tabBtn = sf.ui.proTools.mainWindow.cursorToolCluster.buttons
                                    .whoseTitle.is('Tab to Transients').first;
                                
                                ensureButtonEnabled(linkBtn);
                                ensureButtonEnabled(timeBtn);
                                ensureButtonEnabled(tabBtn);
                                
                                sf.ui.proTools.appActivateMainWindow();
                                sf.app.proTools.invalidate();
                                
                                // Save the original timeline selection
                                const originalSelection = sf.app.proTools.getTimelineSelection();
                                
                                //
                                // Find Inputs From selected tracks
                                //
                                
                                
                                const selectedTracks = sf.ui.proTools.visibleTrackHeaders
                                    .filter(track => track.isSelected);
                                
                                if (!selectedTracks.length) {
                                    throw new Error("No tracks selected.");
                                }
                                
                                const bounceTracks = selectedTracks
                                    .map(track => {
                                        if (!track.inputPathButton.exists) return null;
                                
                                        return {
                                            name: track.normalizedTrackName,
                                            input: track.inputPathButton.value.invalidate().value
                                        };
                                    })
                                    .filter(Boolean);
                                
                                const matchingTrackNames = bounceTracks.map(t => t.name);
                                
                                const firstStemName = matchingTrackNames[0];
                                const lastStemName =
                                    matchingTrackNames[matchingTrackNames.length - 1];
                                
                                const mixSources = bounceTracks.map(t => [
                                    "bus",
                                    `${t.input} (Stereo)`
                                ]);
                                
                                sf.app.proTools.selectTracksByName({
                                    trackNames: [lastStemName]
                                });
                                
                                //
                                // Open Bounce Window
                                //
                                
                                sf.ui.proTools.appActivateMainWindow();
                                
                                // Open bounce window
                                sf.ui.proTools.sfx.getMenuItem('File', 'Bounce Mix...').elementClick();
                                
                                // Wait for bounce window
                                const bounceWindow = sf.ui.proTools.sfx.windows.whoseTitle.is("Bounce Mix").first;
                                bounceWindow.elementWaitFor();
                                
                                //
                                // Bounce Settings
                                //
                                
                                const locationGroup = bounceWindow.groups.whoseTitle.is("Location").first;
                                const importAfterBounceCbx = locationGroup.checkBoxes.whoseTitle.is("Import After Bounce").first;
                                
                                //  unique filename with timestamp
                                const timestamp = new Date().getTime();
                                const uniqueFileName = `t${timestamp}`;
                                
                                bounceWindow.textFields.first.elementSetTextAreaValue({
                                    value: uniqueFileName
                                });
                                
                                // Set file type to WAV
                                if (bounceWindow.popupButtons.first.value.value !== 'WAV (BWF)') {
                                    try {
                                        bounceWindow.popupButtons.first.popupMenuSelect({ menuPath: ['WAV (BWF)'] });
                                    } catch (err) {
                                        bounceWindow.buttons.whoseTitle.is("Cancel").first.elementClick();
                                        throw new Error("Failed to set file type to WAV");
                                    }
                                }
                                
                                // Ensure "Import After Bounce" is enabled
                                importAfterBounceCbx.checkboxSet({ targetValue: "Enable" });
                                
                                //
                                // Adjust Source Count
                                //
                                
                                // Count existing sources
                                let existingSources = bounceWindow.buttons.whoseTitle.is("Move row").allItems.length;
                                
                                // If no Move Row buttons exist then there is only one existing source
                                if (existingSources === 0) existingSources = 1;
                                
                                // Determine how many sources to add or delete
                                const sourceDifference = mixSources.length - existingSources;
                                
                                if (sourceDifference > 0) {
                                    // Add sources
                                    for (let i = 0; i < sourceDifference; i++) {
                                        bounceWindow.invalidate();
                                        const addButton = bounceWindow.buttons.whoseTitle.is("Add row").first;
                                        addButton.elementClick();
                                        sf.wait({ intervalMs: 200 });
                                    }
                                } else if (sourceDifference < 0) {
                                    // Remove sources
                                    const rowsToRemove = Math.abs(sourceDifference);
                                    
                                    for (let i = 0; i < rowsToRemove; i++) {
                                        const removeButton = bounceWindow.buttons.whoseTitle.is("Remove row").first;
                                        removeButton.elementClick();
                                        sf.wait({ intervalMs: 100 });
                                    }
                                }
                                
                                // Verify 
                                sf.waitFor({
                                    callback: () => {
                                        bounceWindow.invalidate();
                                        let currentSources = bounceWindow.buttons.whoseTitle.is("Move row").allItems.length;
                                        if (currentSources === 0) currentSources = 1;
                                        return currentSources === mixSources.length;
                                    },
                                    timeout: 5000
                                }, 'Failed to adjust source count to match mixSources');
                                
                                sf.wait({ intervalMs: 300 });
                                
                                //
                                // Set Bounce Sources
                                //
                                
                                mixSources.forEach((path, index) => {
                                    bounceWindow.invalidate();
                                    const popupButton = bounceWindow.popupButtons.allItems[index + 1];
                                    
                                    popupButton.popupMenuSelect({
                                        menuSelector: menuItems => menuItems.find(menuItem => {
                                            return menuItem.path.length === path.length &&
                                                   menuItem.path.every((segment, i) => segment === path[i]);
                                        })
                                    });
                                    
                                    sf.wait({ intervalMs: 300 });
                                });
                                
                                // Set bounce location to session folder
                                bounceWindow.groups.whoseTitle.is("Location").first
                                    .radioButtons.whoseTitle.is("Session Folder:").first
                                    .elementClick();
                                
                                //
                                // Bounce
                                //
                                
                                bounceWindow.buttons.whoseTitle.is("Bounce").first.elementClick();
                                
                                // Wait for bounce to complete
                                const dlg = sf.ui.proTools.confirmationDialog;
                                
                                sf.waitFor({
                                    callback: () => {
                                        dlg.invalidate();
                                        return !dlg.children.whoseRole.is('AXStaticText')
                                            .whoseValue.is("Bouncing...").first.exists;
                                    },
                                    timeout: -1
                                }, 'Failed waiting for bounce dialog to leave');
                                
                                sf.wait({ intervalMs: 1500 });
                                
                                //
                                // Import and Paste
                                //
                                
                                // Wait for 'Audio Import Options' window
                                let importWin = sf.ui.proTools.dialogWaitForManual({ 
                                    dialogTitle: 'Audio Import Options', 
                                    timeout: -1 
                                }).dialog;
                                
                                importWin.buttons.whoseTitle.is("OK").first.elementClick();
                                
                                sf.ui.proTools.waitForNoModals();
                                
                                sf.wait({ intervalMs: 500 });
                                
                                // Get selected tracks (the imported tracks)
                                const importedTracks = sf.ui.proTools.selectedTrackNames;
                                
                                // Copy all the imported clips
                                sf.app.proTools.copy();
                                
                                // Select the matching tracks (your color-coded destination tracks)
                                sf.ui.proTools.trackSelectByName({
                                    names: matchingTrackNames,
                                });
                                
                                sf.wait({ intervalMs: 150 });
                                
                                // Paste clips into the correct tracks
                                sf.ui.proTools.appActivateMainWindow(); 
                                sf.app.proTools.paste();
                                
                                sf.wait({ intervalMs: 300 });
                                
                                // Delete the temporary imported tracks
                                sf.ui.proTools.trackSelectByName({
                                    names: importedTracks,
                                });
                                
                                sf.wait({ intervalMs: 150 });
                                
                                sf.ui.proTools.appActivateMainWindow(); 
                                sf.ui.proTools.trackDelete();
                                
                                // Wait for and confirm delete dialog
                                sf.ui.proTools.confirmationDialog.elementWaitFor({
                                    timeout: 1000,
                                    waitType: "Appear", 
                                    onError: "Continue"
                                });
                                
                                sf.ui.proTools.confirmationDialog.buttons.whoseTitle.is("Delete").first.elementClick({
                                    onError: "Continue"
                                });
                                
                                //
                                // Final Cleanup
                                //
                                
                                // Enable Tab To Transient
                                sf.ui.proTools.menuClick({
                                    menuPath: ["Options", "Tab to Transient"],
                                    targetValue: "Enable"
                                });
                                
                                // Select first stem track
                                sf.app.proTools.selectTracksByName({
                                    trackNames: [firstStemName]
                                });
                                
                                1. LLou Teti @Lou_Teti
                                    2026-02-06 20:26:55.016Z

                                    Hi Brandon,

                                    Ah man, I really can't thank you enough for your help here. I've really only just started playing with the scripting and honestly I'm pretty terrible with it still. I'm afraid that this isn't quite working for me. It's not recognizing the correct busses from the input of the tracks I select. Or at least it's not assigning the correct busses in the bounce window for some reason. It also seems to have a very long delay from when I click the button to when it gets to the bounce window. Anyhow, I can try digging in to this as well at some point, but I totally appreciate your help even getting me this far. Just knowing that this is possible is super helpful. I don't want to ask you to do all sorts of extra work on my behalf since you've already got something that's working well for you. That said, if you keep tweaking feel free to share. I'll do the same if I manage to get anywhere!

                                    Lou

                                    1. BBrandon Jiaconia @Brandon_Jiaconia
                                        2026-02-06 23:37:13.007Z

                                        @Matt_Friedman was right, track bouncing is pretty cool! His Batch Track Bounce package is great and gave me a genuine laugh with a joke in the confirmation box.

                        2. Progress
                        3. S
                          SoundFlow Bot @soundflowbot
                            2026-02-06 03:47:58.689Z
                            SoundFlow support ticket: SFSUP-90