Benutzer-Werkzeuge

Webseiten-Werkzeuge


Seitenleiste

ss15:schallwerkzeuge

Schallwerkzeuge

1. Über die Datei

Die Datei schallwerkzeuge.py stammt aus der digitalen Feder von Stefan Born und ist, wie der Name schon vermuten lässt, eine Sammlung von allerlei nützlichen Werkzeugen um mit pyaudio Schall zu erzeugen und zu verarbeiten. Wir haben diese Funktionen vielfach in unserem Projekt benutzt und wollen hier die einzelnen Komponenten beschreiben.

2. Präambel

In der Präambel werden einige Module importiert und globale Variablen gesetzt.

#!/usr/bin/python
# coding=utf8
 
## Verhalten von / wie in Python 3    a/b  = float
 
from __future__ import division
 
### Audio-Module
 
import pyaudio
from scipy.io import wavfile
from scipy import signal
 
###  Fourier, Numerik
 
import numpy.fft as FFT
import numpy as np
 
 
##############
 
# Graphik
 
import matplotlib.pyplot as plt
 
 
###
 
CHANNELS=1
RATE=44100
DAUER=1
ANZAHL=DAUER*RATE # ANZAHL der Frames,
 
CHUNK=2**10  # Anzahl der Frames, die auf einmal an die Soundkarte 
             # geschickt werden
 
 
# globale Variablen, schlechter Programmierstil, hier aber ganz
# praktisch: Nach Aufnahme oder Lesen werden diese Variablen 
# entsprechend gesetzt.

3. Funktionen

3.1 recordsnd

Die Funktion recordsnd dient zur Aufnahme von akustischen Signalen über das Mikrofon.

def recordsnd(filename, time):
	'''
	Nimmt eine  time  Sekunden lange Schallsequenz
	auf (mit der Samplerate 48000 Hz) auf und speichert,
	speichert sie in der Datei filename und gibt die
	Aufnahme als numpy-array mit Werten zwischen -1 und 1 zurück
	'''
	global ANZAHL
	global RATE
	global DAUER
	global CHANNELS 
 
	DAUER=time
	ANZAHL=int(RATE*DAUER)
 
 
	p = pyaudio.PyAudio()
	raw_input("Aufnehmen  "+str(time)+ " Sekunden): Eingabetaste drücken...")
 
	stream = p.open(format =pyaudio.paInt16 ,
                channels = CHANNELS,
	                rate = RATE,
	                input = True,
	                frames_per_buffer = CHUNK)#ANZAHL)
 
 
	yy=stream.read(ANZAHL)
	y=np.fromstring(yy,dtype=np.short)
	if CHANNELS==2:
		y=y.reshape((y.shape[0]//2,2))
 
	print("Aufgenomen: " + str(ANZAHL) + " Frames")
	stream.close()
	p.terminate()
	yy=np.array(y,dtype='d')/32768.0
	if filename!=None:
		wavwrite(filename, yy)
 
	return yy
 
 
def wavwrite(filename, y):
	'''Schreibt ein wav-File aus einem numpy-array'''
	wavfile.write(filename, RATE, np.array(y*2**15, dtype=int))

3.2 wavwrite und wavread

Über wavwrite lassen sich Aufnahmen als wav-Dateien speichern und über wavread wieder einlesen.

def wavread(filename):
	'''Liest ein wav-File in ein numpy-Array'''
	global ANZAHL
	global RATE
	global DAUER
	global CHANNELS 
 
	RATE,y=wavfile.read(filename)
	ANZAHL=y.shape[0]
	if len(y.shape)==2:
		CHANNELS=y.shape[1]
	else:
		CHANNELS=1
	DAUER=ANZAHL/RATE
 
	return np.array(y,dtype=np.float)/2**15

3.3 playsnd

playsnd ist für uns eine sehr wichtige Funktion, da sie ermöglicht Arrays mit Audio-Daten über den Lautsprecher abzuspielen.

def playsnd(y, r):
	'''
	spielt das numpy-array (bzw. Vektor) y als Klang 
	mit der Samplerate r  [Hz] ab.
	'''
	p = pyaudio.PyAudio()
	stream = p.open(format =pyaudio.paInt16 ,
	                channels = CHANNELS,
	                rate = r,
	                output = True,
	                frames_per_buffer=CHUNK)#ANZAHL)
	yy=np.array(y.flatten()*2**15,dtype=np.short)
	for i in range(0,len(yy),CHANNELS*CHUNK):
		stream.write(yy[i:i+CHANNELS*CHUNK].tostring(order='F'))
	stream.close()
	p.terminate()

3.4 inspectsnd und inspectspec

Über inspectsnd lassen sich Aufnahmen als Graph visualisieren, inspectspec stellt dagegen das Frequenz-Spektrum der Aufnahme durch die Diskrete Fourier-Transformation dar.

def inspectsnd(y):
	'''Zeigt einen Plot von y'''
 
	n=y.shape[0]
	fig=plt.Figure(figsize=(6,4),dpi=100)
	ax=fig.add_subplot(111)
	x=np.arange(0,n,1)/np.float32(RATE)
	plt.plot(x,y)
 
	plt.show()
 
 
 
def inspectspec(y):
	'''zeigt einen Plot des DFT-Spektrums von y'''
	global RATE
 
	#  Vorbereitungen, um ein Fenster zum Plotten zu kriegen
	plt.figure(1)
 
	n=len(y)
	window=np.blackman(n)
	sumw=sum(window*window)
 
	A=FFT.fft(y*window) 
	B2=(A*np.conjugate(A)).real
	sumw*=2.0   
	sumw/=1/np.float(RATE)  # sample rate
	B2=B2/sumw
 
 
	x=np.arange(0,n/2,1)/np.float(n)*RATE
 
 
	eps=1e-8
	plt.plot(x, np.log10(B2[0:n/2]+eps))
	plt.show()

3.5 sinewave

Auch sinewave ist wichtig zur Schallerzeugung, da die Methode ein Sinus-Signal mit der gewünschten Frequenz liefert, welches dann wiedergegeben werden kann.

def sinewave(f,r,d):
	'''erzeugt die Daten einer Sinusschwingung mit Frequenz f, Dauer d
	und Samplerate r'''
	global RATE
	global DAUER
	global ANZAHL
 
	RATE=r
	DAUER=d
	ANZAHL=DAUER*RATE
	y=np.zeros(int(r*d))
	for i in range(0,int(r*d)):
		y[i]=np.sin(2*np.pi*f*i/float(r))
	return y
ss15/schallwerkzeuge.txt · Zuletzt geändert: 2016/05/10 14:46 (Externe Bearbeitung)