AGB  ·  Datenschutz  ·  Impressum  







Anmelden
Nützliche Links
Registrieren
Zurück Delphi-PRAXiS Projekte erweiterte Demo für BASSMIDI.DLL

erweiterte Demo für BASSMIDI.DLL

Ein Thema von Delfiano · begonnen am 10. Nov 2020 · letzter Beitrag vom 22. Feb 2021
Antwort Antwort
Seite 1 von 3  1 23   
Delfiano
Registriert seit: 13. Jul 2020
Das Projekt "BassMidiTest" ist eine erweitere Zusammenfassung der beiden Beispielsprogramme, die
un4seen.com zur Verfügung stellt. Damit lassen sich Midi-Dateien unter Verwendung von SoundFonts
abspielen und prüfen, welcher SoundFont wie klingt und was er enthält. Um die ZIP-Datei nicht zu
groß werden zu lassen, habe ich nur wenige Midi-Dateien und wenige SoundFonts beigefügt.

Es gibt Probleme beim Wechsel von Laufwerksbuchstaben und Pfaden. Wahrscheinlich müssen dann
vorher alle laufenden Prozesse abgebrochen werden. Ich habe mir erlaubt, zum compilierten
Beispiel die Verzeichnisse "MID" und "SF2" mit jeweils einigen MIDI-Dateien und Soundfonts
hinzuzupacken.

Das Ende der Trackbar ist unzuverlässig. Das Ende der Datei muss anders berechnet werden.
Leider habe ich keine Ahnung wie. Mir ging es vor allem darum, die Beispiele von un4seen.com
wenigstens halbwegs nützlich abzuändern. Sorry, dass es mir nicht vollständig geglückt ist,
was die Funktionalitäten betrifft, die ich nicht überblicken kann.

Sinnvoll wäre natürlich der weitere Ausbau, z.B. mit Lautstärkereglern etc.

Weil ich nicht so der Funktionalitätenbeschreiber bin, möge sich bitte jeder die Quelltexte
selbst durchsehen. Die Originalunits bass.pas und bassmidi.pas musste ich leicht abändern, um
sie mit Delphi 5 compilieren zu können.

Inhalt der ersten ZIP-Datei ( SOURCE.ZIP )
23.556 BaseUnit.dfm
43.696 BaseUnit.pas
128.181 bass.dll // un4seen.com
52.805 bass.pas // un4seen.com, leicht modifiziert
25.356 bassflac.dll // un4seen.com
58.818 bassmidi.dll // un4seen.com
17.758 bassmidi.pas // un4seen.com, leicht modifiziert
266 BassMidiTest.dpr
876 BassMidiTest.res
32.557 basswv.dll // un4seen.com

Inhalt der zweiten ZIP-Datei ( BIN.ZIP )
455.168 BassMidiTest.exe // compiliertes Programm

Sorry, die ZIP-Datei mit den SoundFonts und Midi-Dateien ist leider zum Hochladen zu gross.

Anpassung:
Die ZIP-Datei "Source_2.ZIP" enthält nur die geänderte Basisunit.

Eine neue EXE-Datei habe ich nicht hochgeladen, weil die grundsätzliche Funktionalität auch schon aus der ersten ersichtlch ist.

Der Quelltext wurde teilweise vereinfacht und es kam eine Option für zufällige Klangerzeugung dazu.

