Jump to content

kuba90

Members
  • Posts

    217
  • Credits

  • Joined

  • Last visited

  • Feedback

    0%

Everything posted by kuba90

  1. Στο επόμενο post τώρα που η μηχανή είναι έτοιμη θα σχεδιάσουμε ένα Event στο οποίο οι πέκτες κάνουν PVP για ένα Raid Boss.
  2. Για να συνδέσουμε όλα τα Events με το l2j θα χρησιμοποιήσουμε μια κλαση διεπαφής με όνομα TSManager. package L2Relapse.EventEngine; import java.util.Calendar; import java.util.logging.Logger; import javolution.util.FastMap; import L2Relapse.EventEngine.Conquest.ConquestEvent; import L2Relapse.EventEngine.utils.EventStatus; import L2Relapse.Utils.Developer; import com.l2jserver.gameserver.ThreadPoolManager; import com.l2jserver.gameserver.model.actor.L2Character; import com.l2jserver.gameserver.model.actor.instance.L2PcInstance; /** * @author Issle * */ public class TSManager { protected static final Logger _log = Logger.getLogger(TSManager.class.getName()); //Indicates if the TSManager is running an event atm. public static boolean eventIsRunning = false; //Holds the active event that is running atm. public static AbstractEvent activeEvent = null; //A list of the events that the manager will run and their dates. public FastMap<Calendar, AbstractEvent> events; //Sample event for testing. ConquestEvent sampleEvent = new ConquestEvent(5000, "Conquest Event"); public void loadEvents() { //Initialize the events list. events = new FastMap<Calendar, AbstractEvent>(); activeEvent = sampleEvent; } public synchronized static void setEvent() { activeEvent.setEventStatus(EventStatus.active); eventIsRunning = true; } /** * Inactivates the active event and informs the Scheduling manager. */ public synchronized static void clearEvent() { activeEvent.setEventStatus(EventStatus.inactive); eventIsRunning = false; } public synchronized static boolean getEvent() { return eventIsRunning; } public class ManagerTask implements Runnable { public ManagerTask() { //doNothing. } @Override public void run() { ThreadPoolManager.getInstance().scheduleGeneral(new ManagerTask(), 15000); if(getEvent()) { Developer.printEventMessage("THere is an event running."); return; } setEvent(); activeEvent.startEvent(); } } public static void onLogin(L2PcInstance activeChar) { if(eventIsRunning) activeEvent.onLogin(activeChar); } public static void onLogout(L2PcInstance activeChar) { if(eventIsRunning) activeEvent.onLogout(activeChar); } public static void onKill(L2Character killerCharacter, L2PcInstance killedPlayerInstance) { if(eventIsRunning) activeEvent.onKill(killerCharacter, killedPlayerInstance); } public static void onEscapeUse(L2PcInstance activeChar) { if(eventIsRunning) activeEvent.onEscapeUse(activeChar); } public static boolean isInEvent(L2PcInstance activeChar) { if(eventIsRunning && activeEvent != null) { return true; } return false; } private TSManager() { _log.info("[L2Relapse]Starting Time Scheduling Manager."); loadEvents(); ThreadPoolManager.getInstance().scheduleGeneral(new ManagerTask(), 15000); } public static class SingletonHolder{ public static final TSManager INSTANCE = new TSManager(); } public static TSManager getInstance(){ return SingletonHolder.INSTANCE; } }
  3. Όμοια και για το Event έχουμε ένα AbstractEvent που ορίζει το καλούπι για όλα τα Events. Κάθε event έχει: 1)Ρολόι 2)Όνομα 3)Λίστα από στάδια ( px Registration , Fight ktl ktl ). Επίσης το Event περιέχει συνθήκες ελέγχου onKill κτλ. Δεν υλοποιούνται γιατί όπως και προηγουμένος η κλάση αποτελεί καλούπι κατα κάποιο τρόπο. Επίσης έχει έναν χρονιστή ( που θέλει λίγη βελτίωση και Optimization :-\ sorry ). package L2Relapse.EventEngine; import java.util.LinkedList; import com.l2jserver.gameserver.ThreadPoolManager; import L2Relapse.EventEngine.utils.EventStatus; import L2Relapse.EventEngine.utils.RegistrationStatus; import com.l2jserver.gameserver.model.actor.L2Character; import com.l2jserver.gameserver.model.actor.instance.L2PcInstance; /** * @author Issle * * Common information that all the events use. * */ public abstract class AbstractEvent { public LinkedList<AbstractEventState> eventStates = new LinkedList<AbstractEventState>(); //Setting event parameters. public int clockRate = 10000; public String name = "NoName"; //The active state of this event. public AbstractEventState activeState; //The status of the event ( open /closed ). public EventStatus eventStatus; public RegistrationStatus registrationStatus; /** * This is the core initialization of the event engine. It * reads the first state, and then schedules the checks for * the advancement of the event. The clock rate will not * affect the slow/fast pace of the event. It controls the * rate in which the core checks for conditions in each event * state. */ public void startEvent() { if(eventStates.isEmpty()) return; //The event has started, change its status to active. eventStatus = EventStatus.active; //Get the activeState of the event whici is always the first state. activeState = eventStates.get(0); //Execute the activeState. activeState.onEnterState(); //Check the advancing conditions on the future. ThreadPoolManager.getInstance().scheduleGeneral(new ConditionTask(this), clockRate); } /** * This class checks the active states conditions. If * the conditions are met, the state advances. Each state * indicates to what state the system must advance. * * @author Issle * */ public class ConditionTask implements Runnable { AbstractEvent event; public ConditionTask(AbstractEvent event) { this.event = event; } public void run() { //Are the conditions met ? if(activeState.checkConditions()) { //Exits the current state. activeState.onExitState(); //Tries to load the next state. if(activeState.getNextStateId()!= 0) { //Change the active state. activeState = eventStates.get(activeState.getNextStateId()-1); //Enter the current state. activeState.onEnterState(); } } //If there is NO other state, then the event has ended. //In that case do not schedule a new conditions task. if(activeState.getNextStateId()!= 0) { ThreadPoolManager.getInstance().scheduleGeneral(new ConditionTask(event), clockRate); return; } //else ... TSManager.clearEvent(); System.out.println("Event is now inactive."); } } public String getName() { return name; } public void setEventStatus(EventStatus evt) { eventStatus = evt; } /** * @param activeChar */ public abstract void register(L2PcInstance activeChar); /** * @param activeChar */ public abstract void onEscapeUse(L2PcInstance activeChar); /** * @param killerCharacter * @param killedPlayerInstance */ public abstract void onKill(L2Character killerCharacter, L2PcInstance killedPlayerInstance); /** * @param playerInstance */ public abstract void onLogin(L2PcInstance playerInstance); /** * @param playerInstance */ public abstract void onLogout(L2PcInstance playerInstance); /** * Cleans the teams. */ public abstract void cleanTeams(); public void setRegistrationStatus(RegistrationStatus status) { registrationStatus = status; } /** * Returns the current events clock rate in milliseconds. * @return clockRate */ public int getClockRate() { return clockRate; } } Πλέον έχουμε έτοιμο το καλούπι για τα state για τα Event και απομένεί να χρησιμοποιήσουμε μία κλάση που θα συνδέσει τα Event μας με το L2J. To be continued ...
  4. Ας πάμε τώρα στο Event State. Κάθε Event State, έχει τα παρακάτω: 1)Έναν αριθμό που προσδιορίζει την θέση του ανάμεσα στα υπόλοιπα state του event. 2)Έναν αριθμό που προσδιορίζει ποιό state θα ακολουθήσει μετά την λήξη του. 3)Έναν αριθμό που προσδιορίζει για πόσο χρόνο θα διαρκέσει ένα State. 4)Αναφορά στο Event στο οποίο ανήκει, ας το ονομάσουμε AbstractEvent. 1)Μία συνάρτηση εισόδου (onEnterState()) που λέει τι θα γίνει μόλις το State ενεργοποιηθεί. 2)Μία συνάρτηση εξόδου ( onExitState()) που λέει τι θα γίνει μόλις το State τελειώσει. 3)Μία συνάρτηση ελέγχουν (checkConditions()) που εκτελείτε κάθε X seconds και ελέγχει την κατάσταση. package L2Relapse.EventEngine; /** * @author Issle * */ public abstract class AbstractEventState { protected int stateId; protected int nextStateId; protected int duration = 240000; protected int remainingTime; protected AbstractEvent activeEvent; public void initializeTime() { remainingTime = duration; } public AbstractEvent getEvent() { return activeEvent; } public int getNextStateId() { return nextStateId; } public void decreaseTime() { remainingTime -= activeEvent.getClockRate(); } public abstract void onEnterState(); public abstract void onExitState(); public abstract boolean checkConditions(); } Η κλάση αυτή είναι Abstract που σημένει οτι μέρη της κλάσης δεν υλοποιούνται και ούτε μπορεί να χρησημοποιηθεί. Η κλάση αυτή ορίζει ένα πρότυπο για το πώς θα σχεδιαστούν τα States. Δηλαδή ορίζει για παράδειγμα οτι όλα τα States έχουν συνάρτηση onEnterState() αλλά καθένα ίσως την υλοποιήσει διαφορετικά.
  5. Κάθε event έχει μιά κατάσταση λειτουργίας και μιά κατάσταση Register. Για παράδειγμα ένα event είναι ενεργό ή ανενεργό. Επίσης ένα event έχει ενεργοποιημένη την εγγραφή ή απενεργοποιημένη ή δεν έχει καθόλου εγγραφή. Οι παρακάτω κώδικες αποτελόυν τμήμα του κάθε event και είναι Enumerations. package L2Relapse.EventEngine.utils; /** * @author Issle * * An event should be active or inactive. * All inner states of the event should not * be in an enumeration, cuase the form a unique * state class in the state machine model. * */ public enum EventStatus { active, inactive } καί package L2Relapse.EventEngine.utils; /** * @author Issle * */ public enum RegistrationStatus { free,open,closed } Αυτά τα δύο ορίζουν πλήρως την κατάσταση ενός Event εξωτερικά, όπως την βλέπει ένας χρήστης που δεν συμετέχει στο Event.
  6. Ο IronMan (aka) Tony Stark, δεν είχε πολύ μυαλό. Είχε πολύ καλά εργαλεία. Σε αυτό το topic θα σχεδιάσουμε μαζί μία μηχανή για Events. Οι στόχοι του Topic: 1)Σχεδιασμός μηχανής για Event. 2)Καλή χρήση της Java. 3)Βήμα προς βήμα οδηγείες και για αυτούς που ξέρουν πολύ λίγη Java. 4)Σχεδιασμός ενός απλού Event. Προαπαιτούμενα: - Ο αναγνώστης γνωρίζει πώς να κάνει Compile με NetBeans ή Eclipse. - O αναγνωστης γνωρίζει πώς να περνάει στο pack του Patches. - O αvαγνωστης γνωρίζει τα πολύ βασικά για την Java. - Χρησιμοποιούμε L2JServer epilogue ( αλλά και Interlude μας βολεύει. ) - Επισης μας βολευόυν τα δευτερέυοντα packs ( l2jbrazil, l2jteon, l2jarchid και λοιπές μαλακίες ). Αν διαβάζεις αυτό το topic και δεν γνωρίζεις τα πρώτα τρία από παραπάνω φύγε από το topic, δεν θα καταλάβεις τίποτα. Απλά περίμενε να τελειώσουμε για να πάρεις το Patch έτοιμο στο τέλος (όπως άλλωστε συνηθίζεις εδώ και καιρό ...:) ). Δεν κάνω post την μηχανή για Events κατευθείαν παρόλο που την έχω έτοιμη γιατί στόχος του topic δεν είναι απλά να πετάξω ένα patch ξεκάρφωτο αλλά να δείξω πώς να γράφει κανείς σωστά κώδικα και να σχεδιάζει ( τουλάχιστον για τους 10 - 15 που ενδιαφέρονται ). Ξεκινάμε :). Τα προβλήματα που έχουμε με τα Events αυτή τη στιγμή είναι οτι το καθένα ( tvt,dm,ctf ) πρέπει να το περάσεις σε 15 διαφορετικά μέρη του κώδικα. Επίσης με δεδομένο ένα event δεν είναι εύκολο να το τροποποιήσεις ώστε να φτιάξεις ένα event. Με βάση αυτές τις δύο παρατηρήσεις θα σχεδιάσουμε την μηχανή μας. Το πρώτο πράγμα που θα πρέπει να κάνουμε είναι να βρούμε τι κοινό έχουν τα περισσότερα events μεταξύ τους. Εγώ σκέυτηκα ώς εξής. Κάθε event οτιδήποτε και να κάνει, περνάει από μία σειρά από στάδια. Για παράδειγμα: -TVTEvent : Registration --> fighting --> rewarding --> end. -CTFEvent: Registration --> fighting --> rewarding --> end. Σαν πρώτη ιδέα λοιπον μπορούμε να πούμε οτι ένα event αποτελείτε από ένα σύνολο από στάδια. Με βάση αυτό ανακύπτει η ερώτηση: Πώς μεταβαίνουμε από στάδιο σε στάδιο ? Και η απάντηση θα μπορούσε να ήταν κάθε στάδιο εκτελεί κάποιες ενέργιες όταν ενεργοποιείτε, κάποιες ενέργειες όταν απενεργοποιείται και ενημερώνει το Event να μετακινηθεί στο επόμενo στάδιο. Ένα ολοκληρωμένο παράδειγμα είναι το TvTEvent όπως φαίνεται παρακάτω: Αυτό που φαίνεται εξαρχής είναι οτι κάθε state κάνει κάποια πράγματα στην αρχή, κάποια στο τέλος και ενδιάμεσα ελέγχει συνθήκες. ΠΧ αν τελείωσε ο χρόνος του, άν δεν ικανοποιούνται οι συνθήκες και ενημερώνει το event λέγοντάς του σε ποιό state να μεταβεί. Για παράδειγμα άν το Registration State δεί οτι δέν υπάρχουν αρκετά άτομα για να γίνει το Event ενημερώνει το Event να λήξει. Αλλιώς του λέει να μεταβέι στο Fighting State. To Be Continued.
  7. PC 1: Game server ( HD 1 ) Login server ( HD 2 ) PC 2: Database ( HD1 ) Exoun lan ta pc ? Giati allios ta dedomena tha metaferonte apo kai pros tin basi meso Internet kai tha argei poli o server sou sto ksekinima kai sto stamatima. Otan ixa server ixa kanei ayto to setup meso WAN kai otan kliname ton server ( restart ktl ) ekane giro sta 10 lepta na apothikeysei characters stin database :).
  8. How great can this "network" or "server" or whatever it is be, when the creator cant even explain in simple english what he wants to do ... Nowadays everyone is looking for "experienced" developers, "experienced" gms , "experienced" admins, but the main fact is that the one searching is completelly inexperienced. Every noob out there thinks he will make the next great server or next "maxcheaters.com". There exists a simple rule in this business: If you cant code, you cant own a sucessful server. And thats the bottom line.
  9. 149 euro den einai polla. Gia ton aplo logo, an mpeis ston kopo na anoikseis server sobara exeis sto nou sou 500+ atoma online pou simenei trelo donate. An pali den pisteyeis oti exeis tin ikanonita na trabikseis 500 atoma ( koinos an o server sou einai "just another server" ) tote eksarxis min mpeneis ston kopo na asxolitheis me servers. Pare ena client kai pekse stous servers pou iparxoun idi :)
  10. gia dokimase na antikatastiseis to -Xmn512m me: -Xmn128m -Xms512m -Xmx512m
  11. gia kane copy/paste ta contents apo to gameserver.bat. Den kses kamia fora mporei na einai piragmenes i times tou sorou.:) (deksi click --> edit sto gameserver.bat)
  12. prosexe otan alazeis to access level enos character, o character na einai offline. Allios to access level tha epistrepsei opos itan otan kaneis logout i otan perasei ligos xronos.
  13. pou skata to eides ayto ? oti ta skills einai adia ? Den einai apla exei lathos sto string formation.
  14. Kapios pou kserei pos na setarei server kai na grapsei kodika ( aka developer ) den xriazete esena gia afentiko ston server tou. Kanei diko tou server kai pernei poli perisostera apo 150 euro to mina. Opos eipa gia malakes psaxneis ...
  15. etsi pou to ekanes nooba diegrapses to attribute. Xalases to skill diladi. To sosto einai na peraseis to neo attribute mesa sto stats.java. Alla pou na katalabeis afou eipame oti eisai xazos :)
  16. There is one thing to consider though. Which is "when" do you count the ppl that are inside the zone ? Each time a player clicks the gatekeeper, or do you schedule a task to do so every 20-30 secs ? Accuracy vs performance .
  17. Eisai xazos :) Den katalabeneis den pirazei.
  18. 112-1508-1 112 = duelist , 1508 = kapio skill tou duelist , 1 = level. Aytos o sindiasmos iparxei idi ston pinaka mesa. To script sou prospathei na ton balei ksana kai den ginete. Apla diegrapse ton ite apo ton pinaka ite apo to script sou.
  19. [Err] 1062 - Duplicate entry '112-1508-1' for key 'PRIMARY' Toso diskolo einai ?
  20. PS: Δεν το τέσταρα και πολύ αλλά λίγο που δοκίμασα δουλεύει καλά.
  21. Κάποιος το ζήτησε στο dev section. Βασικά αυτό που κάνει είναι να διατηρεί τα Buffs σου όταν ψοφάς άν φοράς τα κατάλληλα armor parts. Index: java/com/l2jserver/gameserver/Custom/ArmorNoblesse.java =================================================================== --- java/com/l2jserver/gameserver/Custom/ArmorNoblesse.java (revision 0) +++ java/com/l2jserver/gameserver/Custom/ArmorNoblesse.java (revision 0) @@ -0,0 +1,72 @@ +/* + * This program is free software: you can redistribute it and/or modify it under + * the terms of the GNU General Public License as published by the Free Software + * Foundation, either version 3 of the License, or (at your option) any later + * version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more + * details. + * + * You should have received a copy of the GNU General Public License along with + * this program. If not, see <http://www.gnu.org/licenses/>. + */ +package com.l2jserver.gameserver.Custom; + +import com.l2jserver.gameserver.model.actor.instance.L2PcInstance; +import com.l2jserver.gameserver.model.itemcontainer.Inventory; +import com.l2jserver.gameserver.model.itemcontainer.PcInventory; + +/** + * @author Issle + * + */ +public class ArmorNoblesse +{ + public static final int bodyId = 0; + public static final int pantsId = 0; + public static final int glovesId = 0; + public static final int bootsId = 0; + public static final int helmetId = 0; + + public static boolean hasArmorNoblesse(L2PcInstance activeChar) + { + PcInventory inventory = activeChar.getInventory(); + + int _pantsId = inventory.getPaperdollItemId(Inventory.PAPERDOLL_LEGS); + int _bodyId = inventory.getPaperdollItemId(Inventory.PAPERDOLL_CHEST); + int _helmetId = inventory.getPaperdollItemId(Inventory.PAPERDOLL_HEAD); + int _glovesId = inventory.getPaperdollItemId(Inventory.PAPERDOLL_GLOVES); + int _bootsId = inventory.getPaperdollItemId(Inventory.PAPERDOLL_FEET); + + if(_pantsId != pantsId) + return false; + if(_glovesId != glovesId) + return false; + if(_bodyId != bodyId) + return false; + if(_helmetId != helmetId) + return false; + if(_bootsId != bootsId) + return false; + activeChar.sendMessage("You maintained your buffs cause of your special armor configuration."); + return true; + } + + private static void printParts(L2PcInstance activeChar, int part) + { + activeChar.sendMessage(String.valueOf(part)); + } +} Index: java/com/l2jserver/gameserver/model/actor/L2Playable.java =================================================================== --- java/com/l2jserver/gameserver/model/actor/L2Playable.java (revision 4222) +++ java/com/l2jserver/gameserver/model/actor/L2Playable.java (working copy) @@ -14,6 +14,7 @@ */ package com.l2jserver.gameserver.model.actor; +import com.l2jserver.gameserver.Custom.ArmorNoblesse; import com.l2jserver.gameserver.ai.CtrlEvent; import com.l2jserver.gameserver.model.L2Effect; import com.l2jserver.gameserver.model.actor.instance.L2PcInstance; @@ -136,6 +137,10 @@ if (getCharmOfLuck()) //remove Lucky Charm if player have Nobless blessing buff stopCharmOfLuck(null); } + else if(this instanceof L2PcInstance && ArmorNoblesse.hasArmorNoblesse((L2PcInstance)this)) + { + //do nothing. + } else stopAllEffectsExceptThoseThatLastThroughDeath(); Στα μηδενικά που έχει βάζεις τα ID από το Armor. Άν δεν υπάρχει armor (πχ όταν έχεις full-body , δεν έχεις pants ) βάζεις 0.
  22. Το κάνω share σε δύο λεπτάκια στο Greek Share section.
  23. Blakeies lete. Exeis apla kenourgio datapack pou exei mesa ena attribute sta skills pou legete fall. O pirinas sou omos ( core ) einai palios kai den to ipostirizei. H allakse datapack pou na einai simbato, i allakse pirina ( pare ta up-to-date ) files apo to pack pou xrisimopoieis.
  24. "geia sas pedia, eimai asxetos apo servers, alla pisteyo oti xoris na exo kamia empireia tha anoikso fobero server, kai thelo enan malaka pou kserei ta panta, alla den exei diko tou server , na kanei ta panta gia mena kai na tou dino 15 euro.". Na pos xalaei i piatsa, otan o kathe malakas anoigei server kai exei to astronomiko poso ton 56 players :) !!!!
×
×
  • Create New...