Hallo Besucher, der Thread wurde 19k mal aufgerufen und enthält 92 Antworten

letzter Beitrag von Sierohpätsch am

BREADAMP - ein "Winamp" für den C64 [1541u / TC64]

  • Der Bühnenmensch bin ich eher nicht, aber wer sich für das Programm interessiert, kann mich gern an meinem Platz dazu ausfragen und sich das Programm + Musikfiles bei mir auf einen USB-Stick kopieren, um es am eigenen C64 mit 1541u zu benutzen. Ich werde das sicher regelmäßig benutzen und an meinem Platz ein bisschen Musik hören, dafür habe ich mir das Programm ja zusammengebastelt.

  • Der Bühnenmensch bin ich eher nicht, aber wer sich für das Programm interessiert, kann mich gern an meinem Platz dazu ausfragen und sich das Programm + Musikfiles bei mir auf einen USB-Stick kopieren, um es am eigenen C64 mit 1541u zu benutzen. Ich werde das sicher regelmäßig benutzen und an meinem Platz ein bisschen Musik hören, dafür habe ich mir das Programm ja zusammengebastelt.

    Ich schau dann mal bei Dir vorbei :-)

  • Programm + Musikfiles

    Kannst Du das nicht auch in die Wolke beamen?

  • Nach einigen Wochen Programmierarbeit ist es nun soweit: BREADAMP v03 ist fertig !


    Hier kann man sie herunterladen: von meinem Webspace oder von der CSDB


    Diese neue Version bietet folgende neue Funktionen:

    - Stereo-Unterstützung für C64 mit 2 SIDs oder FPGASID (zweiter SID muss auf Speicheradresse $D500 liegen, wird beim FPGASID automatisch eingestellt)- Longplayformate, die eine geringere Tonqualität, aber deutlich längere Spielzeit bieten (bis zu 97 Minuten und 44 Sekunden)

    - automatische Konfiguration bei Nutzung eines FPGASIDs, dieser kann alle Dateien abspielen, egal für welchen SID sie erstellt wurden

    - NTSC-Unterstützung (NTSC-C64 mit "neuen" VIC, der Player funktioniert aber auch mit dem "alten" VIC, da er dafür nicht optimiert ist, ist dann aber die Tonqualität geringer)

    - Möglichkeit die Abspielreihenfolge der Titel zu ändern

    - Steuerung mittels Joystick(s)

    - Formatanzeige, die Informationen über die Datei gibt (SID-Typ, TV-Norm, FPGASID-Modus)

    - Rahmen-, Hintergrund und Textfarbe kann geändert werden

    - "Diskomodus", bei dem beim Abspielen jede Sekunde die Rahmen- und / oder Hintergrundfarbe gewechselt wird

    - erweiterte Fehlererkennung (falsche TV-Norm / Gerätetyp und Datei für FPGASID, aber kein FPGASID eingebaut)

    - Rückwärtskompatibilität: der Player spielt auch Dateien der v02


    Sollte jemand einen Bug entdecken, bitte melden. Aufgrund der Komplexität, die das Programm mittlerweile erreicht hat (ca. 3000 Assembler-Befehle), können sich immer mal Bugs einschleichen, ich habe die letzten Tage noch einige entdeckt und gefixt, die nur unter ganz bestimmten Umständen aufgetreten und somit nur durch Zufall zu finden sind.


    In zukünftigen Versionen habe ich noch geplant:

    - Trackrepeatfunktion (wollte ich eigentlich schon in dieser Version machen, habe ich aber vergessen, da es nicht so wichtig ist, habe ich es auch nicht noch "schnell reingepatcht")

    - Aufnahmefunktion für C64er mit FPGASID (der FPGASID hat einen Audio IN mit dem man samplen kann)

    - eventuell weitere Funktionen


    Die Erstellung von eigenen Musikdateien mit dem BREADAMP_v03_REUmaker wurde auch vereinfacht:

    Als Eingabedateien dienen nun wav-Dateien, die mit den für den Konverter nötigen Parametern mit Hilfe von Audacity erstellt wurden. Dadurch entfällt bei der Verwendung von mp3-, ogg- oder flac-Dateien der Zwischenschritt über die Konvertierung in eine "normale" wav-Datei und man kann seine Musik direkt in das benötigte wav-Format konvertieren.

    Durch die Verwendung des wav-Formats haben die konvertierten Dateien einen Header, der zum einen das Abspielen in einem normalen Audioplayer wie Winamp ermöglicht (zwecks Kontrolle) und zum anderen vom REUmaker ausgewertet werden kann, der bei Unstimmigkeiten (z.B. nicht unterstützte Samplerate) die Datei beanstandet, wodurch einige Fehler schon beim Konvertieren und nicht erst beim Anhören erkannt werden können.


    Wie man eigene Musikdateien erstellen kann, welche Tonformate mit welchen Spielzeiten unterstützt werden und weitere Informationen zum Player findet man in der im Archiv enthaltenen Dokumentation.


    Hier der Player in Aktion in Form zweier Youtube-Videos:


    Der Player mit den Standardabspielmethoden 8 Bit Mahoney und 4 Bit "classic":

    [Externes Medium: https://youtu.be/Nqjo_SY4Hpk]


    Die Samplewiedergabemethode, die nur auf einem FPGASID funktioniert, indem dessen "Digifixregister" benutzt wird:

    [Externes Medium: https://youtu.be/-VOAKlGvUEg]

  • Mir wurde gemeldet, dass es momentan Probleme mit dem Download gibt. Dies liegt vermutlich an einem DNS-Eintrag, der noch auf den alten Webspace zeigt.

    Wer Probleme mit dem Download hat, kann diesen Alternativlink nutzen: http://w244471.virtualuser.de/c64/BREADAMPv03+Demofile.rar

  • daddlertl

    Mal so als Idee für dich: Du könntest dir wahrscheinlich das Konvertieren der Wave-Dateien ins Mahoney Format sparen. Deine Abspielgeschwindigkeit liegt doch stets unter 22KHz, da sollte es reichen, die Wave-Datei einfach direkt beim Abspielen zu konvertieren. Das würde den Usern das Umwandeln ersparen. Ich hab das bei BR-TV nicht gemacht, weil ich auch 44.1KHz abspiele (aber selbst da wäre wohl noch genug Zeit dafür) und wegen Speed/Animation keinen Index (y,x) mehr so ohne weiteres "frei" hatte.


    Das Prinzip ist einfach: Ohne deinen Source-Code gesehen zu haben - irgendwann fetcht du ja das aktuelle Sample-Byte aus der REU an die Abspieladresse, in deinem Fall der schon konvertierte Wert. Du könntest aber auch den "Original"-Wert in einen Index fetchen (z.B. y) und mit dem dann per lda Tabelle,y den konvertierten Wert holen und an die Abspieladresse übergeben. Du müßtest nur zuvor den benutzten SID ermitteln, damit du die richtige Tabelle nutzt.


    Das ist quasi das gleiche, was du sonst im Umwandlungs-Tool machst. Nur eben on-the-fly, Byte per Byte, und ohne Abspeichern. Ungefähr so:


    Aber länger nichts mehr mit der REU gemacht, also falls da ein Denkfehler ist... :sleeping:

    :angel

  • Der Bühnenmensch bin ich eher nicht, aber wer sich für das Programm interessiert, kann mich gern an meinem Platz dazu ausfragen

    oder

    Ich kann gar nicht sagen, wie begeistert ich von diesem Programm bin!

    Andi hat ja schon "Bühnen-Erfahrung"... vielleicht mag er es ja mit anderen "SID-Künsten" verbinden...


    ich finde das Thema auch für die DORECO-Bühne "akustisch" und "visuell" sehr geeignet :bia

  • @Squidward An eine On-the-fly-Konvertierung hatte ich auch gedacht - das Problem sind die verfügbaren Takte, insbesondere in den Bad Lines des VIC, da werden einem nämlich von den 63 Takten der Zeile mindestens 40 vom VIC "geklaut", d.h. man hat an diesen Stellen maximal 23 Takte übrig, meist weniger (hängt davon ab, welcher Befehl im Moment des IRQ ausgeführt wird). Problematisch sind also 2 aufeinanderfolgende Samples von denen einer vor und einer nach der Bad Line gespielt werden muss.


    Der Player-IRQ macht das beim Abspielen eines Samples:

    -Akku auf Stack sichern (nötig, weil er zum Senden des REU-Kommandos gebraucht wird)

    -IRQ bestätigen

    -per REU-Kommando das Sample in den SID schieben lassen (braucht 2+4+1 = 7 Takte) ***

    -Adresse (Lo) der REU um 1 erhöhen

    -wenn nicht 0, dann zum Ende gehen

    -sonst die (Hi)-Adresse der REU und ggf. auch noch die REU-Bank erhöhen (letzteres braucht eine Hilfsvariable, weil direktes Erhöhen den REU-Wraparound-Bug auslöst)

    -am Ende Akku vom Stack zurück holen und IRQ verlassen


    In Summe verbraucht man dabei schon ca. 32 Takte (oder mehr, wenn die Hi-Adresse und evtl. sogar die Bank erhöht werden muss), d.h. ein paar Samples bekommen schon einen "Bad Line - Treffer" und werden dadurch etwas verzögert, aber wesentlich weniger als wenn man die Bad Lines gar nicht beachtet. Ich habe durch Hörtests ausprobiert, an welcher "X-Kordinate" des Rasterstrahls man den IRQ am besten starten lässt und den Wert genommen, der sich für mich am besten angehört hat.


    *** Würde man jetzt noch eine On-the-fly-Konvertierung durchführen bräuchte man folgendes:

    -per REU-Kommando das Sample in eine Variable in der Zeropage schieben lassen (braucht auch 7 Takte)

    -die Variable (Samplewert) ins X-Register laden (3 Takte)

    -den Mahoneywert x-referenziert aus der Lookuptabelle holen (4 Takte)

    -den Mahoneywert in den SID schieben (4 Takte)

    --> d.h. das ganze würde 17 Takte brauchen, also nochmal 10 mehr wie beim direkten Schreiben der Mahoney-Werte, somit wäre der Jitter im Bereich der Bad Lines deutlich größer und das ganze würde zumindest bei 15,6 kHz nicht mehr gut klingen (bei den geringeren Sampleraten würde es sicher funktionieren, aber bei Stereo hätte man kaum eine Chance einen vernünftigen Klang hinzubekommen)


    Der Quellcode des Programms liegt im Archiv vor, wer eine Idee hat, wie man eine On-the-fly-Konvertierung bei vernünftigen Klang hinbekommt, kann das Programm gern modifizieren. Dies ist mein erstes größeres Assemblerprojekt, d.h. ich kenne ganz sicher nicht alle "Szenetricks" für maximalen Speed und maximale Präzision, aber vielleicht kennt ja jemand eine Möglichkeit wie man das ausreichend schnell hinbekommen kann.

    Das ist auch der Grund, warum ich den Quellcode beilege: damit interessierte Programmierer ihre Ideen am Programm ausprobieren oder das Programm an eigene Bedürfnisse anpassen können (auf Facebook meinte z.B. jemand, dass er gern eine andere Schriftart für die Texte hätte, da konnte ich ihm mitteilen, dass er gern eine eigene Schriftart einfügen kann, was recht einfach ist, weil auch das verwendete Charset im Archiv liegt -> man kann es mit einem Charset-Editor, z.B. Charpad, bearbeiten und anschließend das Programm neu kompilieren - dabei wird dann das geänderte Charset ins Programm integriert).


    Aufgrund der Bad Line - Problematik habe ich die maximale unterstützte Samplerate auf 15638 Hz (=Zeilenfrequenz des VIC) festgelegt, weil mehr bei eingeschalteter Bildausgabe einfach keinen Sinn macht (bei 44,1 kHz hat man pro Sample nur 22 Takte, d.h. eine Bad Line "frisst" 2 komplette Samples und das hört man sehr deutlich, weswegen ich eine Samplewiedergabe bei Zeilenfrequenz wesentlich angenehmer empfinde, als eine von Bad Lines zerhackte 44,1 kHz - Wiedergabe. Bei der Entwicklung des Players war mein oberstes Ziel eine möglichst gute Wiedergabequalität bei eingeschalter Bildschirmausgabe zu erzielen (aufgrund der technischen Limitierungen erreicht man damit natürlich keine Bose-Qualität, aber für den Zweck für den ich den Player programmiert habe, nämlich auf Retropartys Musik mit dem C64 hören zu können, reicht mir die Tonqualität).

  • Hier der Player in Aktion in Form zweier Youtube-Videos:

    Ich geh am Stock, das wird ja immer besser! Absoluter Hammer8o:hammer:

  • -Akku auf Stack sichern (nötig, weil er zum Senden des REU-Kommandos gebraucht wird)

    Statt pha,pla kannst du einen Cycle sparen, wenn du stattdessen Selfmod-Code benutzt:

    Code
    1. Player_Start
    2. sta MOD_Accu_Save+1 ; schreibt den Accu hinter dem lda Befehl am Ende des Players in den Speicher
    3. ...
    4. ...
    5. Player_Wrap
    6. MOD_Accu_Save ; Label für Self-Mod Code
    7. lda #$ff ; wird ersetzt durch den Accu-Wert von Player_Start
    8. rti


    -per REU-Kommando das Sample in den SID schieben lassen (braucht 2+4+1 = 7 Takte) ***

    Wenn du einen Index frei hast kannst du den zuvor einmalig mit dem Command-Byte laden und im Player dann immer nur zur REU schreiben:

    Code
    1. STATT
    2. lda #253
    3. sta REU_Command
    4. NUR NOCH
    5. stx REU_Command ; x holds #253

    Spart zwei Cycles :)


    -per REU-Kommando das Sample in eine Variable in der Zeropage schieben lassen (braucht auch 7 Takte)

    -die Variable (Samplewert) ins X-Register laden (3 Takte)

    Den Zwischenschritt mit der Zeropage kannst du dir sparen, wenn du gleich (wie in meinem Beispiel aus Post #50 in Zeile 12) als Zieladresse das Byte im Speicher hinter dem ldx/ldy Befehl definierst (oben Zeilen 20-21) = Selfmod-Code


    :)


    In jedem Fall Gratulation zu deinem Assembler-Projekt! Dafür hast du dir gleich ein ganz schönes Mammut-Projekt ausgesucht ;)

  • Mir ist gerade eine Idee gekommen, wie ich noch mehr Takte sparen kann, wenn ich das gesamte Programm so umbaue, dass ein Register (z.B. y) immer frei bleibt (ist natürlich eine Menge Arbeit):


    -den IRQ nicht mit lda $dd0d, sondern mit bit $dd0d bestätigen (das gilt auch als Lesen, benutzt aber den Akku nicht)

    -das freigehaltene Register statt dem Akku zu benutzen, um der REU das Kommando zu geben -> da dieses vom Hauptprogramm nicht mehr geändert werden soll, braucht nicht jedes mal der Wert reingeladen werden -> spart 2 Takte, so wie du geschrieben hast

    -da der Akku nicht mehr benutzt wird, können die Befehle pha und pla entfallen, somit werden weitere 3 + 4 = 7 Takte eingespart


    In Summe werden also 9 Takte pro Sample eingespart, macht bei einer Samplerate von 15638 Hz eine Ersparnis von 140742 Takten pro Sekunde, d.h. es werden 14,2% CPU-Last eingespart, die dann das Frontend noch schneller machen (es ist jetzt schon rasant schnell mit ca. 100 fps bei 15,6 kHz Mono), aber vor allem den Samplejitter im Bereich der Badlines verringert, was für einen etwas besseren Klang sorgen könnte (zumindest theoretisch, ob man wirklich einen Unterschied hört, wird sich dann zeigen). Erstmal brauche ich eine Weile Pause, aber wenn ich wieder Lust drauf habe und die großen Retropartys vorbei sind, werde ich das sicher mal ausprobieren.


    Das einzige, wo ich in der Playerschleife ein Register bräuchte, wäre beim Umschalten der REU-Bank, weil ich die in einer Variable verwalten muss (das direkte Inkrementieren der REU-Bank löst leider den REU-Wraparound-Bug aus), somit müsste ich das "reservierte" Register kurz benutzen und anschließend wieder auf 253 setzen, kostet 2 Takte mehr, aber nur alle 65536 Samples, also ca. alle 4 Sekunden bei höchster Qualitätsstufe.


    Die eingesparten Takte lassen sich nicht für "On-the-Fly-Konvertierung nutzen", da man dafür ja wieder die Register bräuchte, aber eben zur Verringerung des Samplejitters.

  • Ich verwende in VICE, wie auch im echten C64, einen modifizierten Zeichensatz. Es wäre klasse, wenn der auch in BreadAMP sichtbar wäre, also wenn du nur die oberen 128 Zeichen (die du ja modifizierst) überschreiben würdest und die normalen Zeichen (Buchstaben, Ziffern, Satzzeichen ...) aus dem eingebauten ROM verwendet würden. Wäre das machbar?

  • Momentan nutze ich tatsächlich nur die oberen 128 Zeichen, das kann sich in den nächsten Versionen aber ändern (wird es wahrscheinlich auch, weil wirklich alle oberen 128 Zeichen verbraucht sind, und für neue Features dann auch unwichtige Zeichen im oberen Bereich benutzt werden müssen).


    Ich habe mal auf die Schnelle was zusammengehackt, sodass die unteren 128 Zeichen aus dem Systemrom und die oberen aus meinem Custom-Charset geladen werden. Ich habe mir mal auf die Todoliste für die nächste Version geschrieben, dass auch da alle unveränderten Zeichen aus dem Systemrom geladen werden sollen.


    Hier mal ein Screenshot, wie es jetzt aussieht: links Standardfont, rechts Alternativfont:


    Im Anhang die veränderte Version. Dies ist keine offizielle Releaseversion, sondern ein schnell zusammengebasteltes Proof-of-Concept. Ich habe auch nur einen Schnelltest gemacht, ob mir Fehler auffallen, scheint soweit ok zu sein.

  • Mir ist gerade eine Idee gekommen, wie ich noch mehr Takte sparen kann...

    Willkommen bei den Assemblerianern... :)


    Mein Player aus BR-TV braucht 17 Cycles (plus einstellbare Delays in 1-Cycle-Schritten zur KHz-Anpassung), wenn ich mich recht erinnere. Er läuft aber nicht im IRQ, sondern wird von ihm nur unterbrochen, wenn ein Frame gefetcht wird. Ist halt eher ein Videoplayer mit Audio-Support als ein reiner Sample-Player. Deshalb musste ich vorsichtig mit a,x&y sein, da ich ja zwischendurch immer von völlig anderen Stellen aus der REU völlig andere Datenmengen in völlig andere Speicherbereiche des C64 fetchen musste :/ Am Ende hat der Player in y das REU Command erwartet und sonst nur mit dem Accu die Sample-Position und den Bankwrap gemanaged...