Overview
The VirtualMicrophoneDevice class represents a virtual microphone that can be used to stream audio frames into a Daily call. You can create a virtual microphone device and write audio frames to it programmatically.
Creation
Create a virtual microphone device using the Daily.create_microphone_device() static method:
from daily import Daily
microphone = Daily.create_microphone_device(
device_name="my-virtual-microphone",
sample_rate=16000,
channels=1,
non_blocking=False
)
Parameters
The name of the virtual microphone device
The sample rate of the audio in Hz (e.g., 16000, 48000)
The number of audio channels (1 for mono, 2 for stereo)
Whether the write operation should be non-blocking
Properties
The name of the virtual microphone device
The sample rate of the audio in Hz
The number of audio channels
Methods
write_frames()
Writes audio frames to the virtual microphone device.
written = microphone.write_frames(frame, completion=None)
Parameters
The audio frame data as bytes. The data should be in the format matching the sample rate and channel configuration
Optional callback function that will be called with the number of frames written
Returns
int - The number of frames written
Example Usage
from daily import Daily, CallClient
import numpy as np
import time
# Initialize Daily
Daily.init()
# Create a virtual microphone device
microphone = Daily.create_microphone_device(
device_name="my-microphone",
sample_rate=16000,
channels=1
)
# Create a client and join a call
client = CallClient()
client.join("https://your-domain.daily.co/room")
# Update inputs to use the virtual microphone
client.update_inputs({
"microphone": {
"isEnabled": True,
"settings": {
"deviceId": microphone.name
}
}
})
# Generate and write audio frames
while True:
# Generate audio samples (example: sine wave at 440 Hz)
duration_ms = 20 # 20ms of audio
num_samples = int(microphone.sample_rate * duration_ms / 1000)
t = np.linspace(0, duration_ms / 1000, num_samples, False)
frequency = 440 # A4 note
audio = np.sin(2 * np.pi * frequency * t)
# Convert to 16-bit PCM
audio_int16 = (audio * 32767).astype(np.int16)
# Write frames to the virtual microphone
frames_written = microphone.write_frames(audio_int16.tobytes())
# Control timing
time.sleep(duration_ms / 1000)
Non-blocking Mode
When creating a virtual microphone with non_blocking=True, the write_frames() method will return immediately without waiting for the frames to be processed:
microphone = Daily.create_microphone_device(
device_name="my-microphone",
sample_rate=16000,
channels=1,
non_blocking=True
)
# Write frames without blocking
frames_written = microphone.write_frames(audio_data)
Completion Callback
You can provide a completion callback to be notified when frames are written:
def on_frames_written(count):
print(f"Wrote {count} frames")
microphone.write_frames(audio_data, completion=on_frames_written)