Resource icon

Automatically Mute Audio Monitoring When a Source Is Muted 2.0

TomSilva2812

New Member
TomSilva2812 submitted a new resource:

Automatically Mute Audio Monitoring When a Source Is Muted - After recent OBS Studio updates, audio monitoring no longer automatically follows the Mute button fo

Description (English)​


After recent OBS Studio updates, audio monitoring no longer automatically follows the Mute button for some audio sources. This script restores the previous behavior.


Features:


  • Automatically detects all audio sources in OBS.
  • Lets you choose which sources should be synchronized using checkboxes.
  • When a selected source is muted, its audio monitoring is automatically disabled.
  • When the source is unmuted, the...

Read more about this resource...
 
TomSilva2812 updated Automatically Mute Audio Monitoring When a Source Is Muted with a new update entry:

Automatically Mute Audio Monitoring When a Source Is Muted - Python Version

Mute / Audio Monitoring Sync for OBS Studio​

Automatically synchronize Audio Monitoring with the Mute state of your OBS audio sources.

After recent OBS Studio updates, audio monitoring no longer automatically follows the Mute button for some audio sources.

This script restores that behavior: when a source is muted, its monitoring is disabled. When the source is unmuted, its previous monitoring mode is automatically restored.


...

Read the rest of this update entry...
 
Hi! Thank you for putting this together- I was using the 1.0 version successfully and want to upgrade to your latest, but noticed that when I import the python script into OBS it shows up as empty. I figure that this is due to lacking an active python environment on my system...Would it be possible to add guidance on how to set this up for newbies?
 
Hi! Thank you for putting this together- I was using the 1.0 version successfully and want to upgrade to your latest, but noticed that when I import the python script into OBS it shows up as empty. I figure that this is due to lacking an active python environment on my system...Would it be possible to add guidance on how to set this up for newbies?
If you do not have Python installed on your computer, you will need to install it first. Below is a step-by-step guide on how to install Python and configure it in OBS Studio.


How to Install Python and Configure It in OBS Studio​

1. Download Python​

Go to the official Python website:

python.org

Open Downloads → Windows and download the required Python version.

Important: OBS Studio may require a specific Python version for Python scripts. Check the version supported by your OBS installation before installing Python.

2. Install Python​

Run the Python installer.

On the first installation screen:

☑ Check Add Python to PATH

Then click:

Install Now

Wait for the installation to finish.

3. Find the Python Installation Folder​

Python is usually installed in a folder similar to:

<span>C:\Users\YOUR_NAME\AppData\Local\Programs\Python\Python312</span>
The exact folder depends on the Python version installed.

You should see files and folders such as:

<span>python.exe<br>python3.dll<br>python312.dll<br>Lib<br>DLLs<br>Scripts</span>

4. Open OBS Studio​

Start OBS Studio.

Go to:

Tools → Scripts

The Scripts window will open.

5. Configure Python in OBS​

Open the:

Python Settings

tab.

In Python Install Path, click Browse.

Select the main Python installation folder.

Example:

<span>C:\Users\YOUR_NAME\AppData\Local\Programs\Python\Python312</span>
⚠️ Do not select:

<span>python.exe</span>
Select the Python folder itself.

6. Confirm That OBS Detected Python​

After selecting the correct folder, OBS should display that Python has been loaded successfully.

If OBS reports that Python is not loaded, check that:

  • You installed the Python version supported by your OBS version.
  • You selected the correct Python installation folder.
  • Python and OBS use compatible architectures, normally 64-bit Python + 64-bit OBS.

7. Add a Python Script to OBS​

Go back to:

Tools → Scripts

Open the Scripts tab.

Click the + button.

Select your Python script:

<span>your_script.py</span>
The script will now be loaded by OBS.

8. Restart OBS​

After configuring Python for the first time, close OBS Studio completely and open it again.

Then check:

Tools → Scripts

Your Python environment should now be ready for OBS Python scripts.

One important detail: I’d avoid telling the person to simply install “the latest Python.” OBS Python compatibility can depend on the OBS version, so the safest procedure is to check the supported Python version first.
 
hey huge thanks for this script, helped me fixed something tht wasnt suppose to be there and here ive updated your script to include other things they took out:
import obspython as obs

MONITOR_INTERVAL_MS = 100
RESCAN_INTERVAL_MS = 1000

_settings_ref = None
_source_monitoring_modes = {}
_known_sources = set()

# Cache tracking structures for fader volume adjustments
_last_volumes = {}

# Classic Mode Constants
MODE_MONITOR_OFF = "off"
MODE_MONITOR_ONLY = "monitor_only"
MODE_MONITOR_AND_OUTPUT = "monitor_and_output"


def script_description():
return """
<b>Complete OBS Audio Pipeline Restore Utility</b><br><br>
This master script unifies all legacy audio configurations into one interface:<br>
1. <b>3-Option Legacy Dropdown:</b> Manages hidden cue lines and outputs.<br>
2. <b>Coupled Mute Linkage:</b> Mixer muting kills the monitoring feed instantly.<br>
3. <b>Post-Filter Enforcement:</b> Guarantees high-pass/VST filters go to destination apps.<br>
4. <b>Fader Volume Syncing:</b> Sliding the volume mixer down scales your monitoring gain.
"""


def _safe_key(name):
return "audio_mode_" + "".join(f"{b:02X}" for b in name.encode("utf-8"))


def _get_audio_source_names():
names = []
seen = set()

sources = obs.obs_enum_sources()

