zGosu 396 Опубликовано 26 ноября, 2016 Небольшой скрипт, идея которого была реализовать "Уникального Босса для сервера (Server Boss)".Скрипт довольно старый (21.04.2015), но может быть кому-то понадобится.Боссы обладают уникальный AI, поэтому он не будет скучный как на многих серверах, где просто заспавнили обычного NPC, где добавили только прибавку к статам и дроп.О реализации: Уникальный Босс спавнится на месте убитого простого рб (в скрипте указаны список ID боссов) Включает себя "комплект" Боссов (в данном случае их 3, но можно добавить еще) Реализованы Minion, которые появляются когда у босса определенное количество HP (в данном случае это 50%) О появлении Уникального Босса анонсируется в общий чат После убийства первого Босса появляется еще один случайный Босс и т.д. Всё описывать не буду, посмотрите сами. ServerBossEvent.java package events.ServerBoss; import com.l2spartan.gameserver.Announcements; import com.l2spartan.gameserver.datatables.SkillTable; import com.l2spartan.gameserver.model.L2Effect; import com.l2spartan.gameserver.model.actor.L2Npc; import com.l2spartan.gameserver.model.actor.instance.L2PcInstance; import com.l2spartan.gameserver.network.serverpackets.NpcSay; import com.l2spartan.util.Rnd; import ai.group_template.L2AttackableAIScript; public class ServerBossEvent extends L2AttackableAIScript { private static final int[] raidBoss = {100000}; private static final int[] eliteBoss = {120000, 110000}; private static final int[] helpers = {110001}; private static L2Npc eventBoss; private static L2Npc helper1; private static L2Npc helper2; private static L2Npc helper3; private static L2Npc helper4; private static final int[] bosses = { 25001, 25004, 25007, 25010, 25013, 25016, 25019, 25020, 25023, 25026, 25029, 25032, 25035, 25038, 25041, 25044, 25047, 25050, 25051, 25054, 25057, 25060, 25063, 25064, 25067, 25070, 25073, 25076, 25079, 25082, 25085, 25088, 25089, 25092, 25095, 25098, 25099, 25102, 25103, 25106, 25109, 25112, 25115, 25118, 25119, 25122, 25125, 25126, 25127, 25128, 25131, 25134, 25137, 25140, 25143, 25146, 25149, 25152, 25155, 25158, 25159, 25162, 25163, 25166, 25169, 25170, 25173, 25176, 25179, 25182, 25185, 25188, 25189, 25192, 25198, 25199, 25202, 25205, 25208, 25211, 25214, 25217, 25220, 25223, 25226, 25229, 25230, 25233, 25234, 25235, 25238, 25241, 25244, 25245, 25248, 25249, 25252, 25255, 25256, 25259, 25260, 25263, 25266, 25269, 25272, 25273, 25276, 25277, 25280, 25281, 25282, 25283, 25286, 25290, 25293, 25296, 25299, 25302, 25305, 25306, 25309, 25312, 25315, 25316, 25319, 25322, 25325, 25328, 25352, 25354, 25357, 25360, 25362, 25365, 25366, 25369, 25372, 25373, 25375, 25378, 25380, 25383, 25385, 25388, 25391, 25392, 25394, 25395, 25398, 25401, 25404, 25407, 25410, 25412, 25415, 25418, 25420, 25423, 25426, 25429, 25431, 25434, 25437, 25438, 25441, 25444, 25447, 25450, 25453, 25456, 25460, 25463, 25467, 25470, 25473, 25475, 25478, 25481, 25484, 25487, 25490, 25493, 25496, 25498, 25501, 25504, 25506, 25509, 25512, 25514, 25523, 25524, 25527, 25528, 25531, 25532, 25534, 25536, 25539, 25540, 25542, 25544, 25603, 25609, 25610, 25611, 25612, 25616, 25617, 25618, 25619, 25620, 25621, 25622, 25624, 25671, 25674, 25677, 25680, 25681, 25684, 25687, 25690, 25691, 25692, 25693, 25694, 25695, 29030, 29033, 29036, 29037, 29056, 29060, 29062, 29065, 29095, 29096, 29129, 29132, 29135, 29138, 29141, 29144, 29147 }; public ServerBossEvent(int Id, String name, String descr) { super(Id, name, descr); registerMobs(raidBoss); registerMobs(eliteBoss); registerMobs(helpers); registerMobs(bosses); } private boolean hasBoss() { if (eventBoss != null) return true; return false; } private boolean helpers() { if (helper1 == null && helper2 == null && helper3 == null && helper4 == null) return true; return false; } private void spawnHelpers(L2Npc npc, int npcId) { if (helpers()) { npc.broadcastPacket(new NpcSay(npc.getObjectId(), 0, npc.getNpcId(), "Help me!")); helper1 = addSpawn(npcId, npc.getX() - 100, npc.getY() + 100, npc.getZ(), 0, false, 0); helper2 = addSpawn(npcId, npc.getX() + 100, npc.getY() - 100, npc.getZ(), 0, false, 0); helper3 = addSpawn(npcId, npc.getX() - 100, npc.getY() - 100, npc.getZ(), 0, false, 0); helper4 = addSpawn(npcId, npc.getX() + 100, npc.getY() + 100, npc.getZ(), 0, false, 0); helper1.setIsNoRndWalk(true); helper2.setIsNoRndWalk(true); helper3.setIsNoRndWalk(true); helper4.setIsNoRndWalk(true); } } private boolean helpersDelete() { if (helper1 != null || helper2 != null || helper3 != null || helper4 != null) return true; return false; } private void deleteHelpers() { if (helpersDelete()) { helper1.deleteMe(); helper1.getSpawn().stopRespawn(); helper2.deleteMe(); helper2.getSpawn().stopRespawn(); helper3.deleteMe(); helper3.getSpawn().stopRespawn(); helper4.deleteMe(); helper4.getSpawn().stopRespawn(); } } private boolean limitBoss(L2Npc npc) { int count = 0; L2Effect[] effects = npc.getAllEffects(); for (L2Effect e : effects) { if ((e.getId() == 139) || (e.getId() == 176) || (e.getId() == 420)) { count++; break; } } if (count > 0) return true; return false; } @Override public String onAttack(L2Npc npc, L2PcInstance attacker, int damage, boolean isPet) { int rnd; if (contains(raidBoss, npc.getNpcId())) { rnd = Rnd.get(100); if (rnd < 10) { npc.setTarget(attacker); npc.doCast(SkillTable.getInstance().getInfo(1509, 1)); } if ((rnd >= 10) && (rnd < 20)) { npc.setTarget(attacker); npc.doCast(SkillTable.getInstance().getInfo(3436, 1)); } if ((rnd >= 20) && (rnd < 30)) { if (npc.getCurrentHp() <= (npc.getMaxHp() / 2)) { npc.setTarget(attacker); npc.doCast(SkillTable.getInstance().getInfo(121, 1)); } } } if (contains(eliteBoss, npc.getNpcId())) { rnd = Rnd.get(100); if (npc.getNpcId() == 110000) { if (rnd >= 5) { npc.setTarget(attacker); npc.doCast(SkillTable.getInstance().getInfo(5496, 1)); } if (rnd < 3) { npc.setTarget(attacker); npc.doCast(SkillTable.getInstance().getInfo(5495, 1)); } if ((rnd >= 3) && (rnd < 5)) { npc.setTarget(attacker); npc.doCast(SkillTable.getInstance().getInfo(5498, 1)); } if (npc.getCurrentHp() < (npc.getMaxHp() / 2)) { spawnHelpers(npc, 110001); } } if (npc.getNpcId() == 120000) { if (rnd <= 10) { npc.setTarget(attacker); npc.doCast(SkillTable.getInstance().getInfo(5500, 1)); } if ((rnd > 10) && (rnd < 20)) { npc.setTarget(attacker); npc.doCast(SkillTable.getInstance().getInfo(5501, 1)); } if ((rnd >= 20) && (rnd < 30)) { npc.setTarget(attacker); npc.doCast(SkillTable.getInstance().getInfo(5502, 1)); } if (npc.getCurrentHp() < (npc.getMaxHp() * 0.3)) { if (!limitBoss(npc)) { npc.broadcastPacket(new NpcSay(npc.getObjectId(), 0, npc.getNpcId(), npc.getName() + " is Boss, " + attacker.getName() + " is Noob! Axaxa!")); npc.doCast(SkillTable.getInstance().getInfo(420, 3)); if (rnd < 50) npc.doCast(SkillTable.getInstance().getInfo(139, 3)); else npc.doCast(SkillTable.getInstance().getInfo(176, 3)); } } } } if (contains(helpers, npc.getNpcId())) { if (npc.getNpcId() == 110001) { npc.setTarget(attacker); if (npc.getCurrentHp() < (npc.getMaxHp() * 0.3)) { if (!limitBoss(npc)) { npc.doCast(SkillTable.getInstance().getInfo(420, 3)); if (Rnd.get(100) < 50) npc.doCast(SkillTable.getInstance().getInfo(139, 3)); else npc.doCast(SkillTable.getInstance().getInfo(176, 3)); } } } } return super.onAttack(npc, attacker, damage, isPet); } @Override public String onKill(L2Npc npc, L2PcInstance killer, boolean isPet) { int npcId = npc.getNpcId(); int rnd = Rnd.get(1, 2); int newNpcId = 0; for (int bossId : bosses) { if (npcId == bossId) { if (!hasBoss()) { eventBoss = addSpawn(100000, npc.getX(), npc.getY(), npc.getZ(), 0, false, 0); killer.sendMessage("Event Boss has awakened!"); Announcements.getInstance().announceToAll("Player " + killer.getName() + " awakened to " + eventBoss.getName() + "!"); Announcements.getInstance().announceToAll("The Event Boss came out Raid Boss name is..."); Announcements.getInstance().announceToAll(npc.getName() + "!"); } else { if (killer.isNoble()) { killer.sendMessage("Event Boss is standing by coordinates:"); killer.sendMessage("X: " + eventBoss.getX() + " Y: " + eventBoss.getY() + " Z: " + eventBoss.getZ()); } } } } if (rnd == 1) newNpcId = 120000; else if (rnd == 2) newNpcId = 110000; if (npcId == 100000) { npc.getSpawn().stopRespawn(); npc.deleteMe(); Announcements.getInstance().announceToAll("Player " + killer.getName() + " kill to " + npc.getName() + "! Now spawn Elite Boss!!!"); for (int i = 0; i < 30000; i += 1000) { try { Thread.sleep(1000); } catch (Exception e) { } } L2Npc rb = addSpawn(newNpcId, npc.getX(), npc.getY(), npc.getZ(), 0, false, 0); rb.setIsNoRndWalk(true); Announcements.getInstance().announceToAll("Elite Boss spawn! Kill here!!!"); } if (npcId == 110001) { npc.deleteMe(); npc.getSpawn().stopRespawn(); deleteHelpers(); } if (npcId == 110000) { npc.deleteMe(); npc.getSpawn().stopRespawn(); deleteHelpers(); Announcements.getInstance().announceToAll("Player " + killer.getName() + " kill to " + npc.getName() + "! Elite Boss is dead!"); } if (npcId == 120000) { npc.deleteMe(); npc.getSpawn().stopRespawn(); Announcements.getInstance().announceToAll("Player " + killer.getName() + " kill to " + npc.getName() + "! Elite Boss is dead!"); } return super.onKill(npc,killer,isPet); } public static void main(String[] args) { new ServerBossEvent(-1, "ServerBossEvent", "events"); } } 2 Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
LifeGame32 312 Опубликовано 26 ноября, 2016 Небольшой скрипт, идея которого была реализовать "Уникального Босса для сервера (Server Boss)". Скрипт довольно старый (21.04.2015), но может быть кому-то понадобится. Боссы обладают уникальный AI, поэтому он не будет скучный как на многих серверах, где просто заспавнили обычного NPC, где добавили только прибавку к статам и дроп. О реализации: Уникальный Босс спавнится на месте убитого простого рб (в скрипте указаны список ID боссов) Включает себя "комплект" Боссов (в данном случае их 3, но можно добавить еще) Реализованы Minion, которые появляются когда у босса определенное количество HP (в данном случае это 50%) О появлении Уникального Босса анонсируется в общий чат После убийства первого Босса появляется еще один случайный Босс и т.д. Всё описывать не буду, посмотрите сами. Вы сами пишите? Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
zGosu 396 Опубликовано 26 ноября, 2016 Вы сами пишите? Этот скрипт писал сам на сборке L2Spartan. Код мб корявый, но требуемого функционала смог добиться. Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
LifeGame32 312 Опубликовано 26 ноября, 2016 Этот скрипт писал сам на сборке L2Spartan. Код мб корявый, но требуемого функционала смог добиться. метод spawnHelpers(L2Npc npc, int npcId) - заспавнит только 1 раз и всё потом только через ребут метод deleteHelpers() бросит exception так как .getSpawn() вернет null если npc мертв Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
zGosu 396 Опубликовано 26 ноября, 2016 метод spawnHelpers(L2Npc npc, int npcId) - заспавнит только 1 раз и всё потом только через ребут метод deleteHelpers() бросит exception так как .getSpawn() вернет null если npc мертв spawnHelpers не планируется повторный респ мобов. После убийства его точка респа сразу удаляется if (npcId == 110001) // сам хелпер { npc.deleteMe(); npc.getSpawn().stopRespawn(); deleteHelpers(); // да, в этом методе нужна поправка } Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
LifeGame32 312 Опубликовано 26 ноября, 2016 в каком месте им будет присвоен null? private static L2Npc helper1; private static L2Npc helper2; private static L2Npc helper3; private static L2Npc helper4; private boolean helpers() { if (helper1 == null && helper2 == null && helper3 == null && helper4 == null) return true; return false; } private void spawnHelpers(L2Npc npc, int npcId) { if (helpers()) { npc.broadcastPacket(new NpcSay(npc.getObjectId(), 0, npc.getNpcId(), "Help me!")); helper1 = addSpawn(npcId, npc.getX() - 100, npc.getY() + 100, npc.getZ(), 0, false, 0); helper2 = addSpawn(npcId, npc.getX() + 100, npc.getY() - 100, npc.getZ(), 0, false, 0); helper3 = addSpawn(npcId, npc.getX() - 100, npc.getY() - 100, npc.getZ(), 0, false, 0); helper4 = addSpawn(npcId, npc.getX() + 100, npc.getY() + 100, npc.getZ(), 0, false, 0); helper1.setIsNoRndWalk(true); helper2.setIsNoRndWalk(true); helper3.setIsNoRndWalk(true); helper4.setIsNoRndWalk(true); } } Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
zGosu 396 Опубликовано 26 ноября, 2016 Не очень понял вопроса (как тут будет null? В deleteHelpers понятно то) private static final int[] helpers = {110001}; // ID хелпера /** * Вызывается 4 хелпера */ private static L2Npc helper1; private static L2Npc helper2; private static L2Npc helper3; private static L2Npc helper4; // тут надо убедиться, что хелперы не вызывались раньше, т.к. они должны вызваться только 1 раз (а то будет каждый "10 сек" респаться по 4 хелпера) private boolean helpers() { if (helper1 == null && helper2 == null && helper3 == null && helper4 == null) return true; return false; } private void spawnHelpers(L2Npc npc, int npcId) { if (helpers()) // если хелперы еще не вызывались (защита от повторного респа) { npc.broadcastPacket(new NpcSay(npc.getObjectId(), 0, npc.getNpcId(), "Help me!")); // MIAN босс пишет в чат "Help me" /** * Присваиваем каждой переменной (4 хелпера) моба с ид = 110001 */ helper1 = addSpawn(npcId, npc.getX() - 100, npc.getY() + 100, npc.getZ(), 0, false, 0); helper2 = addSpawn(npcId, npc.getX() + 100, npc.getY() - 100, npc.getZ(), 0, false, 0); helper3 = addSpawn(npcId, npc.getX() - 100, npc.getY() - 100, npc.getZ(), 0, false, 0); helper4 = addSpawn(npcId, npc.getX() + 100, npc.getY() + 100, npc.getZ(), 0, false, 0); helper1.setIsNoRndWalk(true); helper2.setIsNoRndWalk(true); helper3.setIsNoRndWalk(true); helper4.setIsNoRndWalk(true); } } if (npc.getCurrentHp() < (npc.getMaxHp() / 2)) { spawnHelpers(npc, 110001); // вызов метода (MAIN BOSS, id хелпера) не Null } А в методе на удаление надо добавить проверку, чтобы не удаляло хелперов, которые уже убиты, т.к. их респ удаляется сразу после смерти. if (npcId == 110001) { npc.deleteMe(); npc.getSpawn().stopRespawn(); deleteHelpers(); // удаляет сразу всех хелперов при убийстве хотя бы 1 из них } Хз, по плану это было или нет... не помню уже. Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
LifeGame32 312 Опубликовано 26 ноября, 2016 Не очень понял вопроса (как тут будет null? В deleteHelpers понятно то) // тут надо убедиться, что хелперы не вызывались раньше, т.к. они должны вызваться только 1 раз (а то будет каждый "10 сек" респаться по 4 хелпера) Хз, по плану это было или нет... не помню уже. И они больше не вызовутся пока не перезагрузить скрипт или сервер. они спавнятся только для npcID 110000 Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
zGosu 396 Опубликовано 26 ноября, 2016 И они больше не вызовутся пока не перезагрузить скрипт или сервер. они спавнятся только для npcID 110000 всё верно. так и задумано. я же писал выше что они повторно не будут вызываться и они респаются только для 1 рб, у другого рб свои фишки. Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты