Beiträge von Professor Chaos

    Heya, hier ein Spaßexperiment. Und Wissensquiz: Wie heißt dieses Stück?


    Getestet unter FreeProfan32, XProfan 12.1 und Windows 7. Compiliert besser! Ich weiß leider nicht, wie es unter 3 Ghz läuft. Wenn es mal ruckelt, geht in ein anderes Fenster (Graphen werden solange nicht neugezeichnet). Unter FreeProfan64 funktioniert es irgendwie nicht (waveOutPrepareHeader gibt MMSYSERR_INVALPARAM zurück, sodass alles stumm ist).


    Erstmal die SYNTH.INC:


    Und dann das Hauptprogramm:

    Danke an alle! :)


    Bugfixes:

    • Nach dem Game Over durfte man in einem seltenen Fall ewig weiterspielen.
    • Die Explosion eines Gegners kam manchmal nicht. Der darauffolgende Gegner auch nicht.
    • Das Punktesystem wurde erweitert. Für jedes einzelne Raumschiff gibt es 5 Punkte (nach wie vor). Schießt man alle 6 Gegner in einer Formation ab (nicht einfach nur den letzten sichtbaren, wie bisher...), gibt es statt 5 gleich 50 Punkte. Und in der letzten Phase, wo die Felswände aufhören zu scrollen und die Gegner schneller werden, gibt's sogar doppelt/dreifach/... soviel.
    • Die Raumschiffe, die rückwärts fliegen, haben jetzt auch Düsen. ;)


    Ist sogar kürzer geworden. :D 4020 Bytes...


    So, hab' nun auch noch etwas in 4096 (genauer bisher: 4037) Bytes stopfen können: Ein Shoot 'em up mit "Arial-Grafik", ein paar Gegnerformationen, halbwegs algorithmischem Sound und keinerlei Netzwerkzugriff. Am ehesten angelehnt wohl an die Arcade- und C64-Spiele Anfang bis Mitte der 80er.


    Ziel des Spiels:

    • Highscore überbieten und gut is'.


    Steuerung:

    • Pfeiltasten: Raumschiff bewegen
    • STRG: schießen (Leertaste ging nicht, weil meine Tastatur bestimmte 3-Tasten-Kombinationen überhaupt nicht annimmt)
    • F10: Pause (solange das Fenster den Fokus hat)
    • Alt+F4: aufgeben (sowie den einzigen Highscore aktualisieren)


    Getestet hab ich's unter Vista Home Premium 32 und Windows 7 64, wo es sogar interpretiert (auch mit der WProfan.exe) gut läuft. Kompiliert läuft es aber auf jeden Fall besser, sogar auf meinem alten 1,8-Ghz-Windows-Me-Rechner (der sich immer noch nicht entschieden hat, ob und wann er explodieren will)...


    [Blockierte Grafik: http://s24.postimg.org/v0qyoeb4h/Screen_28_03_2013_08_Uhr_51_44_Sek.jpg]


    Und hier der wunderschöne Quellcode (lesbar werde ich ihn wohl am 31. März posten):


    Noch 'ne alte Spielerei, um XProfan's Musikalität zu demonstrieren. :D;)
    Diesmal, wie man MIDI-Dateien ohne MCISend$ abspielt, sondern selber parst und die richtigen API-Aufrufe zur richtigen Zeit tätigt.


    Download als .exe-Datei: http://www.profchaos.mynetcolo…oding/MIDI-Visualizer.zip


    Features:
    + Zeigt alle Tasten an, die gerade gedrückt sind, mit ihren jeweiligen Lautstärken (deren Verhältnis zueinander) -> Gelbanteil auf den individuellen Tasten.
    + Zeigt den Namen des Instruments an.
    + Zeigt die Tonhohenänderung innerhalb einer Note ("Pitch Bend") an -> linke Ziffer (0-16383).
    + Zeigt die Lautstärkenänderung innerhalb einer Note ("Expression") an -> rechte Ziffer (0-127).
    + Einzelne MIDI-Kanäle können durch Mausklick (in die entsprechende Zeile) sofort ein- bzw. ausgeschaltet werden.
    + Freie Auswahl des MIDI-Geräts (OnBoard-Soundkarte mit Verzögerung, Wavetable-Soundkarte ohne Verzögerung, Keyboard etc.)


    Beschränkungen:
    - Bildschirmauflösung sollte mindestens 1024x768 sein.
    - RMI-Dateien funktionieren nicht (man müsste für sowas aber auch nur die ersten 20 Bytes der Datei überspringen).
    - Ich habe nicht die leiseste Ahnung, wieviel Mhz das Ding wirklich braucht.


    Als funktionierend getestet mit:
    + XProfan 9
    + FreeProfan32 (heute runtergeladen)
    + Windows Me, 1.8 Ghz
    + Windows Vista Home Premium 32 Bit, 2.8 Ghz
    + bisher noch jeder MID-Datei, die ich kenne! Nur halt keiner RMI-Datei.


    Der Code könnte zugegeben besser dokumentiert und lesbarer sein. Ich hab zwar gerade nochmal drübergesehen, aber in den letzten 5 Jahren nichts weiter getan. :oops:
    Das Ganze lässt sich bestimmt komplett auf den PLAY-Befehl umstellen - ohne direkte API-Aufrufe! - (Abstriche: vor allem Lautstärkenverhältnisse) und auf 4k kürzen (Abstriche: vor allem Ästhetik). Könnte ich mal was draus machen... bei Interesse. Aber nicht für den 4k-Wettbewerb. Für sowas würde ich eher was neues schreiben. Wenn ich das zeitlich hinkriege. Aber egal, ich schweife ab, hier der Quelltext zum Selber-sofort-kompilieren und -starten:


    Hab keine Probleme mehr gefunden! Zur Feier des Tages zeigt die FreeProfan32-Popband jetzt noch, was sie kann :cool::D
    (Hoffentlich stimmt die Qualität aber auch auf euren Soundkarten)


    Viel besser! :)
    Neulich habe ich mein 'Beethoven-Demo' noch erweitert (fetziger; werd ich wohl morgen hochladen), und die Ergebnisse der PolyMusic.inc und des Music-Befehls nähern sich sehr an.
    Zwei wesentliche Bugs höre ich aber noch raus:


    • Die Töne werden weit weniger zuverlässig gestoppt, wenn man zwischendurch die Oktave wechselt:

      Code
      cls
      music "I64 L2 ML C C D C >C< C >D< C <C> C <D> P"


    • Das Pause-Makro pausiert nicht nur die Noten im eigenen Kanal, sondern auch die in anderen Kanälen (was nicht im Sinne eines Notenblatts ist):

      Code
      cls
      var a$="I37 L16 [32 <C>C]"
      music a$,"K9 O3 L16 [4 C F#F#F#D F#F#C C F#C F#D F#F#F#]" ' richtig, der banale Bass läuft komplett durch
      music a$,"K9 O3 L16 [4 C P P P D P P C C P C P D P P P ]" ' falsch, Bass wird geradezu erstickt



    Gruß, Sebastian

    Fantastisch! Sind Bugreports schon möglich? :D
    Falls ja (ich weiß schließlich, du hast geschrieben, "experimentell" und nicht für X2.1), habe ich leider gleich mehrere davon:

    • Töne mit Halbtonverschiebungen (- + #) werden nie gestoppt:
      Code
      music "L4 I80 C D E F G- G G+ A A# H > C1"
    • Legatonoten werden nie gestoppt, und soweit ich höre, werden die "MN"- und "ML"-Makros eine Note zu früh angewandt:
      Code
      music "L8 I80 MS CDEFGAH > MN CDEFGAH > ML CDEFGAH > C1 P"
    • Das letzte Makro wird nie angenommen:
      Code
      music "C2 E2 G2 P2" ' alle drei Noten hörbar
      music "C2 E2 G2" ' nur zwei Noten hörbar

    Gruß, Sebastian

    Ob experimentiell oder nicht, da kann ich nicht testlos zusehen... :)


    Ich hab's auf Windows Vista Home Premium 32-Bit probiert.


    Ein paar Fehler:

    • Wird eine Note mit einer Oktave zwischen 7 und 10 angeschlagen (was bei MIDI gültig und auch schon mal nötig ist!), stürzen FreeProfan32 Interpreter und Runtime ab.
    • Ohne * stürzen FreeProfan32 Interpreter und Runtime ab.
    • Die FreeProfan32 Runtime kennt die Systemvariable &hmusic nicht. %playing aber schon.


    Und eine Idee fürs 'Final':

    • Gibt es eigentlich noch QBasic-Umsteiger? Bei QBasic musste man nämlich "MB" schreiben (B = Background), damit die Musik im Hintergrund läuft, vielleicht kann man das auch in Profan so übernehmen.


    Übrigens, mein Testcode:

    Code
    var a$="O4 CCCC > CCCC > CCCC > CCCC"
    if messagebox("Im Vordergrund?","Frage",36)=6
      music a$
    else
      music "*"+a$
      while 1
        sleep 50
        print %playing,&hmusic
      endwhile
    endif

    Gruß, Sebastian

    Eine 2 Jahre alte Spielerei zu einem (vielleicht zurecht) seltenen Programmierthema... ;)


    Genauer gesagt:
    Ein Nachbau des in XProfan eingebauten Befehls "Music" - der mit der Makrosprache aus dem alten MS-DOS-QBasic.
    Das besondere daran ist, dass die Musik mehrstimmig sein darf und das Hauptprogramm während der Musikwiedergabe noch etwas anderes machen kann.
    Konzipiert wurde das ganze als Include für XProfan 9 (und neuer).


    Eine Demo dazu:



    Die wichtigen Befehle und Funktionen sind:

    • polymusic_start S[,S[,S]...]
      Initialisiert ein mehrstimmiges Musikstück. Für jede Stimme in diesem Stück übergibt man einen String. Das Format eines solchen Strings ist kompatibel mit dem XProfan-Befehl Music. Siehe XProfan-Hilfe.
    • polymusic_run
      Muss oft und regelmäßig - z.B. alle 20 Millisekunden - aufgerufen werden, damit die Musik kommt.
    • polymusic_stop
      Stoppt alle laufenden Noten und gibt sämtliche Ressourcen frei.
    • polymusic_playing()
      Gibt 1 zurück, solange das Stück läuft, ansonsten 0.


    Ach ja, und natürlich die PolyMusic.inc selbst:


    Vista Home Premium, Service Pack 2, 32 Bit

    (Identisch mit Volkmars Vista-32.)

    Bis Windows XP kann man in der Systemsteuerung ein bevorzugtes Gerät zur MIDI-Wiedergabe (z.B. Soundkarte, Keyboard) auswählen. XProfan berücksichtigt diese auch! :)
    Ab Windows Vista kann ich diese Einstellung leider nicht finden... :mad:


    Ich habe die "Vorrichtung zur Erregung öffentlichen Ärgernisses mittels MIDI" :lol: mit folgenden Geräten getestet:


    Creative S/W Synth: Jeder Ton kommt sofort.
    SB Live! MIDI Synth: Jeder Ton kommt sofort.
    Bontempi PM 683: Jeder Ton kommt sofort, wird aber nie angehalten.
    Microsoft GS Wavetable Synth: Den haben anscheinend viele Windows-User. ;) Wenn ich die Leertaste drücke, kommt der nächste Ton um eine halbe Sekunde verzögert (das ist seltsam!). Jeder andere kommt um eine Zehntelsekunde (das passiert in Nicht-XProfan-Programmen auch).

    Trotz XProfan-Forum will ich dich noch schnell was fragen:

    Zitat von Frabbing;882621

    Statt JB besser JNE

    Was ist denn da der Vorteil (jetzt speziell in so einer aufwärts zählenden Schleife)?
    Zumindest bei Anfängern dürfte JB (oder generell der "<"-Operator) sicherer als JNE (<>) sein.

    Nicht ganz. Dein Code ist jetzt so aufgebaut, dass hinter CMP ecx, der Offset des letzten Array-Elements stehen muss, nicht aber die Anzahl der Elemente!


    In deiner Anfangszeit mit x86-Assembler kannst du ja mal versuchen, den Weg, den der Prozessor mit dem Code geht, 'gedanklich' nachzustellen, z.B. so:

    Verspätet ist übrigens auch meine Antwort auf deine Frage 3 ganz oben... :lol:
    Du wolltest wissen, ob das geht:

    Code
    @Call(Addr(ASMCode#))

    Frank hat schon geantwortet, aber: Wenn du sowas doch mal ohne XPIA machen wolltest (sei es auch nur probehalber), dann musst du das Addr unbedingt weglassen:

    Code
    @Call(ASMCode#)

    Unter XProfan X2 könnte das natürlich anders sein.


    Witzigerweise funktioniert ein Ausdruck, der mit einem String-Literal beginnt, aber sehr wohl; auch ab XProfan 8:

    Code
    declare a$
    
    
    a$="Hello, world."
    def MessageBoxA(4) !"USER32","MessageBoxA"
    MessageBoxA(0,""+a$,0,0)
    
    
    a$="Goodbye, world."
    external("USER32","MessageBoxA",0,""+a$,0,0)

    Vor wenigen Jahren war ich technisch rückständig... Die TV-Karte und das dazugehörige Programm waren aus den 90ern, gingen bei Aufnahme von mehr als 320x240 Pixeln in die Knie und hörten bei 2 GB (ca. 24 Minuten) komplett auf.


    Andere Leute konnten bereits längere Sendungen größer aufzeichnen; sogar dann, wenn sie nicht zuhause waren. Konnte ich auch, aber nur durch Fernsteuerung des TV-Programms:



    Hat prima geklappt, vor allem, wenn sich der jeweilige Fernsehsender exakt an meine Eingaben und Hardwarebeschränkungen gehalten, man selber keine Anzeigeeinstellungen verändert und den Satellitenreceiver während des Staubsaugens nicht aus der Steckdose geschmissen hat. (Der zweite Punkt war immer zutreffend!)

    Im Sommer/Herbst 2001 hatte ich ein Vier-Gewinnt-Spiel mit Computergegner und ein paar minimalistischen Animationen geschrieben.
    Die KI war mir wohl nur 'n bißchen zu langsam (Taktfrequenz 300 Mhz), jedenfalls wollte ich die in einen eigenen Thread (naja, oder Prozess, je nach Kenntnisstand) auslagern. Das Hauptprogramm hätte diesem eine Bereichsvariable mit dem aktuellen Stand (7x6-Spielfeld) senden, währenddessen die besagten Animationen ablaufen lassen und auf die Antwort (in welche Spalte...?) warten können.


    Hier mein Ansatz in einem Testprogramm, welches mich vom Gegenteil überzeugt hatte:



    Der Code ist heute Müll, weil das zweite Programm zu lange zum Starten braucht (vielleicht war das unter Windows 98 anders), sodass das erste Programm in eine Endlosschleife kommt (Alt+F4 funktioniert aber).
    Und selbst wenn nicht, würden aktuelle XProfan-Versionen abbrechen, weil der Bereich b# so groß wie a# sein muss.
    Und selbst wenn nicht, wäre das Verfahren an sich immer noch Müll, weil jeder Prozess seinen eigenen Speicherraum hat und einem Prozess auf diese Art keine Bereiche übergeben kann. ;)


    Und jetzt, wo ich das alles schreibe, fällt mir ein, ich hätte die Parameter einfach über die Kommandozeile übergeben können... :kopfschüttel: :wand: