Process-level audio tap for Windows
Project description
๐ก ProcTap
Per-Process Audio Capture for Windows
ProcTap is a Python library with a high-performance C++ backend that enables per-process audio capture on Windows 10/11 (20H1+) using ActivateAudioInterfaceAsync.
Capture audio from a specific process only โ without system sounds or other app audio mixed in. Ideal for VRChat, games, DAWs, browsers, and AI audio analysis pipelines.
๐ Features
-
๐ง Capture audio from a single target process
(VRChat, games, browsers, Discord, DAWs, streaming tools, etc.) -
โก Uses ActivateAudioInterfaceAsync (modern WASAPI)
โ More stable than legacy IAudioClient2 loopback approaches -
๐งต Low-latency, thread-safe C++ engine โ 44.1 kHz / stereo / 16-bit PCM format
-
๐ Python-friendly high-level API
- Callback-based streaming
- Async generator streaming (
async for)
-
๐ Native extension for high-throughput PCM delivery
-
๐ช Windows-only (10/11, 20H1+)
๐ฆ Installation
From PyPI (coming soon):
pip install proctap
From TestPyPI (for testing pre-releases):
pip install --index-url https://test.pypi.org/simple/ --extra-index-url https://pypi.org/simple/ proctap
From Source:
git clone https://github.com/m96-chan/ProcTap
cd ProcTap
pip install -e .
๐ Requirements
- Windows 10 / 11 (20H1 or later recommended)
- Python 3.10+
- WASAPI support
- No admin privileges required
(Per-process loopback capture works with standard user permissions)
๐งฐ Basic Usage (Callback API)
from proctap import ProcTap, StreamConfig
def on_chunk(pcm: bytes, frames: int):
print(f"Received {len(pcm)} bytes ({frames} frames)")
pid = 12345 # Target process ID
tap = ProcTap(pid, StreamConfig(), on_data=on_chunk)
tap.start()
input("Recording... Press Enter to stop.\n")
tap.close()
๐ Async Usage (Async Generator)
import asyncio
from proctap import ProcTap
async def main():
tap = ProcTap(pid=12345)
tap.start()
async for chunk in tap.iter_chunks():
print(f"PCM chunk size: {len(chunk)} bytes")
asyncio.run(main())
๐ API Overview
class ProcTap
Control Methods:
| Method | Description |
|---|---|
start() |
Start WASAPI per-process capture |
stop() |
Stop capture |
close() |
Release native resources |
Data Access:
| Method | Description |
|---|---|
iter_chunks() |
Async generator yielding PCM chunks |
read(timeout=1.0) |
Synchronous: read one chunk (blocking) |
Properties:
| Property | Type | Description |
|---|---|---|
is_running |
bool | Check if capture is active |
pid |
int | Get target process ID |
config |
StreamConfig | Get stream configuration |
Utility Methods:
| Method | Description |
|---|---|
set_callback(callback) |
Change or remove audio callback |
get_format() |
Get audio format info (dict) |
Audio Format
Note: The native extension uses a fixed audio format (hardcoded in C++):
| Parameter | Value | Description |
|---|---|---|
| Sample Rate | 44,100 Hz | CD quality (fixed) |
| Channels | 2 | Stereo (fixed) |
| Bit Depth | 16-bit | PCM format (fixed) |
The StreamConfig class exists for API compatibility but does not change the native backend format.
๐ฏ Use Cases
- ๐ฎ Record audio from one game only
- ๐ถ Capture VRChat audio cleanly (without system sounds)
- ๐ Feed high-SNR audio into AI recognition models
- ๐น Alternative to OBS "Application Audio Capture"
- ๐ง Capture DAW/app playback for analysis tools
๐ Example: Save to WAV
from proctap import ProcTap
import wave
pid = 12345
wav = wave.open("output.wav", "wb")
wav.setnchannels(2)
wav.setsampwidth(2) # 16-bit PCM
wav.setframerate(44100) # Native format is 44.1 kHz
def on_data(pcm, frames):
wav.writeframes(pcm)
with ProcTap(pid, on_data=on_data):
input("Recording... Press Enter to stop.\n")
wav.close()
๐ Example: Synchronous Read API
from proctap import ProcTap
tap = ProcTap(pid=12345)
tap.start()
try:
while True:
chunk = tap.read(timeout=1.0) # Blocking read
if chunk:
print(f"Got {len(chunk)} bytes")
# Process audio data...
else:
print("Timeout, no data")
except KeyboardInterrupt:
pass
finally:
tap.close()
๐ Build From Source
git clone https://github.com/m96-chan/ProcTap
cd ProcTap
pip install -e .
Requirements:
- Visual Studio Build Tools
- Windows SDK
- CMake (if you modularize the C++ code)
๐ง Project Structure
ProcTap/
โโ LICENSE
โโ README.md
โโ pyproject.toml
โโ setup.cfg
โโ setup.py
โโ src/
โ โโ proctap/
โ โโ __init__.py
โ โโ core.py
โ โโ _native.cpp
โ โโ _native.pyi
โโ examples/
โ โโ record_proc_to_wav.py
โโ .github/
โโ workflows/
โโ build-wheels.yml
๐ GitHub Action (Wheel Build)
name: Build and publish wheels
on:
push:
tags:
- "v*.*.*"
workflow_dispatch: {}
jobs:
build-wheels:
runs-on: windows-latest
strategy:
matrix:
python-version: ["3.10", "3.11", "3.12", "3.13"]
steps:
- uses: actions/checkout@v4
- name: Setup Python
uses: actions/setup-python@v5
with:
python-version: ${{ matrix.python-version }}
- name: Install build tools
run: |
pip install --upgrade pip
pip install build
- name: Build wheel
run: |
python -m build --wheel
- name: Upload artifact
uses: actions/upload-artifact@v4
with:
name: wheels-py${{ matrix.python-version }}
path: dist/*.whl
publish:
needs: build-wheels
runs-on: ubuntu-latest
if: startsWith(github.ref, 'refs/tags/v')
steps:
- uses: actions/download-artifact@v4
with:
path: dist
- name: Flatten wheels
shell: bash
run: |
mkdir -p upload
find dist -name '*.whl' -exec cp {} upload/ \;
- name: Publish to PyPI
uses: pypa/gh-action-pypi-publish@v1.12.4
with:
user: __token__
password: ${{ secrets.PYPI_API_TOKEN }}
packages_dir: upload
๐ค Contributing
Contributions are welcome!
- Bug fixes
- Feature requests
- Performance improvements
- Type hints / async extension
- Documentation improvements
PRs from WASAPI/C++ experts are especially appreciated.
๐ License
MIT License
๐ค Author
Yusuke Harada (m96-chan)
Windows Audio / VRChat Tools / Python / C++
https://github.com/m96-chan
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file proc_tap-0.1.0.tar.gz.
File metadata
- Download URL: proc_tap-0.1.0.tar.gz
- Upload date:
- Size: 18.4 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.12.8
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
92668d80386c2e99e4ea74b2656ce5f7b5598287a2c783b8ca84025e67e05294
|
|
| MD5 |
ebe01c328bf02ed10430e5234c1481f9
|
|
| BLAKE2b-256 |
252477bf8a6be319ff2a8bf958b3b7074f16cb3d80450348da0e20e85429aa47
|
File details
Details for the file proc_tap-0.1.0-cp311-cp311-win_amd64.whl.
File metadata
- Download URL: proc_tap-0.1.0-cp311-cp311-win_amd64.whl
- Upload date:
- Size: 32.0 kB
- Tags: CPython 3.11, Windows x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.1.0 CPython/3.12.8
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
9ecdd5f2b1f30a15e1973c097371526dd9c3c7c06e6163c74ee6a076772ccd13
|
|
| MD5 |
525e8fa1c6d5159f4a31a3ef0549b56b
|
|
| BLAKE2b-256 |
aa6e62f130fe7cd7b1f314bf52154d67ffce89ddef38982e3a8a9a1253c8110d
|