Jan schrieb:
> Wie kann ich Presacler und Period wärend der "Laufzeit" ändern. oder
> muss jedes mal den Timer abschlaten und mit dem neuen Tonwert
> initialisieren?
Nein, sowas geht ganz anders.
Zunächst stellst du dir die Periode deines PWM-Timers so ein, daß sie
groß genug ist, um darin etwas mehr als sämtliche vorkommende
Amplitudenwerte unterzubringen.
Also wenn du deine Töne mit 10 Bit Amplitudenauflösung abspielen willst,
dann setzt du die Periode auf so etwa 1024+10+10, macht 1044. Das machst
du, um mit der Amplitude nicht direkt an die Rails anzuecken, denn du
mußt die PWM-Ausgabe ja analog weiterverarbeiten.
Dann stellst du den Prescaler so ein, daß sich mit Prescaler und
Zählumfang von hier im Beispiel 1044 eine Audio-Samplerate deiner Wahl
ergibt, die du auch noch per Interrupt verarbeiten kannst.
Dann stellst du den Comparewert auf Mitte ein, also 1024/2 + 10, macht
522.
Dann hast du die Wahl:
a) du machst dir einen Ringpuffer ausreichender Größe und füllst ihn mit
522.
b) du machst eine Variable, aus der dein Interruptprogramm erkennt, ob
es was spielen soll oder nicht.
So, nun kannst du den PWM einschalten.
Im zugehörigen Interruptprogramm machst du folgendes:
Variante a) nimm den nächsten Wert aus dem Ringpuffer und schreibe an
dessen Stelle 522 in den Ringpuffer. Dann wandelst du das Sample um:
addiere 522 und schreib das in das Compare-register
Variante b) guck nach, ob du dudeln sollst. Wenn ja, dann nimm das
nächste Sample aus deinem Puffer, wandle es wieder um (+522) und
schreibe es in das Compareregister. Wenn nein, schreibe 522 in das
Compareregister.
Hinter dem Ganzen auf der Pin-Seite mußt du natürlich das PWM per
geeignetem Tiefpaß filtern, um die Samplefrequenz ausreichend zu
dämpfen.
Damit kannst du Töne, aber auch kurze Sprachstücke wiedergeben. Für
alles Weitere lies in der Lernbetty nach, da ist auch eine dezente
Kompression der Audiodaten per SOL (Sierra-Format) dabei.
W.S.