/// <summary> /// Decides whether player can jump to the target point. /// All messages with reasons must be sent here. /// Can change destination too. /// </summary> /// <param name="targetPoint">The jump destination</param> /// <param name="player">The jumping player</param> /// <returns>True if allowed</returns> public bool IsAllowedToJump(ZonePoint targetPoint, GamePlayer player) { if (GameServer.Instance.Configuration.ServerType != eGameServerType.GST_Normal) return true; if (ServerProperties.Properties.ALLOW_ALL_REALMS_DF) return true; return (player.Realm == DarknessFallOwner); }
public bool IsAllowedToJump(ZonePoint targetPoint, GamePlayer player) { if (player.Level < 10 && player.Level > 4) { return true; } player.Client.Out.SendMessage("You do not meet the requirements to enter this region!", eChatType.CT_System, eChatLoc.CL_ChatWindow); return false; }
/// <summary> /// Decides whether player can jump to the target point. /// All messages with reasons must be sent here. /// Can change destination too. /// </summary> /// <param name="targetPoint">The jump destination</param> /// <param name="player">The jumping player</param> /// <returns>True if allowed</returns> public bool IsAllowedToJump(ZonePoint targetPoint, GamePlayer player) { if (player.CurrentRegion is BaseInstance == false) return true; if (((BaseInstance)player.CurrentRegion).OnInstanceDoor(player, targetPoint)) return true; else return false; //Let instance handle zoning by itself in this case... }
public bool IsAllowedToJump(ZonePoint targetPoint, GamePlayer player) { if(player.Client.Account.PrivLevel > 1) { return true; } if(player.Level < 5) { return true; } player.Client.Out.SendMessage(LanguageMgr.GetTranslation(player.Client.Account.Language, "DemonsBreachJumpPoint.Requirements"), eChatType.CT_System, eChatLoc.CL_ChatWindow); return false; }
/// <summary> /// Decides whether player can jump to the target point. /// All messages with reasons must be sent here. /// Can change destination too. /// </summary> /// <param name="targetPoint">The jump destination</param> /// <param name="player">The jumping player</param> /// <returns>True if allowed</returns> public bool IsAllowedToJump(ZonePoint targetPoint, GamePlayer player) { StartupLocations.StartLocation loc = StartupLocations.MainTownStartingLocations[player.CharacterClass.ID] as StartupLocations.StartLocation; if (loc != null) { targetPoint.TargetX = loc.X; targetPoint.TargetY = loc.Y; targetPoint.TargetZ = loc.Z; targetPoint.TargetHeading = (ushort)loc.Heading; return true; } return false; }
/// <summary> /// Decides whether player can jump to the target point. /// All messages with reasons must be sent here. /// Can change destination too. /// </summary> /// <param name="targetPoint">The jump destination</param> /// <param name="player">The jumping player</param> /// <returns>True if allowed</returns> public bool IsAllowedToJump(ZonePoint targetPoint, GamePlayer player) { StartupLocation loc = StartupLocations.GetNonTutorialLocation(player); if (loc != null) { targetPoint.TargetX = loc.XPos; targetPoint.TargetY = loc.YPos; targetPoint.TargetZ = loc.ZPos; targetPoint.TargetHeading = (ushort)loc.Heading; targetPoint.TargetRegion = (ushort)loc.Region; return true; } return false; }
/// <summary> /// Decides whether player can jump to the target point. /// All messages with reasons must be sent here. /// Can change destination too. /// </summary> /// <param name="targetPoint">The jump destination</param> /// <param name="player">The jumping player</param> /// <returns>True if allowed</returns> public bool IsAllowedToJump(ZonePoint targetPoint, GamePlayer player) { //Handles zoning INTO an instance. GameLocation loc = null; //First, we try the groups mission. if (player.Group != null) { Group grp = player.Group; if (grp.Mission != null && grp.Mission is TaskDungeonMission) { //Attempt to get the instance entrance location... TaskDungeonMission task = (TaskDungeonMission)grp.Mission; loc = task.TaskRegion.InstanceEntranceLocation; } } else if (player.Mission != null && player.Mission is TaskDungeonMission) { //Then, try personal missions... TaskDungeonMission task = (TaskDungeonMission)player.Mission; loc = task.TaskRegion.InstanceEntranceLocation; } if (loc != null) { targetPoint.TargetX = loc.X; targetPoint.TargetY = loc.Y; targetPoint.TargetZ = loc.Z; targetPoint.TargetRegion = loc.RegionID; targetPoint.TargetHeading = loc.RegionID; return true; } player.Out.SendMessage("You need to have a proper mission before entering this area!", eChatType.CT_System, eChatLoc.CL_SystemWindow); return false; }
//Below we have a void I've added. By default, it will do nothing, but its intention is for inherited //classes. //This concerns instances that have a door or other zone-method within them. If you recall, the players //regionID.Skin is the region the player thinks its in. As such, it will always call the zone point //of the same region, regardless of the instance the client is in. //This gives us a problem here: Lets say TaskDungeon1 wants to zone out to mularn, wherethe player entered. //Thats all dandy, and the database is set up that this is the case - as it most often will be. BUT, //another quest, 'Find Dinberg's Hat', uses the same regionID and wants the door not to even zone back to //mularn, but actually wants the door to go to a castle, in another instanced region. //The below method can be thus overriden to return false when the default method should NOT be used. //moving of the player can be handled inside this void. /// <summary> /// Invoked when the player attempts to use a door or zone point inside an instance. /// </summary> /// <returns>True if the player should be moved to default locations.</returns> public virtual bool OnInstanceDoor(GamePlayer player, ZonePoint zonePoint) { //zone point ID is also used for larger instances, eg Jordheim, with multiple exits. return true; }
public void HandlePacket(GameClient client, GSPacketIn packet) { ushort jumpSpotID = packet.ReadShort(); eRealm targetRealm = client.Player.Realm; if (client.Player.CurrentRegion.Expansion == (int)eClientExpansion.TrialsOfAtlantis && client.Player.CurrentZone.Realm != eRealm.None) { // if we are in TrialsOfAtlantis then base the target jump on the current region realm instead of the players realm // this is only used if zone table has the proper realms defined, otherwise it reverts to old behavior - Tolakram targetRealm = client.Player.CurrentZone.Realm; } var zonePoint = GameServer.Database.SelectObject<ZonePoint>("`Id` = '" + jumpSpotID + "' AND (`Realm` = '" + (byte)targetRealm + "' OR `Realm` = '0' OR `Realm` = NULL)"); if (zonePoint == null || zonePoint.TargetRegion == 0) { ChatUtil.SendDebugMessage(client, "Invalid Jump (ZonePoint table): [" + jumpSpotID + "]" + ((zonePoint == null) ? ". Entry missing!" : ". TargetRegion is 0!")); zonePoint = new ZonePoint(); zonePoint.Id = jumpSpotID; } //tutorial zone if (client.Player.CurrentRegionID == 27) { zonePoint = new ZonePoint(); switch (client.Player.Realm) { case eRealm.Albion: zonePoint.TargetRegion = 1; break; case eRealm.Midgard: zonePoint.TargetRegion = 100; break; case eRealm.Hibernia: zonePoint.TargetRegion = 200; break; } zonePoint.ClassType = "DOL.GS.GameEvents.TutorialJumpPointHandler"; } if (client.Account.PrivLevel > 1) { client.Out.SendMessage("JumpSpotID = " + jumpSpotID, eChatType.CT_System, eChatLoc.CL_SystemWindow); client.Out.SendMessage("ZonePoint Target: Region = " + zonePoint.TargetRegion + ", ClassType = '" + zonePoint.ClassType + "'", eChatType.CT_System, eChatLoc.CL_SystemWindow); } //Dinberg: Fix - some jump points are handled code side, such as instances. //As such, region MAY be zero in the database, so this causes an issue. if (zonePoint.TargetRegion != 0) { Region reg = WorldMgr.GetRegion(zonePoint.TargetRegion); if (reg != null) { // check for target region disabled if player is in a standard region // otherwise the custom region should handle OnZonePoint for this check if (client.Player.CurrentRegion.IsCustom == false && reg.IsDisabled) { if ((client.Player.Mission is TaskDungeonMission && (client.Player.Mission as TaskDungeonMission).TaskRegion.Skin == reg.Skin) == false) { client.Out.SendMessage("This region has been disabled!", eChatType.CT_System, eChatLoc.CL_SystemWindow); if (client.Account.PrivLevel == 1) { return; } } } } } // Allow the region to either deny exit or handle the zonepoint in a custom way if (client.Player.CurrentRegion.OnZonePoint(client.Player, zonePoint) == false) { return; } //check caps for battleground Battleground bg = GameServer.KeepManager.GetBattleground(zonePoint.TargetRegion); if (bg != null) { if (client.Player.Level < bg.MinLevel && client.Player.Level > bg.MaxLevel && client.Player.RealmLevel >= bg.MaxRealmLevel) return; } IJumpPointHandler customHandler = null; if (string.IsNullOrEmpty(zonePoint.ClassType) == false) { customHandler = (IJumpPointHandler)m_customJumpPointHandlers[zonePoint.ClassType]; // check for db change to update cached handler if (customHandler != null && customHandler.GetType().FullName != zonePoint.ClassType) { customHandler = null; } if (customHandler == null) { //Dinberg - Instances need to use a special handler. This is because some instances will result //in duplicated zonepoints, such as if Tir Na Nog were to be instanced for a quest. string type = (client.Player.CurrentRegion.IsInstance) ? "DOL.GS.ServerRules.InstanceDoorJumpPoint" : zonePoint.ClassType; Type t = ScriptMgr.GetType(type); if (t == null) { Log.ErrorFormat("jump point {0}: class {1} not found!", zonePoint.Id, zonePoint.ClassType); } else if (!typeof(IJumpPointHandler).IsAssignableFrom(t)) { Log.ErrorFormat("jump point {0}: class {1} must implement IJumpPointHandler interface!", zonePoint.Id, zonePoint.ClassType); } else { try { customHandler = (IJumpPointHandler)Activator.CreateInstance(t); } catch (Exception e) { customHandler = null; Log.Error( string.Format("jump point {0}: error creating a new instance of jump point handler {1}", zonePoint.Id, zonePoint.ClassType), e); } } } if (customHandler != null) { m_customJumpPointHandlers[zonePoint.ClassType] = customHandler; } } new RegionChangeRequestHandler(client.Player, zonePoint, customHandler).Start(1); }
/// <summary> /// Constructs a new RegionChangeRequestHandler /// </summary> /// <param name="actionSource">The action source</param> /// <param name="zonePoint">The target zone point</param> /// <param name="checker">The jump point checker instance</param> public RegionChangeRequestHandler(GamePlayer actionSource, ZonePoint zonePoint, IJumpPointHandler checkHandler) : base(actionSource) { if (zonePoint == null) throw new ArgumentNullException("zonePoint"); m_zonePoint = zonePoint; m_checkHandler = checkHandler; }
/// <summary> /// Handles players leaving this region via a zonepoint /// </summary> /// <param name="player"></param> /// <param name="zonePoint"></param> /// <returns>false to halt processing of this request</returns> public virtual bool OnZonePoint(GamePlayer player, ZonePoint zonePoint) { return true; }
/// <summary> /// Decides whether player can jump to the target point. /// All messages with reasons must be sent here. /// Can change destination too. /// </summary> /// <param name="targetPoint">The jump destination</param> /// <param name="player">The jumping player</param> /// <returns>True if allowed</returns> public bool IsAllowedToJump(ZonePoint targetPoint, GamePlayer player) { //Handles zoning INTO an instance. GameLocation loc = null; AdventureWingInstance previousInstance = null; // Do we have a group ? if(player.Group != null) { //Check if there is an instance dedicated to this group foreach(Region region in WorldMgr.GetAllRegions()) { if(region is AdventureWingInstance && ((AdventureWingInstance)region).Group != null && ((AdventureWingInstance)region).Group == player.Group) { // Our group has an instance ! previousInstance = (AdventureWingInstance)region; break; } else if(region is AdventureWingInstance && ((AdventureWingInstance)region).Player != null && ((AdventureWingInstance)region).Player == player.Group.Leader) { // Our leader has an instance ! previousInstance = (AdventureWingInstance)region; previousInstance.Group = player.Group; break; } } } else { // I am solo ! //Check if there is an instance dedicated to me foreach(Region region in WorldMgr.GetAllRegions()) { if(region is AdventureWingInstance && ((AdventureWingInstance)region).Player != null && ((AdventureWingInstance)region).Player == player) { // I have an Instance ! previousInstance = (AdventureWingInstance)region; previousInstance.Group = player.Group; break; } } } if(previousInstance != null) { // We should check if we can go in ! if(previousInstance.Skin != targetPoint.TargetRegion) { //we're trying to enter in an other instance and we still have one ! //check if previous one is empty if(previousInstance.NumPlayers > 0) { //We can't jump ! player.Out.SendMessage("You have another instance (" + previousInstance.Description + ") running with people in it !", eChatType.CT_System, eChatLoc.CL_SystemWindow); return false; } else { log.Warn("Player : "+ player.Name +" requested new Instance, destroying instance " + previousInstance.Description + ", ID: " + previousInstance.ID + ", type=" + previousInstance.GetType().ToString() + "."); WorldMgr.RemoveInstance(previousInstance); previousInstance = null; } } } if(previousInstance == null) { // I have no instance to go to, create one ! previousInstance = (AdventureWingInstance)WorldMgr.CreateInstance(targetPoint.TargetRegion, typeof(AdventureWingInstance)); if(targetPoint.SourceRegion != 0 && targetPoint.SourceRegion == player.CurrentRegionID) { //source loc seems legit... previousInstance.SourceEntrance = new GameLocation("source", targetPoint.SourceRegion, targetPoint.SourceX, targetPoint.SourceY, targetPoint.SourceZ); } if(player.Group != null) { previousInstance.Group = player.Group; previousInstance.Player = player.Group.Leader; } else { previousInstance.Group = null; previousInstance.Player = player; } //get region data long mobs = 0; long merchants = 0; long items = 0; long bindpoints = 0; previousInstance.LoadFromDatabase(previousInstance.RegionData.Mobs, ref mobs, ref merchants, ref items, ref bindpoints); if (log.IsInfoEnabled) { log.Info("Total Mobs: " + mobs); log.Info("Total Merchants: " + merchants); log.Info("Total Items: " + items); } //Attach Loot Generator LootMgr.RegisterLootGenerator(new LootGeneratorAurulite(), null, null, null, previousInstance.ID); // Player created new instance // Destroy all other instance that should be... List<Region> to_delete = new List<Region>(); foreach(Region region in WorldMgr.GetAllRegions()) { if (region is AdventureWingInstance && (AdventureWingInstance)region != previousInstance) { AdventureWingInstance to_clean = (AdventureWingInstance)region; // Won't clean up populated Instance if(to_clean.NumPlayers == 0) { if(to_clean.Group != null && player.Group != null && to_clean.Group == player.Group) { // Got another instance for the same group... Destroy it ! to_delete.Add(to_clean); } else if(to_clean.Player != null && (to_clean.Player == player || (player.Group != null && player.Group.Leader == to_clean.Player))) { // Got another instance for the same player... Destroy it ! to_delete.Add(to_clean); } else if(to_clean.Group == null && to_clean.Player == null) { //nobody owns this instance anymore to_delete.Add(to_clean); } } } } //enumerate to_delete foreach(Region region in to_delete) { log.Warn("Player : "+ player.Name +" has provoked an instance cleanup - " + region.Description + ", ID: " + region.ID + ", type=" + region.GetType().ToString() + "."); WorldMgr.RemoveInstance((BaseInstance)region); } } //get loc of instance if(previousInstance != null) { loc = new GameLocation(previousInstance.Description + " (instance)", previousInstance.ID, targetPoint.TargetX, targetPoint.TargetY, targetPoint.TargetZ, targetPoint.TargetHeading); } if (loc != null) { // Move Player, changing target destination is failing !! player.MoveTo(loc); return false; } player.Out.SendMessage("Something went Wrong when creating Instance !", eChatType.CT_System, eChatLoc.CL_SystemWindow); return false; }