Ausserdem kann "SF2_WORK" (https://www.delphipraxis.net/205992-...m-sf2comp.html) direkt aufgerufen werden, wenn die Dateien "SF2_WORK.exe", "SF2Comp.exe" und "SFEDT32.DLL" im selben Verzeichnis sind. Um keine Fehlermeldung zu erhalten, muss dafür ausserdem ein Verzeichnis "SF2" im Programmpfad vorhanden sein.

zweite Änderung der Basisunit
Der Inhalt der Datei "Source_3.ZIP" ersetzt alle früheren Versionen von "BaseUnit".

Version 0.4 ( Source_04.ZIP enthält wieder nur die Basisunit. )

Bei Auswahl eines Soundfonts werden die Menge enthaltener Drumsets und Instrumente in der Statuszeile angezeigt.

Auf defekte Soundfonts wird nicht mehr mit ShowMessage hingewiesen, sondern in der Statuszeile.

Im Statuspanel werden Datum und Uhrzeit angezeigt, ansatzweise auch wenige Hints.

Beim Start wird ActiveControl auf Midi_FileListBox gesetzt.

Version 0.5 lasse ich aus, weil sich Version 0.6 bereits in Vorbereitung befindet und als wesentlichste Änderung die Integration der in "SF2_WORK.exe" enthaltenen Unit bringt, die zu diesem Zweck geändert und verbessert wurde. Die neue Version von "SF2_WORK.exe" befindet sich bereits unter https://www.delphipraxis.net/205992-...m-sf2comp.html

Version 0.6 ist die vorerst letzte Version
Bass-midiTest_06.ZIP erfordert keine der vorherigen ZIP-Dateien.
Wer allerdings die Hilfedateien für BASS.DLL und BASSMIDI.DLL etc. möchte, findet alles dazu vollständig auf https://www.un4seen.com/ ...

SF2Comp ist komplett auf http://www.hammersound.net/mirrors/last_night/sf.htm zu finden.
Angehängte Dateien
Dateityp: zip SOURCE.ZIP (261,1 KB, 34x aufgerufen)
Dateityp: zip BIN.ZIP (209,6 KB, 22x aufgerufen)
Dateityp: zip Source_2.ZIP (13,0 KB, 19x aufgerufen)
Dateityp: zip Source_3.ZIP (14,7 KB, 20x aufgerufen)
Dateityp: zip Source_04.ZIP (15,4 KB, 19x aufgerufen)
Dateityp: zip Bass-midiTest_06.ZIP (667,1 KB, 22x aufgerufen)
Dateityp: zip 0.8b.zip (312,0 KB, 15x aufgerufen)

Geändert von Delfiano (22. Nov 2020 um 10:25 Uhr) Grund: Erweiterungen/Änderungen/Erläuterungen
 
Delphi.Narium

 
Delphi 7 Professional
 
#2
  Alt 10. Nov 2020, 12:07
Midi-Dateien gibt es u. a. hier:

Doug McKenzie - Jazz Piano
Free MIDI Backing Tracks Downloads
Free Midis - http://www.midis101.com/
FreeMidi.org
Listen to your favorite MIDI files on BitMidi
MIDIMI.ORG
MIDIWORLD.COM
MidiSpace.com - Free MIDI Music
PSR Performer Songs (Midi)
TeleWerkstatt Leutschach

Die Auswahl sollte für jeden Geschmack etwas enthalten

SoundFounts gibt es u. a. hier:

Musical Artifacts (ca. 1200 SoundFonts)
Soundfonts 4U

Verweise auf weitere SoundFont-Quellen: Ultimate List of FREE Soundfonts
  Mit Zitat antworten Zitat
Delfiano
 
#3
  Alt 10. Nov 2020, 17:39
Danke, Delphi.Narium, dass Du mir das abgenommen hast.

Im Nachhineien bekam ich nämlich ein schlechtes Gewissesn, wenn ich dafür nichts hochladen konnte, hätte ich wenigstens Quellen nennen können.
  Mit Zitat antworten Zitat
Delfiano
 
#4
  Alt 13. Nov 2020, 09:57
Die ZIP-Datei "Source_3.ZIP" (im Startbeitrag) enthält nur die nochmal geänderte Basisunit.

Ausser Fehlerkorrekturen kam der Ansatz hinzu, vorhandene Lyrics nicht mehr als Label auszugeben, sondern als Memo und von dort aus dann in einem weiteren Memo zu sammeln, und als Textdatei zu speichern.

Dabei wird aber jeweils die letze Zeile eines Absatzes verschluckt. Das hat damit zu tun, dass die Zeilen immer erst zusammengesetzt werden und ich keine unfertigen Zeilen übernehmen will, weil sich dann nur deren Teilfragmente in jeweils neuen Zeilen sammeln.

Ursächlich liesse sich das sicher durch Änderungen der Vorgabeprozeduren "EndSync", "LyricSync" und "TextSync" sowie der Funktion "ProcessMarkText" abfangen. Aber dafür reicht mein abstraktes Denkvermögen leider nicht aus.

Vielleicht weiss jemand anderes mehr und kann an dieser Stelle weiter helfen.
  Mit Zitat antworten Zitat
Delfiano
 
#5
  Alt 15. Nov 2020, 05:27
Version 0.6 ( Version 0.5 habe ich weg gelassen, weil Version 0.6 erheblich weiter entwickelt ist )

Während Version 0.4 "SF2_WORK.exe" noch extern auruft, wird die (geänderte) Unit nun direkt eingebunden. Dazu war u.a. nötig, den Namen des Forms zu ändern und eine Kontrolle einzubauen, ob die Unit als eigenständiges Programm gestartet wurde oder in ein anderen integriert wurde. Um Verwechslungen mit der alten Unitversion zu vermeiden, habe ich die Unit von "U_SF2" zu "U_SF2a" umbenannt.

Ausserdem wurde die Funktionalität dahingehend erweitert, dass der Aufruf des externen Programms "SF2Comp.exe" nun als LOG-Datei gespeichert werden kann.

noch immer vorhandene (bekannte) Fehler:
Wenn Verzeichnisse gewechselt werden, gelten manchmal plötzlich auch gültige Soundfiles als defekt.
Vorhandene Lyrics werden noch immer nicht korrekt ausgewertet, sondern unvollkommen gespeichert.
Die (nicht von mir stammende) Notenberechnungsbasis "60 - drums * 24"

Die integrierten Optionen zum Stimmen von Gitarre bzw. Bass sind unfertig. Für Bass fehlen Berechnungen je nach Saitenzahl und Stimmung. Wenn SoundFonts weniger als 128 Instrumente enthalten oder nicht standardmässig belegt sind, kann keine wirkliche Prüfung auf Korrektheit der Instrumente erfolgen. Ausserdem fehlt die automatische Wiederholung des gewünschten Tons, wie es zum Stimmen von Saitenistrumenten nötig ist. Momentan habe ich keinen Schimmer, wie das per Timer gelöst werden kann.

Bass-midiTest_06.ZIP( 683.063 Bytes ) enthält alle Dateien des Projektes. Die ZIP-Datei befindet sich im Startbeitrag.
34.869 BaseUnit.dfm
62.375 BaseUnit.pas
128.181 bass.dll // un4seen.com
52.805 bass.pas // un4seen.com, leicht modifiziert
25.356 bassflac.dll // un4seen.com
58.818 bassmidi.dll // un4seen.com
17.758 bassmidi.pas // un4seen.com, leicht modifiziert
369 BassMidiTest.dpr
617.984 BassMidiTest.exe
876 BassMidiTest.res
32.557 basswv.dll // un4seen.com
34.073 help.txt
38.912 SF2Comp.exe //
141.824 SFEDT32.DLL //
11.315 U_SF2a.dfm
22.423 U_SF2a.PAS

Weil ich aktuell mit meinen Weisheiten bzgl. bass.dll, bassmidi.dll usw. am Ende bin, wird es vorerst meinerseits keine neuen Versionen geben, es sei denn, andere helfen mir mit Tipps auf die Sprünge.
  Mit Zitat antworten Zitat
Delfiano
 
#6
  Alt 21. Nov 2020, 02:51
Mittlerweile habe ich zwar eine brauchbare Version 0.8a erzeugt, weiss aber nicht, ob sich überhaupt noch wer dafür interessiert. Trotz mancher Ergänzungen habe ich nämlich einige für mich bedeutende Fehler noch immer nicht beseitigen können. Das sind

- die falsche Startbasis der Tonlage, wobei ich mich am ursprünglichen Beispiel orientieren musste.
- der missglückte Versuch, Lyrics sauber (also komplett) aus Midis zu extrahieren, falls vorhanden
- das Halten von Tönen (autorepeat durch timer) bei der Option zum Instrumenten-Stimmen

Ausserdem habe ich festgestellt, dass sich bei der Midi-Wiedergabe das Instrument eines Kanals ändert, wenn man eins für die Tests auswählt. Anfangs dachte ich, das wäre unabhängig voneinander. Leider fand ich auch in den sehr komplexen Beschreibungen bass.chm und bassmidi.chm nichts dazu, wie man auf einzelne Midi-Kanäle zugreifen kann.
  Mit Zitat antworten Zitat
Delphi.Narium

 
Delphi 7 Professional
 
#7
  Alt 21. Nov 2020, 11:50
Zitat von Delfiano:
- der missglückte Versuch, Lyrics sauber (also komplett) aus Midis zu extrahieren, falls vorhanden
ProcessMarkText sieht bei mir so aus:
Delphi-Quellcode:
function ProcessMarkText(CaptionText, MarkText : string) : string;
begin
  if Length(MarkText) > 0 then begin
    case MarkText[1] of
      '@'     : Result := CaptionText;
      '\'     : Result := #13#10 + Copy(MarkText, 2, pred(Length(MarkText)));
      '/','<' : Result := CaptionText + #13#10 + Copy(MarkText, 2, Length(MarkText));
      '*'     : Result := CaptionText + #13#10 + MarkText + #13#10;
      #13 : Result := CaptionText + #13#10;
    else
      Result := CaptionText + MarkText;
    end;
  end else begin
    Result := CaptionText;
  end;
end;
Sofern bei Deinem Delphi bei Lyrics_Memo WordWrap auf true stehen sollte, ändere das bitte auf false, sonst stimmen die Zeilenumbrüche in der erstellten Datei nicht, dito. bei lbLyrics.

Edit:

Durch die unterschiedliche Breite der beiden Memos und eingeschaltetem WordWrap passt der Vergleich in der Routine lbLyricsChange
Delphi-Quellcode:
    IF Lyrics_Memo.Lines[Lyrics_Memo.Lines.count-1]<>lbLyrics.Lines[lbLyrics.Lines.count-2]
    THEN BEGIN
nicht zwingend, da durch unterschiedliche Zeilenbreiten andere Zeilenumbrüche erfolgen.

Geändert von Delphi.Narium (21. Nov 2020 um 12:41 Uhr) Grund: Text erweitert
  Mit Zitat antworten Zitat
Delfiano
 
#8
  Alt 21. Nov 2020, 22:35
Danke für die Antwort, aber das Probem besteht leider weiter.

Ich hab das jetzt noch paar mal durchgetestet, mal mit wordwrap, mal ohne, mal mit dem ursprünglichen ProcessMarkText und mal mit Deiner übersichtlicheren Version.

Die Ergebnisse sind identisch, ausser dass beider Deiner Version von ProcessMarkText am Dateiende noch eine zusätzliche Leerzeile drangehängt wird. Daraufhin werde ich mir das noch mal genauer ansehen.

Das Problem ist nach wie vor, dass immer die letzte Zeile eines Absatzes geschluckt wird, weil ich doch die vorletzte Zeile auswerte, damit nur vollständige Zeilen geschrieben werden. Ich weiss nicht, wie ich an die letzte (vollständige) Zeile komme, bevor neuer Text eingelesen wird.

Als ich es mal anders machte und wirklich jede Änderung in die Datei schrieb, waren diese letzten Zeilen der Asbätze zwar enthalten, aber dafür jede Menge unbrauchbaren Zeilen.

Mal hier die so erzeugten letzten Zeilen des ersten Absatzes von "achy-breaky-heart" (Midi-Datei im Anhang zur Kontrolle)

But Mr. DJ, please
I'm beggin' on my knees
I just can't take no
But Mr. DJ, please
I'm beggin' on my knees
I just can't take no more
But Mr. DJ, please
I'm beggin' on my knees
I just can't take no more of
But Mr. DJ, please
I'm beggin' on my knees
I just can't take no more of Bil
But Mr. DJ, please
I'm beggin' on my knees
I just can't take no more of Billy
But Mr. DJ, please
I'm beggin' on my knees
I just can't take no more of Billy Ray

Bei der von mir im Prog benutzten Methode, nur vollständige Zeilen zu schreiben, fehlt die letzte, also "I just can't take no more of Billy Ray" und das ist bei allen Absätzen so.

Auch hab ich probiert, erst alles intern (wie oben gezeigt) zwischenzuspeichern und dann auszuwerten, aber auch das ist mißglückt.

Das Problem ist ganz einfach, dass die Texte bruchstückweise erscheinen, damit sie zur jeweiligen Stelle der Musik passen und ich einfach nicht weiss, wie ich sie sauber und vollständig zu einer ganzen Zeile zusammenfassen und speichern kann, bevor die nächste beginnt und alles vorherige löscht.

Ergänzung

Wie weitere Tests ergaben, sind Lyrics in Midi-Dateien absolut nie einheitlich integriert. Mit der ProcessMarkText-Version von Delphi.Narium werden bei einigen saubere Zeilenumbrüche erzeugt, die es bei der Original-Version von un4seen.com nicht gibt. Da klebt manches direkt aneinander.

Aber leider gibt es (je nach Midi-Datei) auch mit der Version von Delphi.Narium Probleme.

Ich häng hier mal noch einen Link zu einer Website mit Karaoke-Midi-Dateien an. Interessanterweise sind da auch die Texte nochmal komplett angegeben, was den Vergleich mit dem erlaubt, was durch das Prog angezeigt bzw. gespeichert wird.

http://www.karaokeden.com/karaoke
Angehängte Dateien
Dateityp: zip achy-breaky-heart.zip (29,3 KB, 10x aufgerufen)

Geändert von Delfiano (22. Nov 2020 um 01:04 Uhr) Grund: Link zu Website mit Karaoke-Midi-Dateien hinzugefügt
  Mit Zitat antworten Zitat
Delfiano
 
#9
  Alt 22. Nov 2020, 10:41
Gerade habe ich meine wahrscheinlich letzte Version 0.8b vom 21.11.2020 in den Startbeitrag hochgeladen. Der Vorschlag von Delphi.Narium ist dabei aber noch nicht enthalten. Die ZIP-Datei enthält nur die EXE-Datei und die geänderte Hauptunit.

Leider bin ich nicht so gut im Beschreiben. Weil es mir gesundheitlich nicht gut geht, ist das wahrscheinlich auch meine letzte Version überhaupt.

Gedanklich bin ich auch so unkonzentriert, dass mir nicht mal geglückt ist, dem Programm Parameter zu übergeben, weil es dann gleich Fehler wegen einem Listenindex von -1 gibt. Wahrscheinlich war es von Anfang an falsch, auf fremden Vorgaben aufzubauen, statt erst ein stabiles Grundgerüst zu erstellen und erst danach die anderen Sachen zu integrieren.

Wer möchte, kann, darf und sollte meine paar nützlichen Features gerne jederzeit ungefragt in eigene Projekt übernehmen oder dieses hier nach eigenen Vorstellungen weiterentwickeln oder völlig umbauen.

Was mir noch auffiel, obwohl es keine unmittelbare Auswirkungen hat:

Weil ich statt einem TLabel für die Lyrics ein TMemo nahm, wären vielleicht diese Korrekturen sinnvoll:

LyricSync:
//TLabel(user).Caption := ProcessMarkText(TLabel(user).Caption, Mark.text);
TMemo(user).Text := ProcessMarkText(TMemo(user).Text, Mark.text);

TextSync:
//TLabel(user).Caption := ProcessMarkText(TLabel(user).Caption, Mark.text);
TMemo(user).Text := ProcessMarkText(TMemo(user).Text, Mark.text);

EndSync:
//TLabel(user).Caption := '';
TMemo(user).Text := '';

Geändert von Delfiano (22. Nov 2020 um 10:45 Uhr) Grund: ergänzender Hinweis
  Mit Zitat antworten Zitat
Delphi.Narium

 
Delphi 7 Professional
 
#10
  Alt 22. Nov 2020, 11:12
Ausgehend vom textlichen Inhalt bei Midi-Dateien herrscht da wohl eher ein absolutes Chaos vor.

Hast Du eine Midi, bei der nix klapp und Du passt Deine Routine an, bis es klapp, dann klappt es für diese Midi. Nimmst Du nun eine andere und Du passt die Routine an ..., wird es bei der ersten Midi meist nicht mehr klappen.

Du brauchst "nur" eine Lösung, die meist in Ordnung ist.

Letzte Zeile:

Der Text wird immer im OnChange des lbLyrics (lbLyricsChange) übernommen. Dort wird immer der bisher vorhandene Text in den Gesamttext übernommen. Beim letzten (bisherigen) OnChange wird also alles bis zur vorletzten Zeile übernommen. Um die letzte Zeile zu bekommen, musst Du (höchstwahrscheinlich) das OnChange noch einmal "händisch" aufrufen, z. B. beim Beenden der Wiedergabe.

In EndSync setzt Du Caption auf ''. Dies dürfte das lbLyrics leeren, hier müsstest Du aber noch die letzte Zeile übernehmen die zwar schon in lbLyrics enthalten ist, deren Übernahme in die Ausgabe aber noch fehlt.

Ändere das bitte mal um z. B. so:
Delphi-Quellcode:
procedure EndSync(Handle : HSYNC; Stream : HSTREAM; data : DWORD; user : Pointer); stdcall;
begin
  // Hierdurch müsste das Ereignis lbLyricsChange zweimal ausgelöst werden.
  // Beim ersten mal kann dort die letzte Zeile übernommen werden.
  // Beim zweiten Mal wird lbLyrics gelehrt.
  // Da bei der bisherigen Logik immer die letzte Zeile fehlt, wäre die nun
  // fehlende letzte Zeile halt '--- Ende ---', das können wir verschmerzen ;-)
  TLabel(user).Caption := ProcessMarkText(TLabel(user).Caption, '\--- Ende ---');
  TLabel(user).Caption := '';
  // bzw.
  TMemo(user).Text := ProcessMarkText(TMemo(user).Text, '\--- Ende ---');
  TMemo(user).Text := '';
end; {EndSync}
Ist halt 'nen Versuch wert, habe es aber nicht getestet.

Bzgl. TLabel(user).Caption und TMemo(user).Text hat mich gewundert, dass die erste Variante überhaupt funktioniert hat
  Mit Zitat antworten Zitat
Antwort Antwort
Seite 1 von 3  1 23   

Themen-Optionen Thema durchsuchen
Thema durchsuchen:

Erweiterte Suche
Ansicht

Forumregeln

Es ist dir nicht erlaubt, neue Themen zu verfassen.
Es ist dir nicht erlaubt, auf Beiträge zu antworten.
Es ist dir nicht erlaubt, Anhänge hochzuladen.
Es ist dir nicht erlaubt, deine Beiträge zu bearbeiten.

BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus.
Trackbacks are an
Pingbacks are an
Refbacks are aus

Gehe zu:

Impressum · AGB · Datenschutz · Nach oben
Alle Zeitangaben in WEZ +1. Es ist jetzt 03:16 Uhr.
Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz