Sooo I am running into some issues with this script.
Script
//Ice Lynel - An upgraded version of the Blue Lynel that gradually grows layers of ice over it that protect it from damage and increase the power of it's sword beams. These layers of ice break when they are hit by attacks and the layers do not protect against all forms of damage. Very dangerous in groups and are very difficult to kill if you don't hit them constantly. As a workaround from a bug, Boomerangs will not stun the Lynel.
//Settings
//HP, Damage, Weapon Damage, Weapon, Step speed, Random Rate, Halt Rate and Homing: Works as usual.
//Misc Attribute 1: The velocity of the sword beam, in pixels per second, being fired at the player. Defaults to 300, which is 3 pixels per frame.
//Misc Attribute 2: The delay, in frames, between firing sword beams. Defaults to 60 frames, which is 1 second.
//Misc Attribute 3: The amount of damage each Ice Layer adds to the Lynel's beam attack, in quarter hearts. Defaults to 4, which is 1 Heart
//Misc Attribute 4: The number of ice layers the Lynel can get. Defaults to 2.
//Misc Attribute 5: The delay between each time the Lynel gains an ice layer.
//Misc Attribute 6: The number of hits it takes to remove each layer. Defaults to 2.
//Misc Attribute 7: The number of layers the Ice Lynel starts off with. Defaults to 0.
//Misc Attribute 8: The flags determining what defenses the ice layer does not defend against. By default, the ice layer does not protect against Bombs, Super Bombs, Fires, Reflected Fireballs and Script LWeapons. Look up the Misc Attr Flags and std_constant.zh for more details of which flags correspond to which defense.
//Misc Attribute 9: The base tile for the ice layer. Set this to the tile of the first ice layer.
//Misc Attribute 10: The CSet for the ice layer. Default to 7.
//Misc Attribute 11: The starting combo the Lynel uses. Must be the combo that corresponds to its up-facing sprites
//Misc Attribute 12: The number of the FFC script the Lynel uses.
ffc script Lynel{
void run(int enemyID){
//Initializes the enemy.
npc ghost;
ghost = Ghost_InitAutoGhost(this, enemyID);
//Reads the Lynel's settings
int ShotSpeed = Ghost_GetAttribute(ghost, 0, 300);
int ShotDelay = Ghost_GetAttribute(ghost, 1, 60);
int IceBonus = Ghost_GetAttribute(ghost, 2, 4);
int IceLayers = Ghost_GetAttribute(ghost, 3, 2);
int IceDelay = Ghost_GetAttribute(ghost, 4, 120);
int IceStrikes = Ghost_GetAttribute(ghost, 5, 2);
int IceStart = Ghost_GetAttribute(ghost, 6, 0);
int DefenseFlags = Ghost_GetAttribute(ghost, 7, 139286);
int IceTile = Ghost_GetAttribute(ghost, 8, 0);
int IceCSet = Ghost_GetAttribute(ghost, 9, 7);
int turnTimer = ghost->Rate * 10; //The turning timer
int curStep = ghost->Step; //Keep the original step speed in memory.
int layers[1] = {0}; //The number of ice layers the Lynel has. Starts off at 0.
layers[0] = IceStart;
int layercounter[1] = {0}; //The counter used to determine when the Lynel can add another ice layer.
int currlayer[1] = {0}; //The counter used to keep track of the Lynel's layers.
int layerhp[1] = {0}; //The counter used to keep track of the Lynel's layer hits.
layerhp[0] = IceStrikes;
//Sets its flags.
Ghost_SetFlag(GHF_KNOCKBACK_4WAY);
Ghost_SetFlag(GHF_SET_DIRECTION);
Ghost_SetFlag(GHF_4WAY);
Ghost_SetFlag(GHF_STUN);
Ghost_Data = GH_INVISIBLE_COMBO; //Make the combo on the FFC invisible.
while(true){
turnTimer = Ghost_HaltingWalk4(turnTimer, ghost->Step, ghost->Rate, ghost->Homing, 2, ghost->Haltrate, 45); //Move the Lynel
if(turnTimer == 15){ //Halted for 15 frames, fire an icy sword beam at the player that deals little damage (initially).
eweapon Beam = FireNonAngularEWeapon(WeaponTypeToID(ghost->Weapon), Ghost_X, Ghost_Y, Ghost_Dir, ShotSpeed, ghost->WeaponDamage+(IceBonus*layers[0]), -1, -1, EWF_ROTATE); //Fire the EWeapon
}
layercounter[0] += 1; //Increment the layer counter.
Screen->FastCombo(2, Ghost_X, Ghost_Y, ghost->Attributes[10]+Ghost_Dir, this->CSet, OP_OPAQUE); //Draw the Lynel to the screen first.
IceLynelWaitframe(this, ghost, IceLayers, IceDelay, IceStrikes, DefenseFlags, IceTile, IceCSet, layers, layercounter, currlayer, layerhp);
}
}
void IceLynelWaitframe(ffc this, npc ghost, int icelayers, int icedelay, int icestrikes, int defenseflags, int icetile, int icecset, int layers, int layercounter, int currlayer, int layerhp){
if(layers[0] < icelayers && layercounter[0] == icedelay){ //If Lynel has fewer ice layers than it can have after Attribute 3 frames, create an ice layer.
layers[0] ++; //Add an ice layer.
layercounter[0] = 0; //Reset the layer counter
layerhp[0] = icestrikes;
}
if(layers[0] > 0 && Ghost_GotHit()){ //If the Lynel is hit and has an ice layer, subtract its HP and reset the layer counter.
layerhp[0] --;
layercounter[0] = 0; //Reset the layer counter
}
if(layers[0] > 0 && layerhp[0] == 0){ //Ice Layer HP is depleted, remove a yeter
layers[0] --; //Remove an ice layer.
layercounter[0] = 0; //Reset the layer counter
layerhp[0] = icestrikes;
}
if(layers[0] > 0){ //Draw the ice tile over the Lynel if it has an ice layer active
Screen->FastTile(2, Ghost_X, Ghost_Y, icetile + (layers[0] - 1), icecset, OP_TRANS); //Draw the ice tile over the Lynel
}
IceCheck(ghost, defenseflags, currlayer, layers); //Check the ice layers
currlayer[0] = layers[0]; //Update the layer check.
Ghost_Waitframe(this, ghost, true, true);
}
void IceCheck(npc ghost, int flags, int prevlayer, int layer){ //Checks for the ice layers
int layerdefense = layer[0];
if(layerdefense > 2){ //If the layers go above 2, Lynel takes no damage from anything except what the ice doesn't protect against.
layerdefense = NPCDT_BLOCK;
}
if(prevlayer[0] != layer[0]){ //Check to see if the Lynel has just added or lost a layer
for(int i = 0; i <= 17; i ++){ //Set all defenses except the ice does not protect against.
if(!AttributeFlagCheck(flags, i)){ //Check to see wherever it's defense is affected in the flags or not.
ghost->Defense[i] = layerdefense; //Sets the defenses it doesn't skip
}
}
}
}
}
//These functions and constants can only be included in your script file once.
//Misc Attribute Flag constants.
const int MISC_ATTR_FLAG1 = 1; //000000000000000001b
const int MISC_ATTR_FLAG2 = 2; //000000000000000010b
const int MISC_ATTR_FLAG3 = 4; //000000000000000100b
const int MISC_ATTR_FLAG4 = 8; //000000000000001000b
const int MISC_ATTR_FLAG5 = 16; //000000000000010000b
const int MISC_ATTR_FLAG6 = 32; //000000000000100000b
const int MISC_ATTR_FLAG7 = 64; //000000000001000000b
const int MISC_ATTR_FLAG8 = 128; //000000000010000000b
const int MISC_ATTR_FLAG9 = 256; //000000000100000000b
const int MISC_ATTR_FLAG10 = 512; //000000001000000000b
const int MISC_ATTR_FLAG11 = 1024; //000000010000000000b
const int MISC_ATTR_FLAG12 = 2048; //000000100000000000b
const int MISC_ATTR_FLAG13 = 4096; //000001000000000000b
const int MISC_ATTR_FLAG14 = 8192; //000010000000000000b
const int MISC_ATTR_FLAG15 = 16384; //000100000000000000b
const int MISC_ATTR_FLAG16 = 32768; //001000000000000000b
const int MISC_ATTR_FLAG17 = 65536; //010000000000000000b
const int MISC_ATTR_FLAG18 = 131072; //100000000000000000b
bool AttributeFlagCheck(int attribute, int flag){ //For use in for loops. Use in conjunction with misc or D variables as a shorthand way of setting flags.
if((attribute&000000000000000001b) != 0 && flag == 0){ //1
return true;
}
else if((attribute&000000000000000010b) != 0 && flag == 1){ //2
return true;
}
else if((attribute&000000000000000100b) != 0 && flag == 2){ //4
return true;
}
else if((attribute&000000000000001000b) != 0 && flag == 3){ //8
return true;
}
else if((attribute&000000000000010000b) != 0 && flag == 4){ //16
return true;
}
else if((attribute&000000000000100000b) != 0 && flag == 5){ //32
return true;
}
else if((attribute&000000000001000000b) != 0 && flag == 6){ //64
return true;
}
else if((attribute&000000000010000000b) != 0 && flag == 7){ //128
return true;
}
else if((attribute&000000000100000000b) != 0 && flag == 8){ //256
return true;
}
else if((attribute&000000001000000000b) != 0 && flag == 9){ //512
return true;
}
else if((attribute&000000010000000000b) != 0 && flag == 10){ //1024
return true;
}
else if((attribute&000000100000000000b) != 0 && flag == 11){ //2048
return true;
}
else if((attribute&000001000000000000b) != 0 && flag == 12){ //4096
return true;
}
else if((attribute&000010000000000000b) != 0 && flag == 13){ //8192
return true;
}
else if((attribute&000100000000000000b) != 0 && flag == 14){ //16384
return true;
}
else if((attribute&001000000000000000b) != 0 && flag == 15){ //32768
return true;
}
else if((attribute&010000000000000000b) != 0 && flag == 16){ //65536
return true;
}
else if((attribute&100000000000000000b) != 0 && flag == 17){ //131072
return true;
}
else{
return false;
}
}
Basically, my problems with this Ice Lynel script is that if the enemy is stunned, the script will not draw the enemy sprite or the ice layer (which occurs because they both use drawing commands and stunning stops GhostWaitframe from returning, preventing them from being drawn). Anyone know to alleviate this issue to allow for these Ice Lynels to be stunned?

