Doku fuer Ebenen-SVs

Vorab eingebaut, damit Magier schonmal lesen koennen.

Change-Id: If2b30f52ead280131acfd8c0efc065195d7273c6
diff --git a/doc/beispiele/ebenen/supervisor-thing.c b/doc/beispiele/ebenen/supervisor-thing.c
new file mode 100644
index 0000000..dc0f0f3
--- /dev/null
+++ b/doc/beispiele/ebenen/supervisor-thing.c
@@ -0,0 +1,34 @@
+#pragma strong_types,rtt_checks
+
+inherit "/std/thing";
+
+// Standard-Ebenen-Supervisor erben, Variablen nosave, die sollen hier nicht
+// gespeichert werden, falls jemand save_object() ruft.
+nosave variables inherit "/std/channel_supervisor";
+
+#include <properties.h>
+#include <language.h>
+
+protected void create()
+{
+  ::create();
+  SetProp(P_SHORT,"Eine kleine Knolle namens Lilly.");
+  SetProp(P_LONG,"Die Knolle ist bestimmt magisch.\n");
+  AddId("lilly");
+  SetProp(P_NAME, "Lilly");
+  SetProp(P_GENDER, FEMALE);
+  // Das systemweite Init-File einlesen und die Zugriffsrechte fuer die Ebenen
+  // merken, in denen dieses Objekt SV ist.
+  ch_read_init_file();
+}
+
+public varargs string name(int casus,int demon)
+{
+  return thing::name(casus, demon);
+}
+
+public varargs string Name(int casus, int demon)
+{
+  return thing::Name(casus, demon);
+}
+
diff --git a/doc/beispiele/ebenen/supervisor.c b/doc/beispiele/ebenen/supervisor.c
new file mode 100644
index 0000000..475df8a
--- /dev/null
+++ b/doc/beispiele/ebenen/supervisor.c
@@ -0,0 +1,17 @@
+#pragma strong_types,rtt_checks
+
+inherit "/std/channel_supervisor";
+
+protected void create()
+{
+  ::create();
+  // Namen setzen, der auf den Ebenen genannt werden soll.
+  ch_set_sv_name("Wotan");
+  // Das systemweite Init-File einlesen und die Zugriffsrechte fuer die Ebenen
+  // merken, in denen dieses Objekt SV ist.
+  ch_read_init_file();
+  // Alternativ kann ein eigenes File im gleichen Format genutzt werden. (ggf.
+  // ist dann eine eUID noetig!)
+  // ch_read_init_file("/path/to/custom/initfile");
+}
+
diff --git a/doc/beispiele/ebenen/supervisor.txt b/doc/beispiele/ebenen/supervisor.txt
new file mode 100644
index 0000000..7c8085f
--- /dev/null
+++ b/doc/beispiele/ebenen/supervisor.txt
@@ -0,0 +1,84 @@
+Supervisoren fuer Ebenen
+************************
+
+Die Supervisoren von Ebenen werden vom CHANNELD gefragt, ob ein Objekt eine
+bestimmte Aktion auf einer bestimmten Ebenen tun darf, z.B. Betreten einer
+Ebene oder Senden auf einer Ebene. Die SVs sind ebenfalls immer Zuhoerer auf
+der Ebene.
+
+Wird ein SV zerstoert, wird im Normalfall ein neuer SV aus dem Kreise der
+aktuellen Zuhoerer bestimmt, ueblicherweise das am laengsten zuhoerende
+Objekt.
+
+Betritt ein Objekt, was eine Ebene erschaffen hat (der erste Supervisor), eine
+Ebene nach Verlassen erneut, uebernimmt es automatisch die SV-Rolle wieder,
+sofern das Objekt *kein* Spieler oder Magier ist.
+
+
+Erstellen von Supervisoren
+==========================
+
+Im einfachsten Fall wird /std/channel_supervisor geerbt, ein Name konfiguriert
+und das systemweite Init-File fuer Ebenen eingelesen. Anschliessend erhaelt
+man das Standardverhalten, was im Init-File konfiguriert ist. Ein Beispiel
+hierfuer findet sich /doc/beispiele/ebenen/supervisor.c.
+
+Man kann ein bestehendes Objekt zu einem SV machen, indem man
+/std/channel_supervisor zusaetzlich erbt. In diesem Fall muss man ggf. auf
+name() und Name() aufpassen, sofern das Objekt auch /std/thing/description
+oder aehnliche erbt und gezielt die von dort geerbten lfuns aufrufen. Ein
+Beispiel hierfuer steht in /doc/beispiele/ebenen/supervisor-thing.c.
+
+Will man einen SV fuer eine Ebene konfigurieren, die keine Standardebene ist,
+kann man ein eigenes Init-File einlesen (Format s. u.). In diesem Fall ist
+aber zu beachten, dass man auch selber Sorge dafuer tragen muss, dass die
+Ebene erstellt wird (CHANNELD->new()).
+
+Will man einen SV mit einem gaenzlich anderen Verhalten bauen, so ist auch das
+moeglich, indem man die lfun
+  public int ch_check_access(string ch, object user, string cmd)
+ueberschreibt. Diese wird vom CHANNELD im SV gerufen. Gibt sie eine 1 zurueck,
+darf das Objekt <user> auf der Ebene <ch> die Aktion <cmd> ausfuehren.
+Anderendfalls mus 0 zurueckgeben werden.
+<cmd> ist hierbei eine der in /p/daemon/channel.h definierten Kommandos.
+
+Die Ebene <ch> wird immer kleingeschrieben uebergeben. Auch wenn der Name
+Spielern case-sensitiv angezeigt wird, kann es keine zwei Ebenen geben,
+welche sich nur in Gross-/Kleinschreibung unterscheiden und intern erfolgt
+die Verwaltung *immer* kleingeschrieben - dies gilt auch fuer die
+Rechtepruefung.
+
+
+Eigenes Init-File
+-----------------
+
+Das Init-File hat folgenden Aufbau:
+<name>:<recv>:<send>:<accessflags>:<channelflags>:<desc>:<supervisor>
+z.B.
+abgilde: 0: 0: 0: 0:Fuer Abenteurer:/gilden/abenteurer
+
+Fuer SVs sind nur die Felder <name>, <recv>, <send> und <accessflags>
+relevant. Das vordefinierte ch_check_access() entscheidet wie folgt anhand der
+Angaben:
+
+Verlassen (C_LEAVE) ist immer erlaubt. Die anderen Aktionen sind in zwei
+Gruppen eingeteilt:
+  1) RECV. Die Aktionen dieser Gruppe sind Suchen (C_FIND), Auflisten
+           (C_LIST) und Betreten (C_JOIN).
+  2) SEND. Die Aktion dieser Gruppe ist zur Zeit nur Senden (C_SEND).
+
+Aktionen werden zugelassen, wenn Spieler/MagierLevel groesser ist als die
+fuer die jeweilige Aktionsgruppe RECV oder SEND festgelegte Stufe.
+
+Handelt es sich um eine Magierebene (<accessflags> enthaelt das Flag
+CH_ACCESS_WIZARD), muss die Magierstufe des Spielers groesser sein als die
+Mindeststufe der Ebene. Ansonsten wird gegen den Spielerlevel geprueft.
+Enthaelt <accessflags> das Flag CH_ACCESS_NOGUEST, darf die Ebene nicht von
+Gaesten benutzt werden.
+
+Wenn RECV_LVL oder SEND_LVL auf -1 gesetzt ist, sind die Aktionen der
+jeweiligen Gruppen komplett geblockt.
+
+Bemerkung: Im Initfile sollten SVs nur Blueprints verwendet werden - aber SVs
+koennen im Allgemeinen auch Clones sein!
+