Repository reorganisation

Unified kotlin and java into just src/main
Unified the rs09 and core packages
Took all content out of the core package, and placed it into the new content package
Reorganised all source code relating to content to be easier to find and explore
This commit is contained in:
Ceikry
2023-01-26 13:59:28 +00:00
committed by Ryan
parent e4b799c44a
commit a100affda2
3156 changed files with 24205 additions and 30585 deletions
@@ -0,0 +1,79 @@
package core.game.activity;
import core.game.node.entity.player.Player;
import core.tools.SystemLogger;
import core.game.world.GameWorld;
import java.util.HashMap;
import java.util.Map;
/**
* Manages the activities.
* @author Emperor
*/
public final class ActivityManager {
/**
* The mapping of instanced activities.
*/
private static final Map<String, ActivityPlugin> ACTIVITIES = new HashMap<>();
/**
* Constructs a new {@code ActivityManager} {@code Object}.
*/
private ActivityManager() {
/*
* empty.
*/
}
/**
* Registers an activity plugin.
* @param plugin The plugin to register.
*/
public static void register(ActivityPlugin plugin) {
plugin.register();
ACTIVITIES.put(plugin.getName(), plugin);
if (!plugin.isInstanced()) {
plugin.configure();
}
}
/**
* Starts an instanced activity.
* @param player The player.
* @param name The name.
* @param login If we are logging in.
* @param args The arguments.
*/
public static boolean start(Player player, String name, boolean login, Object... args) {
ActivityPlugin plugin = ACTIVITIES.get(name);
if (plugin == null) {
if (GameWorld.getSettings().isDevMode()) {
SystemLogger.logErr(ActivityManager.class, "Unhandled activity - " + name + "!");
}
return false;
}
try {
if (plugin.isInstanced()) {
(plugin = plugin.newInstance(player)).configure();
}
return plugin.start(player, login, args);
} catch (Throwable e) {
e.printStackTrace();
if (GameWorld.getSettings().isDevMode()) {
player.getPacketDispatch().sendMessage("Error starting activity " + (plugin == null ? null : plugin.getName()) + "!");
}
}
return false;
}
/**
* Gets the activity by the name.
* @param name the name.
* @return the activity.
*/
public static ActivityPlugin getActivity(String name) {
return ACTIVITIES.get(name);
}
}
@@ -0,0 +1,254 @@
package core.game.activity;
import core.ServerConstants;
import core.game.node.entity.Entity;
import core.game.node.entity.player.Player;
import core.game.world.map.Location;
import core.game.world.map.Region;
import core.game.world.map.build.DynamicRegion;
import core.game.world.map.zone.*;
import core.game.world.map.zone.impl.MultiwayCombatZone;
import core.plugin.Plugin;
import core.plugin.PluginManifest;
import core.plugin.PluginType;
/**
* A plugin implementation used for activity plugins.
* @author Emperor
*/
@PluginManifest(type = PluginType.ACTIVITY)
public abstract class ActivityPlugin extends MapZone implements Plugin<Player> {
/**
* If the activity is instanced.
*/
private boolean instanced;
/**
* If the activity is multicombat.
*/
private boolean multicombat;
/**
* If the activity is safe.
*/
private boolean safe;
/**
* The region of the activity.
*/
protected DynamicRegion region;
/**
* The base location.
*/
protected Location base;
/**
* A location which the player is teleported to in the case of death, if this activity is safe.
* Defaults to the home location of the server.
*/
protected Location safeRespawn = ServerConstants.HOME_LOCATION;
/**
* The player.
*/
protected Player player;
/**
* Constructs a new {@code ActivityPlugin} {@code Object}.
* @param name The name.
* @param instanced If the activity is instanced.
* @param multicombat If the activity is multicombat.
* @param safe If the activity is safe (the player does not lose his/her
* items).
*/
public ActivityPlugin(String name, boolean instanced, boolean multicombat, boolean safe, ZoneRestriction... restrictions) {
super(name, true, ZoneRestriction.RANDOM_EVENTS);
for (ZoneRestriction restriction : restrictions) {
addRestriction(restriction.getFlag());
}
this.instanced = instanced;
this.multicombat = multicombat;
this.safe = safe;
if (safe) {
setZoneType(ZoneType.SAFE.getId());
}
}
@Override
public void register(ZoneBorders borders) {
if (multicombat) {
MultiwayCombatZone.getInstance().register(borders);
}
super.register(borders);
}
/**
* Sets the region base location.
*/
protected void setRegionBase() {
if (region != null) {
if (multicombat) {
region.toggleMulticombat();
}
setBase(Location.create(region.getBorders().getSouthWestX(), region.getBorders().getSouthWestY(), 0));
}
}
/**
* Sets the region base for multiple regions.
* @param regions The regions.
*/
protected void setRegionBase(DynamicRegion[] regions) {
region = regions[0];
Location l = region.getBaseLocation();
for (DynamicRegion r : regions) {
if (r.getX() > l.getX() || r.getY() > l.getY()) {
l = r.getBaseLocation();
}
}
ZoneBorders borders = new ZoneBorders(region.getX() << 6, region.getY() << 6, l.getX() + Region.SIZE, l.getY() + Region.SIZE);
RegionZone multiZone = multicombat ? new RegionZone(MultiwayCombatZone.getInstance(), borders) : null;
RegionZone zone = new RegionZone(this, borders);
for (DynamicRegion r : regions) {
if (multicombat) {
r.setMulticombat(true);
r.getRegionZones().add(multiZone);
}
r.getRegionZones().add(zone);
}
setBase(Location.create(borders.getSouthWestX(), borders.getSouthWestY(), 0));
}
/**
* Starts the activity for the player.
* @param player The player.
* @param login If the player is logging in.
* @param args The arguments.
* @return {@code True} if successfully started the activity.
*/
public boolean start(Player player, boolean login, Object... args) {
this.player = player;
return true;
}
@Override
public boolean enter(Entity e) {
Location l;
if (e instanceof Player && (l = getSpawnLocation()) != null) {
e.getProperties().setSpawnLocation(l);
}
e.getProperties().setSafeZone(safe);
e.getProperties().safeRespawn = this.safeRespawn;
e.setAttribute("activity", this);
return super.enter(e);
}
@Override
public boolean leave(Entity e, boolean logout) {
if (e instanceof Player) {
e.getProperties().setSpawnLocation(ServerConstants.HOME_LOCATION);
}
Location l;
if (instanced && logout && (l = getSpawnLocation()) != null) {
e.setLocation(l);
}
e.getProperties().setSafeZone(false);
e.getProperties().safeRespawn = ServerConstants.HOME_LOCATION;
e.removeAttribute("activity");
return super.leave(e, logout);
}
/**
* Method used to do anything on registration.
*/
public void register() {
}
@Override
public Object fireEvent(String identifier, Object... args) {
return null;
}
@Override
public abstract ActivityPlugin newInstance(Player p) throws Throwable;
/**
* Gets the spawn location for this activity.
*/
public abstract Location getSpawnLocation();
/**
* Gets the instanced.
* @return The instanced.
*/
public boolean isInstanced() {
return instanced;
}
/**
* Sets the instanced.
* @param instanced The instanced to set.
*/
public void setInstanced(boolean instanced) {
this.instanced = instanced;
}
/**
* Gets the multicombat.
* @return The multicombat.
*/
public boolean isMulticombat() {
return multicombat;
}
/**
* Sets the multicombat.
* @param multicombat The multicombat to set.
*/
public void setMulticombat(boolean multicombat) {
this.multicombat = multicombat;
}
/**
* Gets the safe.
* @return The safe.
*/
public boolean isSafe() {
return safe;
}
/**
* Sets the safe.
* @param safe The safe to set.
*/
public void setSafe(boolean safe) {
this.safe = safe;
}
/**
* Gets the player.
* @return The player.
*/
public Player getPlayer() {
return player;
}
/**
* Gets the base.
* @return The base.
*/
public Location getBase() {
return base;
}
/**
* Sets the base.
* @param base The base to set.
*/
public void setBase(Location base) {
this.base = base;
}
}
@@ -0,0 +1,373 @@
package core.game.activity
import core.api.*
import core.game.event.EventHook
import core.game.event.SelfDeathEvent
import core.game.component.Component
import core.game.interaction.MovementPulse
import core.game.node.entity.Entity
import core.game.node.entity.npc.NPC
import core.game.node.entity.player.Player
import core.game.node.scenery.Scenery
import core.game.system.task.Pulse
import core.game.world.map.Direction
import core.game.world.map.Location
import core.game.world.map.Region
import core.game.world.map.RegionManager
import core.game.world.map.build.DynamicRegion
import core.game.world.map.path.Pathfinder
import core.net.packet.PacketRepository
import core.net.packet.context.MinimapStateContext
import core.net.packet.out.MinimapState
import org.rs09.consts.Components
import core.ServerConstants
import core.api.Event
import core.api.utils.PlayerCamera
import core.tools.SystemLogger
import core.game.world.GameWorld
/**
* A utility class for making cutscenes.
* @author Ceikry
*/
abstract class Cutscene(val player: Player) {
lateinit var region: Region
lateinit var base: Location
var exitLocation: Location = player.location.transform(0,0,0)
var ended = false
val camera = PlayerCamera(player)
private val addedNPCs = HashMap<Int, ArrayList<NPC>>()
abstract fun setup()
abstract fun runStage(stage: Int)
/**
* Creates a new dynamic copy of the region identified by regionId, sets this cutscene's region as this new copy, and clears any cutscene-spawned NPCs from the previous region.
* @param regionId the region ID to duplicate.
*/
fun loadRegion(regionId: Int)
{
clearNPCs()
logCutscene("Creating new instance of region $regionId for ${player.username}.")
region = DynamicRegion.create(regionId)
logCutscene("Dynamic region instantiated for ${player.username}. Global coordinates: ${region.baseLocation}.")
base = region.baseLocation
}
/**
* Fade the player's view to black. This process can be safely assumed to take about 8 ticks to complete.
*/
fun fadeToBlack()
{
logCutscene("Fading ${player.username}'s screen to black.")
player.interfaceManager.closeOverlay()
player.interfaceManager.openOverlay(Component(Components.FADE_TO_BLACK_120))
}
/**
* Fade the player's view from black back to normal. This process can be safely assumed to take about 6 ticks to complete.
*/
fun fadeFromBlack()
{
logCutscene("Fading ${player.username}'s screen from black to normal.")
player.interfaceManager.closeOverlay()
player.interfaceManager.openOverlay(Component(Components.FADE_FROM_BLACK_170))
}
/**
* Teleports an entity to a pair of coordinates within the currently active cutscene region
* @param entity the entity to teleport
* @param regionX the region X coordinate to teleport the entity to (0-63)
* @param regionY the region Y coordinate to teleport the entity to (0-63)
* @param plane (optional) the plane to teleport to (0-3)
*/
fun teleport(entity: Entity, regionX: Int, regionY: Int, plane: Int = 0)
{
val newLoc = base.transform(regionX, regionY, plane)
logCutscene("Teleporting ${entity.username} to coordinates: LOCAL[$regionX,$regionY,$plane] GLOBAL[${newLoc.x},${newLoc.y},$plane].")
entity.properties.teleportLocation = newLoc
}
/**
* Moves an entity to the given coordinates within the currently active cutscene region
* @param entity the entity to move
* @param regionX the region X coordinate to move the entity to (0-63)
* @param regionY the region Y coordinate to move the entity to (0-63)
*/
fun move(entity: Entity, regionX: Int, regionY: Int)
{
logCutscene("Moving ${entity.username} to LOCAL[$regionX,$regionY].")
entity.pulseManager.run(object : MovementPulse(entity, base.transform(regionX,regionY,0), Pathfinder.SMART) {
override fun pulse(): Boolean {
return true
}
})
}
/**
* Sends a dialogue to the player using the given NPC ID, which updates the cutscene stage by default when continued.
* @param npcId the ID of the NPC to send a dialogue for
* @param expression the FacialExpression the NPC should use
* @param message the message to send
* @param onContinue (optional) a method that runs when the dialogue is "continued." Increments the cutscene stage by default.
*/
fun dialogueUpdate(npcId: Int, expression: core.game.dialogue.FacialExpression, message: String, onContinue: () -> Unit = {incrementStage()})
{
logCutscene("Sending NPC dialogue update.")
sendNPCDialogue(player, npcId, message, expression)
player.dialogueInterpreter.addAction { _,_ -> onContinue.invoke() }
}
/**
* Sends a non-NPC dialogue to the player, which updates the cutscene stage by default when continued
* @param message the message to send
* @param onContinue (optional) a method that runs when the dialogue is "continued." Increments the cutscene stage by default.
*/
fun dialogueUpdate(message: String, onContinue: () -> Unit = {incrementStage()})
{
logCutscene("Sending standard dialogue update.")
sendDialogue(player, message)
player.dialogueInterpreter.addAction {_,_ -> onContinue.invoke()}
}
/**
* Sends a player dialogue, which updates the cutscene stage by default when continued
* @param expression the FacialExpression to use
* @param message the message to send
* @param onContinue (optional) a method that runs when the dialogue is "continued." Increments the cutscene stage by default.
*/
fun playerDialogueUpdate(expression: core.game.dialogue.FacialExpression, message: String, onContinue: () -> Unit = {incrementStage()})
{
logCutscene("Sending player dialogue update")
sendPlayerDialogue(player, message, expression)
player.dialogueInterpreter.addAction{_,_ -> onContinue.invoke()}
}
/**
* Updates the stage after a set number of ticks.
* @param ticks the number of ticks to wait
* @param newStage (optional) the new stage to update to. If not passed, stage is incremented instead.
*/
fun timedUpdate(ticks: Int, newStage: Int = -1)
{
logCutscene("Executing timed updated for $ticks ticks.")
GameWorld.Pulser.submit(object : Pulse(ticks)
{
override fun pulse(): Boolean {
if(newStage == -1)
incrementStage()
else
updateStage(newStage)
return true
}
})
}
/**
* Retrieves the first NPC from the added-to-cutscene NPCs with a matching ID.
* @param id the ID to grab for.
* @return the first NPC, or null if there are no matching NPCs.
*/
fun getNPC(id: Int): NPC?
{
return addedNPCs[id]?.firstOrNull()
}
/**
* Retrieves all NPCs from the added-to-cutscene NPCs with a matching ID.
* @param id the ID to grab for.
* @return an ArrayList of the matching NPCs, which will be empty if there were no matches.
*/
fun getNPCs(id: Int): ArrayList<NPC>
{
return addedNPCs[id] ?: ArrayList()
}
/**
* Retrieves the object in the region at the given regionX and regionY
* @param regionX the region-local X coordinate to grab the object from (0-63)
* @param regionY the region-local Y coordinate to grab the object from (0-63)
* @param plane the plane to grab the object from (0-3)
*/
fun getObject(regionX: Int, regionY: Int, plane: Int = 0): Scenery?
{
val obj = RegionManager.getObject(base.transform(regionX,regionY,plane))
logCutscene("Retrieving object at LOCAL[$regionX,$regionY], GOT: ${obj?.definition?.name ?: "null"}.")
return obj
}
/**
* Adds an NPC to the cutscene with the given ID, at the region-local X and Y coordinates.
* @param id the ID of the NPC to add.
* @param regionX the region-local X coordinate to place the NPC at
* @param regionY the region-local Y coordinate to place the NPC at
* @param direction the direction the NPC faces when it is initially placed.
* @param plane the plane to place te NPC on. Default is 0.
*/
fun addNPC(id: Int, regionX: Int, regionY: Int, direction: Direction, plane: Int = 0)
{
val npc = NPC(id)
npc.isRespawn = false
npc.isAggressive = false
npc.isWalks = false
npc.location = base.transform(regionX, regionY, plane)
npc.init()
npc.faceLocation(npc.location.transform(direction))
val npcs = addedNPCs[id] ?: ArrayList()
npcs.add(npc)
addedNPCs[id] = npcs
logCutscene("Added NPC $id at location LOCAL[$regionX,$regionY,$plane] GLOBAL[${npc.location.x},${npc.location.y},$plane]")
}
fun start()
{
logCutscene("Starting cutscene for ${player.username}.")
region = RegionManager.forId(player.location.regionId)
base = RegionManager.forId(player.location.regionId).baseLocation
setup()
PacketRepository.send(MinimapState::class.java, MinimapStateContext(player, 2))
runStage(player.getCutsceneStage())
setAttribute(player, ATTRIBUTE_CUTSCENE, this)
setAttribute(player, ATTRIBUTE_CUTSCENE_STAGE, 0)
player.interfaceManager.removeTabs(0,1,2,3,4,5,6,7,8,9,10,11,12,13,14)
player.properties.isSafeZone = true
player.properties.safeRespawn = player.location
player.lock()
player.hook(Event.SelfDeath, CUTSCENE_DEATH_HOOK)
player.logoutListeners["cutscene"] = {player -> player.location = exitLocation; player.getCutscene()?.end() }
content.global.ame.RandomEventManager.getInstance(player)!!.enabled = false
}
/**
* Ends this cutscene, fading the screen to black, teleporting the player to the exit location, and then fading it back in and executing the endActions passed to this method.
* @param endActions (optional) a method that executes when the cutscene fully completes
*/
fun end(endActions: (() -> Unit)? = null)
{
ended = true
fadeToBlack()
GameWorld.Pulser.submit(object : Pulse(){
var tick: Int = 0
override fun pulse(): Boolean {
when(tick++)
{
8 -> player.properties.teleportLocation = exitLocation
9 -> fadeFromBlack()
16 -> {
try {
endActions?.invoke()
} catch (e: Exception) {
SystemLogger.logErr(this::class.java, "There's some bad nasty code in ${this::class.java.simpleName} end actions!")
e.printStackTrace()
}
return true
}
}
return false
}
override fun stop() {
super.stop()
player ?: return
player.removeAttribute(ATTRIBUTE_CUTSCENE)
player.removeAttribute(ATTRIBUTE_CUTSCENE_STAGE)
player.properties.isSafeZone = false
player.properties.safeRespawn = ServerConstants.HOME_LOCATION
player.interfaceManager.restoreTabs()
player.unlock()
clearNPCs()
player.unhook(CUTSCENE_DEATH_HOOK)
player.logoutListeners.remove("cutscene")
content.global.ame.RandomEventManager.getInstance(player)?.enabled = true
PacketRepository.send(MinimapState::class.java, MinimapStateContext(player, 0))
}
})
}
/**
* Moves the camera to the specified regionX and regionY
* @param regionX the region-local X coordinate to move the camera to (0-63)
* @param regionY the region-local Y coordinate to move the camera to (0-63)
* @param height (optional) the height of the camera, defaults to 300.
* @param speed (optional) the speed of the camera transition, defaults to 100.
*/
fun moveCamera(regionX: Int, regionY: Int, height: Int = 300, speed: Int = 100)
{
val globalLoc = base.transform(regionX, regionY, 0)
camera.panTo(globalLoc.x, globalLoc.y, height, speed)
}
/**
* Rotates the camera to face the given region-local X and Y coordinates
* @param regionX the region-local X coordinate to rotate the camera to (0-63)
* @param regionY the region-local Y coordinate to rotate the camera to (0-63)
* @param height (optional) the height of the camera, defaults to 300.
* @param speed (optional) the speed of the camera transition, defaults to 100.
*/
fun rotateCamera(regionX: Int, regionY: Int, height: Int = 300, speed: Int = 100)
{
val globalLoc = base.transform(regionX, regionY, 0)
camera.rotateTo(globalLoc.x, globalLoc.y, height, speed)
}
/**
* Sets the location the player is placed at when the cutscene ends.
*/
fun setExit(location: Location)
{
exitLocation = location
}
private fun loadCurrentStage()
{
if(ended) return
runStage(player.getCutsceneStage())
}
/**
* Increments the player's stage attribute by 1
*/
fun incrementStage()
{
setAttribute(player, ATTRIBUTE_CUTSCENE_STAGE, player.getCutsceneStage() + 1)
loadCurrentStage()
}
/**
* Sets the player's stage attribute to a new stage
*/
fun updateStage(newStage: Int)
{
setAttribute(player, ATTRIBUTE_CUTSCENE_STAGE, newStage)
loadCurrentStage()
}
fun logCutscene(message: String)
{
if(ServerConstants.LOG_CUTSCENE)
SystemLogger.logInfo(this::class.java, "$message")
}
fun clearNPCs() {
for(entry in addedNPCs.entries)
{
logCutscene("Clearing ${entry.value.size} NPCs with ID ${entry.key} for ${player.username}.")
for(npc in entry.value) npc.clear()
}
addedNPCs.clear()
}
companion object {
const val ATTRIBUTE_CUTSCENE = "cutscene"
const val ATTRIBUTE_CUTSCENE_STAGE = "cutscene:stage"
object CUTSCENE_DEATH_HOOK : EventHook<SelfDeathEvent>
{
override fun process(entity: Entity, event: SelfDeathEvent) {
if(entity !is Player) return
entity.getCutscene()?.end() ?: entity.unhook(this)
}
}
}
}
@@ -0,0 +1,337 @@
package core.game.activity;
import core.game.component.Component;
import core.game.node.entity.Entity;
import core.game.node.entity.npc.NPC;
import core.game.node.entity.player.Player;
import core.game.system.task.Pulse;
import core.game.world.GameWorld;
import core.game.world.map.Location;
import core.game.world.map.build.DynamicRegion;
import core.net.packet.PacketRepository;
import core.net.packet.context.MinimapStateContext;
import core.net.packet.out.MinimapState;
import core.plugin.PluginManifest;
import core.plugin.PluginType;
import java.util.ArrayList;
import java.util.List;
/**
* Represents the plugin used to handle a cutscene.
* @author Vexia
* @date 28/12/2013
*/
@PluginManifest(type = PluginType.ACTIVITY)
public abstract class CutscenePlugin extends ActivityPlugin {
/**
* The list of tabs to remove.
*/
private static final int[] TABS = new int[] { 0, 1, 2, 3, 4, 5, 6, 11, 12 };
/**
* The npcs in our cutscene.
*/
protected final List<NPC> npcs = new ArrayList<>(100);
/**
* The start pulse used for effect.
*/
private final StartPulse startPulse = new StartPulse();
/**
* The ending pulse used for effect.
*/
private final EndPulse endPulse = new EndPulse();
/**
* If we should use a fade in or not.
*/
private final boolean fade;
/**
* Constructs a new {@code CutscenePlugin} {@code Object}.
* @param name the name of the cutscene/mapzone.
* @param fade fading in or not.
*/
public CutscenePlugin(String name, final boolean fade) {
super(name, true, false, true);
this.fade = fade;
}
/**
* Constructs a new {@code CutscenePlugin} {@code Object}.
* @param name the name.
*/
public CutscenePlugin(final String name) {
this(name, true);
}
@Override
public boolean start(final Player player, boolean login, Object... args) {
player.setAttribute("cutscene:original-loc", player.getLocation());
player.removeAttribute("real-end");
player.setAttribute("real-end", player.getLocation());
if (isFade()) {
GameWorld.getPulser().submit(getStartPulse());
} else {
PacketRepository.send(MinimapState.class, new MinimapStateContext(player, getMapState()));
player.getInterfaceManager().removeTabs(getRemovedTabs());
player.getProperties().setTeleportLocation(getStartLocation());
player.unlock();
player.getWalkingQueue().reset();
player.getLocks().lockMovement(1000000);
player.getInterfaceManager().close();
open();
}
player.lock();
return super.start(player, login, args);
}
@SuppressWarnings("deprecation")
@Override
public boolean leave(final Entity e, boolean logout) {
if (player != null) {
if (logout) {
player.setLocation(player.getAttribute("cutscene:original-loc", player.getLocation()));
end();
} else {
unpause();
}
player.unlock();
player.getInterfaceManager().openDefaultTabs();
player.getWalkingQueue().reset();
player.getLocks().unlockMovement();
}
return super.leave(e, logout);
}
@Override
public Object fireEvent(String identifier, Object... args) {
return null;
}
/**
* Method used to stop the cutscene.
* @param fade if we should use a fade cutout.
*/
public void stop(boolean fade) {
if (fade) {
GameWorld.getPulser().submit(endPulse);
} else {
end();
}
}
/**
* Method used to end the cutscene.
*/
public void end() {
if (region != null) {
for (int i = 0; i < region.getPlanes().length; i++) {
for (NPC n : region.getPlanes()[i].getNpcs()) {
if (n == null) {
continue;
}
n.clear();
}
}
}
PacketRepository.send(MinimapState.class, new MinimapStateContext(player, 0));
player.getInterfaceManager().restoreTabs();
player.unlock();// incase he was locked.
player.getWalkingQueue().reset();
}
/**
* Represents the pulse used when starting a cutscene. This is used to give
* dramatic effect for entering a cutscene. In the future allow for this to
* be toggled.
* @author 'Vexia
* @date 30/12/2013
*/
public class StartPulse extends Pulse {
/**
* Represents the counter.
*/
private int counter = 0;
/**
* Constructs a new {@code StartPulse} {@code Object}.
*/
public StartPulse() {
super(1, player);
}
@Override
public boolean pulse() {
switch (counter++) {
case 1:
player.lock();
player.getInterfaceManager().openOverlay(new Component(115));
break;
case 3:
PacketRepository.send(MinimapState.class, new MinimapStateContext(player, getMapState()));
player.getInterfaceManager().removeTabs(getRemovedTabs());
break;
case 4:
player.getProperties().setTeleportLocation(getStartLocation());
break;
case 5:
player.getInterfaceManager().closeOverlay();
player.getInterfaceManager().close();
player.unlock();
player.getWalkingQueue().reset();
player.getLocks().lockMovement(1000000);
open();
return true;
}
return false;
}
}
/**
* Represents the pulse used when ending a cutscene. This is used to give
* dramatic effect for entering a cutscene.
* @author 'Vexia
* @date 30/12/2013
*/
public class EndPulse extends Pulse {
/**
* Represents the counter.
*/
private int counter = 0;
/**
* Constructs a new {@code EndPulse} {@code Object}.
*/
public EndPulse() {
super(1, player);
}
@Override
public boolean pulse() {
switch (counter++) {
case 1:
player.lock();
player.getInterfaceManager().openOverlay(new Component(115));
break;
case 3:
PacketRepository.send(MinimapState.class, new MinimapStateContext(player, getMapState()));
player.getInterfaceManager().removeTabs(getRemovedTabs());
break;
case 4:
Location loc = (Location) (player.getAttribute("real-end", player.getAttribute("cutscene:original-loc", player.getLocation())));
player.getProperties().setTeleportLocation(loc);
break;
case 5:
end();
stop();
fade();// specfic for fadeout.
if (player.getSession().isActive()) {
PacketRepository.send(MinimapState.class, new MinimapStateContext(player, 0));
}
player.getInterfaceManager().closeOverlay();
if (player.getSession().isActive()) {
player.getInterfaceManager().close();
}
player.getProperties().setSafeZone(false);
return true;
}
return false;
}
}
/**
* Method called when the dim interface is closed. And you can see the
* cutscene.
*/
public void open() {
}
/**
* Method called on the end of the cutscene.
*/
public void fade() {
}
/**
* Gets the mapstate to use. (override if needed).
* @return the state.
*/
public int getMapState() {
return 2;
}
/**
* Gets the removed tabs. (override if needed).
* @return the tabs.
*/
public int[] getRemovedTabs() {
return TABS;
}
/**
* Gets the starting location (region based, override if needed).
* @return the location.
*/
public Location getStartLocation() {
return getBase();
}
/**
* Method used to unpause this cutscene.
*/
public final void unpause() {
stop(true);
}
/**
* Gets the player.
* @return The player.
*/
public Player getPlayer() {
return player;
}
/**
* Gets the region.
* @return The region.
*/
public DynamicRegion getRegion() {
return region;
}
/**
* Gets the nPCS.
* @return The nPCS.
*/
public List<NPC> getNPCS() {
return npcs;
}
/**
* Gets the fade.
* @return The fade.
*/
public boolean isFade() {
return fade;
}
/**
* Gets the start pulse.
* @return the pulse.
*/
public Pulse getStartPulse() {
return startPulse;
}
public Pulse getEndPulse(){return new EndPulse();}
}