Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- import "std.zh"
- ////////////////////////////////////////////////////////////////
- //// Engine Constants.
- // Combo Flag for soft platforms.
- const int CF_SOFT = 98;
- //// Block Types.
- // An empty block.
- const int BLOCK_EMPTY = 0;
- // A fallthrough block.
- const int BLOCK_SOFT = 1;
- // A standard block.
- const int BLOCK_HARD = 2;
- //// Stair combo types.
- const int CT_NEG = 142;
- const int CT_CROSS = 143;
- const int CT_POS = 144;
- //// Custom Engine Constants.
- // Link's walk speed.
- const float LINK_WALK = 1.5;
- // Link's gravitic acceleration.
- const float LINK_GRAV = 0.16;
- // Link's terminal velocity.
- const float LINK_TERM = 3.2;
- ////////////////////////////////////////////////////////////////
- //// Global Variables
- ////////////////
- //// Link's State
- //// How to handle Link's movement.
- // We're letting the ZC engine handle movement.
- const int LINK_MODE_ENGINE = 0;
- // We're dealing with Link's movement ourselves.
- const int LINK_MODE_CUSTOM = 1;
- // We're moving link accourding to the stair system.
- const int LINK_MODE_STAIR = 2;
- // Link's current movement mode.
- int LinkMode = LINK_MODE_ENGINE;
- // Link's Location. This is so we can have fractional movement.
- float LinkX = 0;
- float LinkY = 0;
- // Link's Vertical Velocity.
- float LinkVy = 0;
- // What Link is standing on.
- int LinkBlock = BLOCK_HARD;
- // Link's jump speed.
- float LinkJump = -4;
- // Link's hop speed.
- float LinkHop = -1;
- //// Fake input since we're cancelling it.
- bool InputJump = false;
- bool PressJump = false;
- //// Various parts of Link's state from last frame.
- // Link's Position.
- float OldLinkX = 0;
- float OldLinkY = 0;
- int OldLinkAction = LA_NONE;
- //// Stair State.
- // On a down-left up-right stair.
- const int STAIR_NEG = -1;
- // Not on any stairs.
- const int STAIR_NONE = 0;
- // On an up-left down-right stair.
- const int STAIR_POS = 1;
- //// Stair Positioning - where we are on a stair.
- // We're in the middle of the stair.
- const int STAIR_MIDDLE = 0;
- // We're anchored to the side of a stair.
- const int STAIR_BOTTOM = 1;
- // We're anchored to a stair diagonally.
- const int STAIR_TOP = 2;
- // The current kind of stair that Link is standing on.
- int StairMode = STAIR_NONE;
- // If the stairs were mounted this frame.
- bool StairMount = false;
- // The combo position fo the stair that Link is anchored to.
- int StairLoc = -1;
- // Where we are on the stair.
- int StairPos = STAIR_MIDDLE;
- // The x position of the edge of the stairs.
- int StairEdgeX = -1;
- // The left edge of the stairs that Link is on.
- int StairLeft = 0;
- // The right edge of the stairs that Link is on.
- int StairRight = 0;
- // If the anchored stair has another above it.
- bool StairAbove = false;
- // If the anchored stair has another below it.
- bool StairBelow = false;
- // The y offset of the current stair.
- int StairY = 0;
- ////////////////
- //// Screen Change
- //// Screen State on the previous frame.
- // DMap from last frame.
- int OldDMap = -1;
- // DMap Screen from last frame.
- int OldDScreen = -1;
- // If the dmap has changed from the last frame.
- bool DMapChanged = false;
- // If the screen has changed from the last frame.
- bool ScreenChanged = false;
- // Used so that ScreenChanged is only set on the first frame
- // of a scrolling screen change.
- bool _ScreenChanged_ScrollFlag = false;
- // The ScreenChange FFC sets this so that maze screens can be used.
- bool _ScreenChanged_ForceFlag = false;
- // If the screen change has been handled by custom code.
- bool ScreenChangeHandled = true;
- // We're pretty sure that the screen change was caused by a warp of
- // some sort.
- const int SCREEN_CHANGE_WARP = -1;
- // Best guess for which direction we changed screens in
- // based on Link's current position.
- int ScreenChangeDir = SCREEN_CHANGE_WARP;
- global script Active {
- void run() {
- LinkX = Link->X;
- LinkY = Link->Y;
- while (true) {
- OldLink_Update1();
- ScreenChange_Update1();
- Stair_Update1();
- Input_Update1();
- //Input_Update2();
- // Performs Game Logic.
- Waitdraw();
- ScreenChange_Update2();
- DetermineLinkMode();
- // If we're not using custom movement, update Link's positioning
- // variables to match whatever the engine says.
- if (LinkMode == LINK_MODE_ENGINE) {
- LinkX = Link->X;
- LinkY = Link->Y;}
- // Perform custom movement.
- if (LinkMode == LINK_MODE_CUSTOM) {
- StairMode = STAIR_NONE;
- LinkCustomOnScreenChange();
- LinkCustomUpdatePosition();
- LinkCustomJump();
- LinkCustomMountStair();}
- // We could possibly switch to stair movement at this point.
- if (LinkMode == LINK_MODE_STAIR) {
- Link->Jump = 0;
- LinkStairOnScreenChange();
- LinkStairFindStair();
- LinkStairFallOff();}
- // And away from it at this point.
- if (LinkMode == LINK_MODE_STAIR) {
- LinkStairUpdatePosition();
- LinkStairJump();}
- LinkAdjust();
- // Wait for the screen to draw.
- // (You wouldn't think it from the name, right?)
- Waitframe();}}}
- // If the combo location (in units of tiles) is valid, it is returned.
- // otherwise, -1 is returned.
- int FindLoc(int tx, int ty) {
- if (tx < 0 || tx > 15 || ty < 0 || ty > 10) {
- return -1;}
- return tx + (ty << 4);}
- // Determine whether we'll be relying on the ZC engine for movement
- // or on this custom code.
- // Place after Waitdraw, and before anything that needs to know Link's mode.
- void DetermineLinkMode() {
- // Check for various situations in which we want to fallback on
- // the built-in ZC engine.
- if (// If we're not a sideview screen, we definitely want
- // to use the ZC engine.
- !IsSideview() ||
- // If Link is Frozen, he's probably using the hookshot.
- Link->Action == LA_FROZEN ||
- // If the screen is scrolling, we can't do anything anyway.
- Link->Action == LA_SCROLLING ||
- // If he's hurt, we want to rely on the built-in knockback.
- Link->Action == LA_GOTHURTLAND ||
- Link->Action == LA_GOTHURTWATER) {
- // Rely on the engine.
- LinkMode = LINK_MODE_ENGINE;}
- // There's on reason not to, so use our custom engine or stairs..
- else if (StairMode != STAIR_NONE) {
- LinkMode = LINK_MODE_STAIR;}
- else {
- LinkMode = LINK_MODE_CUSTOM;}}
- // Return true if the combo at the given position is a stair.
- bool IsStair(int x, int y) {
- if (x < 0 || x >= 256 || y < 0 || y >= 176) {return false;}
- else {return IsStair((y & 240) + (x >> 4));}}
- bool IsStair(int loc) {
- if (loc == -1) {return false;}
- int ct = Screen->ComboT[loc];
- return CT_NEG <= ct && ct <= CT_POS;}
- bool IsValidStair(int loc) {
- if (StairMode == STAIR_NEG) {return IsNegStair(loc);}
- else if (StairMode == STAIR_POS) {return IsPosStair(loc);}}
- bool IsValidStair(int x, int y) {
- if (StairMode == STAIR_NEG) {return IsNegStair(x, y);}
- else if (StairMode == STAIR_POS) {return IsPosStair(x, y);}}
- bool IsPosStair(int x, int y) {
- if (x < 0 || x > 255 || y < 0 || y > 175) {return false;}
- else {return IsPosStair((y & 240) + (x >> 4));}}
- bool IsPosStair(int loc) {
- if (loc == -1) {return false;}
- int ct = Screen->ComboT[loc];
- return ct == CT_CROSS || ct == CT_POS;}
- bool IsNegStair(int x, int y) {
- if (x < 0 || x > 255 || y < 0 || y > 175) {return false;}
- else {return IsNegStair((y & 240) + (x >> 4));}}
- bool IsNegStair(int loc) {
- if (loc == -1) {return false;}
- int ct = Screen->ComboT[loc];
- return ct == CT_CROSS || ct == CT_NEG;}
- // Gets the block type at the given position on screen.
- int GetBlockType(int x, int y) {
- // Outside the screen is always considered open.
- if (x < 0 || x >= 256 || y < 0 || y >= 176) {return BLOCK_EMPTY;}
- // Non-solid blocks are always empty.
- else if (!Screen->isSolid(x, y)) {return BLOCK_EMPTY;}
- // Otherwise, if has the soft flag or is a stair,
- // it is a soft block.
- else if (ComboFI(x, y, CF_SOFT) || IsStair(x, y)) {return BLOCK_SOFT;}
- // Otherwise it is hard.
- else {return BLOCK_HARD;}}
- // Updates Old Link position when the screen changes.
- void LinkUpdateOldOnScreenChange() {
- // Set old link position to the edge of the screen we came in from.
- if (ScreenChangeDir == DIR_UP) {
- OldLinkY = 160;}
- else if (ScreenChangeDir == DIR_DOWN) {
- OldLinkY = 0;}
- else if (ScreenChangeDir == DIR_LEFT) {
- OldLinkX = 240;}
- else if (ScreenChangeDir == DIR_RIGHT) {
- OldLinkX = 0;}}
- // Various actions to perform if the screen changed on us.
- void LinkCustomOnScreenChange() {
- if (ScreenChangeHandled) {return;}
- // Respect any warps or such.
- LinkX = Link->X;
- LinkY = Link->Y;
- LinkUpdateOldOnScreenChange();
- // Mark as being handled.
- ScreenChangeHandled = true;}
- // Perform the actual movement of Link.
- void LinkCustomUpdatePosition() {
- // First, move according to player input.
- if (// We can only move if we're standing still or walking.
- Link->Action == LA_NONE || Link->Action == LA_WALKING ||
- // Or we're in the air and attacking.
- (Link->Action == LA_ATTACKING && LinkBlock == BLOCK_EMPTY)) {
- // Then move left or right, but not both.
- if (Link->InputLeft) {LinkX -= LINK_WALK;}
- else if (Link->InputRight) {LinkX += LINK_WALK;}}
- // Check against running into a wall to the left.
- if (// First check that we moved left.
- LinkX < OldLinkX &&
- (// Then check for hard blocks at Link's top, middle, and bottom.
- GetBlockType(LinkX, LinkY) == BLOCK_HARD ||
- GetBlockType(LinkX, LinkY + 8) == BLOCK_HARD ||
- GetBlockType(LinkX, LinkY + 15) == BLOCK_HARD)) {
- // If he hit, move Link right to the next multiple of 8.
- LinkX += 8 - (LinkX % 8);}
- // Check against running into a wall to the right.
- if (// First check that we moved right.
- LinkX > OldLinkX &&
- (// Then check for hard blocks at Link's top, middle, and bottom.
- GetBlockType(LinkX + 15, LinkY) == BLOCK_HARD ||
- GetBlockType(LinkX + 15, LinkY + 8) == BLOCK_HARD ||
- GetBlockType(LinkX + 15, LinkY + 15) == BLOCK_HARD)) {
- // If he hit, move Link left to the previous multiple of 8.
- LinkX &= 0x1FFF8;}
- // Then move Link according to his vertical velocity.
- LinkY += LinkVy;
- // Check against running into a hard block above.
- if (// First check that we're moving up.
- LinkY < OldLinkY &&
- (// Then check against Link's middle-left and middle-right.
- GetBlockType(LinkX + 5, LinkY) == BLOCK_HARD ||
- GetBlockType(LinkX + 11, LinkY) == BLOCK_HARD)) {
- // If he hit, move Link down to the next multiple of 8.
- LinkY += 8 - (LinkY % 8);
- // and get rid of his vertical velocity.
- LinkVy = 0;}
- // Check against running into a block below, and assign the block type
- // below Link to LinkBlock for this round.
- // First check to make sure we're moving down.
- if (LinkY > OldLinkY) {
- // Get the hardest type of platform below Link.
- // Check against his middle-left and middle-right.
- LinkBlock = Max(GetBlockType(LinkX + 5, LinkY + 16),
- GetBlockType(LinkX + 11, LinkY + 16));
- // See if we ran into a block.
- if (// A hard block always counts.
- LinkBlock == BLOCK_HARD ||
- // A soft block counts as long as we're not holding the jump
- // button down, or we started out past it.
- (LinkBlock == BLOCK_SOFT &&
- !InputJump &&
- !(OldLinkY > (LinkY & 0x1FFF8)))) {
- // If he hit, move Link up to the previous multiple of 8.
- LinkY &= 0x1FFF8;
- // and get rid of his vertical velocity.
- LinkVy = 0;}}
- // Otherwise, we're in the air.
- else {
- LinkBlock = BLOCK_EMPTY;}
- Link->Jump = 0;
- Link->Z = 0;
- // Gravity.
- LinkVy = Min(LinkVy + LINK_GRAV, LINK_TERM);}
- // Perform a sideview jump.
- void SideviewJump() {
- Game->PlaySound(SFX_JUMP);
- // We're holding down, so only hop.
- if (Link->InputDown) {LinkVy = LinkHop;}
- // Otherwise do the full jump.
- else {LinkVy = LinkJump;}}
- // Jump according to custom mode rules.
- void LinkCustomJump() {
- if (// The Jump button is pressed.
- PressJump &&
- // Can't jump in the air.
- LinkBlock != BLOCK_EMPTY &&
- // Must have positive y velocity.
- LinkVy >= 0 &&
- // Can't be doing anything but walking.
- (Link->Action == LA_NONE || Link->Action == LA_WALKING)) {
- // Jump!
- SideviewJump();}}
- // Check if we need to get onto stairs from custom mode.
- void LinkCustomMountStair() {
- // We never get on a stair unless we're standing on something.
- if (LinkBlock == BLOCK_EMPTY) {return;}
- // We must have a positive or 0 y velocity.
- if (LinkVy < 0) {return;}
- // We're moving up-left, so check an up-left going stair on the same
- // tile as Link.
- if (Link->InputLeft && Link->InputUp && IsPosStair(LinkX, LinkY + 15)) {
- MountStair(LinkX, LinkY + 15, STAIR_POS);
- StairPos = STAIR_BOTTOM;}
- // We're moving up-right, so check an up-right going stair on the same
- // tile as Link.
- else if (Link->InputRight && Link->InputUp &&
- IsNegStair(LinkX + 15, LinkY + 15)) {
- MountStair(LinkX + 15, LinkY + 15, STAIR_NEG);
- StairPos = STAIR_BOTTOM;}
- // We're moving down-left, so check a down-left going stair on the
- // tile below Link.
- if (Link->InputLeft && Link->InputDown && IsNegStair(LinkX + 2, LinkY + 18)) {
- MountStair(LinkX + 2, LinkY + 18, STAIR_NEG);
- StairPos = STAIR_TOP;}
- // We're moving down-right, so check a down-right going stair on the
- // tile below Link.
- if (Link->InputRight && Link->InputDown &&
- IsPosStair(LinkX + 13, LinkY + 18)) {
- MountStair(LinkX + 13, LinkY + 18, STAIR_POS);
- StairPos = STAIR_TOP;}}
- // Causes Link to mount the stair at the given position.
- // Returns true if the stair was mounted.
- bool MountStair(int x, int y, int mode) {
- // First, make sure there's actually a stair there.
- int start = (y & 240) + (x >> 4);
- if (x < 0 || x >= 256 || y < 0 || y >= 176 || !IsStair(start)) {
- LinkMode = LINK_MODE_CUSTOM;
- StairMode = STAIR_NONE;
- return false;}
- // Change to stair movement mode.
- LinkMode = LINK_MODE_STAIR;
- StairMode = mode;
- StairLoc = ComboAt(x, y);
- // Mark the stairs being mounted this frame.
- StairMount = true;
- // Set the Y offset.
- x = ComboX(start);
- y = ComboY(start);
- StairY =
- // Start with the y position of the stair combo.
- y
- // Move to 1 cell above it.
- - 16
- // Adjust for the x position of the stair combo in the stair direction.
- - x * StairMode;
- return true;}
- void Stair_Update1() {
- StairMount = false;}
- // Adjust Link's position if the screen changed.
- void LinkStairOnScreenChange() {
- if (ScreenChangeHandled) {return;}
- int stairTX = StairLoc % 16;
- int stairTY = StairLoc >> 4;
- LinkUpdateOldOnScreenChange();
- // If we walked off the top of the screen.
- if (ScreenChangeDir == DIR_UP) {
- int adjust = (StairLoc >> 4) + 1;
- stairTX -= adjust * StairMode;
- stairTY = 10;
- StairLoc = FindLoc(stairTX, stairTY);
- LinkX = (stairTX + StairMode) * 16;
- LinkY = 160;}
- // We walked off the bottom of the screen.
- else if (ScreenChangeDir == DIR_DOWN) {
- int adjust = 11 - stairTY;
- // First check if there is actually a stair on the top of the new screen.
- int loc = FindLoc(stairTX + StairMode * adjust, 0);
- if (!IsValidStair(loc)) {
- // If there isn't then just set Link's X to where that stair would be.
- LinkX = ComboX(loc);
- StairLoc = -1;}
- // If there is, proceed as normal.
- else {
- stairTX += 2 * StairMode;
- stairTY = 1;
- StairLoc = FindLoc(stairTX, stairTY);
- LinkX = stairTX * 16;}
- LinkY = 0;}
- // We walked off the left edge of the screen. Make sure that the
- // stairs actually reached all the way to the left as well.
- else if (ScreenChangeDir == DIR_LEFT &&
- (// If we were on the edge stair, then we know it existed.
- stairTX == 0 ||
- // Check above or below based on stair direction
- Cond(StairMode == STAIR_POS, StairAbove, StairBelow))) {
- stairTX = 15;
- // How far away the stair we're anchored to is from the wall.
- int adjust = (StairLoc % 16) + 1;
- stairTY -= adjust * StairMode;
- StairLoc = FindLoc(stairTX, stairTY);
- LinkX = 240;
- LinkY = (stairTY - 1) * 16;
- // If there isn't a valid stair there, and we were moving up, then
- // move Link down a tile, because he never climbed it while the
- // screen was scrolling.
- if (StairMode == STAIR_POS && !IsValidStair(StairLoc)) {
- LinkY += 16;}}
- // We walked off the right edge of the screen. Make sure that the
- // stairs actually reached all the way to the right as well.
- else if (ScreenChangeDir == DIR_RIGHT &&
- (// If we were on the edge stair, then we know it existed.
- stairTX == 15 ||
- // Check above or below based on stair direction
- Cond(StairMode == STAIR_POS, StairBelow, StairAbove))) {
- stairTX = 0;
- // How far away the stair we're anchored to is from the wall.
- int adjust = 16 - (StairLoc % 16);
- stairTY += adjust * StairMode;
- StairLoc = FindLoc(stairTX, stairTY);
- LinkX = 0;
- LinkY = (stairTY - 1) * 16;
- // If there isn't a valid stair there, and we were moving up, then
- // move Link down a tile, because he never climbed it while the
- // screen was scrolling.
- if (StairMode == STAIR_NEG && !IsValidStair(StairLoc)) {
- LinkY += 16;}}
- // Otherwise, cancel stairs.
- else {
- LinkX = Link->X;
- LinkY = Link->Y;
- StairMode = STAIR_NONE;
- LinkMode = LINK_MODE_CUSTOM;}
- if (StairMode != STAIR_NONE) {
- MountStair(stairTX << 4, stairTY << 4, StairMode);}
- ScreenChangeHandled = true;}
- // Update Link's position based on the stair he's on.
- void LinkStairUpdatePosition() {
- // First, move according to player input.
- if (// We can only move if we're standing still or walking.
- Link->Action == LA_NONE || Link->Action == LA_WALKING) {
- // Then move left or right, but not both.
- if (Link->InputLeft) {LinkX -= LINK_WALK;}
- else if (Link->InputRight) {LinkX += LINK_WALK;}}
- // If we're at the top or bottom of the stair, check against running
- // into walls.
- if (StairPos != STAIR_MIDDLE) {
- // Check against running into a wall to the left.
- if (// First check that we moved left.
- LinkX < OldLinkX &&
- // Then check that we're not at the top of a negative stair.
- (StairPos != STAIR_TOP || StairMode != STAIR_NEG) &&
- (// Then check for hard blocks at Link's top, middle, and bottom.
- GetBlockType(LinkX, LinkY) == BLOCK_HARD ||
- GetBlockType(LinkX, LinkY + 8) == BLOCK_HARD ||
- GetBlockType(LinkX, LinkY + 15) == BLOCK_HARD)) {
- // If he hit, move Link right to the next multiple of 8.
- LinkX += 8 - (LinkX % 8);}
- // Check against running into a wall to the right.
- if (// First check that we moved right.
- LinkX > OldLinkX &&
- // Then check that we're not at the top of a positive stair.
- (StairPos != STAIR_TOP || StairMode != STAIR_POS) &&
- (// Then check for hard blocks at Link's top, middle, and bottom.
- GetBlockType(LinkX + 15, LinkY) == BLOCK_HARD ||
- GetBlockType(LinkX + 15, LinkY + 8) == BLOCK_HARD ||
- GetBlockType(LinkX + 15, LinkY + 15) == BLOCK_HARD)) {
- // If he hit, move Link left to the previous multiple of 8.
- LinkX &= 0x1FFF8;}}
- //// Then adjust y positioning.
- // If we're at the middle of the stair, use the standard formula.
- LinkY = LinkX * StairMode + StairY;
- // If we're at the bottom, align Link with the anchored stair.
- if (StairPos == STAIR_BOTTOM &&
- ((StairMode == STAIR_NEG && LinkX <= ComboX(StairLoc) - 16) ||
- (StairMode == STAIR_POS && LinkX >= ComboX(StairLoc) + 16))) {
- LinkY = ComboY(StairLoc);}
- // If we're at the top, align Link with the cell above the anchored stair.
- else if (StairPos == STAIR_TOP &&
- ((StairMode == STAIR_NEG && LinkX >= ComboX(StairLoc) - 1) ||
- (StairMode == STAIR_POS && LinkX <= ComboX(StairLoc) + 1))) {
- LinkY = ComboY(StairLoc) - 16;}}
- // Find the stair that Link is currently standing on.
- void LinkStairFindStair() {
- if (StairLoc == -1) {return;}
- //// First, check if we've moved off of the stair we're currently anchored to.
- // Get the edge closest to the stair.
- int x = LinkX + Cond(StairMode == STAIR_POS, 0, 15);
- int stairX = ComboX(StairLoc);
- int stairTX = StairLoc % 16;
- int stairTY = StairLoc >> 4;
- // Direction we've shifted.
- int shiftDir = 0;
- // We've moved off the left side of the stair, so move the StairLoc
- // 1 to the left, plus up or down as appropriate.
- if (x < stairX) {
- stairTX--;
- stairTY -= StairMode;
- shiftDir = -1;}
- // We've moved off the right side of the stair, so move the StairLoc
- // 1 to the right, plus up or down as appropriate.
- else if (x >= stairX + 16) {
- stairTX++;
- stairTY += StairMode;
- shiftDir = 1;}
- StairLoc = FindLoc(stairTX, stairTY);
- StairPos = STAIR_MIDDLE;
- // If we found the stairs, but we're on the top edge of a stair (and
- // not on the edge of a screen), set to the top edge anyway.
- if (IsValidStair(StairLoc) &&
- ((StairMode == STAIR_POS && stairTX != 0) ||
- (StairMode == STAIR_NEG && stairTX != 15))) {
- int aboveLoc = FindLoc(stairTX - StairMode, stairTY - 1);
- if (!IsValidStair(aboveLoc)) {
- StairPos = STAIR_TOP;}}
- // Check for a stair to the side.
- if (// First, make sure that we didn't already find a stair.
- !IsValidStair(StairLoc) &&
- // And then also make sure that we didn't shift up the stair,
- // because we're shifting up again and a double shift doesn't
- // make sense.
- shiftDir * StairMode != -1) {
- StairLoc = FindLoc(stairTX - StairMode, stairTY - 1);
- // If we're on the bottom of the screen, assume there's more
- // stairs on the next screen.
- if (stairTY - 1 < 10) {
- StairPos = STAIR_BOTTOM;}}
- // Then check for a stair diagonally downward.
- if (!IsValidStair(StairLoc)) {
- StairLoc = FindLoc(stairTX + StairMode, stairTY + 1);
- StairPos = STAIR_TOP;}
- // Check if we failed.
- if (!IsValidStair(StairLoc)) {
- StairLoc = -1;
- return;}
- // Set StairLeft and StairRight to the proper values for Link's position.
- if (StairPos == STAIR_MIDDLE) {
- StairLeft = 0;
- StairRight = 255;}
- else {
- stairTX = StairLoc % 16;
- StairLeft = (stairTX - 1) * 16 - 2;
- StairRight = (stairTX + 1) * 16 + 2;}
- // Find if there's a stair above and below.
- StairAbove = IsValidStair(FindLoc(stairTX - StairMode, stairTY - 1));
- StairBelow = IsValidStair(FindLoc(stairTX + StairMode, stairTY + 1));}
- // See if Link is leaving the stairs.
- void LinkStairFallOff() {
- if (// Getting hurt knocks you off of stairs.
- Link->Action == LA_GOTHURTLAND || Link->Action == LA_GOTHURTWATER ||
- // If we couldn't locate a stair earlier, that means we fall off, too.
- StairLoc == -1 ||
- // Or if we've moved too far off of the top or bottom of a stair.
- LinkX < StairLeft || LinkX > StairRight) {
- StairMode = STAIR_NONE;
- LinkMode = LINK_MODE_CUSTOM;}}
- // Jump according to stair mode rules.
- void LinkStairJump() {
- if (// The Jump button is pressed.
- PressJump &&
- // Can't be doing anything but walking.
- (Link->Action == LA_NONE || Link->Action == LA_WALKING)) {
- StairMode = STAIR_NONE;
- LinkMode = LINK_MODE_CUSTOM;
- // Jump!
- SideviewJump();}}
- // Assigns all the OldLink variables for the upcoming frame.
- // Place before Waitdraw().
- void OldLink_Update1() {
- OldLinkX = Link->X;
- OldLinkY = Link->Y;
- OldLinkAction = Link->Action;}
- // Record the current dmap and dscreen right before they are changed.
- // Place before Waitdraw().
- void ScreenChange_Update1() {
- OldDMap = Game->GetCurDMap();
- OldDScreen = Game->GetCurDMapScreen();}
- // Updates information dealing with changing screens.
- // Place after Waitdraw(), when the screen changes happen.
- void ScreenChange_Update2() {
- // Grab current values.
- int dMap = Game->GetCurDMap();
- int dScreen = Game->GetCurDMapScreen();
- // Compare with old values.
- DMapChanged = dMap != OldDMap;
- ScreenChanged = DMapChanged || dScreen != OldDScreen;
- // Check for scrolling change to the same screen.
- if (Link->Action == LA_SCROLLING) {
- if (!ScreenChanged && !_ScreenChanged_ScrollFlag) {
- ScreenChanged = true;
- _ScreenChanged_ScrollFlag = true;}}
- // We're no longer scrolling, so reset scroll flag.
- else {
- _ScreenChanged_ScrollFlag = false;}
- // Check for a forced screen change flag.
- if (_ScreenChanged_ForceFlag) {
- ScreenChanged = true;
- _ScreenChanged_ForceFlag = false;}
- // Find the screen change direction.
- if (ScreenChanged) {
- // Mark the screen change as needing to be handled.
- ScreenChangeHandled = false;
- // Try to guess the direction.
- if (Link->Y >= 160) {ScreenChangeDir = DIR_UP;}
- else if (Link->Y <= 0) {ScreenChangeDir = DIR_DOWN;}
- else if (Link->X >= 240) {ScreenChangeDir = DIR_LEFT;}
- else if (Link->X <= 0) {ScreenChangeDir = DIR_RIGHT;}
- else {ScreenChangeDir = SCREEN_CHANGE_WARP;}}}
- // Adjust some of Link's variables after all the mechanical
- // manipulation is done.
- void LinkAdjust() {
- // Don't do anything in engine mode.
- if (LinkMode == LINK_MODE_ENGINE) {return;}
- // Update Link's actual position.
- Link->X = Round(LinkX);
- Link->Y = Round(LinkY);
- // Force the walking animation if we moved and have no other action.
- if (Link->Action == LA_NONE && (LinkX != OldLinkX || LinkY != OldLinkY)) {
- Link->Action = LA_WALKING;}
- // Set the direction according to input.
- if (Link->InputUp) {Link->Dir = DIR_UP;}
- else if (Link->InputDown) {Link->Dir = DIR_DOWN;}
- else if (Link->InputLeft) {Link->Dir = DIR_LEFT;}
- else if (Link->InputRight) {Link->Dir = DIR_RIGHT;}}
- // Don't scroll through items on sideview screens with L.
- void Input_Update1() {
- // Ignore L if this is a sideview screen.
- if (IsSideview()) {
- InputJump = Link->InputL;
- PressJump = Link->PressL;
- Link->InputL = false;
- Link->PressL = false;}}
- // Change the inputs so the engine doesn't set Link facing a weird
- // direction or something else we don't want.
- void Input_Update2() {
- // If we're not in engine mode, up and down take preference for
- // direction.
- if (LinkMode != LINK_MODE_ENGINE &&
- (Link->InputUp || Link->InputDown)) {
- Link->InputLeft = false;
- Link->InputRight = false;
- Link->PressLeft = false;
- Link->PressRight = false;}}
- ffc script ScreenChange {
- void run() {
- _ScreenChanged_ForceFlag = true;}}
- // Don't carry over velocity or stair state.
- global script OnContinue {
- void run() {
- StairMode = STAIR_NONE;
- LinkVy = 0;}}
- // Set first argument to Link's full jump speed.
- // Set second argument to Link's jump speed while holding down.
- item script AdjustLinkJump {
- void run (int jumpSpeed, int hopSpeed) {
- LinkJump = jumpSpeed;
- LinkHop = hopSpeed;}}
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement