Copy to Clipboard Test

Light Beam Code

//=========================================Beam of Light=======================================
//For push block puzzles. If 2 types of blocks are used, max 6. If one block is used, max 7.
//Place FFC at the Light Emitter's position. Light Draw starts from the FFC.
//Flag 98 "General purpose 1 (scripts)" will block the light.
//D0: Starting direction of light beam. Use DIR_ constants.
//D1: Set Light on or off. If 1 Light will be on. If 0 Light will be off unless Screen->D[0] value is 1.
//D2: The difference between the map of layer 0 and the map of the layer the Light is on.
//eg. If layer 0 is on map 1 and the light is on layer 5, which is on map 5, the difference is 4.
//D3: Screen Pos of the secret trigger. Use Combo positions not [X,Y]. Use -1 if there is no secret.
//Secrets are permanent!
//D4: CSet of the push blocks.
//D5-6: Ignore screen in this direction. If set the screen will not set the D[0] values. MirrorOut_ combo's 
//will override ignore values. Best used if Light screens are next to each other but you don't want them to 
//affect each other or if screen uses D[0]. Use DIR_ constants for directions. Use the opposite DIR_ of the emitter to disable this check.

//Light Combos
const int LightU = 0; //Combo of Light moving up.
const int LightD = 0; //Combo of Light moving down.
const int LightL = 0; //Combo of Light moving left.
const int LightR = 0; //Combo of Light moving right.
const int LightB = 0; //Combo of Light hitting a mirror.
const int LightS = 0; //Combo of Light hitting an impassable.
const int LightEmitter_Up = 0; //Combo of Light on the emitter moving Up.
const int LightEmitter_Down = 0; //Combo of Light on the emitter moving Down.
const int LightEmitter_Left = 0; //Combo of Light on the emitter moving Left.
const int LightEmitter_Right = 0; //Combo of Light on the emitter moving Right.
const int LightOut_Up = 0; //Combo of Light leaving the screen moving Up.
const int LightOut_Down = 0; //Combo of Light leaving the screen moving Down.
const int LightOut_Left = 0; //Combo of Light leaving the screen moving Left.
const int LightOut_Right = 0; //Combo of Light leaving the screen moving Right.

//Mirror Combos
const int MirrorA_Push = 0; //Combo of Mirror Up-Left, Down-Right. Pushable.
const int MirrorB_Push = 0; //Combo of Mirror Up-Right, Down-Left. Pushable.
const int MirrorOut_Up = 0; //Combo of Mirror leaving the screen Up.
const int MirrorOut_Down = 0; //Combo of Mirror leaving the screen Down.
const int MirrorOut_Left = 0; //Combo of Mirror leaving the screen Left.
const int MirrorOut_Right = 0; //Combo of Mirror leaving the screen Right.

//Draw Layer
const int Layer = 0; //Layer to draw the Light combos. Layer should have no other combos.
const int LightColor = 0; //Cset of Light combos.

//Sounds
const int LightSound = 0; //Sound of light beam.
const int SoundCycle = 0; //Number of frames before the sound loops.

ffc script LightBeam{
	void run(int LightDir, int Light, int MapDiff, int Secret, int BlockColor, int IgnoreA, int IgnoreB){
	
		int StartDir = LightDir;
		int X = this->X;
		int Y = this->Y;
		int index = 1;
		int timer = 0;
		
		//Check for first run.
		if(Light == 1 && Screen->D[0] < 2){
			Screen->D[0] = 2;
			SetDIndex(index);
		}//end if
		else if(Screen->D[0] == 1){
			Screen->D[0] = Screen->D[0] + 1;
			SetDIndex(index);
		}//end else if
		else if(Screen->ComboT[ComboAt(CenterLinkX(), CenterLinkY())] == CT_RESET){
			SetDIndex(index);
		}//end else if
		else if(Light == 1 || Screen->D[0] == 2){
			index = BlockDrawA(BlockColor, index);
			index = BlockDrawB(BlockColor, index);
		}//end else
		
		DrawBlank();
	
		while(Light == 1 || Screen->D[0] == 2){
			DrawBlank();
			BlockSaveA(index);
			index = BlockDrawA(BlockColor, index);
			BlockSaveB(index);
			index = BlockDrawB(BlockColor, index);
			
			//Play Light sound every SoundCycle frames.
			if(timer == SoundCycle){
				Game->PlaySound(LightSound);
				timer = 0;
			}//end if
			else{
				timer++;
			}//end else
			
			//Draw the Emitter combo.
			if(LightDir == DIR_UP){
				SetLayerComboD(Layer, ComboAt(X, Y), LightEmitter_Up);
				Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
			}//end if
			else if(LightDir == DIR_DOWN){
				SetLayerComboD(Layer, ComboAt(X, Y), LightEmitter_Down);
				Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
			}//end else if
			else if(LightDir == DIR_LEFT){
				SetLayerComboD(Layer, ComboAt(X, Y), LightEmitter_Left);
				Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
			}//end else if
			else{
				SetLayerComboD(Layer, ComboAt(X, Y), LightEmitter_Right);
				Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
			}//end else
			
			//Loop runs in one frame.
			do{
				//Check if Link is in the Light path.
				if(GetLayerComboD(Layer, ComboAt((Link->X + 8), (Link->Y + 8))) == GetLayerComboD(Layer, ComboAt(X, Y))){
					LightDir = LinkMirror(LightDir);
				}//end if
				
				//Check for flag 98 and stop Light.
				if(Screen->ComboF[ComboAt(X, Y)] == CF_SCRIPT1 || Screen->ComboI[ComboAt(X, Y)] == CF_SCRIPT1){
					SetLayerComboD(Layer, ComboAt(X, Y), LightS);
					Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
					break;
				}//end if
				
				//Check if Light is on a MirrorOut Combo.
				//Check if Light is on a Trigger Secret Combo. Checked by Combo Pos.
				if(LightScreenPass(X, Y, MapDiff, StartDir, IgnoreA, IgnoreB) || LightScreenSecret(X, Y, MapDiff, Secret)){
					break;
				}//end if
				
				//Check Light Direction and draw Light path.
				if(LightDir == DIR_UP){ //Up
					Y = Y - 16;
					LightDir = DrawCombo(LightDir, X, Y, LightU, MapDiff);
				}//end if
				else if(LightDir == DIR_DOWN){ //Down
					Y = Y + 16;
					LightDir = DrawCombo(LightDir, X, Y, LightD, MapDiff);
				}//end else if
				else if(LightDir == DIR_LEFT){ //Left
					X = X - 16;
					LightDir = DrawCombo(LightDir, X, Y, LightL, MapDiff);
				}//end else if
				else if(LightDir == DIR_RIGHT){ //Right
					X = X + 16;
					LightDir = DrawCombo(LightDir, X, Y, LightR, MapDiff);
				}//end else if
			}while(ScreenCheck(X, Y)); //Loop while the Light path is in Screen boundaries.
			
			X = this->X;
			Y = this->Y;
			LightDir = StartDir;
			Waitframe();
		}//end while
	
	}//end run
}//end ffc

void SetDIndex(int index){
	for(index; index <= 7; index++){
		Screen->D[index] = -1;
	}//end for
}//end SetDIndex

void BlockSaveA(int index){
	for(int a = 0; a <= 175; a++){
		if(Game->GetComboData(Game->GetCurMap(), Game->GetCurScreen(), a) == MirrorA_Push){
			Screen->D[index] = a;
			index++;
		}//end if
		else{
			Screen->D[index] = -1;
		}//end else
	}//end for
}//end BlockSaveA