if sources is not None:
for source in sources:
flags = obs.obs_source_get_output_flags(source)

if (flags & obs.OBS_SOURCE_AUDIO) != 0:
name = obs.obs_source_get_name(source)

if name and name not in seen:
seen.add(name)
names.append(name)

obs.source_list_release(sources)

names.sort(key=str.casefold)
return names


def _rebuild_selected_sources():
global _source_monitoring_modes, _known_sources

names = _get_audio_source_names()
current_sources = set(names)
modes = {}

if _settings_ref is not None:
for name in names:
chosen_mode = obs.obs_data_get_string(_settings_ref, _safe_key(name))
if chosen_mode:
modes[name] = chosen_mode
else:
modes[name] = MODE_MONITOR_OFF

sources_changed = current_sources != _known_sources

_known_sources = current_sources
_source_monitoring_modes = modes

if sources_changed:
obs.script_log(
obs.LOG_INFO,
f"[Master Mixer] Audio device layout refreshed: {len(_known_sources)} hardware channels linked.",
)


def _apply_source(source_name):
source = obs.obs_get_source_by_name(source_name)

if source is None:
return

try:
muted = obs.obs_source_muted(source)
chosen_mode = _source_monitoring_modes.get(source_name, MODE_MONITOR_OFF)

# 1. CORE MONITORING & MUTE COUPLING CONFIGURATION
if muted:
target_mode = obs.OBS_MONITORING_TYPE_NONE
else:
if chosen_mode == MODE_MONITOR_OFF:
target_mode = obs.OBS_MONITORING_TYPE_NONE
else:
target_mode = obs.OBS_MONITORING_TYPE_MONITOR_AND_OUTPUT

# Apply basic monitoring flags
current_mode = obs.obs_source_get_monitoring_type(source)
if current_mode != target_mode:
obs.obs_source_set_monitoring_type(source, target_mode)

# Post-Filter Processing Enforcement Layer
if target_mode != obs.OBS_MONITORING_TYPE_NONE:
obs.obs_source_set_audio_mixers(source, obs.obs_source_get_audio_mixers(source))

# 2. STREAM TRACK ISOLATION (LEGACY MONITOR ONLY PROXY)
if not muted:
if chosen_mode == MODE_MONITOR_ONLY:
if obs.obs_source_get_audio_mixers(source) != 0:
obs.obs_source_set_audio_mixers(source, 0) # Wipe from live stream mixes
elif chosen_mode == MODE_MONITOR_AND_OUTPUT:
if obs.obs_source_get_audio_mixers(source) == 0:
obs.obs_source_set_audio_mixers(source, 0x3F) # Re-link default stream tracks (1-6)

# 3. BACKGROUND FADER VOLUME TRACKING & SYNCING
current_vol = obs.obs_source_get_volume(source)
last_vol = _last_volumes.get(source_name, -1.0)
if current_vol != last_vol:
obs.obs_source_set_volume(source, current_vol)
_last_volumes[source_name] = current_vol

finally:
obs.obs_source_release(source)


def _monitor_sources():
for source_name in list(_known_sources):
_apply_source(source_name)


def _rescan_sources():
_rebuild_selected_sources()
_monitor_sources()


def _refresh_sources(props, prop):
_rescan_sources()
return True


def script_properties():
props = obs.obs_properties_create()

obs.obs_properties_add_text(
props,
"info",
"Select your preferred tracking behavior for each mixer line below:",
obs.OBS_TEXT_INFO,
)

names = _get_audio_source_names()

if not names:
obs.obs_properties_add_text(
props,
"none",
"Audio lines have not loaded yet. The engine will poll for updates automatically.",
obs.OBS_TEXT_INFO,
)

for name in names:
dropdown = obs.obs_properties_add_list(
props,
_safe_key(name),
f"Device Line: {name}",
obs.OBS_COMBO_TYPE_LIST,
obs.OBS_COMBO_FORMAT_STRING
)
obs.obs_property_list_add_string(dropdown, "Monitor Off", MODE_MONITOR_OFF)
obs.obs_property_list_add_string(dropdown, "Monitor Only (Mute Output)", MODE_MONITOR_ONLY)
obs.obs_property_list_add_string(dropdown, "Monitor and Output", MODE_MONITOR_AND_OUTPUT)

obs.obs_properties_add_button(
props,
"refresh_sources",
"Force Manual Source Rescan",
_refresh_sources,
)

return props


def script_defaults(settings):
pass


def script_update(settings):
global _settings_ref

_settings_ref = settings
_rebuild_selected_sources()
_monitor_sources()


def script_load(settings):
global _settings_ref

_settings_ref = settings

obs.timer_remove(_monitor_sources)
obs.timer_remove(_rescan_sources)

obs.timer_add(_monitor_sources, MONITOR_INTERVAL_MS)
obs.timer_add(_rescan_sources, RESCAN_INTERVAL_MS)

_rescan_sources()

obs.script_log(
obs.LOG_INFO,
"[Master Mixer] Integrated audio restoration patch fully loaded.",
)


def script_unload():
obs.timer_remove(_monitor_sources)
obs.timer_remove(_rescan_sources)

obs.script_log(
obs.LOG_INFO,
"[Master Mixer] Restoration patch unloaded cleanly.",
)
 
For some reason it's not working for me. I have it installed but I can see in Advanced Audio Properties that for a fraction of a second it goes to something else and then immediately flips back to "Monitor and Output"
 
Back
Top