/* putanim.c * opens an animation iff file by outputing the starting * bitmap. Then successive change frames may be output * followed by closing the file. * * written by G. Bonham May 1986 * SPARTA, Inc. * Laguna Hills, Calif */ #include #include #include #include #include #include #include #include typedef struct { UBYTE operation; /* =5 for RIFF style */ UBYTE mask; UWORD w,h; WORD x,y; ULONG abstime; /* for timing w.r.t. start of anim file in jiffies (notused)*/ ULONG reltime; /* for timing w.r.t. last frame in jiffies */ UBYTE interleave; /* =0 for XORing to two frames back, =1 for last frame (not used yet) */ UBYTE pad0; ULONG bits; UBYTE pad[16]; } AnimationHeader; #define BODY_BUFSIZE 512 #define MaxDepth 6 #define CkErr(exp) {if(ifferror == IFF_OKAY) ifferror = (exp);} GroupContext fileC, form1C, form2C; LONG Pop; static IFFP ifferror = 0; static UWORD bHw,bHh; static WORD bHx,bHy; BOOL OpenAnim(LONG file,struct BitMap *bm,WORD pageW,WORD pageH,WORD *colorMap,ULONG modes,BYTE *buffer,LONG bufsize); BOOL AddAnim(struct BitMap *bm,WORD pageW,WORD pageH,WORD pop,BYTE *buffer,LONG bufsize); BOOL AddAnim2(LONG *data,LONG ndata,LONG pop); BOOL CloseAnim(LONG file); VOID InitAnimHdr(AnimationHeader *aH,WORD op); /* =================================================== */ BOOL OpenAnim(LONG file,struct BitMap *bm,WORD pageW,WORD pageH,WORD *colorMap,ULONG modes,BYTE *buffer,LONG bufsize) { UBYTE depth; BitMapHeader bmHdr; if((ifferror = InitBMHdr(&bmHdr,bm,(WORD)mskNone,(WORD)cmpByteRun1,0,pageW,pageH)) == IFF_OKAY) { if(bufsize > 2 * BODY_BUFSIZE) { if(GWriteDeclare(file,buffer + BODY_BUFSIZE,(long)(bufsize - BODY_BUFSIZE)) < 0) ifferror = DOS_ERROR; bufsize = BODY_BUFSIZE; } } depth = bm -> Depth; if(depth > MaxDepth) depth = MaxDepth; CkErr(OpenWIFF(file,&fileC,(long)szNotYetKnown)); CkErr(StartWGroup(&fileC,(ID)FORM,(long)szNotYetKnown,ID_ANIM,&form1C)); CkErr(StartWGroup(&form1C,(ID)FORM,(long)szNotYetKnown,ID_ILBM,&form2C)); CkErr(PutCk(&form2C,ID_BMHD,(long)sizeof(BitMapHeader),(BYTE *)&bmHdr)); if(colorMap) CkErr(PutCMAP(&form2C,colorMap,depth)); CkErr(PutCk(&form2C,ID_CAMG,(long)sizeof(CamgChunk),(BYTE *)&modes)); CkErr(PutBODY(&form2C,bm,(long)NULL,&bmHdr,buffer,(long)bufsize)); CkErr(EndWGroup(&form2C)); CkErr(CloseWGroup(&form1C)); return((BOOL)(ifferror == IFF_OKAY)); } BOOL AddAnim(struct BitMap *bm,WORD pageW,WORD pageH,WORD pop,BYTE *buffer,LONG bufsize) { AnimationHeader animHdr; BitMapHeader bmHdr; /* InitBMHdr sets w and h and x and y in bmHdr */ Pop = pop; ifferror = InitBMHdr(&bmHdr,bm,(WORD)mskNone,(WORD)cmpByteRun1,0,pageW,pageH); bHx = bmHdr.x; bHy = bmHdr.y; bHw = bmHdr.w; bHh = bmHdr.h; InitAnimHdr(&animHdr,pop); CkErr(OpenWGroup(&fileC,&form1C)); CkErr(StartWGroup(&form1C,(ID)FORM,(long)szNotYetKnown,ID_ILBM,&form2C)); CkErr(PutCk(&form2C,ID_ANHD,(long)sizeof(AnimationHeader),(BYTE *)&animHdr)); CkErr(PutBODY(&form2C,bm,(long)NULL,&bmHdr,buffer,(long)bufsize)); CkErr(EndWGroup(&form2C)); CkErr(CloseWGroup(&form1C)); return((BOOL)(ifferror == IFF_OKAY)); } BOOL AddAnim2(LONG *data,LONG ndata,LONG pop) { AnimationHeader animHdr; InitAnimHdr(&animHdr,pop); CkErr(OpenWGroup(&fileC,&form1C)); CkErr(StartWGroup(&form1C,(ID)FORM,(long)szNotYetKnown,ID_ILBM,&form2C)); CkErr(PutCk(&form2C,ID_ANHD,(long)sizeof(AnimationHeader),(BYTE *)&animHdr)); CkErr(PutCk(&form2C,ID_DLTA,ndata,data)); CkErr(EndWGroup(&form2C)); CkErr(CloseWGroup(&form1C)); return((BOOL)(ifferror == IFF_OKAY)); } BOOL CloseAnim(LONG file) { Pop = 0; CkErr(PutCkEnd(&fileC)); CkErr(CloseWGroup(&fileC)); if(GWriteUndeclare(file) < 0 && ifferror == IFF_OKAY) ifferror = DOS_ERROR; return((BOOL)(ifferror == IFF_OKAY)); } VOID InitAnimHdr(AnimationHeader *aH,WORD op) { memset(aH,0,sizeof(AnimationHeader)); aH -> operation = op; }