void BlockSaveB(int index){
	for(int a = 0; a <= 175; a++){
		if(Game->GetComboData(Game->GetCurMap(), Game->GetCurScreen(), a) == MirrorB_Push){
			Screen->D[index] = a;
			index++;
		}//end if
		else{
			Screen->D[index] = -1;
		}//end else
	}//end for
}//end BlockSaveB

int BlockDrawA(int BlockColor, int index){
	for(int a = 0; a <= 175; a++){
		if(Game->GetComboData(Game->GetCurMap(), Game->GetCurScreen(), a) == MirrorA_Push){
			Screen->ComboD[a] = 0;
		}//end if
	}//end for
	
	for(index; index <= 7; index++){
		if(Screen->D[index] == -1){
			index++;
			return index;
		}//end if
		Screen->ComboD[Screen->D[index]] = MirrorA_Push;
		Screen->ComboC[Screen->D[index]] = BlockColor;
	}//end for
}//end BlockDraw

int BlockDrawB(int BlockColor, int index){
	for(int a = 0; a <= 175; a++){
		if(Game->GetComboData(Game->GetCurMap(), Game->GetCurScreen(), a) == MirrorB_Push){
			Screen->ComboD[a] = 0;
		}//end if
	}//end for
	
	for(index; index <= 7; index++){
		if(Screen->D[index] == -1){
			index = 1;
			return index;
		}//end if
		Screen->ComboD[Screen->D[index]] = MirrorB_Push;
		Screen->ComboC[Screen->D[index]] = BlockColor;
	}//end for
	index = 1;
	return index;
}//end BlockDrawB

bool LightScreenSecret(int X, int Y, int MapDiff, int Secret){
	if(ComboAt(X, Y) == Secret){
		SetLayerComboD(Layer, ComboAt(X, Y), LightS);
		Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
		if(!Screen->State[ST_SECRET]){
			Screen->TriggerSecrets();
			Screen->State[ST_SECRET] = true;
			Game->PlaySound(SFX_SECRET);
		}//end if
		return true;
	}//end if
	else{
		return false;
	}//end else
}//end LightScreenSecret

bool LightScreenPass(int X, int Y, int MapDiff, int StartDir, int IgnoreA, int IgnoreB){
	if(Game->GetComboData(Game->GetCurMap(), Game->GetCurScreen(), ComboAt(X, Y)) == MirrorOut_Up){
		SetLayerComboD(Layer, ComboAt(X, Y), LightOut_Up);
		Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
		Game->SetDMapScreenD(Game->GetCurDMap(), (Game->GetCurDMapScreen() - 16), 0, 1);
		return true;
	}//end if
	else if(Game->GetComboData(Game->GetCurMap(), Game->GetCurScreen(), ComboAt(X, Y)) == MirrorOut_Down){
		SetLayerComboD(Layer, ComboAt(X, Y), LightOut_Down);
		Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
		Game->SetDMapScreenD(Game->GetCurDMap(), (Game->GetCurDMapScreen() + 16), 0, 1);
		return true;
	}//end else if
	else if(Game->GetComboData(Game->GetCurMap(), Game->GetCurScreen(), ComboAt(X, Y)) ==  MirrorOut_Left){
		SetLayerComboD(Layer, ComboAt(X, Y), LightOut_Left);
		Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
		Game->SetDMapScreenD(Game->GetCurDMap(), (Game->GetCurDMapScreen() - 1), 0, 1);
		return true;
	}//end else if
	else if(Game->GetComboData(Game->GetCurMap(), Game->GetCurScreen(), ComboAt(X, Y)) == MirrorOut_Left){
		SetLayerComboD(Layer, ComboAt(X, Y), LightOut_Right);
		Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
		Game->SetDMapScreenD(Game->GetCurDMap(), (Game->GetCurDMapScreen() + 1), 0, 1);
		return true;
	}//end else if
	else{
		if(!StartDir == DIR_DOWN || !IgnoreA == DIR_UP || !IgnoreB == DIR_UP){
			Game->SetDMapScreenD(Game->GetCurDMap(), (Game->GetCurDMapScreen() - 16), 0, 0); //One screen up.
		}//end if
		if(!StartDir == DIR_UP || !IgnoreA == DIR_DOWN || !IgnoreB == DIR_DOWN){
			Game->SetDMapScreenD(Game->GetCurDMap(), (Game->GetCurDMapScreen() + 16), 0, 0); //One screen down.
		}//end if
		if(!StartDir == DIR_RIGHT || !IgnoreA == DIR_LEFT || !IgnoreB == DIR_LEFT){
			Game->SetDMapScreenD(Game->GetCurDMap(), (Game->GetCurDMapScreen() - 1), 0, 0); //One screen left.
		}//end if
		if(!StartDir == DIR_LEFT || !IgnoreA == DIR_RIGHT || !IgnoreB == DIR_RIGHT){
		Game->SetDMapScreenD(Game->GetCurDMap(), (Game->GetCurDMapScreen() + 1), 0, 0); //One screen right.
		}//end if
		return false;
	}//end else
}//end LightScreenPass

