diff --git a/std/items/fishing/angel.c b/std/items/fishing/angel.c
new file mode 100644
index 0000000..1b5709f
--- /dev/null
+++ b/std/items/fishing/angel.c
@@ -0,0 +1,510 @@
+/*
+  Zusammenfassung Bedingungen:
+  - Angel auswerfen
+      - Haken muss dran sein
+      - Haken muss Koeder haben
+      - darf nur ein Haken drin sein, sonst nix, und genau ein Haken
+      - Angel im Inventar
+      - Angel darf nicht schon ausgeworfen sein
+      - passendes Gewaesser im Raum
+      - Move-Hook muss korrekt registrierbar sein
+  - Angel einholen
+      - Angel-Callout muss ueberhaupt erstmal laufen
+  - Waehrend des Angelns
+      - bewegen beendet das Angeln
+      - Ausloggen beendet das Angeln
+      - Ende beendet das Angeln
+      - nichts rausnehmen
+      - nichts reintun, ausser Fisch am Ende der Wartezeit
+      - Langbeschreibung zeigt "ausgeworfen", Koeder und gefangenen Fisch an
+  - Fisch fangen (call_out zuende)
+      - Gewaesser passt (immer noch)
+      - Fisch passt noch in die Angel rein
+  - Haken dranhaengen
+      - Haken im Inv
+      - Haken muss "echter" Angelhaken sein
+      - Angel im Inv
+      - Koeder am Haken
+      - noch kein anderer Koeder dran
+      - Angel ist nicht ausgeworfen
+  - generell
+      - nur Haken dranstecken, nix anderes reintun
+      - reintun nur mit Syntax "haenge" etc. (damit sind Fische aussen vor,
+        weil die Syntax auf Haken prueft)
+        (ggf. ist dann das PreventInsert() zu vereinfachen)
+ */
+
+#pragma strong_types, save_types, rtt_checks
+#pragma no_clone, no_shadow
+
+inherit "/std/container";
+inherit "/std/hook_consumer";
+
+#include <new_skills.h>
+#include <language.h>
+#include <properties.h>
+#include <moving.h>
+#include <hook.h>
+#include <wizlevels.h>
+#include <items/fishing/fishing.h>
+#include <items/fishing/aquarium.h>
+
+#define TP this_player()
+#define ME this_object()
+#define BS(x) break_string(x, 78)
+
+#define MIN_DELAY       80   // Mindestdelay bis Fisch beisst!
+#define STD_DELAY_PLUS  60   //  +/- 60 sekunden Tolerant
+#define MAX_FISH_BONUS  60   // max. Wartezeitverkuerzung durch P_FISH
+#define WRONGWATER      60   // 1-2 min, falls Angel nicht geeignet
+#define WRONGWORM       60   // 1-2 min, falls Koeder nicht geeignet
+
+#define KOEDER_LOST     10
+// Verlustwahrsch. fuer Koeder falls Fisch zu schwer
+
+private object room, current_user;
+private int active, actime;
+private mapping aquarium = STDFISHLIST;
+
+nomask varargs void StopFishing(string msg_me, string msg_room);
+int IsFishing();
+
+protected void create() {
+  ::create();
+  
+  SetProp(P_SHORT, "Eine Angel");
+  SetProp(P_LONG, "Eine nagelneue Angel.\n");
+  SetProp(P_NAME, "Angel");
+  AddId(({"angel", "rute", ANGEL_ID}));
+
+  SetProp(P_GENDER, FEMALE);
+  SetProp(P_MATERIAL,([MAT_MISC_WOOD:90,MAT_WOOL:10]));
+  SetProp(P_TRANSPARENT,1);
+  SetProp(P_WEIGHT,200);
+  SetProp(P_MAX_WEIGHT, 10000);
+  SetProp(P_WATER, W_USER);     //muss (mehrere) Flags gesetzt haben!
+  SetProp(P_SOURCE_PREPOSITION, "von");
+  SetProp(P_NR_HANDS, 2); 
+
+  Set(P_NODROP, function string () {
+    return (IsFishing()?"Du solltest die Angel nicht fallenlassen, solange "
+      "Du angelst.\n":0);
+  }, F_QUERY_METHOD);
+
+  AddCmd(({"angel","angle"}),"angel");
+  AddCmd("hole|hol&@ID&ein", "stopit", "Was willst Du (ein)holen?|"
+    "Willst Du @WEN2 einholen?");
+  AddCmd("haenge|haeng|befestige&@PRESENT&@ID", "move_in",
+    "Was willst Du woran @verben?|"
+    "Woran willst Du @WEN2 denn @verben?");
+
+  AddCmd("atell","tell_stat");
+  AddCmd("angeltest","qangel");
+}
+ 
+protected void create_super() {
+  set_next_reset(-1);
+}
+     
+static int stopit(string str) {
+  if( find_call_out("do_angel")==-1 )
+    tell_object(TP, "Du angelst nicht!\nTP, ");
+  else 
+    StopFishing();
+  return 1;
+}
+
+varargs string long(int mode) {
+  string descr = QueryProp(P_LONG);
+  if(!QueryProp(P_TRANSPARENT)) 
+    return descr;
+
+  if ( find_call_out("do_angel")!=-1 )
+    descr += capitalize(QueryPronoun(WER))  + " ist ausgeworfen.\n";
+
+  object *inv = all_inventory(ME);
+  string inv_descr = make_invlist(TP, inv);
+  if ( inv_descr != "" )
+    descr += "An "+QueryPronoun(WEM) + " haeng"+(sizeof(inv)>1?"en":"t")+
+    ":\n" + inv_descr;
+  
+  return descr;
+}
+
+/*int tell_stat()
+{
+  int n;
+  
+  if(!IS_WIZARD(TP))
+    return 0;
+  if(!active){ 
+    write("Du angelst nicht\n"); return 1; 
+  }
+  n=find_call_out("do_angel");
+  if(active)
+    write(
+     "----------------------------------------------------------------------\n"
+     +"Der Fisch beisst in "+n+" sec!\n"
+     +"Bestandswert des Raumes: "+room->QueryProp(P_FISH)
+     +" = "+(room->QueryProp(P_FISH)+100)+"%.\n"
+     +"Bestandswert des Koeders: "+koeder->QueryProp(P_FISH)
+     +" = "+(100+koeder->QueryProp(P_FISH))+"%.\n"
+     +"Gesamt:"+bestand+" = "+(bestand+100)+"%.\n");
+  if(!(QueryProp(P_WATER)&room->QueryProp(P_WATER)))
+    write("Die Angel passt nicht zum Gewaessertypen.\n");
+  else
+    write("Die Angel passt zum Gewaessertypen.\n");
+  if(!(room->QueryProp(P_WATER)&koeder->QueryProp(P_WATER)))
+    write("Der Koeder passt nicht zum Gewaessertypen.\n");
+  else
+    write("Der Koeder passt zum Gewaessertypen.\n");
+  write(" => Delay="+delay+".\n"
+    +"----------------------------------------------------------------------\n"
+);
+  return 1;
+}*/
+
+static int move_in(string str, mixed *param) {
+  object haken = param[0];
+  // param[1] sind wir selbst, daher ab hier ME verwendet.
+
+  if ( find_call_out("do_angel")!=-1 ) { // angelt noch nicht?
+    tell_object(TP, BS(Name(WER,1)+" ist bereits ausgeworfen, da haengst "
+      "Du jetzt besser nichts mehr dran, das vertreibt nur die Fische."));
+  }
+  else if ( !haken->id(HAKEN_ID) ) { // echter Angelhaken?
+    tell_object(TP, BS(haken->Name(WER,1)+" ist kein Angelhaken, "+
+      haken->QueryArticle(WEN, 1, 1)+"kannst Du nicht an "+name(WEN,1)+
+      " haengen."));
+  }
+  else if ( environment(haken) != TP ) { // Haken im Inv?
+    tell_object(TP, BS("Wie er da so auf dem Boden liegt, schaffst Du es "
+      "einfach nicht, "+haken->name(WEN,1)+" vernuenftig an "+name(WEM,1)+
+      " zu befestigen."));
+  }
+  else if ( environment(ME) != TP ) { // Angel im Inv?
+    tell_object(TP, BS("Es stellt sich viel fummeliger heraus als gedacht, "+
+      haken->name(WEN,1)+" an "+name(WEM,1)+" zu befestigen, solange "+
+      QueryPronoun(WER)+" auf dem Boden herumliegt."));
+  }
+  else if ( present(HAKEN_ID, ME) ) { // anderer Haken schon dran?
+    tell_object(TP, BS("An "+name(WEM,1)+" haengt bereits ein Angelhaken."));
+  }
+  else if ( !haken->QueryKoeder() ) { // Koeder am Haken?
+    tell_object(TP, BS("Du willst "+haken->name(WEN,1)+" gerade an "+
+      name(WEN,1)+" haengen, als Dir auffaellt, dass Du beinahe den Koeder "
+      "vergessen haettest."));
+  }
+  else { // dann darf der Haken rangehaengt werden.
+    if ( haken->move(ME, M_PUT) == MOVE_OK ) {
+      tell_object(TP, BS("Du haengst "+haken->name(WEN,1)+" an "+
+        name(WEN,1)+"."));
+      tell_room(environment(TP), BS(TP->Name(WER)+" haengt etwas metallisch "
+        "Glaenzendes an "+name(WEN)+", vermutlich einen Angelhaken."), 
+        ({TP}));
+    }
+    else {
+      tell_object(TP, BS(haken->Name(WER,1)+" laesst sich nicht an "+
+        name(WEM,1)+" befestigen."));
+    }
+  }
+  return 1;
+}
+
+static int qangel() {
+  if(IS_WIZARD(TP)) {
+    call_out("do_angel",1);
+    return 1;
+  }
+  return 0;
+}
+
+static int angel(string str) {
+  object haken = present(HAKEN_ID,ME);
+  if ( environment(ME) != TP ) {
+    tell_object(TP, BS("Dafuer musst Du die Angel in die Hand nehmen."));
+  }
+  else if ( find_call_out("do_angel")!=-1 ) {
+    tell_object(TP, "Das tust Du doch schon.\n");
+  }
+  else if(!objectp(haken)) {
+    tell_object(TP, "Wie soll das gehen? Du hast ja nichtmal einen Haken "
+      "an der Angel!\n");
+  }
+  else if(!haken->QueryKoeder()) {
+    tell_object(TP, break_string("Ohne Koeder am Haken wird sich kein "
+      "Fisch der Welt fuer Deine Angel interessieren.",78));
+  }
+  else if(present(FISCH_ID,ME)) {
+    tell_object(TP, "Nimm erst mal die Beute von der Angel, die noch daran "
+      "zappelt!\n");
+  }
+  else if ( !TP->UseHands(ME, QueryProp(P_NR_HANDS)) ) { // freie Haende?
+    tell_object(TP, BS("Du musst schon beide Haende frei haben, um die "
+      "Angel sicher festhalten zu koennen."));
+  }
+  else {
+    // Raum festhalten, in dem geangelt wird.
+    room = environment(TP);
+    // Gewaessertyp abfragen
+    active = room->QueryProp(P_WATER);
+    // Kein Wasser vorhanden, oder nicht-befischbarer Sondertyp?
+    if( (!active) || (active & W_OTHER) ) {
+      tell_object(TP, "Du kannst hier nicht angeln.\n");
+      TP->FreeHands(ME);
+    }
+    // totes Gewaesser erwischt
+    else if ( active & W_DEAD ) {
+      write("In dem Gewaesser hier gibt es keine Fische.\n");
+      TP->FreeHands(ME);
+    }
+    // Jetzt aber: es gibt Fisch, Baby. ;-)
+    else {
+      int delay = MIN_DELAY; // 80 Sekunden.
+      // Fischbestand ermitteln aus Raum- und Koederparametern
+      int bonus = room->QueryProp(P_FISH) + haken->QueryProp(P_FISH);
+      // Ist kein Bonus, sondern ein Malus rausgekommen?
+      if ( bonus < 0 ) {
+        // Dann begrenzen auf 5 Min.
+        if ( bonus < -300 )
+          bonus = -300;
+        // Wartezeit erhoehen.
+        delay += random(-bonus);
+      }
+      else {
+        // Bonus deckeln auf Max-Wert (60 Sekunden)
+        if ( bonus > MAX_FISH_BONUS ) {
+          bonus = MAX_FISH_BONUS;
+        }
+        // Delay reduzieren (minimal 20 Sekunden)
+        delay -= random(bonus);
+      }
+  
+      // passt das Gewaesser zur Angel/zum Koeder ?
+      if( !(QueryProp(P_WATER) & room->QueryProp(P_WATER)) )
+        delay += WRONGWATER + random(WRONGWATER);
+      if( !(room->QueryProp(P_WATER) & haken->QueryProp(P_WATER)) &&
+          room->QueryProp(P_WATER) != W_USER )
+        delay += WRONGWORM + random(WRONGWORM);
+
+      int hook = TP->HRegisterToHook(H_HOOK_MOVE, ME, H_HOOK_OTHERPRIO(1),
+                                     H_LISTENER, 0);
+      if ( hook != 1 ) {
+        active = 0;
+        room = 0;
+        TP->FreeHands(ME);
+        tell_object(TP, BS(
+          "Du schleuderst die Angel mit Schwung in Richtung Wasser, aber der "
+          "Haken verfaengt sich in Deinen Sachen und piekst Dir in den "
+          "Allerwertesten. Das versuchst Du besser noch einmal anders."));
+        tell_room(environment(TP), BS(
+          TP->Name()+" schleudert eine Angel in Richtung Wasser, ist dabei "
+          "aber so ungeschickt, dass sich der Haken verfaengt."), ({TP}));
+      }
+      else {
+        // Alle Bedingungen erfuellt: 
+        // - Angel in der Hand.
+        // - Gewaesser stimmt.
+        // - Haken mit Koeder ist dran.
+        // - alte Beute wurde abgenommen.
+        // - Move-Hook gesetzt, um Abbruch ausloesen zu koennen.
+        actime = time();
+        current_user = TP;
+        tell_object(TP, "Du wirfst die Angel aus.\n");
+        tell_room(environment(TP), TP->Name()+" wirft eine Angel aus.\n", 
+          ({TP}));
+        call_out("do_angel", delay);
+      }
+    }
+  }
+  return 1;
+}
+
+private object GetFish(object room) {
+  int wtype = room->QueryProp(P_WATER);
+  string *fische;
+  
+  // Wenn GetAquarium() bei W_USER nichts zurueckliefert, geht der Angler
+  // leer aus. Es kann kein Fisch aus der Std-Liste genommen werden, weil
+  // der Gewaessertyp ja per Definition benutzerdefiniert ist.
+  if ( wtype == W_USER )
+    fische = room->GetAquarium(ME)||({});
+  else 
+    fische = aquarium[wtype];
+
+  string beute = fische[random(sizeof(fische))];
+
+  if ( !beute )
+    return 0;
+  // GetAquarium() liefert volle Pfade, STDFISHLIST nur Dateinamen relativ
+  // zu FISH()
+  else if ( wtype == W_USER )
+    return clone_object(beute);
+  else
+    return clone_object(FISH(beute));
+}
+
+static void do_angel() {
+  object haken = present(HAKEN_ID, ME);
+  object room  = environment(TP);
+  object fisch;
+
+  string msg_self, msg_other;
+  if ( member(TP->QueryProp(P_HANDS_USED_BY), ME)==-1 ) {
+    tell_object(TP, BS("Waehrend Du vertraeumt vor Dich hingeangelt hast, "
+      "hat sich Dein Griff an der Angel wohl gelockert, so dass der "
+      "Fisch, der gerade anbeissen wollte, sie Dir beinahe entrissen "
+      "haette."));
+    tell_room(environment(TP), BS(TP->Name(WER)+" hat sich gerade "
+      "ziemlich erschreckt, als "+TP->QueryPronoun(WEM)+" beinahe "+
+      TP->QPP(ME, WEN, SINGULAR)+" "+Name(RAW)+" entrissen worden waere."),
+      ({TP}));
+    if ( !random(3) && haken->KoederGefressen() )
+      tell_object(TP, BS("Der Koeder ist jedenfalls futsch."));
+    return;
+  }
+
+  if ( !objectp(haken) ) {
+    msg_self = "Huch, anscheinend hat sich in einem unbeobachteten "
+      "Moment der Angelhaken von der Angelschnur geloest. War der Knoten "
+      "doch nicht gut genug gesichert?";
+    msg_other = TP->Name()+" zieht unglaeubig eine leere Angelschnur aus "
+      "dem Wasser.";
+  }
+  else if ( !objectp(fisch=GetFish(room)) || 
+            active != room->QueryProp(P_WATER) )
+  {
+    msg_self = "Anscheinend gibt es hier doch keine Fische. Du gibst "
+      "auf und holst "+name(WEN,1)+" wieder ein.";
+    // Leaken von Fischobjekten verhindern.
+    if (objectp(fisch))
+      fisch->remove();
+  }
+  else if ( fisch->move(ME) != MOVE_OK ) {
+    msg_self = fisch->Name(WER)+" biss an, war aber zu schwer fuer "
+      "Dich (oder Deine Angel). "+capitalize(fisch->QueryPronoun(WER))+
+      " entgleitet Dir und plumpst zurueck ins Wasser!";
+    
+    if( !(fisch->QueryProp(P_FISH) & F_NOTHUNGRY) ) {
+      haken->KoederGefressen();
+      if(!random(KOEDER_LOST)) {
+        msg_self += " Dein Haken ist dabei leider abgerissen!";
+        tell_room(environment(TP), BS(Name(WER,1)+" von "+TP->Name(WEM)+
+          " wackelte sehr stark."), ({TP}));
+        haken->remove();
+      }
+    }
+    fisch->remove(1);
+  }
+  else {
+    haken->KoederGefressen();
+  }
+  StopFishing(msg_self, msg_other);
+}
+
+varargs int remove(int silent) {
+  if ( find_call_out("do_angel")!=-1 )
+    StopFishing(Name(WER,1)+" loest sich ploetzlich im Nichts auf.");
+  return ::remove(silent);
+}
+
+// Jemand macht "ende" waehrend er angelt?
+protected void NotifyMove(object dest, object oldenv, int method) {
+  if ( find_call_out("do_angel")!=-1 && oldenv == current_user && 
+       dest->IsRoom() ) {
+    StopFishing("Du holst die Angel ein und legst sie beiseite.");
+  }
+  return ::NotifyMove(dest, oldenv, method);
+}
+
+// Spieler loggt waehrend des Angelns aus? Dann angeln einstellen.
+void BecomesNetDead(object pl) {
+  if ( find_call_out("do_angel")!=-1 && pl == current_user ) {
+    StopFishing("Angeln ist so eine beruhigende Freizeitbeschaeftigung! "
+      "Bevor Du mit der Angel in der Hand einschlaeft, holst Du sie "
+      "lieber schnell ein.", pl->Name()+" holt schnell noch die Angel ein, "
+      "bevor "+pl->QueryPronoun(WER)+" einschlaeft.");
+  }
+}
+
+int PreventInsert(object ob) {
+  // Funktion wird aus einer Spielereingabe heraus gerufen
+  // Ich nehme hier nicht TP, weil der call_out("do_angel") die
+  // gefangenen Fische per move() in die Angel bewegt: Bei call_out()s wird
+  // TP durch die Kette weitergereicht, so dass dann hier keine 
+  // Unterscheidung zwischen Spielereingabe und call_out() moeglich waere.
+  SetProp(P_NOINSERT_MSG, 0);
+  if ( stringp(query_verb()) &&
+       member(({"haenge","haeng","befestige"}), query_verb()) == -1 ) {
+    SetProp(P_NOINSERT_MSG, BS(Name(WER,1)+" ist nur dafuer geeignet, "
+      "Angelhaken daranzuhaengen."));
+    return 1;
+  }
+  if( ob->id(FISCH_ID) ) {
+    write("Etwas zappelt an Deiner Angel.\n");
+  }
+  return ::PreventInsert(ob);
+}
+
+// Wenn geangelt wird, nimmt hier niemand was raus.
+public int PreventLeave(object ob, mixed dest) {
+  SetProp(P_NOLEAVE_MSG, 0);
+  if ( find_call_out("do_angel")!=-1 ) {
+    if ( objectp(TP) && ob->id(HAKEN_ID) )
+      SetProp(P_NOLEAVE_MSG, BS("Der Haken ist gerade unter Wasser. Es "
+        "waere kontraproduktiv, ihn ausgerechnet jetzt abzunehmen."));
+    return 1;
+  }
+  return ::PreventLeave(ob, dest);
+}
+
+// Beendet das Angeln, indem Aktiv-Flag geloescht, Hook deregistriert
+// und call_out() geloescht wird. Zusaetzlich werden die als Argument ueber-
+// gebenen Meldungen ausgegeben, oder passende generische verwendet.
+nomask varargs void StopFishing(string msg_me, string msg_room) {
+  active = 0;
+  while(remove_call_out("do_angel")!=-1);
+  object env = environment(ME);
+  if ( objectp(env) && env == current_user ) {
+    env->FreeHands(ME);
+    current_user = 0;
+    env->HUnregisterFromHook(H_HOOK_MOVE, ME);
+    tell_object(env, BS(msg_me||"Du holst Deine Angel wieder ein."));
+    tell_room(environment(env), BS(msg_room||
+      env->Name(WER)+" holt "+env->QueryPossPronoun(ME,WEN,SINGULAR)+" "+
+      name(RAW)+" ein."), ({env}));
+  }
+}
+
+// Diese Methode wird in jedem Hook-Konsumenten eines Hook-Providers
+// aufgerufen, solange die Verarbeitung nicht vorher abgebrochen wurde.
+// Dann jedoch wurde auch die Aktion (Bewegung) nicht ausgefuehrt, d.h.
+// solange hier kein Event ankommt, wurde keine Bewegung ausgefuehrt und 
+// das Angeln kann weiterlaufen.
+mixed HookCallback(object hookSource, int hookid, mixed hookData) {
+  if ( hookid == H_HOOK_MOVE && hookSource == current_user ) {
+    StopFishing("Deine Angelschnur ist zu kurz, um damit rumlaufen zu "
+      "koennen. Du holst die Angel wieder ein.");
+  }
+  return ({H_NO_MOD, hookData});
+}
+
+// Wird gerufen, wenn der Konsument von einem anderen mit hoeherer Prioritaet
+// verdraengt wurde.
+void superseededHook(int hookid, object hookSource) {
+  if ( hookid == H_HOOK_MOVE && hookSource == current_user ) {
+    StopFishing("Irgendetwas ist gerade passiert, das alle Fische "
+      "vertrieben hat. Du siehst sie unter der Wasseroberflaeche davon"
+      "flitzen. Ernuechtert holst Du Deine Angel wieder ein.");
+  }
+}
+
+// Angelzustand abfragen.
+int IsFishing() {
+  return (find_call_out("do_angel")!=-1);
+}
+
+// Gewaessertyp abfragen, in dem gerade geangelt wird.
+int query_active() {
+  return active;
+}
diff --git a/std/items/fishing/fish.c b/std/items/fishing/fish.c
new file mode 100644
index 0000000..4209b35
--- /dev/null
+++ b/std/items/fishing/fish.c
@@ -0,0 +1,222 @@
+//Revision 1.1: QueryQuality() added, sollte aber noch verbessert werden!
+/*
+Letzte Aenderung: Vanion, 26.05.02
+                  - Die Fische haben jetzt wieder einen Wert. Der Preis wird 
+                    von einem Master kontrolliert. Je mehr Fisch ein Spieler
+                    angelt, desto billiger wird der Fisch.
+                  - Gross-Kleinschreibung beim essen korrigiert.
+*/
+
+#pragma strong_types, save_types, rtt_checks
+#pragma no_clone, no_shadow
+
+inherit "/std/thing";
+
+#include <language.h>
+#include <properties.h>
+#include <defines.h>
+#include <items/fishing/fishing.h>
+
+#define TP this_player()
+#define BS(x) break_string(x, 78)
+
+private string eatmessage;
+string corpseobject = "/items/fishing/graeten";
+static int price_modifier;
+
+#define DECAYSTART   600  // beginnt nach 10 min zu faulen
+#define DECAYSTEP    120  // alle 2 Minuten wird er schlechter
+#define MAXQUALITY     4  // nach 4 Decays ist er giftig
+#define KILLFACTOR     5  // reduce_hit_points(STEPS*KILLFACTOR)
+#define HEALFACTOR    32  // 800 g = 25 LP
+#define MAXHEAL       40  // Kein Fisch bringt mehr als 40 LP
+#define MINHEAL        0  // oder weniger als 0
+#define FOODHEALFACTOR 3  // LP=LP + 1/3 des Gewichts
+
+void SetEatMessage(string str);
+void SetCorpseObject(string str);
+int QueryQuality();
+
+protected void create() {
+  ::create();
+  // Reset kurz nach Erreichen des max. Gammelzustands, dann zerstoeren.
+  set_next_reset(DECAYSTART+(MAXQUALITY+1)*DECAYSTEP);
+  AddId(({FISCH_ID ,"fisch"}));
+  SetProp(P_NAME, "Fisch" );
+  SetProp(P_GENDER , MALE);
+  SetProp(P_SHORT, "Ein Fisch" );
+  SetProp(P_LONG, "Ein stinknormaler Fisch.\n");
+  SetProp(P_MATERIAL, MAT_MISC_FOOD);
+  SetProp(P_NOBUY,1);
+  SetProp(P_WEIGHT, 500);
+  AddCmd("iss&@ID", "eatit", "Was willst Du essen?");
+
+  // Vanion, 26.05.02: Der Preis wird erst nach dem create() geholt, 
+  // da das Gewicht dann schon gesetzt werden muss.
+  call_out("GetPriceModifier",0);
+}
+
+protected void create_super() {
+  set_next_reset(-1);
+}
+
+// Wert des Fisches ist abhaengig vom price_modifier und von P_VALUE
+static int _query_value() {
+  int value;
+
+  // Minimalpreis ist immer 1 Muenze. Damit man ihn loswird.
+  if(!price_modifier) 
+    return 1;
+
+  value = Query(P_VALUE, F_VALUE);
+
+  if(!value)
+    return 0; 
+
+  return (value*price_modifier)/100 ;
+}
+
+/*Eingebaut von Vanion, 26.05.02
+  Die Funktion holt den price_modifier aus dem Fish-Master.
+  Hierbei wird ein Wert zwischen 0 und 100 zurueckgegeben, der 
+  den Prozentsatz des Wertes von P_VALUE angibt. 50 bedeutet, dass
+  der Fisch 50% seines Maximalwertes hat. */
+
+#define FISHMASTER "p/daemon/fishmaster"
+
+void GetPriceModifier() {
+  if (!this_player()) return;
+
+  // Jetzt wird der Preis fuer den Fisch bestimmt.
+  price_modifier = FISHMASTER->PriceOfFish(TP, ME);
+  return;
+}
+
+void SetEatMessage(string str) {
+  eatmessage=str;
+}
+
+void SetCorpseObject(string str) {
+  corpseobject=str;
+}
+
+int _set_weight(int gramm) {
+  int tmp = gramm/2 + random(gramm/2); // "nat. Schwankungen" nachbilden
+  Set(P_WEIGHT, tmp, F_VALUE);
+  SetProp(P_VALUE, tmp/4); // Im normalen Laden nur 1/4 Gewicht in Muenzen
+  return tmp;
+}
+
+void init() {
+  ::init();
+  if( QueryProp(P_FISH)&F_REPLACE ) {
+    if(query_once_interactive(environment(ME))) {
+      call_out("ReplaceFish",0);
+    }
+  }
+  return;
+}
+ 
+varargs string long(int mode) {
+  string pron = capitalize(QueryPronoun(WER));
+  string txt = QueryProp(P_LONG);
+ 
+  switch(QueryQuality()) {
+    case 4:  txt += pron+" ist fangfrisch.\n";            break;
+    case 3:  txt += pron+" ist noch recht frisch.\n";     break;
+    case 2:  txt += pron+" ist schon etwas runzlig.\n";   break;
+    case 1:  txt += pron+" sieht schon recht alt aus.\n"; break;
+    case 0:  txt += pron+" ist nicht mehr geniessbar!\n"; break;
+    case -1: txt += pron+" ist vergammelt.\n";            break;
+    default:
+      txt += (pron+" stinkt widerlich und ist bereits voller Maden!\n"+pron+
+        " zerfaellt noch waehrend Du "+QueryPronoun(WEN)+" betrachtest.\n");
+      remove();
+      break;
+  }
+  return(txt);
+}
+
+int _query_fish_age() {
+  return (time()-QueryProp(P_CLONE_TIME));
+}
+
+static int eatit(string str) {
+  string msg_other = TP->Name()+" isst "+name(WEN)+".";
+
+  if ( !eatmessage )
+    eatmessage = "Du isst "+name(WEN,1)+" auf.";
+
+  if ( stringp(corpseobject) ) {
+    object muell=clone_object(corpseobject);
+    if ( muell->move(TP, M_GET) != MOVE_OK ) {
+      muell->move(environment(TP), M_GET);
+    }
+  }
+  
+  // Heilung berechnen.
+  // Heilwert runterskalieren mit Qualitaet, wenn das Mindestalter erreicht
+  // ist, aber nur, wenn der Fisch auch vergammeln kann.
+  int healing = QueryProp(P_WEIGHT)/HEALFACTOR;
+  int age = QueryProp(P_FISH_AGE);
+  if ( age > DECAYSTART && !(QueryProp(P_FISH)&F_NOROTTEN)) {
+    healing = healing * (QueryQuality()*25)/100;
+  }
+  if ( healing > MAXHEAL )
+    healing = MAXHEAL;
+  else if ( healing < MINHEAL )
+    healing = MINHEAL;
+
+  if( age > DECAYSTART + MAXQUALITY*DECAYSTEP) {
+    tell_object(TP, BS(eatmessage + " Dir wird speiuebel, der Fisch war "
+      "zu alt!"));
+    tell_room(environment(TP), BS(msg_other + TP->QueryPronoun(WER)+
+      " verdreht angeekelt die Augen."), ({TP}));
+    TP->reduce_hit_points( ((age-DECAYSTART)/DECAYSTEP)*KILLFACTOR );
+    remove();
+  }
+  else {
+    if ( TP->eat_food(healing*FOODHEALFACTOR) ) {
+      tell_object(TP, BS(eatmessage));
+      tell_room(environment(TP), BS(msg_other), ({TP}));
+      if ( !(QueryProp(P_FISH)&F_NOHEAL) )
+        TP->buffer_hp(healing,5);
+      remove();
+    }
+  }
+  return 1;
+}
+
+// Qualitaet des Fisches ermitteln. Rueckgabewert: 4, 3, 2, 1, 0, -1 ...
+int QueryQuality() {
+  // Alter in Sekunden ueber der Grenze, ab der der Fisch anfaengt zu gammeln
+  int age = QueryProp(P_FISH_AGE)-DECAYSTART;
+  // Wenn die Grenze noch nicht erreicht ist, oder der Fisch generell nicht
+  // gammelt (F_NOROTTEN), dann ist das Alter 0 und die Qualitaet max.
+  if ( age<0 || QueryProp(P_FISH) & F_NOROTTEN ) 
+    age = 0;
+
+  // Qualitaet in DECAYSTEP-Stufen reduzieren (60 s pro Gammelstufe)
+  return MAXQUALITY-(age/DECAYSTEP);
+}
+
+void reset() {
+  if (clonep(ME)) {
+    string msg = BS(Name()+" ist vergammelt und zerfaellt.") ;
+    if ( interactive(environment()) ) {
+      tell_object(environment(), msg);
+    }
+    else if ( environment()->IsRoom() ) {
+      tell_room(environment(), msg);
+    }
+    if ( stringp(corpseobject) ) {
+      object muell=clone_object(corpseobject);
+      if ( muell->move(environment(), M_GET) != MOVE_OK ) {
+        muell->move(environment(environment()), M_GET);
+      }
+    }
+    call_out("remove",0);
+    return; 
+  }
+  return ::reset();
+}
diff --git a/std/items/fishing/haken.c b/std/items/fishing/haken.c
new file mode 100644
index 0000000..66b91f4
--- /dev/null
+++ b/std/items/fishing/haken.c
@@ -0,0 +1,157 @@
+#pragma strong_types, save_types, rtt_checks
+#pragma no_shadow, no_clone
+
+inherit "/std/thing";
+
+#include <language.h>
+#include <properties.h>
+#include <items/fishing/fishing.h>
+#include <items/flasche.h>
+#include <unit.h>
+
+#define TP this_player()
+#define ME this_object()
+
+int QueryKoeder();
+
+protected void create() {
+  ::create();
+
+  AddId(({HAKEN_ID,"haken","angelhaken"}));
+  SetProp(P_NAME, "Haken");
+  SetProp(P_GENDER, MALE);
+  SetProp(P_ARTICLE, 1);
+  SetProp(P_WEIGHT, 5);
+  SetProp(P_SHORT, "Ein Angelhaken");
+  SetProp(P_LONG, "Ein Angelhaken aus Metall.\n");
+  SetProp(P_LONG_EMPTY,"Vielleicht kannst Du etwas damit aufspiessen?\n");
+
+  // Lang- und Kurzbeschreibungen reagieren auf einen evtl. vorhandenen 
+  // Koeder, allerdings nur auf ein tatsaechlich existierendes Koeder-Objekt,
+  // nicht auf einen per ueberschriebenem QueryKoeder() vorgetaeuschten
+  // Koeder, wie es der Spezialhaken tut.
+  Set(P_SHORT, function string () {
+    object koeder = present(WURM_ID, ME);
+    return Query(P_SHORT,F_VALUE)+
+      (objectp(koeder)?" mit "+koeder->name(WEM):"");
+  }, F_QUERY_METHOD);
+  Set(P_LONG, function string () { 
+    object koeder = present(WURM_ID, ME);
+    return Query(P_LONG,F_VALUE) + (objectp(koeder)?
+      koeder->Name(WER)+" haengt daran.\n":QueryProp(P_LONG_EMPTY));
+  }, F_QUERY_METHOD);
+
+  // P_FISH und P_WATER liefern die Daten eines evtl. vorhandenen Koeders
+  // Wenn kein Koeder dranhaengt, werden P_WATER und P_FISH des Hakens
+  // zurueckgegeben, falls es sich um einen Fake-Koeder handelt wie beim
+  // Spezialhaken; in diesem Fall hat der Haken selbst die Properties 
+  // gesetzt.
+  Set(P_FISH, function int () {
+    object koeder = present(WURM_ID, ME);
+    return (objectp(koeder)?koeder->QueryProp(P_FISH):Query(P_FISH));
+  }, F_QUERY_METHOD);
+  Set(P_WATER, function int () {
+    object koeder = present(WURM_ID, ME);
+    return (objectp(koeder)?koeder->QueryProp(P_WATER):Query(P_WATER));
+  }, F_QUERY_METHOD);
+
+  SetProp(P_MATERIAL,([MAT_STEEL:100]));
+
+  AddCmd(({"spiess","spiesse"}),"spiessauf");
+}
+
+protected void create_super() {
+  set_next_reset(-1);
+}
+
+static int spiessauf(string str) {
+  string haken,wurmname,*substr;
+  object wurm;
+  int amount;
+
+  notify_fail("Was willst Du denn aufspiessen?\n");
+  if (!stringp(str) || !sizeof(str)) 
+    return 0;
+  
+  if( sscanf(str, "%s auf%s", wurmname, haken) != 2 )
+    return 0;
+
+  haken = trim(haken);
+
+  notify_fail("So etwas hast Du nicht bei Dir.\n");
+  if ( !objectp(wurm=present(wurmname,TP)) )
+    return 0;
+
+  notify_fail("Das kannst Du nicht aufspiessen.\n");
+  if( !wurm->id(WURM_ID) )
+    return 0;
+
+  notify_fail("Worauf willst Du "+wurm->name(WEN,1)+" denn spiessen?\n");
+  if ( haken!="" && !id(haken) )
+    return 0;
+
+  notify_fail(break_string("Dazu solltest Du "+name(WEN,1)+" erst einmal "
+    "bei Dir haben.",78));
+  if ( environment(ME) != TP )
+    return 0;
+
+  notify_fail("An dem Haken haengt schon ein Koeder.\n");
+  if ( QueryKoeder() )
+    return 0;
+
+  // Haken und Koeder sind im Inventar und fuehlen sich von der Syntax
+  // angesprochen.
+  if( wurm->IsUnit() ) {
+    // Das QueryProp() ist nicht unnoetig. Bei der Abfrage von U_REQ wird
+    // U_REQ genullt, wenn das aktuelle query_verb() != dem letzten ist.
+    // Bei der ersten Abfrage wuerde also das hier gesetzte U_REQ wieder
+    // geloescht. Daher muss das jetzt hier als erstes einmal abgefragt
+    // werden...
+    wurm->QueryProp(U_REQ);
+    wurm->SetProp(U_REQ,1);
+  }
+  tell_object(TP, break_string(
+    "Du spiesst "+wurm->name(WEN,1)+" auf "+name(WEN,1)+".",78));
+  tell_room(environment(TP), break_string(
+    TP->Name(WER)+" spiesst "+wurm->name(WEN)+" auf "+name(WEN)+".",78),
+    ({TP}));
+  // M_GET, damit auch P_NODROP-Koeder aufgespiesst werden koennen.
+  if ( wurm->move(ME,M_GET) != MOVE_OK) {
+    tell_object(TP, break_string(
+      "Verdammt! Jetzt hast Du Dir fast in den Finger gestochen! "+
+      wurm->Name(WEN,1)+" hast Du dabei natuerlich verfehlt.", 78));
+  }
+  return 1;
+}
+
+int QueryKoeder(){ 
+  return objectp(present(WURM_ID, ME));
+}
+
+object QueryKoederObject() {
+  return present(WURM_ID,ME);
+}
+
+int MayAddObject(object ob) {
+  return (objectp(ob) && ob->id(WURM_ID) && sizeof(all_inventory(ME))<=1); 
+}
+
+int _query_total_weight() {
+  int tw;
+  foreach(int w: all_inventory(ME)+({ME}))
+    tw += w->QueryProp(P_WEIGHT);
+  return tw;
+}
+
+varargs int remove(int sil) {
+  all_inventory(ME)->remove(); // funktioniert auch mit leeren Arrays
+  return ::remove(sil);
+}
+
+int KoederGefressen() {
+  // Nicht QueryKoeder() pruefen, da das bei Spezialhaken immer 1 ist.
+  object koeder = present(WURM_ID, ME);
+  if ( objectp(koeder) )
+    return koeder->remove();
+  return -1;
+}
diff --git a/std/items/fishing/koeder.c b/std/items/fishing/koeder.c
new file mode 100644
index 0000000..c63317b
--- /dev/null
+++ b/std/items/fishing/koeder.c
@@ -0,0 +1,28 @@
+#pragma strong_types, save_types, rtt_checks
+#pragma no_clone, no_shadow
+
+inherit "/std/thing";
+
+#include <language.h>
+#include <properties.h>
+#include <items/fishing/fishing.h>
+
+protected void create(){
+  ::create();
+  AddId(({WURM_ID,"koeder", "wurm","regenwurm"}));
+  SetProp(P_NAME, "Wurm");
+  SetProp(P_GENDER , MALE);
+  SetProp(P_ARTICLE, 1);
+  SetProp(P_FISH, 0);
+  SetProp(P_WATER, 0);
+  SetProp(P_SHORT, "Ein kleiner Wurm");
+  SetProp(P_LONG, "Ein kleiner Regenwurm.\n");
+  SetProp(P_MATERIAL, MAT_MISC_LIVING);
+  SetProp(P_VALUE, 1);
+  SetProp(P_WEIGHT, 5);
+}
+
+protected void create_super() {
+  set_next_reset(-1);
+}
+
diff --git a/std/items/flasche.c b/std/items/flasche.c
new file mode 100644
index 0000000..43735fe
--- /dev/null
+++ b/std/items/flasche.c
@@ -0,0 +1,333 @@
+/*OBJ*/
+/* 2013-Mai-23, Arathorn
+   Umfassend ueberarbeitet; setup(), init() und ReplaceWasser() entsorgt,
+   P_WEIGHT und P_LONG dynamisch gebaut, so dass das staendige Umsetzen
+   der Properties mittels setup() nach jedem Fuellen/Leeren entfaellt.
+ */
+
+/* Letzte Aenderung: 4.5.2004, Arathorn.
+   Zeile 149: cont_obj->remove() eingefuegt, damit das geclonte Objekt
+   nach dem Abfragen seines Namens wieder entfernt wird.
+   Update 6.6.2004, Arathorn. Habe um ein destruct() ergaenzt, weil das
+   trotz remove() hartnaeckig weitergebuggt hat. *fluch*
+ */
+
+/* Version 1.3 by Fraggle (17.1.1995) */
+
+ // PreventInsert: verhindert Fuellen wie std/container
+/* Version 1.2 by Fraggle (17.1.1995) */
+
+ // Flasche kann nun mittels environment(TP)->GetLiquid()
+ // etwas anderes als Wasser enthalten, sofern
+ // environment(TP)->QueryProp(P_WATER)==W_OTHER
+ // BUG: auch 1l Methan wiegt 1 Kg, aendere ich spaeter
+
+/* Version 1.1 by Fraggle (17.1.1995) */
+#pragma strong_types,rtt_checks
+#pragma no_clone
+
+inherit "/std/thing";
+#include <language.h>
+#include <properties.h>
+#include <items/flasche.h>
+#include <items/fishing/fishing.h>
+
+#define DEFAULT_LIQ "Wasser"
+#define TP this_player()
+
+private string co_filename;
+public string liquid_name=DEFAULT_LIQ;
+
+string dynamic_long();
+
+protected void create() {
+  ::create();
+
+  AddId(({"wasserbehaelter","behaelter","\nwater_source"}));
+  SetProp(P_NAME, "Wasserbehaelter");
+  SetProp(P_GENDER , MALE);
+  SetProp(P_ARTICLE, 1);
+  SetProp(P_SHORT, "Ein Standard-Wasserbehaelter");
+  SetProp(P_LONG,"none");
+  Set(P_LONG, #'dynamic_long, F_QUERY_METHOD);
+  SetProp(P_LONG_EMPTY,""); // Beschreibung fuer leeren Zustand
+  SetProp(P_LONG_FULL,"");  // Beschreibung fuer gefuellten Zusand
+  SetProp(P_LIQUID,1000);   // Fuellmenge = 1 Liter
+  SetProp(P_WATER,0);       // Flasche ist defaultmaessig leer!
+  SetProp(P_VALUE,10);
+
+  // P_WEIGHT auf Leergewicht der Flasche setzen, QueryMethode liefert
+  // die Summe aus Leergewicht+Fuellung zurueck (Dichte = 1).
+  SetProp(P_WEIGHT,20);
+  Set(P_WEIGHT, function int () {
+     return ( Query(P_WEIGHT,F_VALUE)+
+              (QueryProp(P_WATER)?QueryProp(P_LIQUID):0) );
+     }, F_QUERY_METHOD);
+
+  AddCmd(({"fuell","fuelle"}),"cmd_fuelle");
+  AddCmd(({"leere", "entleere"}),"cmd_leere");
+}
+
+protected void create_super() {
+  set_next_reset(-1);
+}
+
+// Behaelter ist gefuellt, dann ist die Langbeschreibung entweder die 
+// P_LONG_FULL, falls angegben, oder die P_LONG + Beschreibung der Fuellung.
+// Genauso, wenn sie leer ist.
+string dynamic_long() {
+  string l=Query(P_LONG,F_VALUE);
+  if ( QueryProp(P_WATER) ) {
+    string lf = QueryProp(P_LONG_FULL);
+    if ( stringp(lf) && sizeof(lf) )
+      l=lf;
+    else
+      l+=capitalize(QueryPronoun(WER))+" enthaelt "+liquid_name+".\n";
+    // Falls die Flasche mit etwas anderem als Wasser gefuellt wird, die
+    // Langbeschreibung fuer "volle Flasche" (P_LONG_FULL) aber nur fuer
+    // Wasser ausgelegt ist, wird "Wasser" durch den Inhalt von liquid_name
+    // ersetzt.
+    if ( liquid_name != DEFAULT_LIQ )
+      l=regreplace(l, DEFAULT_LIQ, liquid_name, 1);
+  } else {
+    string le = QueryProp(P_LONG_EMPTY);
+    if ( stringp(le) && sizeof(le) )
+      l=le;
+    else
+      l+=capitalize(QueryPronoun(WER))+" ist leer.\n";
+  }
+  return l;
+}
+
+// Zum Ueberschreiben! PreventInsert(object ob){return 0;} z.B.
+// macht die Flasche gasdicht.
+// Oder man kann die Flasche verschliessbar machen.
+int PreventInsert(object obj)
+{
+  if(obj->id("gas")) { //default: NICHT Gasdicht!
+    write(obj->Name(WER,1)+" entweicht sofort wieder!\n");
+    return 1;
+  }
+  return 0;
+}
+
+// Transferiert den Inhalt der Flasche an <dest>
+protected int transfer_to(object dest)
+{
+  int water=QueryProp(P_WATER);
+  if (!water)
+  {
+    write(Name(WER,1) + " ist schon leer!\n");
+    return 0;   // War schon leer!
+  }
+  int contents=QueryProp(P_LIQUID);
+
+  if ( water&W_OTHER )
+  {
+    dest->PutLiquid(co_filename);
+  }
+  else
+  {
+    dest->AddWater(contents);
+  }
+  SetProp(P_WATER,0);
+  RemoveId(lower_case(liquid_name));
+  liquid_name=DEFAULT_LIQ;
+  return contents; //gib die ml an Umgebung ab :)
+}
+
+// Entleert die Flasche ins Environment der Flasche, allerdings nicht, wenn
+// dies ein Lebewesen ist, dann wird das Environment von dem genommen.
+// TODO: Eine Flasche in einem Paket leeren wurde dann in das paket entleeren.
+// Das waere an sich sogar richtig... Nur: gewollt? Alternative koennen wir
+// auch das aeusserste Environment nehmen, was nicht lebt.
+public int empty()
+{
+  if (environment())
+  {
+    // Environment des Benutzers finden.
+    object env = environment();
+    while (living(env))
+      env=environment(env);
+    return transfer_to(env);
+  }
+  return 0;
+}
+
+// Fuellt die Flasche aus <src>
+protected int fill_bottle(object src)
+{
+  int liquidtype = src->QueryProp(P_WATER);
+  if(liquidtype)
+  {
+    if(QueryProp(P_WATER)) {
+      write(Name(WER,1)+" ist bereits voll!\n");
+      return 1;
+    }
+    // Wasser von Umgebung abziehen!
+    // Man kann als Magier die Funktion AddWater(int n) dazu benuetzten,
+    // beispielsweise eine Pfuetze zu leeren, ...
+    src->AddWater(-QueryProp(P_LIQUID));
+    object cont_obj;
+    if(liquidtype&W_OTHER)
+    {
+      // Mittels GetLiquid() kann die Flasche mit was anderem als Wasser
+      // gefuellt werden.
+      co_filename=src->GetLiquid();
+      if (co_filename)
+      {
+        cont_obj=clone_object(co_filename);
+        if(PreventInsert(cont_obj))
+        {
+          // Hier passiert eigentlich das gleiche wie nach dem ifblock, aber
+          // auch noch Funktion beenden.
+          // TODO: Rueckgaenig machen von AddWater()?
+          // TODO: Die Meldung aus dem PreventInsert() muesste eigentlich
+          // _vorher_ noch mit einer Befuellmeldung begleitet werden.
+          cont_obj->remove(1);
+          if ( objectp(cont_obj) )
+            cont_obj->move("/room/muellraum",M_PUT);
+          cont_obj=0;
+          return 0;
+        }
+        else
+          liquid_name=cont_obj->name(WEN);
+        // In jedem Fall wird das Objekt wieder zerstoert - es wurde nur fuer
+        // das Ermitteln des liquid_name benutzt... Weia.
+        if ( cont_obj ) cont_obj->remove();
+        if ( cont_obj ) cont_obj->move("/room/muellraum",M_PUT);
+      }
+    }
+    SetProp(P_WATER,liquidtype);
+    AddId(lower_case(liquid_name));
+    //wie praktisch, 1 ml == 1 g :) // Aber nur fuer Wasser, du VOGEL! :-|
+    return 1;
+  }
+  else {
+    write("Du findest hier nichts, was Du in "+name(WEN,1)+
+      " fuellen koenntest!\n");
+    return 0;
+  }
+  return 0;
+}
+
+static int cmd_leere(string str)
+{
+  object dest;
+  notify_fail("Was willst Du denn (wo hinein) leeren?\n");
+  if (!str)
+    return 0;
+
+  string strbottle,strobj;
+  // leere flasche
+  if (id(str))
+  {
+    //NOOP
+  }
+  // leere flasche in xxx
+  else if (sscanf(str,"%s in %s",strbottle,strobj)==2)
+  {
+    if (!id(strbottle))
+      return 0;
+    dest = present(strobj, environment(this_player()))
+           || present(strobj, this_player());
+    if (!dest)
+      return 0;
+  }
+  else
+    return 0;
+  // Syntaxpruefung fertig.
+
+  if(!QueryProp(P_WATER))
+  {
+    write("Da ist kein "+liquid_name+" drin!\n");
+    return 1;
+  }
+
+  if (dest)
+  {
+    write(break_string("Du leerst "+name(WEN,1)+ " in "
+          + dest->name(WEN) + ".",78));
+    say(break_string(TP->name()+" leert "+name(WEN,0)
+          + " in " + dest->name(WEN) + ".",78),TP);
+    transfer_to(dest);
+    return 1;
+  }
+  write(break_string("Du leerst "+name(WEN,1)+".",78));
+  say(break_string(TP->name()+" leert "+name(WEN,0)+".",78),TP);
+  empty();
+  return 1;
+}
+
+public int cmd_fuelle(string str)
+{
+  string strbottle,strobj;
+
+  notify_fail("Was willst Du denn (womit) fuellen?\n");
+  if(!str)
+    return 0;
+
+  // fuelle flasche
+  if (id(str))
+  {
+    if (fill_bottle(environment(this_player())))
+    {
+      write(break_string("Du fuellst etwas "+liquid_name+" in "
+            +name(WEN,1)+".",78));
+      say(break_string(TP->Name(WER)+" fuellt etwas "
+            +liquid_name+" in "+name(WEN)+".",78), TP);
+    }
+    return 1;
+  }
+  // fuelle flasche aus xxx
+  // fuelle flasche mit xxx
+  // fuelle xxx in flasche
+  // fuelle flasche in xxx
+  // fuelle xxx aus flasche
+  // fuelle xxx mit flasche
+  else if (sscanf(str,"%s in %s",strobj,strbottle)==2
+           || sscanf(str,"%s mit %s",strbottle,strobj)==2
+           || sscanf(str,"%s aus %s",strbottle,strobj)==2)
+  {
+    object obj;
+    // Flasche befuellen?
+    if (id(strbottle)
+        && ( obj=present(strobj, environment(this_player())) 
+                 || present(strobj, this_player()) )
+       )
+    {
+      if (fill_bottle(obj))
+      {
+        write(break_string(
+              "Du fuellst etwas "+liquid_name+" aus " + obj->name(WEM,1) 
+              + " in "+name(WEN,1)+".",78));
+        say(break_string(TP->Name(WER)+" fuellt etwas "+liquid_name+ " aus " 
+              + obj->name(WEM,1) + " in "+name(WEN)+".",78), TP);
+      }
+      return 1;
+    }
+    // anderes Gefaess befuellen?
+    else if (id(strobj)
+        && ( obj=present(strbottle, environment(this_player())) 
+                 || present(strbottle, this_player()) )
+       )
+    {
+      if (transfer_to(obj))
+      {
+        write(break_string(
+              "Du fuellst etwas "+liquid_name+" aus " + name(WEM,1)
+              + " in "+obj->name(WEN,1)+".",78));
+        say(break_string(TP->Name(WER)+" fuellt etwas "+liquid_name+ " aus " 
+              + name(WEM,1) + " in "+obj->name(WEN)+".",78), TP);
+      }
+      return 1;
+    }
+  }
+  // Syntax passt nicht.
+  return 0;
+}
+
+int IsBottle() {
+   return 1;
+}
+
diff --git a/std/items/kraeuter/kraut.c b/std/items/kraeuter/kraut.c
new file mode 100644
index 0000000..2ce5045
--- /dev/null
+++ b/std/items/kraeuter/kraut.c
@@ -0,0 +1,195 @@
+// (c) September 2000 by Padreic (Padreic@mg.mud.de)
+
+#pragma strong_types, save_types, rtt_checks
+
+inherit "/std/thing";
+
+#include <properties.h>
+#include <items/kraeuter/kraeuter.h>
+
+#define PLANT_LIFETIME  (24*3600)
+#define FRESH_TIME      (6*3600)
+// Die plantID wird fuer ungueltig erschaffene Kraeuter auf -1 gesetzt.
+#define DRIED_PLANT     -1
+
+private int age=time();
+// enthaelt die Nummer des Krauts
+private int plantId;
+// enthaelt den Pfad des clonenden Objekts
+private string cloner;
+// Qualitaet des Krautes.
+private int quality=100;
+
+// File kann ein name sein, dessen Eigenschaften der VC konfigurieren sein
+// oder 0, wenn er selber ermitteln soll, was fuer ein File er gerade erzeugt
+// hat.
+// Sprich: real existierende Files auf der Platte muessen da ihren Namen
+// angeben, Standardfall ist aber, dass man 0 angibt und der VC weiss, was er
+// gerade erzeugt hat.
+void customizeMe(string file)
+{
+  if (stringp(file)) 
+    file=explode(file, "/")[<1];
+  KRAEUTERVC->CustomizeObject(file);
+}
+
+protected void create()
+{
+  if (object_name(this_object()) == __FILE__[0..<3])
+  {
+    set_next_reset(-1);
+    return;
+  }
+  ::create();
+ 
+  Set(P_QUALITY, function int () { return quality; }, F_QUERY_METHOD);
+  SetProp(P_WEIGHT, 120);
+  SetProp(P_VALUE, 70);
+  SetProp(P_MATERIAL, MAT_MISC_PLANT);
+}
+
+protected void create_super()
+{
+  set_next_reset(-1);
+}
+
+public string short()
+{
+  string str=QueryProp(P_SHORT);
+  if (!stringp(str)) 
+      return 0;
+  if (plantId==-1)
+      return str+" (unwirksam).\n";
+  else if (age==DRIED_PLANT)
+     return str+" (getrocknet).\n";
+  else if (age+FRESH_TIME+PLANT_LIFETIME<time())
+     return str+" (verfault).\n";
+  return str+".\n";
+}
+
+// Liefert einen Skalierungsfaktor zurueck, der mit dem aktuellen Wert von
+// P_QUALITY verrechnet wird. Rueckgabewerte:
+// Pflanze getrocknet oder nicht aelter als 6 h : 100
+// Pflanze aelter als 6, aber juenger als 30 h : 99...1
+// Pflanze aelter als 30 h: 0.
+// DryPlant() zerstoert das Kraut, wenn P_QUALITY unter 1 faellt.
+public int PlantQuality()
+{
+  int factor;
+  // schon getrocknet oder nicht aelter als 6 h? 
+  // Dann keine weitere Reduktion.
+  if ( age == DRIED_PLANT || age+FRESH_TIME > time()) 
+    factor = 100;
+  // >30 Stunden nach dem Pfluecken ist das Kraut verschimmelt.
+  else if ( age + FRESH_TIME + PLANT_LIFETIME < time() ) 
+    factor = 1;
+  // Zeit zwischen 6 und 30 Stunden nach dem Pfluecken in 99 gleichmaessige
+  // Abschnitte unterteilen. 24 h sind 86400 s, 86400/99 = 873.
+  else
+    factor=(time()-age-FRESH_TIME)/873;
+
+  return QueryProp(P_QUALITY)*factor/100;
+}
+
+// Wie lange (in Sekunden) ist das Kraut noch haltbar?
+public int TimeToLive()
+{
+  if ( age == DRIED_PLANT )
+    return __INT_MAX__;
+  return age-time()+PLANT_LIFETIME;
+}
+
+//TODO: vielleicht etwas zufall? Sonst Kraeuterqualitaet hieran ermittelbar.
+static int _query_value()
+{
+  int val = Query(P_VALUE,F_VALUE)*PlantQuality()/100;
+  if (plantId<=0 || val = 0)
+    return 0;
+  return val-val%10;
+}
+
+static string _query_nosell() 
+{
+  if (age != DRIED_PLANT)
+    return "Mit ungetrockneten Kraeutern handele ich nicht. Die verderben "
+      "immer so schnell im Lager, und dann werde ich sie nicht wieder los.";
+  return 0;
+}
+
+// Mit DryPlant() wird die Pflanze getrocknet. Als Argument wird der Prozent-
+// wert uebergeben, auf den die Qualitaet sinken soll. Als Ausgangswert
+// dieser Berechnung wird der Rueckgabewert von PlantQuality() verwendet.
+// Hintergrund: Die Qualitaet des Krauts sinkt im ungetrockneten Zustand
+// ueber einen Zeitraum von 24 h kontinuierlich von 100 auf 1 ab, sobald
+// es aelter als 6 Stunden ist. Danach ist es verschimmelt, was aber seiner
+// verbleibenden "Wirkung" keinen Abbruch tut.
+// Es wird die zum Zeitpunkt des Trocknungsvorganges gueltige Qualitaet
+// also sozusagen "eingefroren" und entsprechend dem Rueckgabewert von
+// PlantQuality() heruntergerechnet.
+
+// Diese Funktion kann natuerlich auch ueberschrieben werden, wenn bestimmte
+// Kraeuter erst durch trocknen in der Qualitaet steigen.
+
+// TODO: Ist das Argument "qual" dabei prozentual aufzufassen, oder 
+// soll nur ein noch zu bestimmender Festwert abgezogen werden?
+// Arathorn: Es bleibt jetzt erstmal prozentual.
+
+#define DRYING_ALLOWED ({PLANTMASTER, "/items/kraeuter/trockner"})
+
+public void DryPlant(int qual) 
+{
+  // Keine mehrfache Trocknung zulassen.
+  if ( age == DRIED_PLANT )
+    return;
+ 
+  // Nur bestimmte Objekte duerfen Trocknungen ausloesen.
+  if ( member(DRYING_ALLOWED, load_name(previous_object())) == -1 )
+    return;
+
+  // Qualitaet auf 100 deckeln.
+  if ( qual>100 )
+    qual = 100;
+  
+  // Qualitaet mittels PlantQuality() runterskalieren.
+  qual = PlantQuality()*qual/100;
+  
+  if ( qual < 1 ) {
+    if(objectp(this_player()))
+      tell_object(this_player(), 
+        Name(WER,1)+" zerfaellt in unzaehlige feine Kruemel.\n");
+    remove();
+    return;
+  }
+  // Kraut als getrocknet kennzeichnen.
+  age=DRIED_PLANT;
+  quality = qual;
+}
+
+/* Funktionen zum Initialisieren der Pflanze */
+// Der Kraeutermaster prueft den Clone auf Gueltigkeit. Eine einmal gesetzte
+// ID kann auf diesem Weg nicht mehr geaendert werden.
+nomask int SetPlantId(int new_id)
+{
+  if (plantId != 0)
+    return -1;
+  cloner=0;
+  age=time();
+  if (catch(cloner=call_other(PLANTMASTER, "CheckPlant", new_id)) || !cloner)
+    new_id = -1;
+  return (plantId=new_id);
+}
+
+nomask int QueryPlantId()
+{
+  return plantId;
+}
+
+nomask string QueryCloner()
+{
+  return cloner;
+}
+
+nomask int QueryDried() 
+{
+  return (age == DRIED_PLANT);
+}
diff --git a/std/items/kraeuter/trank.c b/std/items/kraeuter/trank.c
new file mode 100644
index 0000000..f3c0efe
--- /dev/null
+++ b/std/items/kraeuter/trank.c
@@ -0,0 +1,1147 @@
+//TODO:
+
+#pragma strong_types,rtt_checks
+
+inherit "/std/thing";
+
+#include <properties.h>
+#include <defines.h>
+#include <items/kraeuter/kraeuter.h>
+#include <items/kraeuter/trankattribute.h>
+#include <hook.h>
+#include <class.h>
+#include <new_skills.h>
+#include <wizlevels.h>
+
+#ifndef BS
+#  define BS(x)             break_string(x, 78)
+#endif
+
+#define allowed(x) (object_name(x)==PLANTMASTER)
+#define DRINK_POTION "lib_kraeutertrank_trinken"
+// for debug
+#define private public
+
+// Ablaufzeit des Tranks, ab dann keine Wirkung mehr
+private nosave int expiry;
+// Ablaufzeit der wirkungen des Trankes (0, wenn Trank nicht getrunken)
+private nosave int duration;
+// Trankattribute, vom Krautmaster schon skaliert, gekappt, beschraenkt auf
+// die jeweils max. positiven Effekte
+private nosave mapping data;
+// Klassen, die bei Schutz oder verstaerktem Schaden betroffen sind. Werte
+// ist der Schutz- oder Attackebonus/-malus.
+private nosave mapping att_classes;
+private nosave mapping prot_classes;
+// max. Summe von Giftstufen (P_POISON und P_LEVEL/10 bei CL_POISON).
+private nosave int prot_poison;
+// max. geheilte Summe von Krankheitslevel (P_LEVEL/5 in CL_DISEASE).
+private nosave int prot_disease;
+// nach Wirkung absteigend sortierte Liste der Effekte, wird beim ersten
+// Aufruf von DetermineStrongesEffect() befuellt.
+private nosave string* sorted_effects;
+
+mixed _query_data() {return data;}
+int _set_data(mixed d) {data=d; expiry = __INT_MAX__; return data!=0;}
+private string effect2colour();
+
+protected void create()
+{
+  if (object_name(this_object()) == __FILE__[0..<3])
+  {
+    set_next_reset(-1);
+    return;
+  }
+  ::create();
+  SetProp(P_GENDER, FEMALE);
+  SetProp(P_NAME, "Glasflasche");
+  SetProp(P_NAME_ADJ, ({"klein"}));
+  SetProp(P_VALUE, 10);
+  SetProp(P_WEIGHT, 100);
+  SetProp(P_KILL_NAME, "Ein Kraeutertrank");
+  SetProp(P_KILL_MSG, "%s hat sich wohl beim Anruehren vertan.");
+  AddId(({"glasflasche", "flasche"}));
+  AddAdjective(({"klein", "kleine"}));
+  AddCmd("trink|trinke&@ID", "cmd_trinken",
+    "Was willst Du trinken?");
+}
+
+protected void create_super()
+{
+  set_next_reset(-1);
+}
+
+static string _query_short()
+{
+  if (!clonep(ME))
+    return "Eine kleine Glasflasche";
+  return Name(WEN, 0)+(data==0 ? "" : " (gefuellt)");
+}
+
+static string _query_long()
+{
+  if (data==0)
+    return break_string(
+      "Eine kleine leere Glasflasche, die mit einem Korken verschlossen "
+      "ist.\n"
+      "Flaschen wie diese werden ueblicherweise verwendet, um darin "
+      "magische Traenke abzufuellen.", 78, 0, BS_LEAVE_MY_LFS);
+
+  return break_string(
+    "Eine kleine Glasflasche, die mit einer "+effect2colour()+"en "
+    "Fluessigkeit gefuellt ist.\n"
+    "Sie ist mit einem Korken verschlossen, um den Inhalt der "
+    "Flasche zu schuetzen.",78, 0, BS_LEAVE_MY_LFS);
+}
+
+private string num2desc(int bumms)
+{
+  switch(abs(bumms))
+  {
+    case 0..499:
+      return "ein wenig";
+    case 500..999:
+      return "so einiges";
+    case 1000..1499:
+      return "erheblich";
+    case 1500..2000:
+      return "unglaublich";
+  }
+  return "ungenehmigt viel"; // kommt hoffentlich nicht vor.
+}
+
+varargs private string DetermineStrongestEffect(int pos)
+{
+  // globale Werteliste befuellen, wenn da noch nichts drinsteht.
+  if ( !pointerp(sorted_effects) ) {
+    sorted_effects = sort_array(m_indices(data) & T_KRAUT_EFFECTS,
+      function int (string a, string b) {
+        return (abs(data[a])<=abs(data[b]));
+      });
+  }
+
+  // Zur Indizierung des Arrays muss <pos> bei Null starten, es wird
+  // aber mit der Bedeutung einer Ordinalzahl (erste, zweite, dritte, ...)
+  // uebergeben. Daher um 1 reduzieren.
+  --pos;
+
+  string ret;
+
+  // Im Array muss mindestens ein Eintrag stehen, sonst gibt's gar keinen
+  // Effekt.
+  if ( sizeof(sorted_effects) )
+  {
+    // Wenn der angefragte Index ausserhalb der Arraygrenzen liegt, wird
+    // angenommen, dass der erste bzw. letzte Eintrag gesucht waren.
+    if ( pos < 0 )
+      ret = sorted_effects[0];
+    else if ( pos >= sizeof(sorted_effects) )
+      ret = sorted_effects[<1];
+    else
+      ret = sorted_effects[pos];
+  }
+  return ret;
+}
+
+// Liefert zu dem maximal wirksamen Effekt die Farbe des Trankes zurueck.
+private string effect2colour()
+{
+  // Ist die Haltbarkeit schon abgelaufen, wird der Trank farblos.
+  if ( time() > expiry )
+    return "farblos";
+
+  // Namen des staerksten Effekts holen.
+  string effect = DetermineStrongestEffect(1);
+  mapping colours = ([
+    T_CARRY:              "trueb braun",
+    T_DAMAGE_ANIMALS:     "blutrot",
+    T_DAMAGE_MAGIC:       "oktarinfarben",
+    T_DAMAGE_UNDEAD:      "anthrazitfarben",
+    T_FLEE_TPORT:         "schwefelgelb",
+    T_FROG:               "schlammgruen",
+    T_HEAL_DISEASE:       "perlmuttfarben",
+    T_HEAL_POISON:        "gruen",
+    T_HEAL_SP:            "blau",
+    T_HEAL_LP:            "scharlachrot",
+    T_PROTECTION_ANIMALS: "metallisch grau",
+    T_PROTECTION_MAGIC:   "violett",
+    T_PROTECTION_UNDEAD:  "strahlend weiss",
+    T_SA_SPEED:           "orangefarben",
+    T_SA_SPELL_PENETRATION: "stahlblau",
+    T_SA_DURATION:        "pinkfarben",
+  ]);
+  string ret = colours[effect];
+  return stringp(ret) ? ret : "farblos";
+}
+
+// Wird gerufen, wenn die Wirkung des Trankes ablaufen soll.
+private void terminate_effects()
+{
+  tell_object(environment(),
+      "Die letzten Wirkungen des Kraeutertrankes klingen ab.\n");
+  remove(1);
+}
+
+// Von den Hooks H_HOOK_ATTACK_MOD und H_HOOK_DEFEND gerufen, erhoeht oder
+// verringert den Schaden gegen Lebenwesen bestimmter Klassen (Keys in
+// <classes>). Der Malus/Bonus steht als Wert zum jeweiligen Key in dem
+// Mapping.
+mixed hcallback(object hookSource, int hookid, mixed hookData)
+{
+    if (hookSource != environment())
+        return ({H_NO_MOD,hookData});
+    switch(hookid)
+    {
+      case H_HOOK_ATTACK_MOD:
+        foreach(string class, int modval : att_classes)
+        {
+          if (hookData[SI_ENEMY]->is_class_member(class))
+          {
+            // Yeah. Treffer. Schaden erhoehen oder verringern... ;)
+            hookData[SI_SKILLDAMAGE] += modval;
+            // Ende. keine weiteren Klassen pruefen.
+            return ({H_ALTERED, hookData});
+          }
+        }
+        break;
+      case H_HOOK_DEFEND:
+        // hookData: ({dam,dam_type,spell,enemy})
+        foreach(string class, int modval : prot_classes)
+        {
+          if (hookData[3]->is_class_member(class))
+          {
+            // Yeah. Treffer. Schaden erhoehen oder verringern... ;)
+            hookData[0] += modval;
+            // Ende. keine weiteren Klassen pruefen.
+            return ({H_ALTERED, hookData});
+          }
+        }
+        break;
+      case H_HOOK_INSERT:
+        // Wenn die Giftschutzkapazitaet noch ausreicht, wird das reinkommende
+        // Objekt zerstoert (und die Kapazitaet reduziert).
+        // hookData: neues object
+        if (prot_poison > 0
+            && hookData->is_class_member(CL_POISON))
+        {
+          // kostet ein Zehntel des Levels, aber min. 1.
+          int p=hookData->QueryProp(P_LEVEL) / 10 + 1;
+          if (p < prot_poison)
+          {
+            hookData->remove(1);
+            prot_poison-=p;
+            return ({H_CANCELLED, hookData});
+          }
+        }
+        // Wenn die Krankheitsschutzkapazitaet noch ausreicht, wird das reinkommende
+        // Objekt zerstoert (und die Kapazitaet reduziert).
+        // hookData: neues object
+        if (prot_disease > 0
+            && hookData->is_class_member(CL_DISEASE))
+        {
+          // kostet ein Fuenftel des Levels, aber min. 1.
+          int lvl = hookData->QueryProp(P_LEVEL) / 5 + 1;
+          if (lvl < prot_disease)
+          {
+            hookData->remove(1);
+            prot_disease-=lvl;
+            return ({H_CANCELLED, hookData});
+          }
+        }
+        break;
+      case H_HOOK_POISON:
+        // hookData: poisonval
+        // Alle Giftlevel werden reduziert auf 0 und von prot_poison
+        // abgezogen. Wenn das 0 ist, endet der Giftschutz.
+        if (prot_poison>0)
+        {
+          if (hookData < prot_poison)
+          {
+            prot_poison-=hookData;
+            hookData = 0;
+          }
+          else
+          {
+            hookData -= prot_poison;
+            prot_poison=0;
+          }
+          return ({H_ALTERED, hookData});
+        }
+        break;
+    }
+    return ({H_NO_MOD, hookData});
+}
+
+private int reg_hook(int hook, int hooktype)
+{
+  // Wenn schon registriert, zaehlt das auch als Erfolg.
+  if (environment()->HIsHookConsumer(hook, #'hcallback))
+    return 1;
+  int res = environment()->HRegisterToHook(hook, #'hcallback,
+                 H_HOOK_OTHERPRIO(0), hooktype, duration);
+  if (res <= 0)
+  {
+    // wenn andere Fehler als -7 (zuviele Hooks registriert) vorkommen:
+    // Fehlermeldung ausgeben
+    if (res != -7)
+      tell_object(environment(),break_string(sprintf(
+          "Technischer Hinweis, den Du an einen Magier weitergeben "
+          "solltest: Beim Registrieren des Hooks %d gab es Fehler: %d\n",
+          hook, res),78));
+    return 0;
+  }
+  return 1;
+}
+
+// effekt: Wirkungswert des Tranks (muss negativ sein)
+// type: 1 fuer Gift, 0 fuer Krankheit
+private void ticktack(int effekt, int type)
+{
+  // Schaden tickt alle 5 Sekunden
+  int delay = 5;
+  // Der halbe Betrag des negativen Effekts wird als Schaden am
+  // Spieler verursacht.
+  // Berechnung: (Schaden pro Sekunde) * (Delay in Sekunden)
+  // in float rechnen ist hier sinnvoll, inkl. aufrunden (durch die +0.5)
+//  int dam = to_int(((-0.5*effekt)/duration)*delay + 0.5);
+  int dam = to_int(0.5*abs(effekt)/data[T_EFFECT_DURATION]*delay + 0.5);
+
+  if (type)
+    tell_object(environment(),
+      break_string("Gift pulsiert brennend durch Deine Adern.",78));
+  else
+    tell_object(environment(),
+      break_string("Du fuehlst Dich schwach und elend, eine Erkrankung "
+      "zehrt an Deinen Kraeften.",78));
+
+  environment()->do_damage(dam, this_object());
+  call_out(#'ticktack, delay, effekt, type);
+}
+
+private int act_attr_heal_poison(int effekt)
+{
+  int erfolgreich;
+  tell_object(environment(), break_string(
+     "Du fuehlst, wie der Trank wie Feuer durch Deinen Koerper schiesst "
+     "und kruemmst Dich vor Schmerzen. Doch Momente spaeter laesst die "
+     "Tortur nach.",78));
+
+  // max. 40 Giftlevel heilen...
+  prot_poison = effekt / 50;
+
+  if (prot_poison < 0)
+  {
+    tell_object(environment(), BS(
+      "Bah! Der Trank schmeckt widerlich bitter. Wenn der mal nicht "
+      "giftig war."));
+    call_out(#'ticktack, 5, effekt, 1); // 1 => Gift
+    return 1;
+  }
+  
+  // ab jetzt nur noch positive Wirkungen.
+
+  // P_POISON zuerst.
+  int poison = environment()->QueryProp(P_POISON);
+  if (poison)
+  {
+    if (poison <= prot_poison)
+    {
+      prot_poison -= poison;
+      environment()->SetProp(P_POISON,0);
+      if (!environment()->QueryProp(P_POISON))
+        ++erfolgreich;
+    }
+    else
+    {
+      poison -= prot_poison;
+      prot_poison=0;
+      environment()->SetProp(P_POISON, poison);
+      // Wenn erfolgreich, direkt Meldung und raus.
+      if (environment()->QueryProp(P_POISON) == poison)
+      {
+        tell_object(environment(), break_string(
+           "Ueberrascht stellst Du fest, dass Du Dich "
+           "besser fuehlst - der Trank hat Deine Vergiftung offenbar "
+           "gelindert.",78));
+        return 1;
+      }
+    }
+  }
+
+  // wenn Trank immer noch positiv (also noch WIrkung uebrig)
+  if (prot_poison > 0)
+  {
+    // Als naechstes Objekte suchen.
+    object *ob = filter_objects(all_inventory(environment()),
+                                "is_class_member", CL_POISON);
+    foreach(object o: ob)
+    {
+      // Entgiften kostet ein Zehntel des Levels, aber min. 1.
+      poison = o->QueryProp(P_LEVEL);
+      if (poison <= prot_poison*10)
+      {
+        prot_poison -= poison/10 + 1;
+        o->SetProp(P_LEVEL, 0);
+        if (o->remove())
+          ++erfolgreich;
+      }
+      else
+      {
+        poison -= prot_poison * 10;
+        prot_poison = 0;
+        o->SetProp(P_LEVEL, poison);
+        if (o->QueryProp(P_LEVEL) == poison)
+          ++erfolgreich;
+      }
+      if (prot_poison <= 0)
+        break;
+    }
+  }
+
+  if (erfolgreich)
+  {
+    tell_object(environment(), break_string(
+      "Ueberrascht stellst Du fest, dass Du Dich viel besser fuehlst - der "
+      "Trank wirkt offenbar gegen Vergiftungen.",78));
+  }
+  else
+  {
+    tell_object(environment(), break_string(
+      "Eine Ahnung sagt Dir, dass der Trank irgendeine positive "
+      "Wirkung hat."));
+  }
+
+  // ggf. an die Hooks registrieren, wenn noch Schutzwirkung uebrig ist.
+  if (prot_poison > 0)
+  {
+    // Rueckgabewerte von HRegisterToHook speichern...
+    int *res = ({ reg_hook(H_HOOK_POISON, H_DATA_MODIFICATOR) });
+    res += ({ reg_hook(H_HOOK_INSERT, H_HOOK_MODIFICATOR) });
+    // Wenn alle versuchten Registrierungen erfolgreich waren...? Ansonsten
+    // andere Meldung... Ich bin noch nicht gluecklich, das hier so explizit
+    // auszugeben, aber ich weiss gerade sonst nicht, wie man drauf kommen
+    // soll, dass es ein Problem gibt.
+    if (sizeof(res) == sizeof(res & ({1})))
+      tell_object(environment(),
+         "Vielleicht haelt diese Wirkung ja sogar noch etwas an?\n");
+    else
+    {
+      // zumindest ein erfolg?
+      if (member(res, 1) > -1)
+        tell_object(environment(),
+            "Vielleicht haelt ein Teil dieser Wirkung ja sogar noch etwas an?\n");
+    }
+  }
+  return 1;
+}
+
+private int act_attr_heal_disease(int effekt)
+{
+  int erfolgreich;
+
+  // max. 40 Krankheitslevel heilen...
+  prot_disease = effekt / 50;
+
+  if (prot_disease > 0)
+  {
+     tell_object(environment(), break_string(
+       "Du fuehlst, wie der Trank in Deinem Bauch eine wohlige Waerme "
+       "verbreitet und laechelst unwillkuerlich.",78));
+   
+    // Objekte suchen.
+    object *ob = filter_objects(all_inventory(environment()),
+                                "is_class_member", CL_DISEASE);
+    foreach(object o: ob)
+    {
+      // Heilen kostet ein Fuenftel des Levels, aber min. 1.
+      int disease = o->QueryProp(P_LEVEL);
+      if (disease <= prot_disease*5)
+      {
+        prot_disease -= disease/5 + 1;
+        o->SetProp(P_LEVEL, 0);
+        if (o->remove())
+          ++erfolgreich;
+      }
+      else
+      {
+        disease -= prot_disease * 5;
+        prot_disease = 0;
+        o->SetProp(P_LEVEL, disease);
+        if (o->QueryProp(P_LEVEL) == disease)
+          ++erfolgreich;
+      }
+      if (prot_disease <= 0)
+        break;
+    }
+  }
+  else
+  {
+    tell_object(environment(), BS(
+      "Der Trank schmeckt eklig faulig. Dein Magen rebelliert umgehend. "
+      "Du kannst Deinen Brechreiz gerade noch unterdruecken, fuehlst "
+      "Dich aber krank."));
+    call_out(#'ticktack, 5, effekt, 0); // 0 => Krankheit
+    return 1;
+  }
+
+  if (erfolgreich)
+  {
+    tell_object(environment(), break_string(
+      "Entspannt durchatmend stellst Du fest, dass Du Dich viel besser fuehlst - der "
+      "Trank wirkt offenbar gegen Krankheiten.",78));
+  }
+  else
+  {
+    tell_object(environment(), break_string(
+      "Eine Ahnung sagt Dir, dass der Trank irgendeine positive "
+      "Wirkung hat."));
+  }
+
+  // ggf. an die Hooks registrieren.
+  if (prot_disease > 0)
+  {
+    // Registrierung erfolgreich...? Ansonsten andere Meldung... Ich bin
+    // noch nicht gluecklich, das hier so explizit auszugeben, aber ich
+    // weiss gerade sonst nicht, wie man drauf kommen soll, dass es ein
+    // Problem gibt.
+    if (reg_hook(H_HOOK_INSERT, H_HOOK_MODIFICATOR)==1)
+      tell_object(environment(),
+         "Vielleicht haelt diese Wirkung ja sogar noch etwas an?\n");
+
+  }
+  return 1;
+}
+
+private string num2desc_fight(int bumms)
+{
+  switch(abs(bumms))
+  {
+    case 0..499:
+      return "ein wenig";
+    case 500..999:
+      return "spuerbar";
+    case 1000..1499:
+      return "deutlich";
+    case 1500..2000:
+      return "erheblich";
+  }
+  return "ungenehmigt viel"; // kommt hoffentlich nicht vor.
+}
+
+// AN: Tiere sind: CL_ANIMAL, CL_FISH, CL_FROG, CL_INSECT, CL_MAMMAL,
+// CL_MAMMAL_LAND, CL_MAMMAL_WATER, CL_REPTILE, CL_ARACHNID, CL_BIRD
+private int act_attr_dam_animals(int effekt)
+{
+  if (reg_hook(H_HOOK_ATTACK_MOD, H_DATA_MODIFICATOR) == 1)
+  {
+    if (!mappingp(att_classes)) att_classes=m_allocate(1);
+    att_classes[CL_ANIMAL] = effekt/20;
+    tell_object(environment(), break_string(
+        "Du spuerst in Dir ein seltsames Verlangen aufsteigen, auf die Jagd "
+        "zu gehen - als wuerde Artemis persoenlich Deine Angriffe "
+        + num2desc_fight(effekt)
+        + " verbessern.",78));
+    return 1;
+  }
+  return 0;
+}
+
+// AN: Magische Wesen sollen sein: CL_ELEMENTAL, CL_ILLUSION, CL_SHADOW
+// CL_DRAGON, CL_DEMON, CL_SHAPECHANGER, CL_HARPY
+private int act_attr_dam_magical(int effekt)
+{
+  if (reg_hook(H_HOOK_ATTACK_MOD, H_DATA_MODIFICATOR) == 1)
+  {
+    if (!mappingp(att_classes)) att_classes=m_allocate(4);
+    att_classes[CL_DRAGON] = att_classes[CL_ELEMENTAL]
+                            = att_classes[CL_SHADOW]
+                            = att_classes[CL_ILLUSION]
+                            = effekt/20;
+    tell_object(environment(), break_string(
+        "Merkwuerdig. Du hast gerade das Gefuehl, als fiele Dir der "
+        "Kampf gegen von Hekate beschenkte Wesen "
+        + num2desc_fight(effekt)
+        + " leichter.",78));
+    return 1;
+  }
+  return 0;
+}
+
+// AN: Untote sollen sein: CL_SKELETON, CL_GHOUL, CL_GHOST, CL_VAMPIRE
+// CL_ZOMBIE, CL_UNDEAD
+// Bloed ist nur, dass CL_UNDEAD alle anderen enthaelt bis auf CL_GHOST.
+// Also lassen wir die Unterscheidung und schrittweise Freischaltung
+// erst einmal sein.
+private int act_attr_dam_undead(int effekt)
+{
+  if (reg_hook(H_HOOK_ATTACK_MOD, H_DATA_MODIFICATOR) == 1)
+  {
+    // Zombies, Skelette, Ghule...
+    if (!mappingp(att_classes)) att_classes=m_allocate(1);
+    att_classes[CL_UNDEAD] =  effekt/20;
+    tell_object(environment(), break_string(
+        "Auf einmal hast Du den Eindruck, dass die Kreaturen des "
+        "Hades Deinen Angriffen "
+        + num2desc_fight(effekt)
+        + " weniger entgegen zu setzen haben.",78));
+    return 1;
+  }
+  return 0;
+}
+
+private int act_attr_prot_animals(int effekt)
+{
+  if (reg_hook(H_HOOK_DEFEND, H_DATA_MODIFICATOR) == 1)
+  {
+    if (!mappingp(prot_classes)) prot_classes=m_allocate(1);
+    prot_classes[CL_ANIMAL] = effekt/20;
+    tell_object(environment(), break_string(
+        "Du hast das Gefuehl, dass Artemis ihre schuetzende Hand "
+        + num2desc_fight(effekt)
+        + " ueber Dich haelt.",78));
+    return 1;
+  }
+  return 0;
+}
+
+private int act_attr_prot_magical(int effekt)
+{
+  if (reg_hook(H_HOOK_DEFEND, H_DATA_MODIFICATOR) == 1)
+  {
+    if (!mappingp(prot_classes)) prot_classes=m_allocate(4);
+    prot_classes[CL_DRAGON] = prot_classes[CL_ELEMENTAL]
+                            = prot_classes[CL_SHADOW]
+                            = prot_classes[CL_ILLUSION]
+                            = effekt/20;
+    tell_object(environment(), break_string(
+        "Du hast das Gefuehl, dass von Hekate beschenkte Wesenheiten Dir "
+        +num2desc_fight(effekt)
+        + " weniger anhaben koennen.",78));
+    return 1;
+  }
+  return 0;
+}
+
+private int act_attr_prot_undead(int effekt)
+{
+  if (reg_hook(H_HOOK_DEFEND, H_DATA_MODIFICATOR) == 1)
+  {
+    // Zombies, Skelette, Ghule...
+    if (!mappingp(prot_classes)) prot_classes=m_allocate(1);
+    prot_classes[CL_UNDEAD] =  effekt/20;
+    tell_object(environment(), break_string(
+        "Du bist ploetzlich zuversichtlich, Angriffen der Kreaturen "
+        "des Hades "
+        + num2desc_fight(effekt)
+        + " besser widerstehen zu koennen.",78));
+    return 1;
+  }
+  return 0;
+}
+
+
+private int act_attr_tragen(int effekt)
+{
+  if ( IS_LEARNER(environment()) )
+    tell_object(environment(), sprintf("effekt: %d\n",effekt));
+  SetProp(P_WEIGHT, QueryProp(P_WEIGHT) - effekt*4);
+  tell_object(environment(),
+      BS("Du fuehlst Dich ploetzlich "+num2desc(effekt)
+        + (effekt>0 ? " entlastet" : " belastet") + "."));
+  return 1;
+}
+
+// Berechnet eine max. Verzoegerung der Wirkung abhaengig von der Wirkung und
+// einer Wirkschwelle. Der rel. Abstand von der Wirkschwelle (relativ zum max.
+// moeglichen Abstand) wird hierbei genutzt. Ausserdem ist die max.
+// Verzoegerung natuerlich die Wirkungsdauer des Trankes.
+// <duration> muss im Trank schon gesetzt sein.
+private int calc_max_delay(int effekt, int wirkschwelle)
+{
+  int abstand = abs(effekt - wirkschwelle);
+  if (!duration) duration = time()+600;
+  if ( IS_LEARNER(environment()) )
+    printf("calc_max_delay: %d\n",((duration-time()) * abstand) /
+      (2000-abs(wirkschwelle)));
+  return ((duration-time()) * abstand) / (2000-abs(wirkschwelle));
+}
+
+//TODO: die Zeitverzoegerung ist nen netter Effekt, aber zeitvergzoegerte
+//Tports sind oefter keine gute Idee -> noch pruefen
+//TODO: Die Zeitverzoegerung bei NO_TPORT_OUT auch nochmal pruefen
+private int act_attr_flee_tport(int effekt)
+{
+  // effekt > 0 teleportiert sofort zu halbwegs sicheren Orten
+  // -750 <= effekt < 0 teleportiert auch sofort zu nicht so dollen Orten
+  // -2000 <= effekt < -750 teleportiert spaeter zu bloeden Orten
+  if (effekt < -750 && effekt >= -2000)
+  {
+    // Verzoegerung ausrechnen und dies hier per call_out nochmal mit einem
+    // effekt rufen, der eine instantane Reaktion ausloest.
+    // effekt - 2000 ist ein Hack, damit nicht nochmal verzoegert wird.
+    call_out(#'act_attr_flee_tport,
+        random(calc_max_delay(effekt, -750))+1, effekt - 2000);
+    tell_object(environment(),
+        "Deine Umgebung fuehlt sich nach und nach unwirklicher an.\n");
+    return 1;
+  }
+
+  // Effekte instantan ausloesen.
+
+  // wenn hier kein P_NO_TPORT erlaubt ist, mal gucken, ob wir spaeter noch
+  // zeit haben.
+  if (environment(environment())->QueryProp(P_NO_TPORT)==NO_TPORT_OUT)
+  {
+    tell_object(environment(),
+        BS("Irgendetwas haelt Dich an diesem Ort fest."));
+    int delay = duration - time();
+    // wenn noch genug Restzeit, nochmal versuchen, sonst nix machen.
+    if (delay>10)
+    {
+      // AN/TODO: Kann das nicht auch ziemlich lang sein?
+      call_out(#'act_attr_flee_tport, random(delay), effekt);
+    }
+    return 0;
+  }
+
+  // den Hack von oben rueckgaengig machen, wir brauchen den originalen
+  // Effektwert zurueck.
+  if (effekt < -2000)
+    effekt += 2000;
+
+  string* dests;
+  if ( effekt > 0 )
+  {
+    switch(effekt)
+    {
+      case 0..499:
+        dests = ({"/d/inseln/zesstra/vulkanweg/room/r1",
+                  "/d/fernwest/li/xian/lab2/grab2",
+                  "/d/ebene/miril/schloss/heide11",
+                  "/d/polar/alle/room/weg4_15",
+                  "/d/dschungel/arathorn/tempel/room/t4-5",
+                  "/d/anfaenger/arathorn/minitut/room/huette_"+
+                    environment()->query_real_name(),
+                 });
+        break;
+      case 500..749:
+        dests = ({"/d/ebene/bertram/ebene/wasser8",
+                  "/d/ebene/room/gebuesch2_3",
+                  "/d/polar/alle/room/eiswueste/eiswueste[4,6]",
+                 });
+        if (environment()->QueryProp(P_REAL_RACE)!="Dunkelelf")
+          dests += ({"/d/unterwelt/padreic/kneipe/kneipe"});
+        break;
+      case 750..999:
+        dests = ({"/d/gebirge/silvana/cronoertal/room/tf4",
+                  "/d/inseln/schiffe/floss",
+                  "/d/polar/humni/hexen/room/leuchtkammer",
+                  "/d/polar/gabylon/temong/rooms/anlegestelle",
+                 });
+        break;
+      case 1000..1249:
+        dests = ({"/d/fernwest/shinobi/konfu_quest/room/insel4",
+                  "/d/fernwest/ulo/mura/tokoro/haus4",
+                  "/d/ebene/room/Halle/shalle14",
+                 });
+        break;
+      case 1250..1499:
+        dests = ({"/d/gebirge/silvana/cronoertal/room/tf4",
+                  "/gilden/zauberer",
+                  "/d/gebirge/georg/room/w11"
+                 });
+        break;
+      case 1500..1749:
+        dests = ({"/gilden/bierschuettler",
+                  "/gilden/kaempfer",
+                  "/d/wald/gundur/hobbitdorf/schrein",
+                  "/d/vland/morgoth/room/city/rathalle",
+                 });
+        break;
+      default:
+        dests = ({environment()->QueryProp(P_START_HOME)||
+                    environment()->QueryDefaultHome(),
+                  environment()->QueryDefaultHome(),
+                  "/d/ebene/room/PortVain/po_haf2",
+                  "/d/gebirge/room/he3x3",
+                  "/d/ebene/room/huette",
+                 });
+        break;
+    }
+  }
+  else if ( effekt < 0 )
+  {
+    switch(effekt)
+    {
+      case -499..0:
+        dests = ({"/d/polar/bendeigid/rooms/neskaya/neskay12",
+                  "/players/ketos/gl/room/gl1x1",
+                  "/d/inseln/zesstra/vulkanweg/room/r10",
+                  "/d/vland/morgoth/room/kata/ktanke",
+                  "/d/ebene/zardoz/burg/feuerrau",
+                 });
+        break;
+      case -999..-500:
+        dests = ({"/d/ebene/room/Hoehle/hg6",
+                  "/d/gebirge/silvana/warok/room/l3/wa_3x7",
+                  "/d/vland/morgoth/room/kata/xkat03",
+                  "/d/vland/morgoth/room/kata/kata5",
+                  "/d/wald/yoru/ort/dravi/weg5",
+                  "/d/wald/atamur/room/e83",
+                 });
+        break;
+      case -1499..-1000:
+        dests = ({"/d/polar/bendeigid/rooms/pass/pass_e1",
+                  "/d/ebene/room/gebuesch",
+                  "/d/gebirge/silvana/warok/room/l1/wa_1x6",
+                  "/d/vland/morgoth/room/kata/gkat17",
+                  "/d/wald/atamur/room/e12",
+                 });
+        if (environment()->QueryProp(P_REAL_RACE)=="Dunkelelf")
+          dests += ({"/d/unterwelt/padreic/kneipe/kneipe"});
+        break;
+      case -1749..-1500:
+        dests = ({"/d/dschungel/wurzel/t2",
+                  "/d/vland/morgoth/room/kata/ukat26",
+                  "/d/vland/morgoth/room/kata/h12",
+                  "/d/gebirge/boing/sm/l5/m5x2",
+                 });
+        if (environment()->QueryProp(P_GUILD)=="chaos")
+          dests+=({"/gilden/klerus"});
+        break;
+      default:
+        dests = ({"/d/ebene/rochus/room/sp10",
+                  "/d/ebene/rochus/quest_3player/room/schacht10",
+                 });
+        if ( IS_SEER(environment()) )
+          dests += ({"/d/wald/paracelsus/froom/sch_6e",
+                     "/d/wald/paracelsus/froom/sch_9x",
+                     "/d/wald/paracelsus/froom/sch2_6d",
+                    });
+        break;
+    }
+  }
+  tell_object(environment(),
+      BS("Eine Kraft zerrt an Dir, die Welt verschwimmt..."));
+  if (environment()->move(dests[random(sizeof(dests))],M_TPORT) == MOVE_OK)
+    tell_object(environment(),
+        "Einen Moment spaeter bist Du ganz woanders.\n");
+  else
+    tell_object(environment(),
+        "Aber sonst passiert nichts.\n");
+  return 1;
+}
+
+private int act_attr_change_dimension(int effekt)
+{
+  // nur effekt >= 1000 aendern die Dimension instantan. ;-)
+  if (effekt > 0 && effekt < 1000)
+  {
+    // Verzoegerung ausrechnen und dies hier per call_out nochmal mit einem
+    // effekt rufen, der eine instantane Reaktion ausloest.
+    call_out(#'act_attr_change_dimension,
+        random(calc_max_delay(effekt,1000))+1, 1000);
+    tell_object(environment(),BS("Um Dich herum wird alles "
+        "langsam grauer.\n"));
+    return 1;
+  }
+  // nur -600 < effekt < 0 aendern die Dimension instantan ;-)
+  if (effekt < -600)
+  {
+    // Verzoegerung ausrechnen und dies hier per call_out nochmal mit einem
+    // effekt rufen, der eine instantane Reaktion ausloest.
+    call_out(#'act_attr_change_dimension,
+        random(calc_max_delay(effekt, -600))+1, -601);
+    tell_object(environment(),BS("Um Dich herum wird alles "
+        "langsam grauer.\n"));
+    return 1;
+  }
+  // Effekte instantan ausloesen.
+  // wenn hier kein Para-Trans erlaubt ist, mal gucken, ob wir spaeter noch
+  // zeit haben.
+  if (environment(environment())->QueryProp(P_NO_PARA_TRANS))
+  {
+    int delay = duration - time();
+    // wenn noch genug Restzeit, nochmal versuchen, sonst nix machen.
+    if (delay>10)
+    {
+      call_out(#'act_attr_change_dimension, random(delay), effekt);
+      tell_object(environment(), BS("Die Welt um Dich wird ein "
+            "wenig grauer."));
+    }
+    return 0;
+  }
+  if ( effekt > 0 )
+  {
+    if ( environment()->QueryProp(P_PARA) > 0 )
+    {
+      environment()->SetProp(P_PARA, 0);
+      tell_object(environment(), BS("Fuer einen kurzen Moment siehst Du nur "
+          "ein graues Wabern um Dich herum, bevor die Welt wieder "
+          "normal aussieht.\n"));
+    }
+    else
+    {
+      tell_object(environment(), BS("Fuer einen kurzen Moment sieht alles um "
+            "Dich herum grau aus."));
+    }
+  }
+  else if ( effekt < 0 )
+  {
+    if ( !environment()->QueryProp(P_PARA) )
+    {
+      environment()->SetProp(P_PARA, 1);
+       tell_object(environment(), BS("Fuer einen kurzen Moment siehst Du nur "
+          "ein graues Wabern um Dich herum, bevor die Welt wieder "
+          "normal aussieht. Aber es bleibt ein ungutes Gefuehl.\n"));
+    }
+    else {
+      tell_object(environment(), BS("Fuer einen kurzen Moment sieht alles um "
+            "Dich herum grau aus."));
+    }
+  }
+  return 1;
+}
+
+private int act_attr_defrog(int effekt)
+{
+  // nur effekt > 1000 entfroscht instantan. ;-)
+  if (effekt > 0 && effekt < 1000)
+  {
+    // Verzoegerung ausrechnen und dies hier per call_out nochmal mit einem
+    // effekt rufen, der eine instantane Reaktion ausloest.
+    call_out(#'act_attr_defrog, random(calc_max_delay(effekt,1000))+1, 1000);
+    tell_object(environment(),BS(
+        "Du hoerst ploetzlich lautes Gequake, was langsam immer leiser "
+        "wird.\n"));
+    return 1;
+  }
+  // nur -500 < effekt < 0 froscht instantan ;-)
+  if (effekt < -500)
+  {
+    // Verzoegerung ausrechnen und dies hier per call_out nochmal mit einem
+    // effekt rufen, der eine instantane Reaktion ausloest.
+    call_out(#'act_attr_defrog, random(calc_max_delay(effekt, -500))+1, -501);
+    tell_object(environment(),BS(
+        "Du hoerst ploetzlich ganz leisess Gequake, was langsam immer lauter "
+        "wird.\n"));
+    return 1;
+  }
+
+  // Effekte instantan ausloesen.
+  if ( effekt > 0 )
+  {
+    if ( environment()->QueryProp(P_FROG) )
+    {
+      environment()->SetProp(P_FROG,0);
+      tell_object(PL, "Du fuehlst Dich deutlich weniger gruen.\n");
+    }
+    else
+    {
+      tell_object(environment(), break_string("Die Welt um Dich herum verliert "
+        "ploetzlich alle gruenen Farbtoene, die bald darauf allmaehlich "
+        "zurueckkehren.",78));
+    }
+  }
+  else if ( effekt < 0 ) {
+    if ( !environment()->QueryProp(P_FROG) ) {
+      environment()->SetProp(P_FROG, 1);
+      tell_object(environment(), "Quak!\n");
+    }
+    else {
+      tell_object(environment(), break_string("Deine Sicht verschwimmt, alles wird "
+        "intensiv gruen. Merkwuerdig. Zum Glueck ist das schnell wieder "
+        "vorbei.",78));
+    }
+  }
+  return 1;
+}
+
+private int act_attr_heal_lp(int effekt)
+{
+  if (effekt > 0)
+  {
+    tell_object(environment(),
+        BS("Du fuehlst Dich schlagartig "+num2desc(effekt)
+          + " besser."));
+    environment()->restore_hit_points(effekt/10);
+  }
+  else
+  {
+    tell_object(environment(),
+        BS("Du fuehlst Dich schlagartig "+num2desc(effekt)
+          + " schlechter."));
+    environment()->do_damage(-effekt/10);
+  }
+  return 1;
+}
+
+private int act_attr_heal_sp(int effekt)
+{
+  if (effekt > 0)
+  {
+    tell_object(environment(),
+        BS("Du fuehlst Dich schlagartig "+num2desc(effekt)
+          + " konzentrierter."));
+    environment()->restore_spell_points(effekt/10);
+  }
+  else
+  {
+    tell_object(environment(),
+        BS("Du fuehlst Dich schlagartig "+num2desc(effekt)
+          + " unkonzentrierter."));
+    environment()->reduce_spell_points(-effekt/10);
+  }
+  return 1;
+}
+
+
+private int modify_sa(string sa, int effekt)
+{
+  string msg;
+  switch (sa)
+  {
+    case SA_SPEED:
+      msg = "Du wirst gerade " + num2desc(effekt)
+            +(effekt>0 ? " schneller." : " langsamer.");
+      effekt = (effekt * 30) / 2000;
+      break;
+    case SA_DURATION:
+      msg = "Du wirst gerade " + num2desc(effekt)
+            +(effekt>0 ? " ausdauernder."
+                       : " weniger ausdauernd.");
+      effekt = (effekt * 25) / 2000;
+      break;
+    case SA_SPELL_PENETRATION:
+      msg = "Deine geistige Durchsetzungskraft hat sich gerade "
+            + num2desc(effekt)
+            +(effekt>0 ? " verbessert." : " verschlechtert.");
+      effekt = (effekt * 30) / 2000;
+      break;
+  }
+  if (environment()->ModifySkillAttribute(sa, effekt, duration-time()) ==
+        SA_MOD_OK)
+  {
+    tell_object(environment(),BS(msg));
+    return 1;
+  }
+  return 0;
+}
+
+private int act_attr_change_sa_speed(int effekt)
+{
+  return modify_sa(SA_SPEED, effekt);
+}
+private int act_attr_change_sa_duration(int effekt)
+{
+  return modify_sa(SA_DURATION, effekt);
+}
+private int act_attr_change_sa_spell_penetration(int effekt)
+{
+  return modify_sa(SA_SPELL_PENETRATION, effekt);
+}
+
+
+// Spieler MUSS das environment() sein!
+private void effekt()
+{
+  // Als erstes die Wirkungsdauer verwursten, einige Effekte brauchen
+  // <duration>.
+  // Wann laufen die Effekte denn spaetenstens ab?
+  duration = time() + data[T_EFFECT_DURATION];
+  call_out(#'terminate_effects, data[T_EFFECT_DURATION]);
+
+  // nur echte wirkungen beruecksichtigen, keine "Metadaten"
+  mapping effects = data & T_KRAUT_EFFECTS;
+  // fuer Spieler wird der Paratrans nicht stattfinden.
+  if (!IS_SEER(environment()))
+    m_delete(data, T_CHANGE_DIMENSION);
+
+  // Waehrend der Wirkung ist dieses Objekt schonmal unsichtbar.
+  SetProp(P_INVIS, 1);
+  // Gewicht nullen, bevor die Wirkungen aktiviert werden, da die
+  // Wirkung von T_CARRY ansonsten wieder deaktiviert wuerde. 
+  SetProp(P_WEIGHT, 0);
+  // neue, leere Flasche ins Inventar des Spielers bewegen.
+  clone_object(TRANKITEM)->move(environment(),M_NOCHECK|M_SILENT);
+
+  // auftrennen in positive und negative Effekte. Keys mit Wert 0 werden
+  // ignoriert.
+  mapping peff = filter(effects, function int (string k, int val)
+                        {return val > 0;});
+  mapping neff = filter(effects, function int (string k, int val)
+                        {return val < 0;});
+  // erst die positiven, dann die negativen Wirkungen aktivieren
+  // fuer jede Wirkung wird eine lfun act_<trankattribut>() gerufen, z.B.
+  // act_attr_tragen() (-> act_T_CARRY() )
+  mapping notactivated =
+          filter(peff, function int (string k, int val)
+              {return !funcall(symbol_function("act_"+k,this_object()), val);})
+         +
+          filter(neff, function int (string k, int val)
+              {return !funcall(symbol_function("act_"+k,this_object()), val);});
+  // Meldungen ausgeben ueber nicht aktivierte Wirkungen?
+  // TODO
+}
+
+static int cmd_trinken(string str, mixed *param)
+{
+  if (environment(this_object()) != PL)
+  {
+    write("Aus auf dem Boden liegende Flaschen trinkt es sich so "
+       "schlecht!\n");
+  }
+  else if (data==0)
+  {
+    write("Die Flasche ist leer, Du muesstest erst etwas hineinfuellen.\n");
+  }
+  else if (time()>expiry) 
+  {
+    write(BS("Irgendwie passiert nichts. Hattest Du vielleicht doch nur "
+      "klares Wasser abgefuellt?"));
+    data=0;
+  }
+  else {
+    // Die Sperrzeit muss hier separat berechnet werden, weil eine
+    // Anpassung der Wirkungsdauer im Krautmaster dazu fuehren wuerde,
+    // dass es keine instantan wirkenden Traenke mehr gaebe.
+    int blocktime = max(60+random(60), data[T_EFFECT_DURATION]);
+    if(environment()->check_and_update_timed_key(blocktime, DRINK_POTION)==-1)
+    {
+      write(BS("Du oeffnest die Flasche und trinkst ihren Inhalt aus."));
+      say(BS(PL->Name(WER, 0)+" oeffnet eine Flasche und trinkt sie in einem "
+        "Schluck aus."));
+      effekt();
+      // TODO: reicht das hier aus, oder muss das noch an anderen Stellen 
+      // eingebaut werden?
+      RemoveId(({"trank","kraeutertrank"}));
+    }
+    else {
+      tell_object(environment(), BS(
+        "Der letzte Trank wirkt noch ein wenig nach. Du kannst Deinem "
+        "Magen nicht so bald schon den naechsten zumuten."));
+    }
+  }
+  return 1;
+}
+
+public nomask int Fill(object *plants)
+{
+  if (!pointerp(plants)) return -1;
+  if (data) return -2;  // schon voll
+  data = PLANTMASTER->make_potion(plants);
+  AddId(({"trank","kraeutertrank"}));
+  if (mappingp(data))
+  {
+    // Pflanzen zerstoert der Master, wenns geklappt hat.
+    expiry=time()+data[T_EXPIRE];
+    SetProp(P_WEIGHT, 300);
+    return 1;
+  }
+  return -3;
+}
+
+void NotifyPlayerDeath(object vic, object killer, int exp)
+{
+  call_out("remove",1);
+}
