Guild PQ + fixed negative EXP error

Implemented Guild PQ. Fixed a problem introduced earlier where negative
EXP would be deemed as "integer overflow", provoking many game breaking
issues as result.
This commit is contained in:
ronancpl
2017-06-18 03:19:53 -03:00
parent 81f9226286
commit 42fe74955d
135 changed files with 822 additions and 564 deletions

View File

@@ -10,7 +10,7 @@ var clearMap; // Upon event clearing, players may be moved to
var minMapId; // Event takes place inside these map id interval. Players found out is instantly dropped from the event.
var maxMapId;
var eventTime; // Max time alloted for the event, in minutes.
var eventTime; // Max time allotted for the event, in minutes.
var lobbyRange = [0, 0]; // Range of concurrent lobbies (min range is 0, max range is 7).

View File

@@ -96,7 +96,7 @@ function setup(level, lobbyid) {
function afterSetup(eim) {}
function respawnStg2(eim) {
if(!eim.getMapInstance(930000200).getAllPlayer().isEmpty()) eim.getMapInstance(930000200).instanceMapRespawn();
if(!eim.getMapInstance(930000200).getPlayers().isEmpty()) eim.getMapInstance(930000200).instanceMapRespawn();
eim.schedule("respawnStg2", 4 * 1000);
}

View File

@@ -30,13 +30,14 @@ var minLevel = 1, maxLevel = 200;
var entryMap = 990000000;
var exitMap = 990001100;
var recruitMap = 101030104;
var clearMap = 990001101;
var clearMap = 990001000;
var minMapId = 990000000;
var maxMapId = 990001101;
var waitTime = 3;
var waitTime = 3; // 3 minutes
var eventTime = 90; // 90 minutes
var bonusTime = 0.5; // 30 seconds
var lobbyRange = [0, 0];
@@ -119,7 +120,7 @@ function setup(level, lobbyid) {
eim.setProperty("guild", 0);
eim.setProperty("canJoin", 1);
eim.setProperty("statusStg1", -1);
eim.setProperty("canRevive", 0);
eim.getInstanceMap(990000000).resetPQ(level);
eim.getInstanceMap(990000100).resetPQ(level);
@@ -175,7 +176,9 @@ function isTeamAllJobs(eim) {
*/
function afterSetup(eim) {
eim.setProperty("guild", "" + eim.getLeader().getGuildId());
var leader = em.getChannelServer().getPlayerStorage().getCharacterById(eim.getLeaderId());
if(leader != null)
eim.setProperty("guild", "" + leader.getGuildId());
}
function respawnStages(eim) {}
@@ -189,16 +192,20 @@ function playerEntry(eim, player) {
}
function scheduledTimeout(eim) {
if(eim.getIntProperty("canJoin") == 1) {
eim.setProperty("canJoin", 0);
if(eim.checkEventTeamLacking(true, minPlayers)) {
end(eim);
} else {
eim.startEventTimer(eventTime * 60000);
}
if(eim.isEventCleared()) {
eim.warpEventTeam(990001100);
} else {
end(eim);
if(eim.getIntProperty("canJoin") == 1) {
eim.setProperty("canJoin", 0);
if(eim.checkEventTeamLacking(true, minPlayers)) {
end(eim);
} else {
eim.startEventTimer(eventTime * 60000);
}
} else {
end(eim);
}
}
}
@@ -222,15 +229,33 @@ function changedMap(eim, player, mapid) {
function changedLeader(eim, leader) {}
function playerDead(eim, player) {}
function playerDead(eim, player) {
if(player.getMapId() == 990000900) {
if(player.getMap().countAlivePlayers() == 0 && player.getMap().countMonsters() > 0) {
end(eim);
}
}
}
function playerRevive(eim, player) { // player presses ok on the death pop up.
if (eim.isEventTeamLackingNow(true, minPlayers, player) && eim.getIntProperty("canJoin") == 0) {
eim.unregisterPlayer(player);
end(eim);
if(eim.getIntProperty("canRevive") == 0) {
if (eim.isEventTeamLackingNow(true, minPlayers, player) && eim.getIntProperty("canJoin") == 0) {
eim.unregisterPlayer(player);
player.setHp(50);
player.changeMap(exitMap);
end(eim);
}
else {
eim.unregisterPlayer(player);
player.setHp(50);
player.changeMap(exitMap);
}
return false;
}
else
eim.unregisterPlayer(player);
return true;
}
function playerDisconnected(eim, player) {
@@ -267,6 +292,9 @@ function giveRandomEventReward(eim, player) {
function clearPQ(eim) {
eim.stopEventTimer();
eim.setEventCleared();
eim.warpEventTeam(clearMap);
eim.startEventTimer(bonusTime * 60000);
}
function monsterKilled(mob, eim) {}

View File

@@ -147,12 +147,12 @@ function action(mode, type, selection) {
var players = Array();
var total = 0;
for (var i = 0; i < 3; i++) {
var z = cm.getMap().getNumPlayersItemsInArea(i);
var z = cm.getMap().getNumPlayersInArea(i);
players.push(z);
total += z;
}
if (total != 3) {
cm.sendOk("There needs to be 3 players OR items on the platforms.");
cm.sendOk("There needs to be exactly 3 players on these platforms.");
} else {
var num_correct = 0;
for (var i = 0; i < 3; i++) {

View File

@@ -45,7 +45,7 @@ function action(mode, type, selection) {
var eim = cm.getEventInstance();
if(!eim.giveEventReward(cm.getPlayer())) {
cm.sendNext("It seems you don't have a free slot in either your #rEquip#k, #rUse#k or #rEtc#k inventories. Please make room and try again.");
cm.sendNext("It seems you don't have a free slot in either your #rEquip#k, #rUse#k or #rEtc#k inventories. Please make some room and try again.");
} else {
cm.warp(221024500);
}

View File

@@ -68,7 +68,7 @@ function action(mode, type, selection) {
cm.sendNext("A stimulator is a special potion that I can add into the process of creating certain items. It gives it stats as though it had dropped from a monster. However, it is possible to have no change, and it is also possible for the item to be below average. There's also a 10% chance of not getting any item when using a stimulator, so please choose wisely.")
cm.dispose();
} else if (selectedType == 1){ //warrior weapon
var selStr = "Very well, then which Warrior weapon shall recieve a dragon's power?#b";
var selStr = "Very well, then which Warrior weapon shall receive a dragon's power?#b";
var weapon = new Array ("Dragon Carbella#k - Lv. 110 One-Handed Sword#b","Dragon Axe#k - Lv. 110 One-Handed Axe#b","Dragon Mace#k - Lv. 110 One-Handed BW#b","Dragon Claymore#k - Lv. 110 Two-Handed Sword#b","Dragon Battle Axe#k - Lv. 110 Two-Handed Axe#b","Dragon Flame#k - Lv. 110 Two-Handed BW#b",
"Dragon Faltizan#k - Lv. 110 Spear#b","Dragon Chelbird#k - Lv. 110 Polearm#b");
for (var i = 0; i < weapon.length; i++){
@@ -76,28 +76,28 @@ function action(mode, type, selection) {
}
cm.sendSimple(selStr);
} else if (selectedType == 2){ //bowman weapon
var selStr = "Very well, then which Bowman weapon shall recieve a dragon's power?#b";
var selStr = "Very well, then which Bowman weapon shall receive a dragon's power?#b";
var weapon = new Array ("Dragon Shiner Bow#k - Lv. 110 Bow#b","Dragon Shiner Cross#k - Lv. 110 Crossbow#b");
for (var i = 0; i < weapon.length; i++){
selStr += "\r\n#L" + i + "# " + weapon[i] + "#l";
}
cm.sendSimple(selStr);
} else if (selectedType == 3){ //magician weapon
var selStr = "Very well, then which Magician weapon shall recieve a dragon's power?#b";
var selStr = "Very well, then which Magician weapon shall receive a dragon's power?#b";
var weapon = new Array ("Dragon Wand#k - Lv. 108 Wand#b","Dragon Staff#k - Lv. 110 Staff#b");
for (var i = 0; i < weapon.length; i++){
selStr += "\r\n#L" + i + "# " + weapon[i] + "#l";
}
cm.sendSimple(selStr);
} else if (selectedType == 4){ //thief weapon
var selStr = "Very well, then which Thief weapon shall recieve a dragon's power?#b";
var selStr = "Very well, then which Thief weapon shall receive a dragon's power?#b";
var weapon = new Array ("Dragon Kanzir#k - Lv. 110 STR Dagger#b","Dragon Kreda#k - Lv. 110 LUK Dagger#b","Dragon Green Sleve#k - Lv. 110 Claw#b");
for (var i = 0; i < weapon.length; i++){
selStr += "\r\n#L" + i + "# " + weapon[i] + "#l";
}
cm.sendSimple(selStr);
} else if (selectedType == 5){ //pirate weapon
var selStr = "Very well, then which Pirate weapon shall recieve a dragon's power?#b";
var selStr = "Very well, then which Pirate weapon shall receive a dragon's power?#b";
var weapon = new Array ("Dragon Slash Claw#k - Lv. 110 Knuckle#b","Dragonfire Revolver#k - Lv. 110 Gun#b");
for (var i = 0; i < weapon.length; i++){
selStr += "\r\n#L" + i + "# " + weapon[i] + "#l";

View File

@@ -68,7 +68,7 @@ function action(mode, type, selection) {
if(cm.getPlayer().getGuildId() > 0) {
var eim = findLobby(cm.getPlayer().getGuildId());
if(eim == null) {
cm.sendOk("You don't have a guild registered and currently on strategy time to assist on this channel.");
cm.sendOk("Your guild is not currently on strategy time on this channel. Check again if your guild is currently planning a Guild Quest or, if so, the channel they are allotted on.");
} else {
if(cm.isLeader()) {
em.getEligibleParty(cm.getParty());
@@ -83,16 +83,22 @@ function action(mode, type, selection) {
cm.dispose();
} else {
cm.sendOk("#e#b<Guild Quest: Sharenian Ruins>#k#n\r\n Team up with your guild members in an auspicious attempt to recover the Rubian from the skeleton's grasp, with teamwork overcoming many puzzles and challenges awaiting inside the Sharenian tombs. Great rewards can be obtained upon the instance completion, and Guild Points can be racked up for your Guild.");
var reqStr = "";
reqStr += "\r\n\r\n Team requirements:\r\n\r\n";
reqStr += " - 1 team member #rbelow or equal level 30#k.\r\n";
reqStr += " - 1 team member who is a #rThief with Dark Sight#k skill and #rmaxed Haste#k.\r\n";
reqStr += " - 1 team member who is a Magician with #rmaxed Teleport#k.\r\n";
reqStr += " - 1 team member who is a #rlong ranged attacker#k like Bowman, Assassin, or Gunslinger.\r\n";
reqStr += " - 1 team member with #rgood jumping skills#k like Assassin with maxed Flash Jump or Gunslinger with Wings.\r\n";
cm.sendOk("#e#b<Guild Quest: Sharenian Ruins>#k#n\r\n Team up with your guild members in an auspicious attempt to recover the Rubian from the skeleton's grasp, with teamwork overcoming many puzzles and challenges awaiting inside the Sharenian tombs. Great rewards can be obtained upon the instance completion, and Guild Points can be racked up for your Guild." + reqStr);
cm.dispose();
}
} else if (status == 2) {
if (sel == 0) {
var entry = em.addGuildToQueue(cm.getPlayer().getGuildId(), cm.getPlayer().getId());
if(entry > 0) {
if(entry == 1) {
cm.sendOk("Your guild has been registered successfully. A message will pop on your chat keeping your guild aware about the registration status. Now, #rimportant#k: as the leader of this instance, #ryou must already be present on this channel#k the right moment your guild is called for the strategy time. #bThe missubmission of this action will void#k your guild registration as a whole, and the next guild will be called immediately. Must be noted also, that if you become absent from the end of the strategy time to any point on the duration of the instance, it will render the instance interrupted, and your guild will be moved out instantly, moving again the queue.");
}
cm.sendOk("Your guild has been registered successfully. A message will pop on your chat keeping your guild aware about the registration status.\r\n\r\nNow, #rimportant#k: as the leader of this instance, #ryou must already be present on this channel#k the right moment your guild is called for the strategy time. #bThe missubmission of this action will void#k your guild registration as a whole, and the next guild will be called immediately. Must be noted also, that if you become absent from the end of the strategy time to any point on the duration of the instance, it will render the instance interrupted, and your guild will be moved out instantly, moving again the queue.");
} else if(entry == 0) {
cm.sendOk("The queue on this channel is already full. Please be patient and try again after a while, or try on another channel.");
} else {

View File

@@ -19,20 +19,48 @@
You should have received a copy of the GNU Affero General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
/*
@ Author : Ronan
@
@ NPC = Nuris (9040001)
@ Map = Sharenian - Returning Path
@ NPC MapId = 990001100
@ NPC Exit-MapId = 101030104
@
*/
/*
* @Author Lerk
*
* Nuris, Sharenian: Returning Path (990001100)
*
* Exit of Guild Quest
*/
var GQItems = new Array(1032033, 4001024, 4001025, 4001026, 4001027, 4001028, 4001029, 4001030, 4001031, 4001032, 4001033, 4001034, 4001035, 4001037);
var status;
function start() {
for (var i = 0; i < GQItems.length; i++)
cm.removeAll(GQItems[i]);
cm.warp(101030104);
cm.dispose();
status = -1;
action(1,0,0);
}
function action(mode, type, selection){
if (mode == 1)
status++;
else {
cm.dispose();
return;
}
if (status == 0) {
var outText = "It seems you have finished exploring Sharenian Keep, yes? Are you going to return to the recruitment map now?";
cm.sendYesNo(outText);
} else if (mode == 1) {
var eim = cm.getEventInstance();
if(eim != null && eim.isEventCleared()) {
if(!eim.giveEventReward(cm.getPlayer())) {
cm.sendNext("It seems you don't have a free slot in either your #rEquip#k, #rUse#k or #rEtc#k inventories. Please make some room first.");
} else {
cm.warp(101030104);
}
cm.dispose();
} else {
cm.warp(101030104);
cm.dispose();
}
}
}

View File

@@ -20,13 +20,20 @@
along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
/*
* @Author TheRamon
* @Author TheRamon, Ronan
*
* Sharen III's Soul, Sharenian: Sharen III's Grave (990000700)
*
* Guild Quest - end of stage 4
*/
function clearStage(stage, eim) {
eim.setProperty("stage" + stage + "clear", "true");
eim.showClearEffect(true);
eim.giveEventPlayersStageReward(stage);
}
var status = 0;
function start() {
status = -1;
@@ -41,39 +48,30 @@ function action(mode, type, selection) {
status++;
else
cm.dispose();
var eim = cm.getPlayer().getEventInstance();
if (eim.getProperty("stage4clear") != null && eim.getProperty("stage4clear").equals("true")) {
cm.sendOk("After what I thought would be an immortal sleep, I have finally found someone that will save Sharenian. I can truly rest in peace now.");
cm.dispose();
return;
}
if (status == 0) {
if (cm.getPlayer().getEventInstance().getProperty("leader").equals(cm.getPlayer().getName())) {
if (cm.getPlayer().getEventInstance().getProperty("stage4clear") != null && cm.getPlayer().getEventInstance().getProperty("stage4clear").equals("true"))
{
cm.sendOk("After what I thought would be an immortal sleep, I have finally found someone that will save Sharenian. I can truly rest in peace now.");
cm.dispose();
}
else {
var prev = cm.getPlayer().getEventInstance().setProperty("stage4clear","true",true);
if (prev == null) {
cm.sendNext("After what I thought would be an immortal sleep, I have finally found someone that will save Sharenian. This old man will now pave the way for you to finish the quest." + mode);
}
else {//if not null, was set before, and Gp already gained
cm.sendOk("After what I thought would be an immortal sleep, I have finally found someone that will save Sharenian. I can truly rest in peace now.");
cm.dispose();
}
}
if (cm.isEventLeader()) {
cm.sendNext("After what I thought would be an immortal sleep, I have finally found someone that will save Sharenian. This old man will now pave the way for you to finish the quest.");
clearStage(4, eim);
cm.getGuild().gainGP(30);
cm.getPlayer().getMap().getReactorByName("ghostgate").forceHitReactor(1);
cm.dispose();
}
else
{
if (cm.getPlayer().getEventInstance().getProperty("stage4clear") != null && cm.getPlayer().getEventInstance().getProperty("stage4clear").equals("true"))
cm.sendOk("After what I thought would be an immortal sleep, I have finally found someone that will save Sharenian. I can truly rest in peace now.");
else
cm.sendOk("I need the leader of your party to speak with me, nobody else.");
cm.sendOk("I need the leader of your party to speak with me, nobody else.");
cm.dispose();
}
}
else if (status == 1) {
cm.getGuild().gainGP(30);
cm.getPlayer().getMap().getReactorByName("ghostgate").hitReactor(cm.getClient());
cm.showEffect("quest/party/clear");
cm.playSound("Party1/Clear");
cm.dispose();
}
}
}

View File

@@ -25,10 +25,7 @@ function start() {
function action(mode, type, selection) {
if(mode == 1) {
var eim = cm.getPlayer().getEventInstance();
if(eim != null) {
eim.removePlayer(cm.getPlayer());
}
cm.warp(990001100);
}
cm.dispose();
}

View File

@@ -1,254 +1,209 @@
/* @Author Lerk
/* @Author Lerk, Ronan
*
* Guardian Statue - Sharenian: Fountain of the Wiseman (990000500)
*
* Guild Quest Stage 3
*/
importPackage(Packages.tools);
function clearStage(stage, eim) {
eim.setProperty("stage" + stage + "clear", "true");
eim.showClearEffect(true);
eim.giveEventPlayersStageReward(stage);
}
function start() {
//everything can be done in one status, so let's do it here.
if (cm.getPlayer().getMap().getReactorByName("watergate").getState() > 0){
cm.sendOk("Excellent work. You may proceed to the next stage.");
cm.dispose();
return;
}
var eim = cm.getPlayer().getEventInstance();
if (eim == null) {
cm.warp(990001100);
} else {
if (eim.getProperty("leader").equals(cm.getName())) {
if (cm.getPlayer().getMap().getReactorByName("watergate").getState() > 0){
cm.sendOk("You may proceed.");
} else {
var currentCombo = eim.getProperty("stage3combo");
if (currentCombo == null || currentCombo.equals("reset")) {
var newCombo = makeCombo();
eim.setProperty("stage3combo",newCombo);
//cm.playerMessage("Debug: " + newCombo);
eim.setProperty("stage3attempt","1");
cm.sendOk("This fountain guards the secret passage to the throne room. Offer items in the area to the vassals to proceed. The vassals shall tell you whether your offerings are accepted, and if not, which vassals are displeased. You have seven attempts. Good luck.")
} else {
var attempt = parseInt(eim.getProperty("stage3attempt"));
var combo = parseInt(currentCombo);
var guess = getGroundItems();
if (guess != null) {
if (combo == guess) {
cm.getPlayer().getMap().getReactorByName("watergate").hitReactor(cm.getClient());
cm.sendOk("You may proceed.");
cm.getPlayer().getMap().broadcastMessage(MaplePacketCreator.showEffect("quest/party/clear"));
cm.getPlayer().getMap().broadcastMessage(MaplePacketCreator.playSound("Party1/Clear"));
var prev = eim.getProperty("stage3clear");
eim.setProperty("stage3clear","true");
if (prev == null) {
cm.getPlayer().getGuild().gainGP(100);
}
} else {
if (attempt < 7) {
//cm.playerMessage("Combo : " + combo);
//cm.playerMessage("Guess : " + guess);
var parsedCombo = parsePattern(combo);
var parsedGuess = parsePattern(guess);
var results = compare(parsedCombo, parsedGuess);
var string = "";
//cm.playerMessage("Results - Correct: " + results[0] + " | Incorrect: " + results[1] + " | Unknown: " + results[2]);
if (results[0] != 0) {
if (results[0] == 1) {
string += "1 vassal is pleased with their offering.\r\n";
} else {
string += results[0] + " vassals are pleased with their offerings.\r\n";
}
}
if (results[1] != 0) {
if (results[1] == 1) {
string += "1 vassal has recieved an incorrect offering.\r\n";
} else {
string += results[1] + " vassals have recieved incorrect offerings.\r\n";
}
}
if (results[2] != 0) {
if (results[2] == 1) {
string += "1 vassal has recieved an unknown offering.\r\n";
} else {
string += results[2] + " vassals have recieved unknown offerings.\r\n";
}
}
string += "This is your ";
switch (attempt) {
case 1:
string += "1st";
break;
case 2:
string += "2nd";
break;
case 3:
string += "3rd";
break;
default:
string += attempt + "th";
break;
}
string += " attempt.";
if (cm.isEventLeader()) {
var currentCombo = eim.getProperty("stage3combo");
if (currentCombo == null || currentCombo.equals("reset")) {
var newCombo = makeCombo();
eim.setProperty("stage3combo",newCombo);
//cm.playerMessage("Debug: " + newCombo);
eim.setProperty("stage3attempt","1");
cm.sendOk("This fountain guards the secret passage to the throne room. Offer items in the area to the vassals to proceed. The vassals shall tell you whether your offerings are accepted, and if not, which vassals are displeased. You have seven attempts. Good luck.");
} else {
var attempt = parseInt(eim.getProperty("stage3attempt"));
var combo = parseInt(currentCombo);
var guess = getGroundItems();
if (guess != null) {
if (combo == guess) {
cm.getPlayer().getMap().getReactorByName("watergate").forceHitReactor(1);
clearStage(3, eim);
cm.getGuild().gainGP(25);
removeGroundItems();
cm.sendOk("Excellent work. You may proceed to the next stage.");
} else {
if (attempt < 7) {
var comboItems = [0, 0, 0, 0];
var guessItems = [0, 0, 0, 0];
var correct = 0, incorrect, unknown = 0;
for(var i = 0; i < 4; i++) {
var guessIdx = Math.floor(guess / Math.pow(10, i)) % 10;
var comboIdx = Math.floor(combo / Math.pow(10, i)) % 10;
if(guessIdx == comboIdx) correct++;
else {
(guessItems[guessIdx])++;
(comboItems[comboIdx])++;
}
}
for(var i = 0; i < 4; i++) {
var diff = guessItems[i] - comboItems[i];
if(diff > 0) unknown += diff;
}
incorrect = 4 - correct - unknown;
var string = "";
//cm.playerMessage("Results - Correct: " + results[0] + " | Incorrect: " + results[1] + " | Unknown: " + results[2]);
if (correct != 0) {
if (correct == 1) {
string += "1 vassal is pleased with their offering.\r\n";
} else {
string += correct + " vassals are pleased with their offerings.\r\n";
}
}
if (incorrect != 0) {
if (incorrect == 1) {
string += "1 vassal has received an incorrect offering.\r\n";
} else {
string += incorrect + " vassals have received incorrect offerings.\r\n";
}
}
if (unknown != 0) {
if (unknown == 1) {
string += "1 vassal has received an unknown offering.\r\n";
} else {
string += unknown + " vassals have received unknown offerings.\r\n";
}
}
string += "This is your ";
switch (attempt) {
case 1:
string += "1st";
break;
case 2:
string += "2nd";
break;
case 3:
string += "3rd";
break;
default:
string += attempt + "th";
break;
}
string += " attempt.";
//spawn one black and one myst knight
spawnMob(9300036, -350, 150, cm.getPlayer().getMap());
spawnMob(9300037, 400, 150, cm.getPlayer().getMap());
//spawn one black and one myst knight
spawnMob(9300036, -350, 150, cm.getPlayer().getMap());
spawnMob(9300037, 400, 150, cm.getPlayer().getMap());
cm.sendOk(string);
eim.setProperty("stage3attempt",attempt + 1);
} else {
//reset the combo and mass spawn monsters
eim.setProperty("stage3combo","reset");
cm.sendOk("You have failed the test. Please compose yourselves and try again later.");
cm.sendOk(string);
eim.setProperty("stage3attempt",attempt + 1);
} else {
//reset the combo and mass spawn monsters
eim.setProperty("stage3combo","reset");
cm.sendOk("You have failed the test. Please compose yourselves and try again later.");
for (var i = 0; i < 6; i++) {
//keep getting new monsters, lest we spawn the same monster five times o.o!
spawnMob(9300036, randX(), 150, cm.getPlayer().getMap());
spawnMob(9300037, randX(), 150, cm.getPlayer().getMap());
}
}
}
} else {
cm.sendOk("Please make sure your attempt is properly set in front of the vassals and talk to me again.");
}
}
}
} else {
cm.sendOk("Please have your leader speak to me.");
}
for (var i = 0; i < 6; i++) {
//keep getting new monsters, lest we spawn the same monster five times o.o!
spawnMob(9300036, randX(), 150, cm.getPlayer().getMap());
spawnMob(9300037, randX(), 150, cm.getPlayer().getMap());
}
}
eim.showWrongEffect();
}
} else {
cm.sendOk("Please make sure your attempt is properly set in front of the vassals and talk to me again.");
}
}
} else {
cm.sendOk("Please have your leader speak to me.");
}
}
cm.dispose();
}
function action(mode, type, selection) {
}
function action(mode, type, selection) {}
function makeCombo() {
var combo = 0;
for (var i = 0; i < 4; i++) {
combo += Math.floor(Math.random() * 4) * Math.pow(10, i);
combo += (Math.floor(Math.random() * 4) * Math.pow(10, i));
}
return combo;
}
//check the items on ground and convert into an applicable string; null if items aren't proper
function getGroundItems() {
var items = cm.getPlayer().getMap().getMapObjectsInRange(cm.getPlayer().getPosition(), Packages.java.lang.Double.POSITIVE_INFINITY, Packages.java.util.Arrays.asList([Packages.server.maps.MapleMapObjectType.ITEM]));
var itemInArea = new Array(-1, -1, -1, -1);
if (items.size() != 4) {
cm.getPlayer().dropMessage("There are too many items in the map. Please remove some");
return null;
}
var iter = items.iterator();
function getRawItems() {
var mapItems = cm.getPlayer().getMap().getItems();
var rawItems = new Array();
var iter = mapItems.iterator();
while (iter.hasNext()) {
var item = iter.next();
var id = item.getItem().getItemId();
if (id < 4001027 || id > 4001030) {
cm.getPlayer().dropMessage("Some items in the map are not part of the 4 items needed");
return null;
continue;
} else {
//check item location
for (var i = 0; i < 4; i++) {
if (cm.getPlayer().getMap().getArea(i).contains(item.getPosition())) {
itemInArea[i] = id - 4001027;
//cm.getPlayer().dropMessage("Item in area "+i+": " + id);
break;
}
}
rawItems.push(item);
}
}
return rawItems;
}
//check the items on ground and convert into an applicable string; null if items aren't proper
function getGroundItems() {
var itemInArea = new Array(-1, -1, -1, -1);
var rawItems = getRawItems();
if (rawItems.length != 4) return null;
for(var j = 0; j < rawItems.length; j++) {
var item = rawItems[j];
var id = item.getItem().getItemId();
//check item location
for (var i = 0; i < 4; i++) {
if (cm.getPlayer().getMap().getArea(i).contains(item.getPosition())) {
itemInArea[i] = id - 4001027;
break;
}
}
}
//guaranteed four items that are part of the stage 3 item set by this point, check to see if each area has an item
if (itemInArea[0] == -1 || itemInArea[1] == -1 || itemInArea[2] == -1 || itemInArea[3] == -1) {
cm.getPlayer().dropMessage("Please place these in correct positions: " + (itemInArea[0] == -1 ? "Statue 1, " : "") + (itemInArea[1] == -1 ? "Statue 2, " : "") + (itemInArea[2] == -1 ? "Statue 3, " : "") + (itemInArea[3] == -1 ? "Statue 4. " : ""));
/* for (var i = 0; i < 4; i++) {
cm.getPlayer().dropMessage("Item in area "+i+": " + itemInArea[i]);
}*/
if (itemInArea[0] == -1 || itemInArea[1] == -1 || itemInArea[2] == -1 || itemInArea[3] == -1)
return null;
}
return (itemInArea[0] * 1000 + itemInArea[1] * 100 + itemInArea[2] * 10 + itemInArea[3]);
return ((itemInArea[0] * 1000) + (itemInArea[1] * 100) + (itemInArea[2] * 10) + itemInArea[3]);
}
//convert an integer for answer or guess into int array for comparison
function parsePattern(pattern) {
var tempPattern = pattern;
var items = new Array(-1, -1, -1, -1);
for (var i = 0; i < 4; i++) {
items[i] = Math.floor(tempPattern / Math.pow(10, 3-i));
tempPattern = tempPattern % Math.pow(10, 3-i);
function removeGroundItems() {
var map = cm.getMap();
var rawItems = getRawItems();
for(var j = 0; j < rawItems.length; j++) {
map.makeDisappearItemFromMap(rawItems[j]);
}
return items;
}
// compare two int arrays for the puzzle
function compare(answer, guess) {
var correct = 0;
var incorrect = 0;
/*var debugAnswer = "Combo : ";
var debugGuess = "Guess : ";
for (var d = 0; d < answer.length; d++) {
debugAnswer += answer[d] + " ";
debugGuess += guess[d] + " ";
}
cm.getPlayer().dropMessage(debugAnswer);
cm.getPlayer().dropMessage(debugGuess);*/
for (var i = 0; i < answer.length; i) {
if (answer[i] == guess[i]) {
correct++;
//cm.getPlayer().dropMessage("Item match : " + answer[i]);
//pop the answer/guess at i
if (i != answer.length - 1) {
answer[i] = answer[answer.length - 1];
guess[i] = guess[guess.length - 1];
}
answer.pop();
guess.pop();
/*/debugAnswer = "Combo : ";
debugGuess = "Guess : ";
for (var d = 0; d < answer.length; d++) {
debugAnswer += answer[d] + " ";
debugGuess += guess[d] + " ";
}
cm.getPlayer().dropMessage(debugAnswer);
cm.getPlayer().dropMessage(debugGuess);*/
}
else {
i++;
}
}
//check remaining answers for "incorrect": correct item in incorrect position
var answerItems = new Array(0, 0, 0, 0);
var guessItems = new Array(0, 0, 0, 0);
for (var j = 0; j < answer.length; j++) {
var aItem = answer[j];
var gItem = guess[j]
answerItems[aItem]++;
guessItems[gItem]++;
}
/*for (var d = 0; d < answer.length; d++) {
cm.getPlayer().dropMessage("Item " + d + " in combo: " + answerItems[d] + " | in guess: " + guessItems[d]);
}*/
for (var k = 0; k < answerItems.length; k++) {
var inc = Math.min(answerItems[k], guessItems[k]);
//cm.getPlayer().dropMessage("Incorrect for item " + k + ": " + inc);
incorrect += inc;
}
return new Array(correct, incorrect, (4 - correct - incorrect));
}
//for mass spawn

View File

@@ -22,6 +22,13 @@
var status;
var stage;
function clearStage(stage, eim) {
eim.setProperty("stage" + stage + "clear", "true");
eim.showClearEffect(true);
eim.giveEventPlayersStageReward(stage);
}
function start() {
status = -1;
action (1, 0, 0);
@@ -39,79 +46,77 @@ function action(mode, type, selection) {
status++;
else
status--;
var eim = cm.getPlayer().getEventInstance();
if (eim == null) {
cm.warp(990001100);
} else {
if (eim.getProperty("leader").equals(cm.getPlayer().getName())) {
if (cm.getPlayer().getMap().getReactorByName("statuegate").getState() > 0){
cm.sendOk("Proceed.");
cm.dispose();
} else {
if (status == 0) {
if (eim.getProperty("stage1status") == null || eim.getProperty("stage1status").equals("waiting")) {
if (eim.getProperty("stage1phase") == null) {
stage = 1;
eim.setProperty("stage1phase",stage);
} else {
stage = parseInt(eim.getProperty("stage1phase"));
}
if (stage == 1) {
cm.sendOk("In this challenge, I shall show a pattern on the statues around me. When I give the word, repeat the pattern to me to proceed.");
}
else {
cm.sendOk("I shall now present a more difficult puzzle for you. Good luck.")
}
}
else if (eim.getProperty("stage1status").equals("active")) {
if(eim.getProperty("stage1clear") == "true") {
cm.sendOk("Excellent work. You may proceed to the next stage.");
cm.dispose();
return;
}
if (cm.isEventLeader()) {
if (status == 0) {
if (eim.getProperty("stage1status") == null || eim.getProperty("stage1status").equals("waiting")) {
if (eim.getProperty("stage1phase") == null) {
stage = 1;
eim.setProperty("stage1phase",stage);
} else {
stage = parseInt(eim.getProperty("stage1phase"));
if (eim.getProperty("stage1combo").equals(eim.getProperty("stage1guess"))) {
if (stage == 3) {
cm.getPlayer().getMap().getReactorByName("statuegate").hitReactor(cm.getClient());
cm.sendOk("Excellent work. Please proceed to the next stage.");
cm.showEffect("quest/party/clear");
cm.playSound("Party1/Clear");
var prev = eim.getProperty("stage1clear");
eim.setProperty("stage1clear","true");
if (prev == null) {
cm.getGuild().gainGP(15);
}
} else {
cm.sendOk("Very good. You still have more to complete, however. Talk to me again when you're ready.");
eim.setProperty("stage1phase", stage + 1);
cm.mapMessage(5, "You have completed part " + stage + " of the Gatekeeper Test.");
}
} else {
cm.sendOk("You have failed this test.");
cm.mapMessage(5, "You have failed the Gatekeeper Test.");
eim.setProperty("stage1phase","1")
}
eim.setProperty("stage1status", "waiting");
cm.dispose();
}
if (stage == 1) {
cm.sendOk("In this challenge, I shall show a pattern on the statues around me. When I give the word, repeat the pattern to me to proceed.");
}
else {
cm.sendOk("Please wait.");
cm.dispose();
cm.sendOk("I shall now present a more difficult puzzle for you. Good luck.");
}
}
else if (status == 1) {
var reactors = getReactors();
var combo = makeCombo(reactors);
cm.mapMessage(5, "Please wait while the combination is revealed.");
var delay = 5000;
for (var i = 0; i < combo.length; i++) {
cm.getPlayer().getMap().getReactorByOid(combo[i]).delayedHitReactor(cm.getClient(), delay + 3500*i);
else if (eim.getProperty("stage1status").equals("active")) {
stage = parseInt(eim.getProperty("stage1phase"));
if (eim.getProperty("stage1combo").equals(eim.getProperty("stage1guess"))) {
if (stage == 3) {
cm.getPlayer().getMap().getReactorByName("statuegate").forceHitReactor(1);
clearStage(1, eim);
cm.getGuild().gainGP(15);
cm.sendOk("Excellent work. You may proceed to the next stage.");
} else {
cm.sendOk("Very good. You still have more to complete, however. Talk to me again when you're ready.");
eim.setProperty("stage1phase", stage + 1);
cm.mapMessage(5, "You have completed part " + stage + " of the Gatekeeper Test.");
}
} else {
eim.showWrongEffect();
cm.sendOk("You have failed this test.");
cm.mapMessage(5, "You have failed the Gatekeeper Test.");
eim.setProperty("stage1phase","1");
}
eim.setProperty("stage1status", "display");
eim.setProperty("stage1combo","");
eim.setProperty("stage1status", "waiting");
cm.dispose();
}
else {
cm.sendOk("The statues are working on the pattern. Please wait.");
cm.dispose();
}
}
else if (status == 1) {
var reactors = getReactors();
var combo = makeCombo(reactors);
cm.mapMessage(5, "Please wait while the combination is revealed.");
var delay = 5000;
for (var i = 0; i < combo.length; i++) {
cm.getPlayer().getMap().getReactorByOid(combo[i]).delayedHitReactor(cm.getClient(), delay + 3500*i);
}
eim.setProperty("stage1status", "display");
eim.setProperty("stage1combo","");
cm.dispose();
}
} else {
cm.sendOk("I need the leader of your party to speak with me, nobody else.");
cm.sendOk("I need the leader of this event to speak with me, nobody else.");
cm.dispose();
}
}
@@ -122,10 +127,10 @@ function action(mode, type, selection) {
function getReactors() {
var reactors = new Array();
var iter = cm.getPlayer().getMap().getMapObjects().iterator();
var iter = cm.getPlayer().getMap().getReactors().iterator();
while (iter.hasNext()) {
var mo = iter.next();
if (mo.getType() == Packages.server.maps.MapleMapObjectType.REACTOR && !mo.getName().equals("statuegate")) {
if (!mo.getName().equals("statuegate")) {
reactors.push(mo.getObjectId());
}
}

View File

@@ -22,26 +22,32 @@
function start() {
var eim = cm.getPlayer().getEventInstance();
if (eim != null) {
if (eim.getProperty("leader").equals(cm.getPlayer().getName())) {
if (cm.isEventLeader()) {
if (cm.haveItem(4001024)) {
cm.removeAll(4001024);
var prev = eim.setProperty("bossclear","true",true);
var prev = eim.setProperty("bossclear", "true");
if (prev == null) {
var start = parseInt(eim.getProperty("entryTimestamp"));
var diff = Packages.java.lang.System.currentTimeMillis() - start;
var diff = Date.now() - start;
var points = 1000 - Math.floor(diff / (100 * 60));
if(points < 100)
points = 100;
if(points < 100) points = 100;
cm.getGuild().gainGP(points);
}
eim.clearPQ();
}
else {
cm.sendOk("This is your final challenge. Defeat the evil lurking within the Rubian and return it to me. That is all.");
}
}
else {
cm.sendOk("This is your final challenge. Defeat the evil lurking within the Rubian and let your event leader return it to me. That is all.");
}
}
else
cm.warp(990001100);
cm.dispose();
}

View File

@@ -51,7 +51,7 @@ function action(mode, type, selection){
var eim = cm.getEventInstance();
if(!eim.giveEventReward(cm.getPlayer())) {
cm.sendNext("It seems you don't have a free slot in either your #rEquip#k, #rUse#k or #rEtc#k inventories. Please make room and try again.");
cm.sendNext("It seems you don't have a free slot in either your #rEquip#k, #rUse#k or #rEtc#k inventories. Please make some room and try again.");
} else {
cm.warp(809050017);
}

View File

@@ -70,7 +70,7 @@ function action(mode, type, selection) {
cm.sendOk("You already have a Gold Maple Leaf. Go give them to your guests before you go into the wedding.");
cm.dispose();
} else if (hasEngageRing) {
cm.sendOk("You have recieved 15 Gold Maple Leaves.");
cm.sendOk("You have received 15 Gold Maple Leaves.");
cm.gainItem(4000313,15);
cm.dispose();
} else {

View File

@@ -42,7 +42,7 @@ function start() {
break;
}
if (hasRing)
cm.sendNext("You've reached the end of the wedding. You will recieve an Onyx Chest for Bride and Groom and an Onyx Chest. Exchange them at Pila, she is at the top of Amoria.");
cm.sendNext("You've reached the end of the wedding. You will receive an Onyx Chest for Bride and Groom and an Onyx Chest. Exchange them at Pila, she is at the top of Amoria.");
else if (cm.haveItem(4000313)) {
cm.sendNext("Wow the end of the wedding already ? Good bye then.!");
status = 20;

View File

@@ -22,10 +22,13 @@
/*
Return from Sharen III's Grave - Guild Quest
@Author Lerk
@Author Ronan
*/
function enter(pi) {
pi.warp(990000600, 1);
var backPortals = [6, 8, 9, 11];
var idx = pi.getEventInstance().gridCheck(pi.getPlayer());
pi.warp(990000600, backPortals[idx]);
return true;
}

View File

@@ -28,6 +28,7 @@ Save location to return.
*/
function enter(pi) {
pi.getEventInstance().gridInsert(pi.getPlayer(), 0);
pi.warp(990000700, "st00");
return true;
}

View File

@@ -28,6 +28,7 @@ Save location to return.
*/
function enter(pi) {
pi.getEventInstance().gridInsert(pi.getPlayer(), 1);
pi.warp(990000700, "st00");
return true;
}

View File

@@ -28,6 +28,7 @@ Save location to return.
*/
function enter(pi) {
pi.getEventInstance().gridInsert(pi.getPlayer(), 3);
pi.warp(990000700, "st00");
return true;
}

View File

@@ -28,6 +28,7 @@ Save location to return.
*/
function enter(pi) {
pi.getEventInstance().gridInsert(pi.getPlayer(), 2);
pi.warp(990000700, "st00");
return true;
}

View File

@@ -27,7 +27,7 @@ Stage 5: Door before Ergoth - Guild Quest
function enter(pi) {
if (pi.getPlayer().getMap().getReactorByName("kinggate").getState() == 1) {
pi.warp(990000900);
pi.warp(990000900, 1);
if (pi.getPlayer().getEventInstance().getProperty("boss") != null && pi.getPlayer().getEventInstance().getProperty("boss").equals("true")) {
pi.changeMusic("Bgm10/Eregos");
}

View File

@@ -26,7 +26,7 @@
function enter(pi) {
if (pi.getPlayer().getMap().getReactorByName("speargate").getState() == 4) {
pi.warp(990000401);
pi.warp(990000401, 0);
return true;
} else {
pi.getPlayer().dropMessage(5, "This way forward is not open yet.");

View File

@@ -25,7 +25,7 @@
*/
function enter(pi) {
if (pi.getPlayer().getMap().getReactorByName("statuegate").getState() == 1) {
pi.warp(990000301);
pi.warp(990000301, 0);
return true;
} else {
pi.getPlayer().dropMessage(5, "The gate is closed.");

View File

@@ -26,7 +26,7 @@ Stage 3: Exit Door - Guild Quest
function enter(pi) {
if (pi.getPlayer().getMap().getReactorByName("watergate").getState() == 1) {
pi.warp(990000600);
pi.warp(990000600, 1);
return true;
} else
pi.getPlayer().dropMessage(5, "This way forward is not open yet.");

View File

@@ -25,6 +25,11 @@
*
*/
function padWithZeroes(n, width) {
while(n.length < width) n = '0' + n;
return n;
}
function act() {
var eim = rm.getPlayer().getEventInstance();
if (eim != null) {
@@ -32,19 +37,25 @@ function act() {
if (status != null && !status.equals("waiting")) {
var stage = parseInt(eim.getProperty("stage1phase"));
if (status.equals("display")) {
var prevCombo = eim.getProperty("stage1combo");
prevCombo += rm.getReactor().getObjectId();
rm.mapMessage(6,"Current Combo: " + prevCombo);
eim.setProperty("stage1combo",prevCombo);
if (prevCombo.length == (3 * (stage + 3))) { //end of displaying
eim.setProperty("stage1status","active");
rm.mapMessage(5, "The combo has been displayed; Proceed with caution.");
eim.setProperty("stage1guess","");
if(!rm.getReactor().isRecentHitFromAttack()) {
var prevCombo = eim.getProperty("stage1combo");
var n = "" + rm.getReactor().getObjectId();
prevCombo += padWithZeroes(n, 3);
eim.setProperty("stage1combo",prevCombo);
if (prevCombo.length == (3 * (stage + 3))) { //end of displaying
eim.setProperty("stage1status","active");
rm.mapMessage(5, "The combo has been displayed; Proceed with caution.");
eim.setProperty("stage1guess","");
}
}
} else { //active
var prevGuess = eim.getProperty("stage1guess");
var prevGuess = "" + eim.getProperty("stage1guess");
if (prevGuess.length != (3 * (stage + 3))) {
prevGuess += rm.getReactor().getObjectId();
var n = "" + rm.getReactor().getObjectId();
prevGuess += padWithZeroes(n, 3);
eim.setProperty("stage1guess",prevGuess);
}
}

View File

@@ -21,10 +21,16 @@
*/
/* @Author Lerk
*
* 9208000.js: Guild Quest - Gatekeeper Puzzle Reactor
* 9208001.js: Guild Quest - Gatekeeper Puzzle Reactor
*
*/
function padWithZeroes(n, width) {
while(n.length < width) n = '0' + n;
return n;
}
function act() {
var eim = rm.getPlayer().getEventInstance();
if (eim != null) {
@@ -33,18 +39,25 @@ function act() {
var stage = parseInt(eim.getProperty("stage1phase"));
//rm.mapMessage(6,"Stage " + stage);
if (status.equals("display")) {
var prevCombo = eim.getProperty("stage1combo");
prevCombo += rm.getReactor().getObjectId();
eim.setProperty("stage1combo",prevCombo);
if (prevCombo.length == (3 * (stage + 3))) { //end of displaying
eim.setProperty("stage1status","active");
rm.mapMessage(5, "The combo has been displayed; Proceed with caution.");
eim.setProperty("stage1guess","");
if(!rm.getReactor().isRecentHitFromAttack()) {
var prevCombo = eim.getProperty("stage1combo");
var n = "" + rm.getReactor().getObjectId();
prevCombo += padWithZeroes(n, 3);
eim.setProperty("stage1combo",prevCombo);
if (prevCombo.length == (3 * (stage + 3))) { //end of displaying
eim.setProperty("stage1status","active");
rm.mapMessage(5, "The combo has been displayed; Proceed with caution.");
eim.setProperty("stage1guess","");
}
}
} else { //active
var prevGuess = eim.getProperty("stage1guess");
var prevGuess = "" + eim.getProperty("stage1guess");
if (prevGuess.length != (3 * (stage + 3))) {
prevGuess += rm.getReactor().getObjectId();
var n = "" + rm.getReactor().getObjectId();
prevGuess += padWithZeroes(n, 3);
eim.setProperty("stage1guess",prevGuess);
}
//rm.mapMessage(6,"Current Guess: " + prevGuess);

View File

@@ -21,10 +21,15 @@
/* @Author Lerk
*
* 9208000.js: Guild Quest - Gatekeeper Puzzle Reactor
* 9208002.js: Guild Quest - Gatekeeper Puzzle Reactor
*
*/
function padWithZeroes(n, width) {
while(n.length < width) n = '0' + n;
return n;
}
function act() {
var eim = rm.getPlayer().getEventInstance();
if (eim != null) {
@@ -32,18 +37,24 @@ function act() {
if (status != null && !status.equals("waiting")) {
var stage = parseInt(eim.getProperty("stage1phase"));
if (status.equals("display")) {
var prevCombo = eim.getProperty("stage1combo");
prevCombo += rm.getReactor().getObjectId();
eim.setProperty("stage1combo",prevCombo);
if (prevCombo.length == (3 * (stage + 3))) { //end of displaying
eim.setProperty("stage1status","active");
rm.mapMessage(5, "The combo has been displayed; Proceed with caution.");
eim.setProperty("stage1guess","");
if(!rm.getReactor().isRecentHitFromAttack()) {
var prevCombo = eim.getProperty("stage1combo");
var n = "" + rm.getReactor().getObjectId();
prevCombo += padWithZeroes(n, 3);
eim.setProperty("stage1combo",prevCombo);
if (prevCombo.length == (3 * (stage + 3))) { //end of displaying
eim.setProperty("stage1status","active");
rm.mapMessage(5, "The combo has been displayed; Proceed with caution.");
eim.setProperty("stage1guess","");
}
}
} else { //active
var prevGuess = eim.getProperty("stage1guess");
if (prevGuess.length != (3 * stage + 9)) {
prevGuess += rm.getReactor().getObjectId();
var prevGuess = "" + eim.getProperty("stage1guess");
if (prevGuess.length != (3 * (stage + 3))) {
var n = "" + rm.getReactor().getObjectId();
prevGuess += padWithZeroes(n, 3);
eim.setProperty("stage1guess",prevGuess);
}
}

View File

@@ -22,9 +22,21 @@
/*
Stage 2: Spear destinations - Guild Quest
@Author Lerk
@Author Lerk, Ronan
*/
function act() {
rm.getPlayer().getEventInstance().getMapInstance(990000400).getReactorByName("speargate").hitReactor(rm.getPlayer().getClient());
var react = rm.getPlayer().getEventInstance().getMapInstance(990000400).getReactorByName("speargate");
react.forceHitReactor(react.getState() + 1);
if(react.getState() == 4) {
var eim = rm.getPlayer().getEventInstance();
var maps = [990000400, 990000410, 990000420, 990000430, 990000431, 990000440];
for(var i = 0; i < maps.length; i++) {
eim.showClearEffect(false, maps[i]);
}
rm.getGuild().gainGP(20);
}
}

View File

@@ -0,0 +1,28 @@
/*
* This file is part of the OdinMS Maple Story Server
Copyright (C) 2008 Patrick Huy <patrick.huy@frz.cc>
Matthias Butz <matze@odinms.de>
Jan Christian Meyer <vimes@odinms.de>
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU Affero General Public License version 3
as published by the Free Software Foundation. You may not use, modify
or distribute this program under any other version of the
GNU Affero General Public License.
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 Affero General Public License for more details.
You should have received a copy of the GNU Affero General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
// Opened GPQ boss room, players may now revive and stay on the GPQ
function act() {
if(rm.getEventInstance() != null) {
rm.getEventInstance().setProperty("canRevive", "1");
}
}