/****************************************************************************\ * * * C R E A T O R O F L E G E N D S * * (AberMud Version 5) * * * * The Creator Of Legends System is (C) Copyright 1989 Alan Cox, All Rights * * Reserved. * * * \****************************************************************************/ /* * Substructure handlers * * 1.00 Handlers For ROOM PLAYER OBJECT * 1.02 Exit Handlers Added For GENEXIT * 1.03 Message And Conditional Exit Drivers Added * 1.10 New SubTypes CONTAINER and CHAIN * 1.12 BACKTRACK System Added - Avoids Players Sticking On UserItems * 1.13 Fixed bug in UnGenExit * 1.14 Added INHERIT * 1.15 Fixed bug in UnUserFlag * 1.16 Register Optimisations Added * 1.17 SetIn SetOut SetHere added * 1.18 BACKTRACK system dumped * 1.19 USERTEXT added * 1.20 Tidying for release 5.06 * 1.21 Added USERFLAG2 Entries, Added working CondExit system(at last) * 1.22 Strict ANSIfication */ #include "System.h" Module "Substructure Handler"; Version "1.22"; Author "----*(A)"; int MakeRoom(ITEM *x) { register ROOM *a; if(FindSub(x,KEY_ROOM)) return(-1); /* Already is */ a=(ROOM *)AllocSub(x,KEY_ROOM,sizeof(ROOM)); a->rm_Short=AllocText("Room"); a->rm_Long=AllocText("Description"); a->rm_Flags=0; return(0); } int UnRoom(ITEM *i) { register ROOM *x=(ROOM *)FindSub(i,KEY_ROOM); if(x==NULL) return(-1); FreeText(x->rm_Short); FreeText(x->rm_Long); FreeSub(i,(SUB *)x); return(0); } int MakeObject(ITEM *x) { register OBJECT *a; if(FindSub(x,KEY_OBJECT)) return(-1); /* Already is */ a=(OBJECT *)AllocSub(x,KEY_OBJECT,sizeof(OBJECT)); a->ob_Text[0]=AllocText("<unset>"); a->ob_Text[1]=AllocText(""); a->ob_Text[2]=AllocText(""); a->ob_Text[3]=AllocText(""); a->ob_Size=0; a->ob_Weight=0; a->ob_Flags=0; return(0); } int UnObject(ITEM *i) { register OBJECT *x=(OBJECT *)FindSub(i,KEY_OBJECT); if(x==NULL) return(-1); FreeText(x->ob_Text[0]); FreeText(x->ob_Text[1]); FreeText(x->ob_Text[2]); FreeText(x->ob_Text[3]); FreeSub(i,(SUB *)x); return(0); } int MakePlayer(ITEM *x) { register PLAYER *a; if(FindSub(x,KEY_PLAYER)) return(-1); /* Already is */ a=(PLAYER *)AllocSub(x,KEY_PLAYER,sizeof(PLAYER)); a->pl_UserKey=-1; a->pl_Size=0; a->pl_Weight=0; a->pl_Flags=0; a->pl_Level=0; a->pl_Score=0; a->pl_Strength=0; return(0); } int UnPlayer(ITEM *i) { register PLAYER *x=(PLAYER *)FindSub(i,KEY_PLAYER); if(x==NULL) return(-1); FreeSub(i,(SUB *)x); return(0); } int MakeGenExit(ITEM *x) { register GENEXIT *a; if(FindSub(x,KEY_GENEXIT)) /* Only one genexit a room */ return(-1); /* Already is */ a=(GENEXIT *)AllocSub(x,KEY_GENEXIT,sizeof(GENEXIT)); a->ge_Dest[0]=0; a->ge_Dest[1]=0; a->ge_Dest[2]=0; a->ge_Dest[3]=0; a->ge_Dest[4]=0; a->ge_Dest[5]=0; a->ge_Dest[6]=0; a->ge_Dest[7]=0; a->ge_Dest[8]=0; a->ge_Dest[9]=0; a->ge_Dest[10]=0; a->ge_Dest[11]=0; return(0); } int UnGenExit(ITEM *i) { register short ct=0; register GENEXIT *x=(GENEXIT *)FindSub(i,KEY_GENEXIT); if(x==NULL) return(-1); while(ct<12) { if(x->ge_Dest[ct]) UnlockItem(x->ge_Dest[ct]); /* Exits should be locked on add */ ct++; } FreeSub(i,(SUB *)x); return(0); } CONDEXIT *MakeCondExit(ITEM *x, ITEM *to, short table, short exit) { register CONDEXIT *a; a=(CONDEXIT *)FindCondExit(x,exit); if(a) UnCondExit(x,a); a=(CONDEXIT *)AllocSub(x,KEY_CONDEXIT,sizeof(CONDEXIT)); a->ce_ExitNumber=exit; a->ce_Table=table; a->ce_Dest=to; if(to) LockItem(to); /* Lock since referred to */ return(a); } CONDEXIT *MakeNLCondExit(ITEM *x, ITEM *to, short table, short exit) { register CONDEXIT *a; a=(CONDEXIT *)FindCondExit(x,exit); if(a) UnCondExit(x,a); a=(CONDEXIT *)AllocSub(x,KEY_CONDEXIT,sizeof(CONDEXIT)); a->ce_ExitNumber=exit; a->ce_Table=table; a->ce_Dest=to; return(a); } int UnCondExit(ITEM *i, register CONDEXIT *x) /* Sub to give which one to do*/ { if(x->ce_Dest!=NULL) UnlockItem(x->ce_Dest); FreeSub(i,(SUB *)x); return(0); } CONDEXIT *FindCondExit(ITEM *i, short d) { register CONDEXIT *a=(CONDEXIT *)FindSub(i,KEY_CONDEXIT); while(a) { if(a->ce_ExitNumber==d) return(a); a=(CONDEXIT *)NextSub((SUB *)a,KEY_CONDEXIT); } return(NULL); } MSGEXIT *MakeMsgExit(ITEM *x, ITEM *to, short d, char *msg) { register MSGEXIT *a; a=FindMsgExit(x,d); if(a) UnMsgExit(x,a); a=(MSGEXIT *)AllocSub(x,KEY_MSGEXIT,sizeof(MSGEXIT)); a->me_Dest=to; if(to) LockItem(a->me_Dest); a->me_ExitNumber=d; a->me_Text=AllocText(msg); return(a); } MSGEXIT *MakeNLMsgExit(ITEM *x, ITEM *to, short d, char *msg) { register MSGEXIT *a; a=FindMsgExit(x,d); if(a) UnMsgExit(x,a); a=(MSGEXIT *)AllocSub(x,KEY_MSGEXIT,sizeof(MSGEXIT)); a->me_Dest=to; a->me_ExitNumber=d; a->me_Text=AllocText(msg); return(a); } int UnMsgExit(ITEM *i, register MSGEXIT *x) { if(x->me_Dest) UnlockItem(x->me_Dest); FreeText(x->me_Text); FreeSub(i,(SUB *)x); return(0); } MSGEXIT *FindMsgExit(ITEM *i, short d) { register MSGEXIT *a=(MSGEXIT *)FindSub(i,KEY_MSGEXIT); while(a) { if(a->me_ExitNumber==d) return(a); a=(MSGEXIT *)NextSub((SUB *)a,KEY_MSGEXIT); } return(NULL); } int AddChain(ITEM *i, ITEM *t) { register CHAIN *c; if(FindChain(i,t)) return(1); c=(CHAIN *)AllocSub(i,KEY_CHAIN,sizeof(CHAIN)); c->ch_Chained=t; LockItem(t); return(1); } int AddNLChain(ITEM *i, ITEM *t) { register CHAIN *c; if(FindChain(i,t)) return(1); c=(CHAIN *)AllocSub(i,KEY_CHAIN,sizeof(CHAIN)); c->ch_Chained=t; LockItem(t); return(1); } CHAIN *FindChain(ITEM *i, ITEM *x) { register CHAIN *c; c=(CHAIN *)FindSub(i,KEY_CHAIN); while(c) { if(c->ch_Chained==x) return(c); c=(CHAIN *)NextSub((SUB *)c,KEY_CHAIN); } return(NULL); } int RemoveChain(ITEM *i, register ITEM *x) { register CHAIN *c; c=FindChain(i,x); if(c==NULL) return(-1); else { UnlockItem(x); FreeSub(i,(SUB *)c); } return(0); } void SynchChain(ITEM *i) { register CHAIN *c; c=(CHAIN *)FindSub(i,KEY_CHAIN); while(c) { SetState(c->ch_Chained,O_STATE(i)); c=(CHAIN *)NextSub((SUB *)c,KEY_CHAIN); } return; } CONTAINER *BeContainer(ITEM *x) { register CONTAINER *c=(CONTAINER *)FindSub(x,KEY_CONTAINER); if(c) return(NULL); c=(CONTAINER *)AllocSub(x,KEY_CONTAINER,sizeof(CONTAINER)); c->co_Volume=0; c->co_Flags=0; return(c); } int UnContainer(ITEM *x) { CONTAINER *c; if((c=(CONTAINER *)FindSub(x,KEY_CONTAINER))==NULL) return(-1); FreeSub(x,(SUB *)c); return(0); } int GetUserFlag(ITEM *i, int n) { USERFLAG *x; if(n<8) x=(USERFLAG *)FindSub(i,KEY_USERFLAG); else x=(USERFLAG *)FindSub(i,KEY_USERFLAG2); if(x==NULL) return(0); if((n<0)||(n>15)) { Log("Userflag out of range"); return(0); } return(x->uf_Flags[(short)(n%8)]); } ITEM *GetUserItem(ITEM *i, int n) { USERFLAG *x; if(n<8) x=(USERFLAG *)FindSub(i,KEY_USERFLAG); else x=(USERFLAG *)FindSub(i,KEY_USERFLAG2); if(x==NULL) return(0); if((n<0)||(n>15)) { Log("UserItem out of range"); return(0); } return(x->uf_Items[(short)(n%8)]); } void SetUserFlag(ITEM *i, int n, int m) { register USERFLAG *x; if(n<8) x=(USERFLAG *)FindSub(i,KEY_USERFLAG); else x=(USERFLAG *)FindSub(i,KEY_USERFLAG2); if(x==NULL) { x=(USERFLAG *)AllocSub(i,n<8?KEY_USERFLAG:KEY_USERFLAG2,sizeof(USERFLAG)); InitUserFlag(x); } if((n<0)||(n>15)) { Log("Userflag out of range"); return; } x->uf_Flags[n%8]=m; } void SetUserItem(ITEM *i, int n, ITEM *m) { register USERFLAG *x; if(n<8) x=(USERFLAG *)FindSub(i,KEY_USERFLAG); else x=(USERFLAG *)FindSub(i,KEY_USERFLAG2); if(x==NULL) { x=(USERFLAG *)AllocSub(i,n<8?KEY_USERFLAG:KEY_USERFLAG2, sizeof(USERFLAG)); InitUserFlag(x); } if((n<0)||(n>15)) { Log("UserItem out of range"); return; } if(x->uf_Items[n%8]) { UnlockItem(x->uf_Items[n%8]); } if(m) { LockItem(m); } x->uf_Items[n%8]=m; } int UnUserFlag(ITEM *x) { register USERFLAG *u=(USERFLAG *)FindSub(x,KEY_USERFLAG); UnUserBlock(u,x); u=(USERFLAG *)FindSub(x,KEY_USERFLAG2); if(u==NULL) return(-1); UnUserBlock(u,x); return(0); } int UnUserBlock(USERFLAG *u, ITEM *x) { register short ct=0; if(u==NULL) return(-1); while(ct<8) { if(u->uf_Items[ct]) { UnlockItem(u->uf_Items[ct]); } ct++; } FreeSub(x,(SUB *)u); return(0); } void InitUserFlag(register USERFLAG *x) { x->uf_Items[0]=NULL; x->uf_Items[1]=NULL; x->uf_Items[2]=NULL; x->uf_Items[3]=NULL; x->uf_Items[4]=NULL; x->uf_Items[5]=NULL; x->uf_Items[6]=NULL; x->uf_Items[7]=NULL; x->uf_Flags[0]=0; x->uf_Flags[1]=0; x->uf_Flags[2]=0; x->uf_Flags[3]=0; x->uf_Flags[4]=0; x->uf_Flags[5]=0; x->uf_Flags[6]=0; x->uf_Flags[7]=0; } int MakeInherit(ITEM *x, ITEM *y) { register INHERIT *a; if((a=(INHERIT *)FindSub(x,KEY_INHERIT))!=NULL) { a->in_Master=y; return(0); /* Already is */ } a=(INHERIT *)AllocSub(x,KEY_INHERIT,sizeof(INHERIT)); a->in_Master=y; LockItem(y); return(0); } int UnInherit(ITEM *i) { register INHERIT *x=(INHERIT *)FindSub(i,KEY_INHERIT); if(x==NULL) return(-1); UnlockItem(x->in_Master); FreeSub(i,(SUB *)x); return(0); } ITEM *Inheritor(ITEM *a) { INHERIT *b; b=(INHERIT *)FindSub(a,KEY_INHERIT); if(b==NULL) return(NULL); return(b->in_Master); } static USERTEXT *GetUT(ITEM *i) { register USERTEXT *u=(USERTEXT *)FindSub(i,KEY_USERTEXT); if(u) return(u); u=(USERTEXT *)AllocSub(i,KEY_USERTEXT,sizeof(USERTEXT)); u->ut_Text[0]=AllocText(""); u->ut_Text[1]=AllocText(""); u->ut_Text[2]=AllocText(""); u->ut_Text[3]=AllocText(""); u->ut_Text[4]=AllocText(""); u->ut_Text[5]=AllocText(""); u->ut_Text[6]=AllocText(""); u->ut_Text[7]=AllocText(""); return(u); } void UnUserText(ITEM *i) { USERTEXT *u=GetUT(i); if(u) { FreeText(u->ut_Text[0]); FreeText(u->ut_Text[1]); FreeText(u->ut_Text[2]); FreeText(u->ut_Text[3]); FreeText(u->ut_Text[4]); FreeText(u->ut_Text[5]); FreeText(u->ut_Text[6]); FreeText(u->ut_Text[7]); FreeSub(i,(SUB *)u); } } void SetUText(ITEM *i, int n, TPTR t) { USERTEXT *u=GetUT(i); FreeText(u->ut_Text[n]); u->ut_Text[n]=AllocText(TextOf(t)); } TPTR GetUText(ITEM *i, int n) { return(GetUT(i)->ut_Text[n]); } INOUTHERE *FindIOH(ITEM *i) { return((INOUTHERE *)FindSub(i,KEY_INOUTHERE)); } void KillIOH(ITEM *i) { SUB *s=FindSub(i,KEY_INOUTHERE); if(s) FreeSub(i,s); } INOUTHERE *GetIOH(ITEM *i) { register INOUTHERE *r=(INOUTHERE *)FindSub(i,KEY_INOUTHERE); if(r) return(r); r=(INOUTHERE *)AllocSub(i,KEY_INOUTHERE,sizeof(INOUTHERE)); r->io_InMsg=AllocText("arrives"); r->io_OutMsg=AllocText("goes"); r->io_HereMsg=AllocText("is here"); return(r); } void SetInMsg(ITEM *it, char *x) { INOUTHERE *i=GetIOH(it); FreeText(i->io_InMsg); i->io_InMsg=AllocText(x); } void SetOutMsg(ITEM *it, char *x) { INOUTHERE *i=GetIOH(it); FreeText(i->io_OutMsg); i->io_OutMsg=AllocText(x); } void SetHereMsg(ITEM *it, char *x) { INOUTHERE *i=GetIOH(it); FreeText(i->io_HereMsg); i->io_HereMsg=AllocText(x); } char *GetInMsg(ITEM *it) { INOUTHERE *i=FindIOH(it); if(i) return(TextOf(i->io_InMsg)); else return("arrives"); } char *GetOutMsg(ITEM *it) { INOUTHERE *i=FindIOH(it); if(i) return(TextOf(i->io_OutMsg)); else return("goes"); } char *GetHereMsg(ITEM *it) { INOUTHERE *i=FindIOH(it); if(i) return(TextOf(i->io_HereMsg)); else return("is here"); }