/* Copyright (c) 1999, 2000 by Kevin Forchione. All Rights Reserved. */
/*
* TADS ADV.T/STD.T LIBRARY EXTENSION
* SMARTLIST.T
* version 1.0
*
* This file defines the sackItem class and modified class thing that
* allows for the implementation of a 'rucksack', into which the game
* automatically tidies away things for the player. The sackItem class
* will automatically move items from the player's possession to the
* designated sackItem once the player attempts to take more than the
* maximum bulk allocated for them.
*
*----------------------------------------------------------------------
* REQUIREMENTS
*
* + HTML TADS 2.2.6 or later
* + Requires ADV.T and STD.T
* + Should be #included after ADV.T and STD.T.
*
*----------------------------------------------------------------------
* IMPORTANT LIBRARY INTERFACE AND MODIFICATION
*
* This module modifies thing class doTake() method.
*
*----------------------------------------------------------------------
* COPYRIGHT NOTICE
*
* You may modify and use this file in any way you want, provided that
* if you redistribute modified copies of this file in source form, the
* copies must include the original copyright notice (including this
* paragraph), and must be clearly marked as modified from the original
* version.
*
*------------------------------------------------------------------------------
* REVISION HISTORY
*
* 99-03-10 programming begun.
*/
#define __SACKITEM_MODULE_
/*
* We modify only the totbulk logic of thing (the idea being that
* a player can only carry so much weight regardless of whether
* they have a sack or not.
*/
modify thing
doTake(actor) =
{
local totbulk, totweight;
if (totweight > actor.maxweight)
"%Your% load is too heavy. ";
else if (totbulk > actor.maxbulk)
{
if ( self.moveToSackItem( actor ) )
{
self.moveInto( actor );
"Taken. ";
}
else
"%You've% already got %your% hands full. ";
}
else
{
self.moveInto(actor);
"Taken. ";
}
}
/*
* This is the heart of the sackItem logic. The logic does not
* check for multiple sackItems, it takes the first one it finds
* Also it does not attempt to optimise the placement of items
* in the sackItem, except that items that are lit or that are
* being worn are not chosen.
*/
moveToSackItem( actor ) =
{
local c, n := [], o, s, totbulk;
/*
* determine if the actor is carrying a sackItem
*/
c := actor.contents;
o := car( c );
while( o )
{
if ( isclass( o, sackItem ) )
{
break;
}
c := cdr( c );
o := car( c );
};
s := o; // sackItem value
if ( s = nil ) return nil;
c := actor.contents - [ s ]; // exclude the sackItem
/*
* Select items that aren't being worn or that aren't lit as
* candidates for the sackItem.
*/
o := car( c );
while( o )
{
if ( not o.isworn and not o.islit )
{
n := n + [ o ];
}
c := cdr( c );
o := car( c );
}
/*
* Determine if an object will fit in the sack and move it
* if it does.
*/
o := car( n );
while( o )
{
totbulk := addbulk( s.contents ) + o.bulk;
if ( totbulk <= s.maxbulk )
{
o.moveInto( s );
"(putting <<o.thedesc>> into <<s.thedesc>> to make room)\n";
return true;
};
n := cdr( n );
o := car( n );
}
return nil;
}
;
/*
* sackItem: openable, clothingItem
*
* This class allows an object to act like a 'rucksack', into which the
* game automatically tidies away things for the player.
*/
class sackItem: openable, clothingItem
maxbulk = 20
;