#charset "us-ascii"
#include "advlite.h"
/*
* OBJTIME EXTENSION
* Objective Time module
*/
/*
* The timeManager object is used to keep track of the notional game time
* in the OBJTIME EXTENSION.
*/
timeManager: InitObject
/*
* In case the game doesn't specify a starting date we default to midnight
* on January 1st 2000.
*/
currentTime = static new Date(2000, 1, 1)
/* Initialize the timeManager. */
execute()
{
/*
* Get our starting time from the gameMain object, unless we're
* getting it from the clockManager (in the SUBTIME extension).
*/
if(defined(clockManager) && clockManager.lastEvent)
;
else if(gameMain.propType(&gameStartTime) == TypeList)
currentTime = new Date(gameMain.gameStartTime...);
else if(gameMain.propType(&gameStartTime) == TypeObject
&& gameMain.gameStartTime.ofKind(Date))
currentTime = gameMain.gameStartTime;
/* Set up the PromptDaemon to reset certain values each turn. */
new PromptDaemon(self, &reset);
}
/* Reset action-dependent counts to zero for a new turn. */
reset()
{
/* Reset the additional time to 0. */
additionalTime = 0;
/* Reset the replacement time to nil */
replacementTime = nil;
}
/*
* The number of seconds to add to the time taken on the current turn in
* addition to the standard time for this action.
*/
additionalTime = 0
/*
* If this is not nil, use this as the number of seconds taken by the
* current turn instead of the number computed from the action plus
* additionalTime.
*/
replacementTime = nil
/*
* Advance the time at the end of a turn (during the afterAction
* processing).
*/
advanceTime(secs)
{
/*
* If we have set a replacementTime (via a call from takeTime()) then
* use that as the length of the action. Otherwise use the time from
* the action plus any time that's been added (or subtracted) via the
* addTime() function.
*/
secs = replacementTime == nil ? secs + additionalTime : replacementTime;
/*
* Don't allow time to go into reverse. Provided secs is positive, add
* secs seconds to the current time.
*/
if(secs > 0)
currentTime = currentTime.addInterval([0,0,0,0,0,secs]);
}
/*
* Return a string containing the current date and time formatted by fmt,
* where fmt is one of the strings specified in the SystemManual entry for
* Date.
*/
formatDate(fmt)
{
return currentTime.formatDate(fmt);
}
/*
* Set the current date and time. The possible arguments are those
* described for the Date constructor in the System Manual.
*/
setTime([args])
{
/*
* If the only argument supplied is a single string, add a nil
* timezone and the current date to make the reference date come out
* as the current date; this ensures that if the string specifies a
* time it will be interpreted as a time on the current in-game date,
* rather than the real-world date.
*/
if(args.length == 1 && dataType(args[1] == TypeSString))
currentTime = new Date(args[1], nil, currentTime);
/*
* Otherwise just pass all the arguments straight through to the Date
* constructor
*/
else
currentTime = new Date(args...);
}
/*
* Adjust the currentDate by interval, where interval is specified as for
* the interval argument for the addInterval method of the Date class, i.e.
* as a list in the format [years, months, days, hours, minutes, seconds],
* from which trailing zeroes may be omitted.
*
* interval may also be specified as an integer (in which case it will be
* taken as the number of minutes to advance) or as a BigNumber (in which
* case it will be taken as the number of hours).
*/
addInterval(interval)
{
/*
* If the interval is specified as a BigNumber, take that to be the
* number of hours.
*/
if(dataType(interval) == TypeObject && interval.ofKind(BigNumber))
interval = [0, 0, 0, interval];
/*
* If the interval is specified as an integer, take that to be the
* number of hours.
*/
if(dataType(interval) == TypeInt)
interval = [0, 0, 0, 0, interval];
currentTime = currentTime.addInterval(interval);
}
;
/*
* Modification to GameDef to add an additional property for use with
* the OBJTIME EXTENSION
*/
modify GameMainDef
/*
* The date and time at which this game notionally starts. This should be
* specified as a list of numbers in the format [year, month, day, hour,
* minute, second, millisecond]. Trailing zero elements may be omitted. We
* default to midnight on 1st January 2000, but game code should generally
* override this. [PART OF OBJTIME EXTENSION]
*/
gameStartTime = [2000, 1, 1, 0, 0, 0, 0]
;
/*
* Modifications to the Action class for use with the OBJTIME EXTENSION.
* The purpose of these modifications is to advance the game clock each turn.
*/
modify Action
/* Advance the notional game time [OBJTIME EXTENSION]*/
advanceTime()
{
if(advanceOnFailure || !actionFailed)
{
timeManager.advanceTime(timeTaken);
}
}
/*
* Flag: should the game time be advanced if this action fails? By default
* we allow it to advance, but this can be overridden to nil for actions
* that should take no time if they're not carried out. [OBJTIME EXTENSION]
*/
advanceOnFailure = true
/*
* The number of seconds it takes to carry out this action. By default we
* assume every action takes one minute, but this can be overridden either
* globally on the Action class or individually on each actiom.
* [OBJTIME EXTENSION]
*/
timeTaken = 60
/*
* The number of seconds to carry out this action as an implicit action.
* By default we don't take any, since the normal convention seems to be
* to count implicit actions as part of the main action, but this could be
* overridden to be, say, the same as timeTaken if zero-time implicit
* actions were felt to give an unfair advantage to timed puzzles.
* [OBJTIME EXTENSION]
*/
implicitTimeTaken = 0
/*
* Add our implicitTimeTaken to the total time taken for the turn.
* [OBJTIME EXTENSION]
*/
addImplicitTime()
{
addTime(implicitTimeTaken);
}
;
modify SystemAction
/*
* For OBJTIME extension; a SystemAction shouldn't normally take any game
* clock time.
*/
timeTaken = 0
;
/*
* A TimeFuse is a Fuse that executes either at a set time or after a set time
*
* obj and prop are the same as for Fuse, i.e. when the Fuse fires it will
* call the prop property of obj.
*
* interval may be speficied as a list, an integer, a BigNumber, a Date or a
* single-quoted string. A string or a Date specifies the time at which the
* Fuse will execute. Anything else specifies the time after which the Fuse
* will execute.
*
* If interval is a list it should be in the form [years, months, days, hours,
* minutes, seconds] (trailing elements can be omitted if they are zero). The
* Fuse will then execute after the interval
*
* If interval is an integer then it specifies the number of minutes into the
* future that the Fuse will execute.
*
* If interval is a BigNumber than it specifies the number of hours into the
* future that the Fuse will execute. E.g. 1.0 specifies 1 hour, while 2.5
* specifies 2 hours 30 minutes.
*
* If interval is a single-quoted String, then it specifies the time at which
* the Fuse will execute. The format may be any of the formats recognized by
* Date.parseDate (for which see the System Manual). For example '15:34' would
* specify that the Fuse is to execute at 15:34 on the current day, while
* '2014:06:22 15:34:00' would specify that the Fuse is to execute at 15:34 on
* 22nd June 2014 (game time, not real time).
*
* [PART OF THE OBJTIME EXTENSION]
*/
class TimeFuse: Fuse
construct(obj, prop, interval)
{
inherited Event(obj, prop);
switch(dataType(interval))
{
case TypeInt:
interval = [0, 0, 0, 0, interval];
/* Fall through deliberately */
case TypeList:
eventTime = timeManager.currentTime.addInterval(interval);
break;
case TypeSString:
eventTime = Date.parseDate(interval, nil,
timeManager.currentTime)[1];
break;
case TypeObject:
if(interval.ofKind(BigNumber))
{
eventTime = timeManager.currentTime.addInterval(
[0, 0, 0, interval]);
break;
}
if(interval.ofKind(Date))
{
eventTime = interval;
break;
}
/* Fall through deliberately if we're some other kind of object */
default:
DMsg(time fuse interval error, 'Bad interval <<interval>> supplied
to TimeFuse constructor. ');
break;
}
}
/* The time (as a Date object) at which this Fuse is set to activate */
eventTime = nil
/*
* If our eventTime is still in the future, return a turn count well into
* the future so we don't execute yet; otherwise return the current turn
* count so we do execute on this turn.
*/
getNextRunTime()
{
if(eventTime > timeManager.currentTime)
return gTurns + 100;
else
return gTurns;
}
;
/*
* A SenseTimeFuse is a TimeFuse that only displays its output if senseObj
* can sense obj via the sense passed in the senseProp parameter at the
* time the fuse executes.
* [PART OF THE OBJTIME EXTENSION]
*/
class SenseTimeFuse: TimeFuse
/*
* senseObj is the object which must be sensed for this Fuse's text to be
* displayed. senseProp is one of &canSee, &canReach, &canHear, &canSmell.
* If these parameters are omitted then the senseObj will be the same as
* the obj whose prop property is executed by the Fuse, and the senseProp
* will be &canSee, probably the most common case.
*/
construct(obj, prop, interval, senseProp = &canSee, senseObj = obj)
{
inherited(obj, prop, interval);
senseObj_ = senseObj;
senseProp_ = senseProp;
}
;
/*
* Modifications to TravelConnector for the OBJTIME EXTENSION. The purpose of
* these modifications is to allow different TravelConnectors to take different
* amounts of time to traverse.
*/
modify TravelConnector
/*
* The number of seconds it takes to traverse this connector (in addition
* to any that come from the Travel action). [OBJTIME EXTENSION ONLY]
*/
traversalTime = 0
/*
* If we want to vary the time to go through this TravelConnector
* depending on where the traveler is starting from (only really relevant
* for rooms), we can override this method instead. [OBJTIME EXTENSION ONLY]
*/
traversalTimeFrom(origin)
{
return traversalTime;
}
;
/*
* Modifications for OBJTIME extension, so make traversing a connector take a
* certain amount of game time.
*/
modify Room
/* Modified in OBJTIME EXTENSION to add the traversal time for entering the room. */
execTravel(actor, traveler, conn)
{
/* Note the actor's starting location */
local origin = actor.getOutermostRoom();
/* Carry out the inherited handling */
inherited(actor, traveler, conn);
/* Add the traversal time for this connector */
addTime(conn.traversalTimeFrom(origin));
}
;
/*
* Add a certain number of seconds to the current action time.
* [OBJTIME EXTENSION]
*/
addTime(secs)
{
timeManager.additionalTime += secs;
}
/*
* Make the current action take secs time in total; this overrides any
* previously calcuated time for this action.
* [OBJTIME EXTENSION]
*/
takeTime(secs)
{
timeManager.replacementTime = secs;
}
/*
* Make the GoTo action use TravelAction's timeTaken by
* default so that any overriding timeTaken on TravelAction
* will automatically be reflected on this travel-related
* action too. [OBJTIME EXTENSION]
*/
modify GoTo
timeTaken = TravelAction.timeTaken
;
/*
* Make the Continue action use TravelAction's timeTaken by
* default so that any overriding timeTaken on TravelAction
* will automatically be reflected on this travel-related
* action too. [OBJTIME EXTENSION]
*/
modify Continue
timeTaken = TravelAction.timeTaken
;
Adv3Lite Library Reference Manual
Generated on 03/07/2024 from adv3Lite version 2.1