Benutzer-Werkzeuge

Webseiten-Werkzeuge


ws1415:ton_zu_bild

Unterschiede

Hier werden die Unterschiede zwischen zwei Versionen gezeigt.

Link zu dieser Vergleichsansicht

Beide Seiten der vorigen Revision Vorhergehende Überarbeitung
Nächste Überarbeitung
Vorhergehende Überarbeitung
ws1415:ton_zu_bild [2015/01/29 18:00]
m.pachael
ws1415:ton_zu_bild [2016/05/10 14:46] (aktuell)
Zeile 3: Zeile 3:
 ===Projektmitglieder=== ===Projektmitglieder===
  
-Claire Melchior+  * Claire Melchior
  
-Mascha Pachael+  * Mascha Pachael
  
-Laila Kulsvehagen+  * Laila Kulsvehagen
  
-Lenny Leass+  * Lenny Leass
  
 ===Ziel=== ===Ziel===
-Am Ende unseres Projekts steht das Ziel, Musik als Video darzustellen. Technisch betrachtet, wollen wir uns also mit der Umwandlung von Tonsignalen in bewegte Bilder beschäftigen. ​ 
-Das heißt, dass das Programm praktisch dazu angewendet werden wird, um sämtliche Töne - von Alltagsgeräuschen über Stimmen hin zu künstlerischen,​ musikalischen Kompostitionen - in verschieden komplexe Formen und Farben umzuwandeln. 
  
-==Teilziel==+Wir wollen Tonsignale in Bilder umwandeln. Hierbei ist es uns am wichtigsten,​ dass die entstehenden Bilder ästhetisch interessant sind.
  
-Daher muss der erste Schritt sein, sich damit auseinander zu setzen, in welcher Form wir Töne und Bilder mathematisch interpretieren können. Wir werden folglich eine Menge von Daten in eine andere Menge umwandeln. Um diese Menge zu differenzieren,​ müssen wir Parameter einführen, die Unterschiede in Lautstärke und Tonhöhe beispielsweise festhalten. 
-Diese Informationen werden anschließend dazu verwendet, uns schrittweise mittels vereinfachter Modelle, an das Kernproblem anzunähern. Ein möglicher Zwischenschritt wäre an dieser Stelle zum Beispiel, eine Menge ganzer Zahlen in den Grundfarben in einer Ebene darzustellen. Mit anderen Worte: Ein Programm zu schreiben, welches aus beliebigen Arrays ein Bild generiert. 
  
 ===Ansätze=== ===Ansätze===
  
-Mittels Fourier-Analyse ​Daten aus Tonsignalen ermittelnwelche wiederum zur Generation von Bildern verwendet ​werden können.+Zuerst müssen die Tonsignale in Daten umgewandelt werdendie dann in unserem Programm verarbeitet ​werden können. Diese Daten können dann auf verschiedene Arten verwendet werden, um Bilder zu generieren.
  
-===Nützliche Programmschnipsel===+===Theoretischer Hintergrund===
  
-Bilder ​generieren:+Zuerst mussten wir uns damit auseinandersetzen,​ wie Schall mathematisch beschrieben werden kann. Wir haben uns die Begriffe Periode, Frequenz, Amplitude etc. noch einmal vergegenwärtigt.  
 + 
 +==Fourier-Analyse== 
 + 
 +Grundlage für die Verarbeitung und Analyse von Tonsignalen ist die Fourier-Analyse.  
 + 
 +Sie bietet eine Möglichkeit,​ Schallsignale in ihre Teilfrequenzen zu zerlegen. Somit kann man z.B. Grundtöne bestimmen, Obertonspektren vergleichen,​ und vieles mehr. 
 + 
 + 
 +===Unser Programm=== 
 + 
 +Um Töne  aufnehmen deren Daten verarbeiten zu können, verwenden wir das Modul pyaudio. 
 +Für die Verarbeitung der Daten verwenden wir das Modul numpy.  
 +Für die Generierung und Darstellung der Bilder ​verwenden wir das Modul matplotlib. 
 + 
 +Ein Funktion zum Aufnehmen von Tönen kann z.B. so aussehen:
  
 <code python> <code python>
  
-import ​Image #Modul aus Python Imaging Library+from __future__ ​import ​division 
 +import pyaudio 
 +import numpy as np
  
  
