Per-App Volume on macOS Without a Driver
Short answer: macOS has one volume for everything, so per-app volume needs a third-party mixer. On macOS 14.2 and later, a mixer can use Core Audio process taps to capture one app’s output, mute the original, and play it back at the level you choose, with no audio driver or kernel extension. FavTray’s per-app volume works this way: 0 to 150% or mute, per app, remembered by app.
TL;DR
- Before 14.2, per-app mixers had to install a virtual audio device or a system audio component, and route your sound through it.
- Since 14.2,
AudioHardwareCreateProcessTaptaps a process’s output. WithmuteBehavior = .mutedWhenTapped, the original goes silent while the tap is being read. - The pipeline: a tap, then a private aggregate device (tap plus your output device), then an IOProc that multiplies samples by your gain and writes them to the output.
- The cost: the System Audio Recording permission, a small added buffer, stereo output, and only the default output device.
Why doesn’t macOS have per-app volume?
macOS mixes every app’s audio into one stream per output device, and the volume in Control Center and System Settings › Sound scales that stream. Apps can set their own volume, and many media apps have a slider, but there’s no system control over another app’s level. To change one app’s volume from outside, a tool has to get between that app and the speakers.
How did per-app volume work before macOS 14.2?
By inserting a device. The open-source Background Music app, for example, installs a virtual audio driver and makes it the default output. Every app plays into it, and the app sets each one’s level before passing the mix on to your real speakers. Commercial mixers took similar routes with their own system components.
It works, but the driver is system-wide, it has to be installed and updated separately, and when it misbehaves, your Mac’s sound breaks with it.
What changed in macOS 14.2?
Apple added process taps to Core Audio (AudioHardwareTapping.h, API_AVAILABLE(macos(14.2))). A tap captures the audio output of chosen processes, and it’s described by a CATapDescription:
CATapDescription(stereoMixdownOfProcesses:)taps the listed processes and mixes them down to stereo.muteBehaviordecides what the original output does:.unmuted: you hear it as normal, and the tap gets a copy..muted: the tap gets the audio and the speakers get nothing..mutedWhenTapped: the speakers get the audio until someone reads the tap, then nothing for as long as the read lasts.
.mutedWhenTapped is the one a mixer wants. While the mixer is reading, you hear only the mixer’s copy. If the mixer stops or crashes, the app’s own sound comes straight back.
How does an app turn a tap into a volume slider?
This is the shape of FavTray’s implementation (AppVolumeTaps.swift):
- Find the process. Core Audio lists the processes using audio as process objects (
kAudioHardwarePropertyProcessObjectList), each with its PID and whether it’s playing (kAudioProcessPropertyIsRunningOutput). - Create the tap. Make a
CATapDescription(stereoMixdownOfProcesses: [processObject]), setmuteBehavior = .mutedWhenTapped, and callAudioHardwareCreateProcessTap. - Build a private aggregate device.
AudioHardwareCreateAggregateDevicewith the current output device as its main sub-device, the tap inkAudioAggregateDeviceTapListKey,kAudioAggregateDeviceTapAutoStartKeyon, andkAudioAggregateDeviceIsPrivateKeyset so it doesn’t show up in other apps’ device lists. - Run an IOProc. On Core Audio’s real-time thread, read the tapped stereo frames, multiply by the gain and write left and right to the output.
- Tear down in reverse when the slider goes back to 100%, or a short while after the app stops playing. An app at 100% is never tapped at all, and FavTray never creates a tap without the permission, because a tap that can’t be read would just silence the app.
A few details decide whether it sounds right:
- Ramp the gain. A jump from 30% to 100% in one buffer clicks. FavTray moves the gain toward its target over about 10 ms.
- Keep the real-time thread clean. No allocation, locks or Swift runtime calls in the IOProc. The gain is handed over as a plain 32-bit value.
- Round off above 100%. Past full scale, samples clip. FavTray applies a soft knee as gain rises past 100%, so a boosted call gets louder without harsh distortion.
- Keep buffers small. Every stage adds a buffer; small ones keep the added delay low enough for calls and video.
What permission does it need?
Reading another app’s audio is capture, so macOS asks. The app’s Info.plist needs NSAudioCaptureUsageDescription, and the grant shows up in System Settings › Privacy & Security under System Audio Recording Only. It’s separate from Screen Recording and from the microphone.
FavTray’s text for that prompt says it never records or saves audio. The audio passes from the tap to your speakers and nowhere else. If you say no, app volumes stay at 100% and the rest of System › Audio still works. When FavTray needs the grant, it opens the right pane with a guide docked beside it (more on that in why macOS asks for permissions again).
What are the limits?
- macOS 14.2 or later. On older versions the Apps card doesn’t appear at all.
- Default output only. An app that plays to a device other than the system output (some DAWs and video tools let you pick) stays at 100%.
- Stereo. The tap is a stereo mixdown, so multichannel output is folded to two channels while you’ve changed that app’s level.
- A little latency. The extra buffers add a small delay to that app’s sound only.
- Boost isn’t magic. 150% makes a quiet call louder; it also makes its hiss louder.
How do I use it in FavTray?
- Open FavTray’s window › System › Audio, or click the output chip in the menu bar cockpit.
- Play something. Apps that are playing, or played recently, appear in the Apps card.
- Drag an app’s slider between 0 and 150%, or click its mute button. Reset puts it back to 100%.
- Grant System Audio Recording the first time. FavTray opens the pane and shows where FavTray is in the list.
The level is saved per app, by bundle ID, so Zoom comes back at 140% next time it plays. Per-app volume is part of FavTray Pro, and the 7-day trial includes it. On Free, the Apps card lists what played with the sliders locked. Output and input switching, device volume and mute, and “playing and recording now” are free in System.
Frequently Asked Questions
Can you change the volume of individual apps on a Mac?
Not with macOS alone: System Settings and Control Center have one output volume for everything. You need a third-party mixer. On macOS 14.2 or later, a mixer can use Core Audio process taps to do it without installing an audio driver; FavTray's per-app volume works this way.
What is a Core Audio process tap?
A process tap, added in macOS 14.2, lets an app capture the audio output of other processes. The tap can also mute the original output while it's being read, so the capturing app can play the audio back at a different level. You create one with a CATapDescription and AudioHardwareCreateProcessTap, then read it through an aggregate device.
Does per-app volume on macOS need a kernel extension or audio driver?
Not on macOS 14.2 or later. Older per-app mixers installed a virtual audio device or a system audio component. Process taps are part of Core Audio, so an app can adjust other apps' volume from user space, and when it quits macOS removes its taps and sound goes back to normal.
Why does a per-app volume app ask for System Audio Recording permission?
Because a process tap reads another app's audio. macOS lists these apps under System Audio Recording Only in Privacy & Security, and the app must explain why in its Info.plist (NSAudioCaptureUsageDescription). FavTray uses the permission only to change volume; it never records or saves audio.
Can I boost an app above 100% volume on a Mac?
Yes, with a mixer that applies gain to the tapped audio. FavTray goes up to 150% and rounds off peaks above full scale so loud audio doesn't clip harshly. Boosting can't add detail that isn't in the source, so a very quiet recording will also make its noise louder.
Is FavTray's per-app volume free?
It's part of FavTray Pro, a one-time Lifetime license, and every install gets Pro free for 7 days. On Free, System › Audio shows the apps that played recently with the sliders locked. It needs macOS 14.2 or later.