! -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
! `floating_contents': a new system for handling floating objects in Inform;
! either complements or replaces `found_in'.
! Giftware by Julian Arnold 1995 (Public Domain) Release 2.
! -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
! ===========================================================================
! The following declares a new property, `floating_contents'. This can be
! thought of as `found_in' in reverse. Thus, one might normally have object
! definitions such as:
! #OBJECT trees "trees"
! with ...
! found_in East_Woods North_Woods South_Woods West_Woods,
! ...
! #OBJECT bushes "bushes"
! with ...
! found_in East_Woods North_Woods South_Woods West_Woods,
! ...
!
! With the `floating_contents' property this becomes:
! #OBJECT East_Woods "East woods"
! with ...
! floating_contents trees bushes,
! ...
! #OBJECT North_Woods "North woods"
! with ...
! floating_contents trees bushes,
! ...
! Et cetera, et cetera.
!
! I have found that source using `floating_contents' is far easier to read
! and keep track of than the equivalent using `found_in', particularly when
! location definitions are in a different file to other object definitions.
! `found_in' has the benefit of being able to be a routine, which
! `floating_contents' may not be. However, I have found this not to be a
! very great problem in practice as routines are not often needed under such
! circumstances. Otherwise, `floating_contents' has the same limitations as
! `found_in'. In any case I have included below two methods to set up
! `floating_contents'. The first will declare an additional property, but
! allows the continued use of `found_in'. There would then be no problems
! with using, say, `found_in East_Wood' in the trees object and
! `floating_contents trees' in the East_Wood object at the same time in
! one's source. The second actually replaces the `found_in' property with
! `floating_contents' so no extra property space is taken up. This will
! also (marginally) speed up your game, as `found_in' necessitates searching
! through all the objects in the game every turn, while `floating_contents'
! on its own only considers the current location object and any "contained"
! objects. However, this method will preclude the use of `found_in' in your
! source (or rather you can use it, it just won't work). It might be
! possible to change `MoveFloatingObjects' so `floating_contents' could be a
! routine, but in such a case `floating_contents' would need very careful
! management by the author, and its nature would negate any speed increase,
! so I don't think it's worth doing.
! ===========================================================================
! ---------------------------------------------------------------------------
! METHOD A: use either `floating_contents' or `found_in' or both, but eats
! up one property.
! ---------------------------------------------------------------------------
! These two declarations should be dropped into your source *before* you
! #INCLUDE "verblib";
#REPLACE MoveFloatingObjects;
#PROPERTY floating_contents;
! Then put this routine into your code wherever you normally keep #REPLACEd
! routines.
[ MoveFloatingObjects i k l m f_address c_address;
for (i=selfobj+1: i<=top_object: i++)
{ f_address=i.&found_in;
if (f_address~=0 && i hasnt absent)
{ if (ZRegion(f_address-->0)==2)
{ if (indirect(f_address-->0)~=0) move i to location;
}
else
{ k=i.#found_in;
for (l=0: l<k/2: l++)
{ m=f_address-->l;
if (m==location || m in location) move i to location;
}
}
}
}
c_address=location.&floating_contents;
if (c_address~=0)
{ k=location.#floating_contents;
for (l=(k/2)-1: l>=0: l--)
{ m=c_address-->l;
if (m hasnt absent) move m to location;
}
}
];
! That's it. Now just remember the rules I've outlined above.
! ---------------------------------------------------------------------------
! METHOD B: use `floating_contents' only. `found_in' will not work
! properly, but at least no extra properties are used.
! ---------------------------------------------------------------------------
! This declaration should be dropped into your source immediately after you
! #INCLUDE "parser"; (BTW, it says in parser not to alias `found_in', but it
! seems to work in this case, perhaps because `floating_contents' does almost
! the same job)...
#PROPERTY floating_contents alias found_in;
! ...and this one *before* you #INCLUDE "verblib";
#REPLACE MoveFloatingObjects;
! Then put this routine into your code wherever you normally keep #REPLACEd
! routines.
[ MoveFloatingObjects k l m c_address;
c_address=location.&floating_contents;
if (c_address~=0)
{ k=location.#floating_contents;
for (l=(k/2)-1: l>=0: l--)
{ m=c_address-->l;
if (m hasnt absent) move m to location;
}
}
];
! Again that's it, just remember `found_in' no longer works.