home *** CD-ROM | disk | FTP | other *** search
Text File | 1996-04-30 | 16.3 KB | 567 lines | [TEXT/SPM ] |
- // StefSpriteStuff.c by Stefan Sinclair ©1995-1996 All Rights Reserved
-
- #include "Spritez.h"
- #include "SpriteCicnNumbers.h"
- #include "SpriteError.h"
- #include "SpriteSecretCodes.h"
-
- #define kErrorAlertID 150
- #define kEmptyString "\p"
-
- extern SpriteGameRec spriteGame;
- extern SndChannelPtr gSoundChanP1, gSoundChanP2, gSoundChanGame;
- extern Handle gP1SoundH[kNumSpriteSounds], gP2SoundH[kNumSpriteSounds];
- extern RgnHandle gWorkRgn; // defined in Spritez.c
- extern PixPatHandle gLifePixPatH;
- extern Point player1TopLeft, projectile1TopLeft;
- extern Point player2TopLeft, projectile2TopLeft;
- extern CWindowPtr gWindowP;
- extern Boolean gQT, gSoundOff, gSoundMax, gSoundMegaMax;
- extern short gSpriteHeight, gSpriteWidth;
- extern Rect gPlayer1DamageRect, gPlayer2DamageRect;
- extern Boolean gSecretCode[kNumSecretCodes];
-
- /** CombatMoveProc **/
- // Here, reset sprite frame range as necessary depending on current & previous actions.
- SW_FUNC void CombatMoveProc(SpritePtr srcSpriteP, Point* spritePoint)
- {
- unsigned char *spriteDataPtr; // use as an array of 8 u. chars.
- Boolean bSpriteAlive;
-
- // Access sprite's userData
- spriteDataPtr = (unsigned char *)&srcSpriteP->userData;
- // Assign the spritePoint to the correct sprite
- switch(spriteDataPtr[kSpriteIDNum])
- {
- case kPlayer1Sprite:
- case kComputer1Sprite:
- player1TopLeft = *spritePoint;
- break;
- case kPlayer2Sprite:
- case kComputer2Sprite:
- player2TopLeft = *spritePoint;
- break;
- default:
- DoError(kUnknownSpriteInGame, TRUE);
- break;
- }
-
- // Is the sprite still alive after this round of events?
- bSpriteAlive = PlayerStatusCheck(srcSpriteP, spritePoint);
- if(spriteDataPtr[kSpriteIDNum] == kPlayer1Sprite ||
- spriteDataPtr[kSpriteIDNum] == kComputer1Sprite)
- {
- gPlayer1DamageRect.left = kP1LifeRectLeft + spriteDataPtr[kSpriteLife] - kSpriteMinLife;
- FillCRect(&gPlayer1DamageRect, gLifePixPatH);
- }
- else
- {
- gPlayer2DamageRect.left = kP2LifeRectLeft + spriteDataPtr[kSpriteLife] - kSpriteMinLife;
- FillCRect(&gPlayer2DamageRect, gLifePixPatH);
- }
-
- // hit bottom - CHECKED IN GRAVITY CHECK
- // hit left wall
- if (srcSpriteP->destFrameRect.left <= srcSpriteP->moveBoundsRect.left)
- {
- srcSpriteP->horizMoveDelta = kMaxSpeed/2;
- spritePoint->h = srcSpriteP->moveBoundsRect.left + 1;
- }
- // hit right wall
- if (srcSpriteP->destFrameRect.right >= srcSpriteP->moveBoundsRect.right)
- {
- srcSpriteP->horizMoveDelta = -kMaxSpeed/2;
- spritePoint->h = srcSpriteP->moveBoundsRect.right - gSpriteWidth - 1;
- }
- }
-
- /** ProjectileMoveProc **/
- // Here, reset sprite frame range as necessary depending on current & previous actions.
- SW_FUNC void ProjectileMoveProc(SpritePtr srcSpriteP, Point* spritePoint)
- {
- unsigned char *spriteDataPtr; // use as an array of 8 u. chars.
- Boolean visible;
-
- // Access sprite's userData
- spriteDataPtr = (unsigned char *)&srcSpriteP->userData;
-
- visible = ProjectileStatusCheck(srcSpriteP, spritePoint);
- if(!visible)
- {
- srcSpriteP->horizMoveDelta = 0;
- srcSpriteP->vertMoveDelta = 0;
- SWSetSpriteVisible(srcSpriteP, FALSE);
- }
- // hit left wall
- else if (srcSpriteP->destFrameRect.left <= srcSpriteP->moveBoundsRect.left)
- {
- srcSpriteP->horizMoveDelta = 0;
- srcSpriteP->vertMoveDelta = 0;
- spriteDataPtr[kCurrentAction] = aProjectileIdle;
- SWSetSpriteVisible(srcSpriteP, FALSE);
- }
- // hit right wall
- else if (srcSpriteP->destFrameRect.right >= srcSpriteP->moveBoundsRect.right)
- {
- srcSpriteP->horizMoveDelta = 0;
- srcSpriteP->vertMoveDelta = 0;
- spriteDataPtr[kCurrentAction] = aProjectileIdle;
- SWSetSpriteVisible(srcSpriteP, FALSE);
- }
- // hit bottomwall
- else if (srcSpriteP->destFrameRect.bottom > srcSpriteP->moveBoundsRect.bottom)
- {
- srcSpriteP->horizMoveDelta = 0;
- srcSpriteP->vertMoveDelta = 0;
- spriteDataPtr[kCurrentAction] = aProjectileIdle;
- SWSetSpriteVisible(srcSpriteP, FALSE);
- }
- // hit top wall
- else if (srcSpriteP->destFrameRect.top <= srcSpriteP->moveBoundsRect.top)
- {
- srcSpriteP->horizMoveDelta = 0;
- srcSpriteP->vertMoveDelta = 0;
- spriteDataPtr[kCurrentAction] = aProjectileIdle;
- SWSetSpriteVisible(srcSpriteP, FALSE);
- }
- }
-
- // CombatSpriteCollideProc----------------------------------------------------------------
- void CombatSpriteCollideProc(SpritePtr srcSpriteP,SpritePtr dstSpriteP,Rect* sectRect)
- {
- register short tempDelta;
- Rect rgnRect;
- unsigned char *srcSpriteDataPtr,*dstSpriteDataPtr; // use as an array of 8 u. chars.
- short srcDrxn, dstDrxn, damage = 0;
- Boolean dstSpriteHit = FALSE, srcSpriteHit = FALSE, somebodyHit;
- static Boolean flipFlop; // to counter the player 1/2 advantage
-
- // Access sprite's userData
- srcSpriteDataPtr = (unsigned char *)&srcSpriteP->userData;
- dstSpriteDataPtr = (unsigned char *)&dstSpriteP->userData;
-
- // If both sprites use the same collision routine (this one),ignore the second collision.
- if ((!srcSpriteP->isVisible || !dstSpriteP->isVisible) ||
- ((srcSpriteP->spriteCollideProc == dstSpriteP->spriteCollideProc) &&
- (srcSpriteP > dstSpriteP)))
- return;
-
- rgnRect = (**srcSpriteP->curFrameP->maskRgn).rgnBBox;
-
- // move the mask region to the new sprite location
- OffsetRgn(srcSpriteP->curFrameP->maskRgn,
- (srcSpriteP->destFrameRect.left - rgnRect.left) +
- srcSpriteP->curFrameP->offsetPoint.h,
- (srcSpriteP->destFrameRect.top - rgnRect.top) +
- srcSpriteP->curFrameP->offsetPoint.v);
-
- rgnRect = (**dstSpriteP->curFrameP->maskRgn).rgnBBox;
-
- // move the mask region to the new sprite location
- OffsetRgn(dstSpriteP->curFrameP->maskRgn,
- (dstSpriteP->destFrameRect.left - rgnRect.left) +
- dstSpriteP->curFrameP->offsetPoint.h,
- (dstSpriteP->destFrameRect.top - rgnRect.top) +
- dstSpriteP->curFrameP->offsetPoint.v);
-
- SectRgn(srcSpriteP->curFrameP->maskRgn, dstSpriteP->curFrameP->maskRgn, gWorkRgn);
-
- if (!EmptyRgn(gWorkRgn)) // There is an overlap
- {
- Point sPt;
- Boolean srcSide;
-
- // A sprite's projectile cannot damage him or herself
- // Player 1
- if((srcSpriteDataPtr[kSpriteIDNum] == kPlayer1Sprite) &&
- (dstSpriteDataPtr[kSpriteIDNum] == kPlayer1ProjectileSprite))
- return;
- if((srcSpriteDataPtr[kSpriteIDNum] == kComputer1Sprite) &&
- (dstSpriteDataPtr[kSpriteIDNum] == kPlayer1ProjectileSprite))
- return;
- if((srcSpriteDataPtr[kSpriteIDNum] == kPlayer1ProjectileSprite) &&
- (dstSpriteDataPtr[kSpriteIDNum] == kPlayer1Sprite))
- return;
- if((srcSpriteDataPtr[kSpriteIDNum] == kPlayer1ProjectileSprite) &&
- (dstSpriteDataPtr[kSpriteIDNum] == kComputer1Sprite))
- return;
- // Player 2
- if((srcSpriteDataPtr[kSpriteIDNum] == kPlayer2Sprite) &&
- (dstSpriteDataPtr[kSpriteIDNum] == kPlayer2ProjectileSprite))
- return;
- if((srcSpriteDataPtr[kSpriteIDNum] == kComputer2Sprite) &&
- (dstSpriteDataPtr[kSpriteIDNum] == kPlayer2ProjectileSprite))
- return;
- if((srcSpriteDataPtr[kSpriteIDNum] == kPlayer2ProjectileSprite) &&
- (dstSpriteDataPtr[kSpriteIDNum] == kPlayer2Sprite))
- return;
- if((srcSpriteDataPtr[kSpriteIDNum] == kPlayer2ProjectileSprite) &&
- (dstSpriteDataPtr[kSpriteIDNum] == kComputer1Sprite))
- return;
-
- // Where am I?
- switch(srcSpriteDataPtr[kSpriteIDNum])
- {
- case kPlayer1Sprite:
- case kComputer1Sprite:
- sPt = player1TopLeft;
- break;
- case kPlayer2Sprite:
- case kComputer2Sprite:
- sPt = player2TopLeft;
- break;
- case kPlayer1ProjectileSprite:
- sPt = projectile1TopLeft;
- break;
- case kPlayer2ProjectileSprite:
- sPt = projectile2TopLeft;
- break;
- }
- // Which drxn to go if hit?
- srcSide = GetSpriteSide(srcSpriteDataPtr);
- if(srcSide == kLeftSide)
- {
- srcDrxn = -2; // I go left
- dstDrxn = 2; // You go right
- }
- else
- {
- srcDrxn = 2; // I go right
- dstDrxn = -2; // You go left
- }
-
- somebodyHit = ((srcSpriteDataPtr[kCurrentAction] == aKick ||
- srcSpriteDataPtr[kCurrentAction] == aPunch ||
- srcSpriteDataPtr[kCurrentAction] == aUppercut ||
- srcSpriteDataPtr[kCurrentAction] == aJumpAttack ||
- srcSpriteDataPtr[kCurrentAction] == aJumpPunch ||
- srcSpriteDataPtr[kCurrentAction] == aJumpKick ||
- srcSpriteDataPtr[kCurrentAction] == aProjectileShoot) ? TRUE : FALSE);
- if(somebodyHit)
- {
- switch(srcSpriteDataPtr[kSpriteIDNum])
- {
- case kPlayer1Sprite:
- case kComputer1Sprite:
- PlaySound(gP1SoundH[sGotHit], gSoundChanP1);
- break;
- case kPlayer2Sprite:
- case kComputer2Sprite:
- PlaySound(gP2SoundH[sGotHit], gSoundChanP2);
- break;
- }
- switch(srcSpriteDataPtr[kCurrentAction])
- {
- case aKick:
- case aPunch:
- case aJumpAttack:
- case aJumpKick:
- case aJumpPunch:
- case aProjectileShoot:
- // swap h/v delta's
- dstSpriteP->horizMoveDelta = kWhipLashVelocity*dstDrxn;
- if(dstSpriteDataPtr[kCurrentAction] != aBlock)
- {
- dstSpriteHit = TRUE;
- }
- break;
- case aUppercut:
- // swap h/v delta's
- dstSpriteP->horizMoveDelta = kWhipLashVelocity*dstDrxn;
- if(dstSpriteDataPtr[kCurrentAction] != aBlock)
- {
- dstSpriteP->vertMoveDelta = -10*kWhipLashVelocity;
- dstSpriteHit = TRUE;
- }
- break;
- }
- }
- somebodyHit = ((dstSpriteDataPtr[kCurrentAction] == aKick ||
- dstSpriteDataPtr[kCurrentAction] == aPunch ||
- dstSpriteDataPtr[kCurrentAction] == aUppercut ||
- dstSpriteDataPtr[kCurrentAction] == aJumpAttack ||
- dstSpriteDataPtr[kCurrentAction] == aJumpPunch ||
- dstSpriteDataPtr[kCurrentAction] == aJumpKick ||
- dstSpriteDataPtr[kCurrentAction] == aProjectileShoot) ? TRUE : FALSE);
- if(somebodyHit)
- {
- switch(srcSpriteDataPtr[kSpriteIDNum])
- {
- case kPlayer1Sprite:
- case kComputer1Sprite:
- PlaySound(gP1SoundH[sGotHit], gSoundChanP1);
- break;
- case kPlayer2Sprite:
- case kComputer2Sprite:
- PlaySound(gP2SoundH[sGotHit], gSoundChanP2);
- break;
- }
- switch(dstSpriteDataPtr[kCurrentAction])
- {
- case aKick:
- case aPunch:
- case aJumpAttack:
- case aJumpKick:
- case aJumpPunch:
- case aProjectileShoot:
- // swap h/v delta's
- srcSpriteP->horizMoveDelta = kWhipLashVelocity*srcDrxn;
- if(srcSpriteDataPtr[kCurrentAction] != aBlock)
- {
- srcSpriteHit = TRUE;
- }
- break;
- case aUppercut:
- // swap h/v delta's
- srcSpriteP->horizMoveDelta = kWhipLashVelocity*srcDrxn;
- if(srcSpriteDataPtr[kCurrentAction] != aBlock)
- {
- srcSpriteP->vertMoveDelta = -10*kWhipLashVelocity;
- srcSpriteHit = TRUE;
- }
- break;
- }
- }
- // Was anybody hurt?
- // Only 1 hit per attack move!!!
- if(flipFlop) // to counter the player 1/2 advantage
- {
- flipFlop = FALSE;
- //goto FLIP_FLOP; // I did have this uncommented
- }
- else
- {
- flipFlop = TRUE;
- }
-
- if(srcSpriteHit && srcSpriteDataPtr[kCurrentAction] != aGotHit
- && dstSpriteDataPtr[kCurrentAction] != aDying)
- {
- srcSpriteDataPtr[kCurrentAction] = aGotHit;
- switch(dstSpriteDataPtr[kCurrentAction])
- {
- case aPunch:
- damage = kPunchDamage;
- dstSpriteDataPtr[kCurrentAction] = aPostAttack;
- break;
- case aKick:
- damage = kKickDamage;
- dstSpriteDataPtr[kCurrentAction] = aPostAttack;
- break;
- case aUppercut:
- damage = kUppercutDamage;
- dstSpriteDataPtr[kCurrentAction] = aPostAttack;
- break;
- case aProjectileShoot:
- damage = kProjectileDamage;
- dstSpriteDataPtr[kCurrentAction] = aProjectileIdle;
- break;
- case aJumpAttack:
- damage = kJumpAttackDamage;
- dstSpriteDataPtr[kCurrentAction] = aPostJumpAttack;
- break;
- case aJumpPunch:
- damage = kJumpPunchDamage;
- dstSpriteDataPtr[kCurrentAction] = aPostJumpAttack;
- break;
- case aJumpKick:
- damage = kJumpKickDamage;
- dstSpriteDataPtr[kCurrentAction] = aPostJumpAttack;
- break;
- default:
- break;
- }
- srcSpriteDataPtr[kSpriteLife] -= damage;
- // Double damage code?
- if(gSecretCode[kDoubleDamageCode])
- srcSpriteDataPtr[kSpriteLife] -= damage;
- }
- FLIP_FLOP:
- // reset damage to zero
- damage = 0;
- if(dstSpriteHit && dstSpriteDataPtr[kCurrentAction] != aGotHit
- && dstSpriteDataPtr[kCurrentAction] != aDying)
- {
- dstSpriteDataPtr[kCurrentAction] = aGotHit;
- switch(srcSpriteDataPtr[kCurrentAction])
- {
- case aPunch:
- damage = kPunchDamage;
- // Double damage code?
- if(gSecretCode[kDoubleDamageCode])
- dstSpriteDataPtr[kSpriteLife] -= kPunchDamage;
- srcSpriteDataPtr[kCurrentAction] = aPostAttack;
- break;
- case aKick:
- damage = kKickDamage;
- srcSpriteDataPtr[kCurrentAction] = aPostAttack;
- break;
- case aUppercut:
- damage = kUppercutDamage;
- srcSpriteDataPtr[kCurrentAction] = aPostAttack;
- break;
- case aProjectileShoot:
- damage = kProjectileDamage;
- srcSpriteDataPtr[kCurrentAction] = aProjectileIdle;
- break;
- case aJumpAttack:
- damage = kJumpAttackDamage;
- srcSpriteDataPtr[kCurrentAction] = aPostJumpAttack;
- break;
- case aJumpPunch:
- damage = kJumpPunchDamage;
- srcSpriteDataPtr[kCurrentAction] = aPostJumpAttack;
- break;
- case aJumpKick:
- damage = kJumpKickDamage;
- srcSpriteDataPtr[kCurrentAction] = aPostJumpAttack;
- break;
- default:
- break;
- }
- dstSpriteDataPtr[kSpriteLife] -= damage;
- // Double damage code?
- if(gSecretCode[kDoubleDamageCode])
- dstSpriteDataPtr[kSpriteLife] -= damage;
- }
- }
- }
-
- /********** PlaySound ***************/
- /* March 1995 */
- void PlaySound(Handle soundHandle, SndChannelPtr sndChan)
- {
- OSErr err;
- SndCommand command;
- SCStatus theStatus;
- long offset;
-
- if(gSoundOff == TRUE) // accessed via secret menu
- return;
- if(soundHandle == NULL)
- DoError(kNULLSoundHandle, TRUE);
- //HLock(soundHandle); - I lock them ahead of time.
- if(sndChan == NULL)
- DoError(kNULLSoundChannel,TRUE);
- if(SndChannelBusy(sndChan))
- {
- command.cmd = flushCmd;
- command.param1 = command.param2 = 0;
- err = SndDoImmediate( sndChan, &command);
- if(err)
- DoError(kCouldNotFlushSoundChannel, TRUE);
- command.cmd = quietCmd;
- command.param1 = command.param2 = 0;
- err = SndDoImmediate( sndChan, &command);
- if(err)
- DoError(kCouldNotQuietSoundChannel, TRUE);
- }
- if(gSoundMax == TRUE) // accessed via a hidden menu
- {
- command.cmd = volumeCmd;
- command.param1 = 0; // unused
- command.param2 = 0x03000300; // 3X Full volume! whoa!
- err = SndDoImmediate(sndChan, &command);
- if(err != noErr)
- DoError(kNeedSoundMgr3ForMegaVolume, TRUE);
- }
- if(gSoundMegaMax == TRUE) // accessed via a hidden menu
- {
- command.cmd = volumeCmd;
- command.param1 = 0; // unused
- command.param2 = 0x07000700; // 7X Full volume! ZOINKS!!!
- err = SndDoImmediate(sndChan, &command);
- if(err != noErr)
- DoError(kNeedSoundMgr3ForMegaVolume, TRUE);
- }
- err = GetSoundHeaderOffset( (SndListHandle)soundHandle,&offset);
- if(err != noErr)
- DoError(kCouldNotGetSoundHeaderOffset, TRUE);
- command.cmd = bufferCmd;
- command.param1 = 0;
- command.param2 = (long)(*soundHandle + offset);
- err = SndDoImmediate( sndChan,&command);
- if( err != noErr)
- DoError(kSoundBufferError, TRUE);
- }
-
- /********** PlaySound ***************/
- /* April 1996 */
- void LoopSound(Handle soundHandle, SndChannelPtr sndChan)
- {
- OSErr err;
- SndCommand command;
- SCStatus theStatus;
- long offset;
-
- if(gSoundOff == TRUE) // accessed via secret menu
- return;
- if(soundHandle == NULL)
- DoError(kNULLSoundHandle, TRUE);
- //HLock(soundHandle); - I lock them ahead of time.
- if(sndChan == NULL)
- DoError(kNULLSoundChannel,TRUE);
- if(SndChannelBusy(sndChan))
- {
- return; // it's busy playing already!
- }
- err = GetSoundHeaderOffset( (SndListHandle)soundHandle,&offset);
- if(err != noErr)
- DoError(kCouldNotGetSoundHeaderOffset, TRUE);
- command.cmd = bufferCmd;
- command.param1 = 0;
- command.param2 = (long)(*soundHandle + offset);
- err = SndDoImmediate( sndChan,&command);
- if( err != noErr)
- DoError(kSoundBufferError, TRUE);
- }
-
- /********** PlaySound ***************/
- /* March 1995 */
- void StopPlayingSound(SndChannelPtr sndChan)
- {
- OSErr err;
- SndCommand command;
-
- if(sndChan == NULL)
- DoError(kNULLSoundChannel,TRUE);
- if(SndChannelBusy(sndChan))
- {
- command.cmd = flushCmd;
- command.param1 = command.param2 = 0;
- err = SndDoImmediate( sndChan, &command);
- if(err)
- DoError(kCouldNotFlushSoundChannel, TRUE);
- command.cmd = quietCmd;
- command.param1 = command.param2 = 0;
- err = SndDoImmediate( sndChan, &command);
- if(err)
- DoError(kCouldNotQuietSoundChannel, TRUE);
- }
- }
-
- /* CODE EXAMPLE #1 */
- short isPressed(unsigned short k)
- // k = any keyboard scan code, 0-127
- {
- unsigned char km[16];
-
- StefGetKeys;
- return ( ( km[k>>3] >> (k & 7) ) & 1);
- }
-
- void StartWaiting(void)
- {
- Cursor watchCurs;
- CursHandle watchCursH;
-
- watchCursH = GetCursor(watchCursor);
- watchCurs = **watchCursH;
- SetCursor(&watchCurs);
- DisposeHandle((Handle)watchCursH);
- }
-
- void StopWaiting(void)
- {
- SetCursor(&qd.arrow);
- }