Ueberarbeitung clean_up()
- Umstellung von Schleifen auf foreach()
- RITEM_OBJECT ist nie ein Array
- Nur Objektpointer mittels -= auf Object-Array, nicht auf Array mit
Pfaden. Es werden alle gleichen Eintraege entfernt und damit werden
Objekte die einmal durch AddItem() hinzugefuegt und einmal sonst wie in
den Raum geraten sind nicht beachtet
- Praezisierung Kommentar
Change-Id: I587d4ad291af209d9bbd95fbd579532fa3fd2fea
diff --git a/std/room.c b/std/room.c
index 93845ba..7c9255f 100644
--- a/std/room.c
+++ b/std/room.c
@@ -108,8 +108,7 @@
return 0;
}
-int
-clean_up(int arg)
+public int clean_up(int arg)
{
// Never try again when P_NEVER_CLEAN is set.
if (Query(P_NEVER_CLEAN)) return 0;
@@ -120,50 +119,46 @@
if (arg>1 || HHasConsumers())
return 1;
- // if there are any items we have produced ourselfes check them
- mixed itema = QueryProp(P_ITEMS);
- if(pointerp(itema))
+ // Pruefen ob Spieler (auch netztote) anwesend sind.
+ // Es fuehrt leider kein Weg dran vorbei einmal über das inventar und einmal
+ // ueber P_ITEMS zu iterieren.
+ object* inv = all_inventory();
+ foreach(object ob : inv)
{
- mixed names;
- int i;
- i = sizeof(names = all_inventory(this_object()));
- while(i--)
+ if(query_once_interactive(ob))
{
- if (query_once_interactive(names[i]))
- {
- Set(" clean counter ",2);
- return 1;
- }
- if(objectp(names[i])) names[i] = explode(object_name(names[i]),"#")[0];
+ Set(" clean counter ",2);
+ return 1;
}
-
- for(i = sizeof(itema)-1; i >= 0; i--)
- {
- // Semantik:
- // 1. Wenn RITEM_OBJECT ein array ist, kann evtl ge'clean'ed werden.
- // 2. Wenn es ein REFRESH_NONE Item ist und es entweder nicht mehr
- // existiert oder nicht in diesem Raum ist, kein clean_up (es wuerde
- // beim neuladen des Raumes ja wieder erzeugt;
- // falls es aber hier ist, wird es mitvernichtet, dann ists ok)
- // 3. Wenn es ein REFRESH_DESTRUCT ist und noch existiert, aber nicht
- // hier ist, KEIN clean_up.
- if (!pointerp(itema[i][RITEM_OBJECT])
- && ((itema[i][RITEM_REFRESH] == REFRESH_NONE
- && (!itema[i][RITEM_OBJECT]
- || environment(itema[i][RITEM_OBJECT])!=this_object()))
- || (itema[i][RITEM_REFRESH] == REFRESH_DESTRUCT
- && itema[i][RITEM_OBJECT]
- && environment(itema[i][RITEM_OBJECT]) != this_object())))
- return 1;
- names -= (pointerp(itema[i][RITEM_FILE]) ?
- itema[i][RITEM_FILE] : ({ itema[i][RITEM_FILE] }));
- }
- // if there are objects left in the room do not clean up but try again later
- if(sizeof(names) && !check_clean_count()) return 1;
}
- else
- // is there any object lying around?
- if(first_inventory(this_object()) && !check_clean_count()) return 2;
+
+ // Auf Objekte aus P_ITEMS pruefen
+ foreach(<object|<string|string*>|int|mapping>* item : QueryProp(P_ITEMS))
+ {
+ // Semantik:
+ // 1. Wenn RITEM_OBJECT ein REFRESH_NONE Item ist und es entweder nicht mehr
+ // existiert oder nicht in diesem Raum ist, kein clean_up (es wuerde
+ // beim neuladen des Raumes ja wieder erzeugt;
+ // falls es aber hier ist, wird es mitvernichtet, dann ists ok)
+ // 2. Wenn es ein REFRESH_DESTRUCT ist und noch existiert, aber nicht
+ // hier ist, KEIN clean_up.
+ // Hier heisst fuer beide Faelle direkt in diesem Raum, befindet es sich in
+ // einem Container koennte es beim Zerstoeren woanders hin bewegt werden und
+ // damit nach dem neuladen doppelt existieren.
+ if( (item[RITEM_REFRESH] == REFRESH_NONE &&
+ (!item[RITEM_OBJECT] ||
+ environment(item[RITEM_OBJECT]) != ME))) ||
+ (item[RITEM_REFRESH] == REFRESH_DESTRUCT &&
+ item[RITEM_OBJECT] &&
+ environment(item[RITEM_OBJECT]) != ME)))
+ {
+ return 1;
+ }
+ inv -= ({item[RITEM_OBJECT]});
+ }
+ // if there are objects left in the room do not clean up but try again later
+ if(sizeof(inv) && !check_clean_count())
+ return 1;
// do clean_up
//log_file("clean_up_log",sprintf(