-def gen_image(lis): +def recordsnd(filename, time): 
- img = Image.new( ​'RGB'(len(lis)-1,len(lis)-1), "​black"​) #​generiert + ''​
- #Bild im Farbschema RGB mit Groesse len(lis)+1, len(lis)-1 und der + Nimmt eine  time  Sekunden lange Schallsequenz 
- #Farbe schwarz. ​ + auf (mit der Samplerate 44100 Hzauf, 
- pixels ​img.load() #Erstellt "pixel map" des Bildes. + speichert sie in der Datei filename und gibt die 
- for i in range(img.size[0]):​ + Aufnahme als numpy-array mit Werten zwischen ​-1 und 1 zurück 
- for j in range(img.size[1]):  + '''​ 
- pixels[i,​j] ​(lis[i], lis[j], 100) #Greift auf jeden Pixel  +        ​CHANNELS ​= 1 
- #zu und faerbt ihn mit entsprechenden RGB-Werten ein. +        ​RATE ​44100 
- img.show()+ DAUER=time 
 + ANZAHL=int(RATE*DAUER)
   
-#Beispiel+  
-gen_image(range(255))+ 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 = 1024)#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
  
 </​code>​ </​code>​
 + 
 +Den numpy-array,​ den wir hierdurch erhalten, können wir uns mit matplotlib anzeigen lassen, z.B. so:
  
 +<code python>
 +import matplotlib.pyplot as plt
  
-===Protokoll===+recordsnd(None,​1) 
 +y[:2000] 
 +y.reshape(len(y),​ 1) + y.reshape(1,​ len(y)) 
 +ax plt.axes() 
 +ax.imshow(y) 
 +plt.show()
  
-**20.11** ​  ​Grundlagen Fourier-Analyse,​ Festlegung der Kommunikationsmittel (Facebook und Dropbox)+</​code>​
  
-**27.11** ​  ​Einrichten der Wiki, Grundlagen ​Fourier-Analyse, ​Erkundung von Schallwekrzeugen in Python+Wenn wir nun auch die Fourier-Analyse ​ins Spiel bringenkönnen wir noch interessantere Bilder erzeugen:
  
-**4.12** ​  ​Erstellen von Klassen Ton und Bild, Beginn der Erstellung von Bildgenerierungsprogrammen+<code python>
  
-**11.12** ​  ​Anfängliche technische SchwierigkeitenDer Befehl img.show() resultiert nicht in der Darstellung des BildesDank Stefans Hilfe konnten ​  wir das Problem schnell beheben, sodass wir nun einen einzelnen Ton als unbewegtes Bild darstellen können.  +y = recordsnd(None,​1) 
-Für unsere Weiterarbeit stellen sich im Wesentlichen zwei Probleme: +y = y[:512] 
-  * 1**In welcher Form soll sich das Bild bewegen?** Dazu müssen wir wissenWird ein Bild einem Ton oder einer Sekunde zugeordnet? Oder orientiert sich unsere Bild an verschiedenen MesswertenLautstärke -> Größe eines Objekts; Tonfrequenz -> Farbe des Objekts. +y = np.abs(np.fft.fft(y)) 
-Aufgrund unseres bishergen Programms haben wir uns dafür entschiedendass das Programm pro Sekunde eine bestimme Anzahl von Bildern generiertDiese lassen wir anschließend hintereinander ablaufen+y = np.concatenate((y[-50:],y[:50]),​axis=0) 
-Ausblick: Das Programm soll nach und nach immer mehr Messwerte berücksichtigen,​ weshalb wir schrittweise mehr Parameter in den Sourcecode einbauen wollen. Diese stellen dann zum Beispiel die Lautstärke oder die Frequenz dar+y = y.reshape(len(y),1) + y.reshape(1,​len(y)) 
-  * 2**Wie können wir die bildliche Darstellung ästhetisch optimieren?​**+ax = plt.axes() 
 +ax.imshow(y) 
 +plt.show()
  
-**08.01** Durch zwei neue Programme von Stefan ist nun eine detailliertere und erweiterte Darstellung des Tons möglich: 
-  - Nummerierter Listenpunkt "​Visuals":​ 3-dimensionale Darstellungen. ​ 
-  -  Das Einlesen von wav-Dateien:​ Anstatt Mikrofonaufnahmen kann jetzt direkt auf die Daten der Tonaufnahmen zugegriffen werden und ins Programm ​  ​eingegeben werden. 
  
-Ausblick für nächste Woche:  +</​code>​
-  *  Einarbeitung und Anwendung der Fourier-Analyse +
-  *  Benutzung von "​Visuals"​ in Python+
  
-**15.01** Bislang haben wir aus einigen Sekunden langen Mikrofonaufnahmen,​ ein 2-dimensionales,​ mehrfaches Bild erzeugt. Das Verfahren gestaltete sich somit grob in die Teilschritte: ​ 
-    * Aufnahme ​ 
-  * -> Datenspeicherung 
-  * -> Umrechnung 
-  * -> Bildanzeige 
  
-Heute ist es gelungendiese zwei grundsätzlichen Prozesse von Mikrofonaufnahme und Bildanzeige jeweils ​kontinuierlich und selbstständig ablaufen ​zu lassen. +Nun brauchen wir eine Methodeum Tondaten ​kontinuierlich ​verarbeiten ​und anzeigen ​zu lassen.  
-Somit können ​wir jetzt beispielsweise ​ein Gespräch aufnehmen und es direkt in ein Bild umwandeln. Das heißtes werden permanent Aufnahmen getätigt, also Daten gesammelt, die direkt und zusammenhängend in eine Bildatei umgewandelt werden. Je nach dem, wie viele Bilder pro Zeit erzeugt werden, entsteht eine Art Film. +Zunächst erstellen ​wir ein Anzeigeobjektzusammen mit einer Methode, wie sich dieses aktualisiert:​
  
-**22.01** Der nächste Schritt ist nun, die Bilddarstellung vielfältiger zu gestalten. Es wird diskutiert, nach welchen ästhetischen Aspekten wir unsere Bilder erzeugen wollen. An dieser Stelle sind zum Beispiel 3-dimensionale Körper interessant. Eine weitere Möglichkeit ist, die eigentliche Bilddatei mit weiteren kleineren Bilddateien zu überlagern;​ also praktisch ein Bild im Bild erzeugen.+<code python>
  
-Hier stoßen wir auf unsere Defizite beim Umgang mit matplotlib. Deshalb steht auch unsere Hausaufgabe bis nächster Woche festHeranarbeitung an das Verständnis von Aufbau und Funktion von matplot, um unsere vielen Ideen zur Bilddarstellung auch technisch umsetzen zu können.  ​+class Anzeige(object):
  
-**29.01** Stefan hat für uns ein matplotlib-Beispiel erstelltwelches alle Möglichkeiten darstellt die man mit diesem Modul hatAuf der Grundlage dessen haben wir nun einen Kreis in einem Koordinatensystem erstelltder seine Farbe entsprechend des Tones ändert der aufgenommen wirdNächste EtappeDer Kreis ändert auf Basis des Tones die GrößeWir wollen demnach als Endergebnis einen pulsierenden seine Farbe ändernden Kreis erzeugen.+ def __init__(self,​chunk,​rate):​ 
 + self.chunk=chunk 
 + self.pixels = np.random.rand(chunk,​chunk) 
 + plt.pause(0.001) 
 + self.rate=rate 
 + self.fig = plt.figure() 
 + self.ax = self.fig.add_axes((0,​0.25,​0.5,​0.5)) 
 + plt.axis("​off"​) 
 + self.ax2 = self.fig.add_axes((0.5,​0.25,​0.5,​0.5)) 
 + plt.axis("​off"​) 
 + #​self.image = self.ax.imshow(self.pixels) 
 + self.fig.canvas.draw() 
 + self.noch_kein_erstes_bild_da=True 
 +  
 +  
 + def update(self,​data):​ 
 + l=len(data) 
 + self.fourier = np.abs(np.fft.fft(data,​ axis=0)) 
 + self.fourier = np.concatenate((self.fourier[-50:,0],self.fourier[:50,0]),​axis=0) 
 + l2 = len(self.fourier) 
 + self.fourier2 = self.fourier.reshape((l2,​1))+self.fourier.reshape((1,​l2)) 
 +  
 + self.pixels=data.reshape((l,​1))+data.reshape((1,​l)) 
 + if self.noch_kein_erstes_bild_da: 
 + self.image = self.ax.imshow(self.pixels) 
 + self.image.set_cmap("​spectral"​) 
 + self.fourier_image = self.ax2.imshow(self.fourier2) 
 + self.fourier_image.set_cmap("​spectral"​) 
 + self.noch_kein_erstes_bild_da=False 
 + self.fig.canvas.draw() 
 + plt.pause(0.05) 
 + self.image.set_data(self.pixels) 
 + self.fourier_image.set_data(self.fourier2)
  
  
- +anzeige=Anzeige(CHUNK,​RATE) 
 + 
 +</​code>​ 
 + 
 + 
 +Dann erstellen wir eine callback-funktion,​ welche unser Anzeige-objekt sich mit neuen Daten aktualisieren lässt: 
 + 
 +<code python>​ 
 + 
 +def micro_callback(in_data,​ frame_count,​ time_info, status): 
 + 
 + if CHANNELS==2:​ 
 + y=y.reshape((y.shape[0]//​2,​2)) 
 + else: 
 + y=y.reshape((y.shape[0],​1)) 
 + anzeige.update(y) 
 + return (in_data, pyaudio.paContinue) 
 + 
 +</​code>​ 
 + 
 +Nun wird ein Audiostream gestartet, welcher, immer wenn CHUNK frames vom Mikrophon gelesen wurden, unsere callback-funktion aufruft: 
 + 
 +<code python>​ 
 + 
 +p = pyaudio.PyAudio() 
 +stream = p.open(format=pyaudio.paInt16 , 
 +                channels=CHANNELS,​ 
 +                rate=RATE,​ 
 +                input=True,​ 
 +                output=False,​ 
 +                stream_callback=micro_callback,​ 
 +                frames_per_buffer=CHUNK) 
 + 
 +stream.start_stream() 
 +time.sleep(0.5) 
 + 
 +</​code>​ 
 + 
 +Schließlich startet unsere Hauptschleife,​ welche das Anzeige-objekt so lange darstellt, wie der Stream aktiv ist: 
 + 
 +<code python>​ 
 + 
 +while stream.is_active():​ 
 + anzeige.fig.canvas.draw() 
 + anzeige.fig.canvas.flush_events() 
 + 
 +     
 +</​code>​ 
 + 
 +===Das Endprodukt=== 
 + 
 +{{ws1415:​projekte_im_wintersemester_2014_15:​bild2.png}}
  
 +[[Protokolle]]
ws1415/ton_zu_bild.1422550858.txt.gz · Zuletzt geändert: 2016/05/10 14:46 (Externe Bearbeitung)