int LinkMirror(int LightDir){
	//Change Light direction if Link is facing left or right and Light is travelling down.
	if(GetLayerComboD(Layer, ComboAt((Link->X + 8), (Link->Y + 8))) == LightD && Link->Item[I_SHIELD3]){
		if(Link->Dir == DIR_LEFT){
			LightDir = DIR_LEFT;
			return LightDir;
		}//end if
		else if(Link->Dir == DIR_RIGHT){
			LightDir = DIR_RIGHT;
			return LightDir;
		}//end else if
		else{
			return LightDir;
		}//end else
	}//end if
	
	//Change Light direction if Link is facing left or right and Light is travelling up.
	else if(GetLayerComboD(Layer, ComboAt((Link->X + 8), (Link->Y + 8))) == LightU && Link->Item[I_SHIELD3]){
		if(Link->Dir == DIR_LEFT){
			LightDir = DIR_LEFT;
			return LightDir;
		}//end if
		else if(Link->Dir == DIR_RIGHT){
			LightDir = DIR_RIGHT;
			return LightDir;
		}//end else if
		else{
			return LightDir;
		}//end else
	}//end else if
	
	//Change Light direction if Link is facing up or down and Light is travelling left.
	else if(GetLayerComboD(Layer, ComboAt((Link->X + 8), (Link->Y + 8))) == LightL && Link->Item[I_SHIELD3]){
		if(Link->Dir == DIR_UP){
			LightDir = DIR_UP;
			return LightDir;
		}//end if
		 else if(Link->Dir == DIR_DOWN){
			LightDir = DIR_DOWN;
			return LightDir;
		}//end else if
		else{
			return LightDir;
		}//end else
	}//end else if
	
	//Change Light direction if Link is facing up or down and Light is travelling right.
	else if(GetLayerComboD(Layer, ComboAt((Link->X + 8), (Link->Y + 8))) == LightR && Link->Item[I_SHIELD3]){
		if(Link->Dir == DIR_UP){
			LightDir = DIR_UP;
			return LightDir;
		}//end if
		else if(Link->Dir == DIR_DOWN){
			LightDir = DIR_DOWN;
			return LightDir;
		}//end else if
		else{
			return LightDir;
		}//end else
	}//end else if
	else{
		return LightDir;
	}//end else
}//end LinkMirror

