ADDCMD() - BEISPIELE
********************


FUNKTION
========

   varargs void AddCmd(mixed cmd, mixed func, mixed flag);


BEMERKUNGEN
===========

   Die hier aufgefuehrten Komplexbeispiele sind zum Verstaendnis gedacht,
   daher fuehren sie oft Alternativen auf. Die letzte Variante ist dann
   jeweils diejenige, welche am leichtesten das Problem loesen koennte.
   Falls die einem zu komplex ist, hilft vielleicht die vorletzte.


BEISPIELE
=========


Einfache Beispiele
------------------

1. SIMPEL: ganz simpel, beinahe wie add_action()

   AddCmd("befiehl","action_befehlen");
   // ...
   int action_befehlen(string str) {
     if(!str || !strlen(str))
       // Fehlermeldung, falls gar keine Funktion 1 dafuer zurueckgibt
       notify_fail("Was willst du befehlen?!\n");
     else {
       write("Du befiehlst \""+str+"\", und alle folgen!\n");
       say(TP->Name(WER)+" befiehlt \""+str+"\", und du folgst!\n");
       return 1;  // ERFOLG - Abbruch der Kommandoauswertung
     }
     return 0;    // MISSERFOLG - Fehlermeldung oben gesetzt
   }

2. SIMPEL .. weitere Beispiele

   AddCmd(({"kletter","klettere"}),"action_klettern" );
   AddCmd(({"renn","renne"}),#'action_rennen);

3. REGELN: eine komplexere Regel

   AddCmd("loesch|loesche|ersticke&feuer|brand|flammen&decke|wolldecke",
          "action_loeschen",
          "Was willst du loeschen?|Womit willst du loeschen?");

4. REGELN: mit Platzhaltern im Fehlerstring

   AddCmd("spring|springe|huepf|huepfe&von|vom&baum|ast|eiche",
          #'action_huepfe,
          "Willst du von etwas @verben?|Von wo willst du @verben?");

5. SCHLECHT: eine unscharfe Regel - sie sollten eine Ausnahme sein (!)

   AddCmd("kletter","fun_klettern",1);

6. FALSCH: sehr schlecht, kein Imperativ verwendet

   AddCmd("lese","eval_lesen");

   ausserdem sollte man fuer Lese-Syntaxen AddReadDetail benutzen

7. SIMPLE REGEL

   static int action_jump(string str);        // Prototype (wegen closure)
   // ...
   AddCmd("spring|springe|huepf|huepfe&von&baum|ast",#'action_jump,
          "Willst Du von etwas @verben?|Wovon willst Du @verben?");
   // ...
   static int action_jump(string str) {
     write(break_string("Du springst vom Baum und kommst hart auf!",78));
     this_player()->move((XXXROOM+"boden"), M_GO, 0,
                         "springt unelegant vom Baum","faellt vom Baum");
     this_player()->Defend(random(100),({DT_BLUDGEON}),([SP_RECURSIVE:1]),
                           this_object());
     return 1;
   }

8. SIMPLE REGEL OHNE METHODE

   mit Regeln kann man auch Aktivitaeten im Raum erlauben, ohne eine
   Funktion aufrufen zu muessen: die letzte Regel ist fuer Spieler
   unmoeglich zu erfuellen, die dazugehoerige Fehlermeldung wird mit
   dem ^ (write-Flag) versehen und entsprechend an den Spieler (und
   den Raum (hinter dem ^)) ausgegeben

   AddCmd("spring|springe&herunter|runter&\n\bimpossible",0,
          "Wohin oder wovon willst Du springen?|"
          "Du springst vom Baum und kommst hart auf.^"
          "@WER1 springt vom Baum und kommt hart auf.");


Komplexbeispiel: Regeln mit Fehlermeldungen
-------------------------------------------


Variante 1a, OHNE REGELN
~~~~~~~~~~~~~~~~~~~~~~~~

   Wenn man keine Regeln verwendet, muss man die Eingabe selbst
   auswerten.

   AddCmd(({"bohr","bohre"}),#'action_bohren);
   // ...
   private int action_bohren(string str) {
     string *tmp;
     notify_fail("Wo willst (etwas) Du bohren?\n");
     if(!str) return 0;       // Tja, keine Argumente ...
     tmp=explode(str," ");    // nach " " in Argument-Array aufspalten
     if((i=member(tmp,"loch"))>=0) { // aha, ab jetzt uebernehmen wir :)
       if((j=member(tmp[(i+1)..],"in"))<0 &&
          (j=member(tmp[(i+1)..],"durch"))<0)
         write("Willst Du das Loch in etwas bohren?\n");
       else if((i=member(tmp[(j+1)..],"boden"))<0 &&
               (i=member(tmp[(j+1)..],"erde"))<0)
         write("In/Durch was willst du das Loch bohren?\n");
       else {
         write("Du bohrst ein Loch in den Boden.\n");
         say(this_player()->Name(WER)+" bohrt ein Loch in den Boden.\n");
       }
       return 1;  // "bohre loch" war so eindeutig, dass nur diese
                  // Methode gemeint sein konnte, also brechen wir die
                  // weitere Auswertung auf jeden Fall ab (und geben
                  // eine write-Fehlermeldung)
     } // end if(..."loch")
     return 0;    // "bohre" allein muss nicht diese Methode meinen,
                  // also nur obige notify_fail()-Meldung, falls
                  // sich nach dieser Methode gar keine sonst
                  // angesprochen fuehlt
   } // end fun


Variante 1b, OHNE REGELN, Alternative
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

   prinzipiell koennte die Methode action_bohren() auch so aussehen,
   ist aber nicht ganz so flexibel:

   private int action_bohren(string str) {
     string unused;
     if(!str || (sprintf(str,"loch in erde%s", unused)!=1 &&
                 sprintf(str,"loch durch erde%s", unused)!=1 &&
                 sprintf(str,"loch in boden%s", unused)!=1 &&
                 sprintf(str,"loch durch boden%s", unused)!=1))
       notify_fail("Willst Du in irgendwas ein Loch bohren?\n");
     else {
       // ...
       return 1;
     }
     return 0;
   }


Variante 2, MIT REGEL
~~~~~~~~~~~~~~~~~~~~~

   das gleiche in etwa mal als einfache Regel

   AddCmd("bohr|bohre&loch&in|durch&erde|boden",#'action_bohren,
          "Was willst du (wohin) bohren?|"
          "Willst du das Loch in etwas bohren?|"
          "Wohin willst du das Loch bohren?");
   // ...
   private int action_bohren(string str, mixed *param) {
     write("Du bohrst ein Loch in den Boden.\n");
     say(this_player()->Name(WER)+" bohrt ein Loch in den Boden.\n");
     // ...
     return 1;
   }


Variante 3, MIT REGEL UND FEHLERMELDUNG
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

   und nun mit Fehlermeldungen mit Ersetzungen, so dass wir mehr auf
   die Eingaben des Spielers eingehen

   AddCmd("bohr|bohre&loch&in|durch&erde|boden",#'action_bohren,
          "Was willst du (wohin) @verben?|"
          "Willst du das Loch in etwas @verben?|"
          "@WER3 was willst du das Loch @verben?");
   // ...
   private int action_bohren(string str, mixed *param) // ...


Variante 4, MIT REGEL, FEHLERMELDUNG UND RETURN 1
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

   In Variante 1 kam sinnvollerweise sehr frueh der Abbruch mit
   "return 1;" und mit Ausgabe von write-Fehlermeldungen, das koennen
   wir auch direkt und ohne eigene Methode.

   AddCmd("bohr|bohre&loch&in|durch&erde|boden",#'action_bohren,
          "Was willst du (wohin) @verben?|"
          "Willst du das Loch in etwas @verben?^|"
          "@WER3 was willst du das Loch @verben?^");
    // ...
    private int action_bohren(string str, mixed *param) // ...


Variante 5, MIT REGEL, FEHLERMELDUNG, RETURN 1, OHNE FUN
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

   // und falls in action_bohren() nichts ausser Ausgaben passiert, koennen
   // wir uns die auch ganz sparen indem wir eine nichterfuellbare Regel
   // samt Fehlermeldung bauen
   AddCmd("bohr|bohre&loch&in|durch&erde|boden&\nimpossible",0,
          "Was willst du (wohin) @verben?|"
          "Willst du das Loch in etwas @verben?^|"
          "@WER3 was willst du das Loch @verben?^|"
          "Du @verbst ein Loch @WER3 den Boden.^@WER1 @verbt "
          "ein Loch @WER3 den Boden.");


Komplexbeispiel: Spezialregeln @PRESENT und @ID
-----------------------------------------------


Variante 1, OHNE REGELN
~~~~~~~~~~~~~~~~~~~~~~~

   Oft agieren Kommandos auf Objekten im Raum, diese muessen dabei per
   present() identifiziert werden: Beispiel ist ein Geldautomat
   (Hinweis: dieses Beispiel dient der Illustration, die
   Funktionalitaet an sich sollte man besser mit einem Container mit
   PreventInsert() erzeugen.)

   AddCmd(({"stopf","stopfe"}),#'action_stopf);
   // ...
   private int action_stopf(string str) {
     string was, unused;
     if(str && (sprintf("%s in automat%s", was, unused)==2 ||
                sprintf("%s in geldautomat%s", was, unused)==2 ||
                sprintf("%s in bankomat%s", was, unused)==2) {
       object o = present(was, this_player());
       if(o) {
         if(o->QueryProp(...)) {
           write(break_string(
             "Du stopfst "+o->name(WEN,1)+" in den Automaten.",78));
           say(...);
         } else {
           write(break_string(
             "Du versuchst "+o->name(WEN,1)+" in den Automaten zu stopfen, "
             "aber "+o->QueryPronoun(WER)+" passt nicht hinein.",78));
           say(...);
         }
       } else {
         write("Was willst du in den Automaten stopfen?\n");
         say(....);
       }
       return 1;
     }
     notify_fail("Was willst du wohin stecken?\n");
     return 0;
   }


Variante 2, MIT REGEL
~~~~~~~~~~~~~~~~~~~~~

   einerseits koennen wir auf diese Weise das Finden von Objekten in
   Inv und Env in die AddCmd()-Regel integrieren und uns andererseits
   das Aufzaehlen aller IDs des Automaten ersparen.

   Wie immer werden die gefundenen Matches als Parameterarray an die
   angegebene Methode uebergeben. Das Array enthaelt die mit @PRESENT
   und @ID gefundenen Treffer praktischerweise als Objekte.

   AddCmd("steck|stecke&@PRESENT&in&@ID",#'action_stopf,
          "Was willst du wohin stopfen?|"
          "Willst du @WEN2 in etwas stopfen?|"
          "Wohinein willst du @WEN2 stopfen?");
   // ...
   private int action_stopf(string str, mixed *param) {
     if(param[0]->QueryProp(...)) {
       write(break_string(
         "Du stopfst "+param[0]->name(WEN,1)+" in den Automaten.",78));
       say(...);
     } else {
       write(break_string(
         "Du versuchst "+param[0]->name(WEN,1)+" in den Automaten zu "
         "stopfen, aber "+param[0]->QueryPronoun(WER)+" passt nicht "
         "hinein.",78));
       say(...);
     }
     return 1;
   }


Komplexbeispiel: gleiches Verb, mehrere Regeln
----------------------------------------------

   Das Problem mehrerer Regeln fuer ein Kommandoverb besteht darin,
   dass letztlich nur eine der Fehlermeldungen zum Tragen kommt -
   welche genau, ist etwas vage. Dabei kann man sich auf eines
   verlassen: juengere AddCmd werden zuerst ausgewertet. Wenn sich das
   aendert, tretet euren EM.


Problem 1: Mehrere Regeln weil mehrere Zwecke
---------------------------------------------


Variante 1 - GLEICHLAUTENDE FEHLERMELDUNG
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

   Fuer alles wird eine identische Fehlermeldung gesetzt, das ist
   natuerlich nicht sehr flexibel oder schoen oder man versucht eine
   bessere Regel zu schaffen, was hier durch die Moeglichkeit von zwei
   oder drei Parameter unmoeglich ist

   AddCmd("kriech|krieche&hoch|hinauf|hinaus|heraus|raus",#'result_kriech,
          "Wohin willst Du kriechen?");
   AddCmd("kriech|krieche&nach&oben",#'result_kriech,
          "Wohin willst Du kriechen??|Wohin willst Du kriechen?");
   AddCmd("kriech|krieche&aus&loch|grube|falle",#'result_kriech);
          "Wohin willst Du kriechen?|Wohin willst Du kriechen?");


Variante 2 - EIGENE AUSWERTUNG
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

   Statt der Verwendung mehrerer aehnlicher AddCmd() bietet sich die
   eigene Weiterauswertung an, was durch die Uebergabe der
   getriggerten Argumente erleichtert wird.

   AddCmd("kriech|krieche&hoch|hinauf|hinaus|heraus|raus|aus|nach",
          #'result_kriech,
          "Wohin willst Du kriechen?");
   // ...
   private int result_kriech(string str, mixed *extra) {
     if(member(extra,"aus")>=0 &&
        !sizeof(({str}),"*.\\<(hoehle|grube|falle)\\>.*"))
       notify_fail("Woraus willst Du kriechen?\n");
     else if(member(extra,"nach")>=0 && strstr(str,"oben")<0)
       notify_fail("In welche Richtung willst Du kriechen?\n");
     else if(this_player()->QueryAttribute(A_DEX)>10 ||
             member(holding_root,this_player())) {
       write("Du kriechst mit Muehe heraus.\n");
       this_player()->move((XXXROOM+"draussen"), M_GO, 0,
                           "kriecht mit Muehe aus der Grube",
                           "kriecht aus einer Grube");
       return 1;
     } else
       write("Du bist zu ungeschickt, halt Dich irgendwo fest.\n");
       return 1;
     }
     return 0;
   }


Problem 2: mehrere Regeln aufgrund von optionalen Parametern
------------------------------------------------------------

   Manchmal will man optionale Parameter erlauben, die aber eine
   Wirkung zeigen sollen. Hierbei ist die Reihenfolge der AddCmd()-
   Anweisungen und ggf. deren Aufbau entscheidend.

   AddCmd("schlag|schlage&@ID&hart",#'action_schlag_hart,
          "Was oder wen willst du @verben?|"
          "Wie willst du @WEN2 schlagen?");
   AddCmd("schlag|schlage&@ID",#'action_schlag,
          "Was oder wen willst du @verben?");

   Da juengere AddCmd aelteren vorgehen, wird die komplexere Regel samt
   ihrer Fehlermeldung nie ausgewertet, da ein "schlag ball hart" auch
   die zweite Regel triggert.

   Anders herum:

   AddCmd("schlag|schlage&@ID",#'action_schlag,
          "Was oder wen willst du @verben?");
   AddCmd("schlag|schlage&@ID&hart",#'action_schlag_hart,
          "Was oder wen willst du @verben?|"
          "Wie willst du @WEN2 schlagen?");

   Jetzt wird die komplexere Regel zuerst ueberprueft und triggert
   auch die richtige Funktion.
   Leider kommt die Fehlermeldung nie zum Tragen, denn was durch Regel 2
   durchfaellt, triggert entweder Regel 1 oder faellt auch durch Regel 1
   durch und ueberschreibt dabei die Meldung.

   AddCmd("schlag|schlage&@ID",#'action_schlag,
          "Was oder wen willst du wie @verben?");
   AddCmd("schlag|schlage&@ID&hart",#'action_schlag_hart);

   Das ist zwar auch nur fast perfekt, besser wird es aber nicht.

Letzte Aenderung: 20.11.2019, Arathorn