int DrawCombo(int LightDir, int X, int Y, int LightCombo, int MapDiff){
	//Light will change direction from up to Right.
	if(GetLayerComboT(0, ComboAt(X, Y)) == CT_MIRRORSLASH && LightDir == DIR_UP || GetLayerComboT(0, ComboAt(X, Y)) == CT_MIRRORSLASH && LightDir == DIR_UP){
		SetLayerComboD(Layer, ComboAt(X, Y), LightB);
		Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
		LightDir = DIR_RIGHT;
	}//end if
	
	//Light will change direction from up to Left.
	else if(GetLayerComboT(0, ComboAt(X, Y)) == CT_MIRRORBACKSLASH && LightDir == DIR_UP || GetLayerComboT(0, ComboAt(X, Y)) == CT_MIRRORBACKSLASH && LightDir == DIR_UP){
		SetLayerComboD(Layer, ComboAt(X, Y), LightB);
		Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
		LightDir = DIR_LEFT;
	}//end else if
	
	//Light will change direction from Down to Left.
	else if(GetLayerComboT(0, ComboAt(X, Y)) == CT_MIRRORSLASH && LightDir == DIR_DOWN || GetLayerComboT(0, ComboAt(X, Y)) == CT_MIRRORSLASH && LightDir == DIR_DOWN){
		SetLayerComboD(Layer, ComboAt(X, Y), LightB);
		Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
		LightDir = DIR_LEFT;
	}//end else if
	
	//Light will change direction from Down to Right.
	else if(GetLayerComboT(0, ComboAt(X, Y)) == CT_MIRRORBACKSLASH && LightDir == DIR_DOWN || GetLayerComboT(0, ComboAt(X, Y)) == CT_MIRRORBACKSLASH && LightDir == DIR_DOWN){
		SetLayerComboD(Layer, ComboAt(X, Y), LightB);
		Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
		LightDir = DIR_RIGHT;
	}//end else if
	
	//Light will change direction from Left to Down.
	else if(GetLayerComboT(0, ComboAt(X, Y)) == CT_MIRRORSLASH && LightDir == DIR_LEFT || GetLayerComboT(0, ComboAt(X, Y)) == CT_MIRRORSLASH && LightDir == DIR_LEFT){
		SetLayerComboD(Layer, ComboAt(X, Y), LightB);
		Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
		LightDir = DIR_DOWN;
	}//end else if
	
	//Light will change direction from Left to Up.
	else if(GetLayerComboT(0, ComboAt(X, Y)) == CT_MIRRORBACKSLASH && LightDir == DIR_LEFT || GetLayerComboT(0, ComboAt(X, Y)) == CT_MIRRORBACKSLASH && LightDir == DIR_LEFT){
		SetLayerComboD(Layer, ComboAt(X, Y), LightB);
		Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
		LightDir = DIR_UP;
	}//end else if
	
	//Light will change direction from Right to Up.
	else if(GetLayerComboT(0, ComboAt(X, Y)) == CT_MIRRORSLASH && LightDir == DIR_RIGHT || GetLayerComboT(0, ComboAt(X, Y)) == CT_MIRRORSLASH && LightDir == DIR_RIGHT){
		SetLayerComboD(Layer, ComboAt(X, Y), LightB);
		Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
		LightDir = DIR_UP;
	}//end else if
	
	//Light will change direction from Right to Down.
	else if(GetLayerComboT(0, ComboAt(X, Y)) == CT_MIRRORBACKSLASH && LightDir == DIR_RIGHT || GetLayerComboT(0, ComboAt(X, Y)) == CT_MIRRORBACKSLASH && LightDir == DIR_RIGHT){
		SetLayerComboD(Layer, ComboAt(X, Y), LightB);
		Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
		LightDir = DIR_DOWN;
	}//end else if
	
	//Light will not change direction
	else{
		SetLayerComboD(Layer, ComboAt(X, Y), LightCombo);
		Game->SetComboCSet((Game->GetCurMap() + MapDiff), Game->GetCurScreen(), ComboAt(X, Y), LightColor);
		return LightDir;
	}//end else
	//if else-if else bracket ends here.
	return LightDir;
}//end DrawCombo

void DrawBlank(){
	for(int a = 0; a < 175; a++){
		SetLayerComboD(Layer, a, 0);
	}//end for
}//end DrawBlank

bool ScreenCheck(int X, int Y){
	if(X > 272 || X < -16 || Y > 192 || Y < -16){
		return false;
	}//end if
	else{
		return true;
	}//end else
}//end ScreenCheck