Compare commits

..

12 Commits

Author SHA1 Message Date
emo
3559ab4d2f fixed cat bug both Player Name and I found at about the same time... 2025-03-10 17:40:34 -04:00
EmoScape
3a0db52215 missing semicolon on enum 2025-03-09 16:58:12 -04:00
EmoScape
a895a09822 Merge branch 'main' of https://git.emoscape.org/emo/emo-server 2025-03-09 16:52:39 -04:00
EmoScape
265f93fff3 temporarily disabled my least favorite randoms until I can think of something funny to do with them to make them more interesting/less buggy 2025-03-09 16:51:28 -04:00
emo
954f0c9319 Update README.md 2025-03-06 20:29:17 +00:00
EmoScape
4edcccee71 both quests now have a bribe option 2025-03-06 15:15:01 -05:00
EmoScape
dd256b9fde made Shield of Arrav completable with bribery to King Roald 2025-03-06 12:18:15 -05:00
EmoScape
7312753e35 initial bribing of King Roald enabled 2025-03-06 08:13:10 -05:00
EmoScape
3eb18586e4 accidentally uncommented out something in the west ardy civilian cat handler 2025-03-05 18:24:14 -05:00
EmoScape
268a15c788 This implements a stat for how many cats get sold for death runes
Merge branch 'cat-sold-counter'
2025-03-05 12:43:03 -05:00
EmoScape
9139e39397 finished the cats sold stat implementation 2025-03-05 12:42:03 -05:00
emo
c7db36d9b6 Merge pull request 'new-exp' (#1) from new-exp into main
This implements the scaled EXP options:

Basically if you select the scaled options, you will start off playing 1x

    if you select the scaled 10x, your exp multiplier will increase proportional to the exp you gain in the skill until you reach 99, after which it will be capped at 10x
    if you select the scaled 5x, your exp multiplier will increase proportional to the exp you gain in the skill until you reach 99, after which it will be capped at 5x

I also brought back HCIM mode!
2025-03-04 23:05:13 +00:00
8 changed files with 286 additions and 154 deletions

View File

@ -43,5 +43,5 @@ I would strongly recommend contributing code to the [2009Scape project](https://
## License ## License
Like 2009Scape, this is AGPLv3. This is, in my opinion, the only proper license for an open source RSPS. The key term of the license being if you wish to use this code, you must also offer the source code for people to inspect and use! (eg no private, for profit RSPS). Like 2009Scape, this is AGPLv3. This is, in my opinion, the only proper license for an open source RSPS. The key term of the license being if you wish to use this code to host your own server, you must also offer the source code for people to inspect and use, and allow them to make modifications to it as I did with 2009Scape's code.

View File

@ -46,23 +46,23 @@ enum class RandomEvents(val npc: RandomEventNPC, val loot: WeightBasedTable? = n
WeightedItem(Items.TOOTH_HALF_OF_A_KEY_985,1,1,0.1), WeightedItem(Items.TOOTH_HALF_OF_A_KEY_985,1,1,0.1),
WeightedItem(Items.LOOP_HALF_OF_A_KEY_987,1,1,0.1) WeightedItem(Items.LOOP_HALF_OF_A_KEY_987,1,1,0.1)
)), )),
MAZE(npc = MazeNPC()), // MAZE(npc = MazeNPC()),
DRILL_DEMON(npc = SergeantDamienNPC()), DRILL_DEMON(npc = SergeantDamienNPC()),
EVIL_CHICKEN(npc = EvilChickenNPC()), EVIL_CHICKEN(npc = EvilChickenNPC()),
STRANGE_PLANT(npc = StrangePlantNPC()), // STRANGE_PLANT(npc = StrangePlantNPC()),
SWARM(npc = SwarmNPC()), // SWARM(npc = SwarmNPC()),
EVIL_BOB(npc = EvilBobNPC(), skillIds = intArrayOf(Skills.FISHING, Skills.MAGIC)), // EVIL_BOB(npc = EvilBobNPC(), skillIds = intArrayOf(Skills.FISHING, Skills.MAGIC)),
DRUNKEN_DWARF(npc = DrunkenDwarfNPC()), DRUNKEN_DWARF(npc = DrunkenDwarfNPC()),
RICK_TURPENTINE(npc = RickTurpentineNPC(), loot = CERTER.loot), RICK_TURPENTINE(npc = RickTurpentineNPC(), loot = CERTER.loot),
SURPRISE_EXAM(npc = MysteriousOldManNPC(), type = "sexam"), SURPRISE_EXAM(npc = MysteriousOldManNPC(), type = "sexam"),
FREAKY_FORESTER(npc = FreakyForesterNPC(), skillIds = intArrayOf(Skills.WOODCUTTING)), FREAKY_FORESTER(npc = FreakyForesterNPC(), skillIds = intArrayOf(Skills.WOODCUTTING)),
PILLORY(npc = PilloryNPC(), skillIds = intArrayOf(Skills.THIEVING)), // PILLORY(npc = PilloryNPC(), skillIds = intArrayOf(Skills.THIEVING)),
TREE_SPIRIT(npc = TreeSpiritRENPC(), skillIds = intArrayOf(Skills.WOODCUTTING)), TREE_SPIRIT(npc = TreeSpiritRENPC(), skillIds = intArrayOf(Skills.WOODCUTTING)),
QUIZ_MASTER(npc = QuizMasterNPC()), QUIZ_MASTER(npc = QuizMasterNPC()),
RIVER_TROLL(RiverTrollRENPC(), skillIds = intArrayOf(Skills.FISHING)), RIVER_TROLL(RiverTrollRENPC(), skillIds = intArrayOf(Skills.FISHING)),
ROCK_GOLEM(RockGolemRENPC(), skillIds = intArrayOf(Skills.MINING)), // ROCK_GOLEM(RockGolemRENPC(), skillIds = intArrayOf(Skills.MINING)),
SHADE(ShadeRENPC(), skillIds = intArrayOf(Skills.PRAYER)), SHADE(ShadeRENPC(), skillIds = intArrayOf(Skills.PRAYER));
ZOMBIE(ZombieRENPC(), skillIds = intArrayOf(Skills.PRAYER)); // ZOMBIE(ZombieRENPC(), skillIds = intArrayOf(Skills.PRAYER));
companion object { companion object {
@JvmField @JvmField

View File

@ -128,7 +128,12 @@ public final class FamiliarManager {
} }
if (currentPet != -1) { if (currentPet != -1) {
int last = this.petDetails.get(currentPet).size() - 1; int last = this.petDetails.get(currentPet).size() - 1;
PetDetails details = this.petDetails.get(currentPet).get(last); PetDetails details;
if (last < 0) { //missing data in save due to historical bug (see GL !2077)
details = new PetDetails(0);
} else {
details = this.petDetails.get(currentPet).get(last);
}
Pets pets = Pets.forId(currentPet); Pets pets = Pets.forId(currentPet);
familiar = new Pet(player, details, currentPet, pets.getNpcId(currentPet)); familiar = new Pet(player, details, currentPet, pets.getNpcId(currentPet));
} else if (familiarData.containsKey("familiar")) { } else if (familiarData.containsKey("familiar")) {
@ -414,6 +419,9 @@ public final class FamiliarManager {
* @param details The new pet details. * @param details The new pet details.
*/ */
public void addDetails(int itemId, PetDetails details) { public void addDetails(int itemId, PetDetails details) {
if (petDetails.get(itemId) == null) {
petDetails.put(itemId, new ArrayList<>());
}
petDetails.get(itemId).add(details); petDetails.get(itemId).add(details);
} }

View File

@ -129,8 +129,8 @@ public final class Pet extends Familiar {
if (pet.isKitten(itemId)) { if (pet.isKitten(itemId)) {
owner.incrementAttribute("/save:stats_manager:cats_raised"); owner.incrementAttribute("/save:stats_manager:cats_raised");
} }
owner.getFamiliarManager().removeDetails(getItemId());
owner.getFamiliarManager().addDetails(newItemId, details); owner.getFamiliarManager().addDetails(newItemId, details);
owner.getFamiliarManager().removeDetails(getItemId());
owner.getFamiliarManager().morphPet(new Item(newItemId), false, location, details.getHunger(), 0); owner.getFamiliarManager().morphPet(new Item(newItemId), false, location, details.getHunger(), 0);
owner.getPacketDispatch().sendMessage("<col=ff0000>Your pet has grown larger.</col>"); owner.getPacketDispatch().sendMessage("<col=ff0000>Your pet has grown larger.</col>");
} }

View File

@ -10,10 +10,15 @@ import core.game.node.entity.player.Player
import core.plugin.Initializable import core.plugin.Initializable
import org.rs09.consts.Items import org.rs09.consts.Items
import org.rs09.consts.NPCs import org.rs09.consts.NPCs
import core.game.node.item.Item
@Initializable @Initializable
class AchiettiesDialogue(player: Player? = null) : DialoguePlugin(player) { class AchiettiesDialogue(player: Player? = null) : DialoguePlugin(player) {
companion object {
const val BRIBE_PRICE = 1_000_000
}
override fun handle(interfaceId: Int, buttonId: Int): Boolean { override fun handle(interfaceId: Int, buttonId: Int): Boolean {
openDialogue(player, AchiettiesDialogueFile(), npc) openDialogue(player, AchiettiesDialogueFile(), npc)
return true return true
@ -34,30 +39,28 @@ class AchiettiesDialogueFile : DialogueBuilderFile() {
b.onQuestStages(Quests.HEROES_QUEST, 0, 1) b.onQuestStages(Quests.HEROES_QUEST, 0, 1)
.branch { player -> .branch { player ->
return@branch getQuestStage(player, Quests.HEROES_QUEST) // Return the current quest stage.
}.let{ branch -> getQuestStage(player, Quests.HEROES_QUEST)
}
.let { branch ->
branch.onValue(0) branch.onValue(0)
.npcl(FacialExpression.FRIENDLY, "Greetings. Welcome to the Heroes' Guild.") .npcl(FacialExpression.FRIENDLY, "Greetings. Welcome to the Heroes' Guild.")
.npcl("Only the greatest heroes of this land may gain entrance to this guild.") .npcl("Only the greatest heroes of this land may gain entrance to this guild.")
// - If the player's skill levels are lower than the quest requirements. (I think this is after 2009)
// linel("Before starting this quest, be aware that one or more of your skill levels are lower than what is required to fully complete it.")
.options() .options()
.let { optionBuilder -> .let { optionBuilder ->
optionBuilder.option("I'm a hero, may I apply to join?") optionBuilder.option("I'm a hero, may I apply to join?")
.playerl("I'm a hero. May I apply to join?") .playerl("I'm a hero. May I apply to join?")
.branch { player -> .branch { player ->
return@branch if (HeroesQuest.hasRequirements(player)) { if (HeroesQuest.hasRequirements(player)) 1 else 0
1
} else {
0
} }
}.let { branch -> .let { branch ->
branch.onValue(0) branch.onValue(0)
.npcl("You're a hero? I've never heard of YOU. You are required to possess at least 55 quest points to file an application.") .npcl("You're a hero? I've never heard of YOU. You are required to possess at least 55 quest points to file an application.")
.npcl("Additionally you must have completed the Shield of Arrav, Lost City, Merlin's Crystal and Dragon Slayer quests.") .npcl("Additionally you must have completed the Shield of Arrav, Lost City, Merlin's Crystal and Dragon Slayer quests.")
.end() .end()
return@let branch branch
}.onValue(1) }
.onValue(1)
.betweenStage { df, player, _, _ -> .betweenStage { df, player, _, _ ->
if (getQuestStage(player, Quests.HEROES_QUEST) == 0) { if (getQuestStage(player, Quests.HEROES_QUEST) == 0) {
setQuestStage(player, Quests.HEROES_QUEST, 1) setQuestStage(player, Quests.HEROES_QUEST, 1)
@ -79,8 +82,30 @@ class AchiettiesDialogueFile : DialogueBuilderFile() {
optionBuilder2.option_playerl("I'll start looking for all those things then.") optionBuilder2.option_playerl("I'll start looking for all those things then.")
.npcl("Good luck with that.") .npcl("Good luck with that.")
.end() .end()
optionBuilder2.option_playerl("Or perhaps the guild needs a bit of financing?")
.npcl("Perhaps a small 'Loan' of 1 million coins?")
// Bribery branch
.options()
.let { optionBuilder3 ->
optionBuilder3.option_playerl("That sounds good")
.branch { player ->
if (inInventory(player!!, 995, AchiettiesDialogue.BRIBE_PRICE)) 1 else 0
}
.let { branch ->
branch.onValue(1)
.playerl(FacialExpression.FRIENDLY, "Here you go!")
.endWith { _, player ->
removeItem(player, Item(995, AchiettiesDialogue.BRIBE_PRICE), Container.INVENTORY)
finishQuest(player, Quests.HEROES_QUEST)
}
branch.onValue(0)
.playerl(FacialExpression.HALF_GUILTY, "Actually, I don't have that much.")
.end()
}
optionBuilder3.option_playerl("1 million coins for this dump? No way")
.end()
}
} }
optionBuilder.option_playerl("Good for the foremost heroes of the land.") optionBuilder.option_playerl("Good for the foremost heroes of the land.")
.npcl("Yes. Yes it is.") .npcl("Yes. Yes it is.")
.end() .end()
@ -90,7 +115,7 @@ class AchiettiesDialogueFile : DialogueBuilderFile() {
.npcl("How goes thy quest adventurer?") .npcl("How goes thy quest adventurer?")
.playerl("It's tough. I've not done it yet.") .playerl("It's tough. I've not done it yet.")
.npcl("Remember, the items you need to enter are:") .npcl("Remember, the items you need to enter are:")
.npcl("An Entranan Firebirds' feather, A Master Thieves armband, and a cooked Lava Eel.") .npcl("An Entranan Firebird's feather, A Master Thieves' armband, and a cooked Lava Eel.")
.options() .options()
.let { optionBuilder2 -> .let { optionBuilder2 ->
optionBuilder2.option_playerl("Any hints on getting the thieves armband?") optionBuilder2.option_playerl("Any hints on getting the thieves armband?")
@ -105,6 +130,29 @@ class AchiettiesDialogueFile : DialogueBuilderFile() {
optionBuilder2.option_playerl("I'll start looking for all those things then.") optionBuilder2.option_playerl("I'll start looking for all those things then.")
.npcl("Good luck with that.") .npcl("Good luck with that.")
.end() .end()
optionBuilder2.option_playerl("Or perhaps the guild needs a bit of financing?")
.npcl("Perhaps a small 'Loan' of 1 million coins?")
// Bribery branch
.options()
.let { optionBuilder3 ->
optionBuilder3.option_playerl("That sounds good")
.branch { player ->
if (inInventory(player!!, 995, AchiettiesDialogue.BRIBE_PRICE)) 1 else 0
}
.let { branch ->
branch.onValue(1)
.playerl(FacialExpression.FRIENDLY, "Here you go!")
.endWith { _, player ->
removeItem(player, Item(995, AchiettiesDialogue.BRIBE_PRICE), Container.INVENTORY)
finishQuest(player, Quests.HEROES_QUEST)
}
branch.onValue(0)
.playerl(FacialExpression.HALF_GUILTY, "Actually, I don't have that much.")
.end()
}
optionBuilder3.option_playerl("1 million coins for this dump? No way")
.end()
}
} }
} }
@ -113,14 +161,14 @@ class AchiettiesDialogueFile : DialogueBuilderFile() {
.npcl("How goes thy quest adventurer?") .npcl("How goes thy quest adventurer?")
.playerl("It's tough. I've not done it yet.") .playerl("It's tough. I've not done it yet.")
.npcl("Remember, the items you need to enter are:") .npcl("Remember, the items you need to enter are:")
.npcl("An Entranan Firebirds' feather, A Master Thieves armband, and a cooked Lava Eel.") .npcl("An Entranan Firebird's feather, A Master Thieves' armband, and a cooked Lava Eel.")
.options() .options()
.let { optionBuilder2 -> .let { optionBuilder2 ->
optionBuilder2.option_playerl("Any hints on getting the thieves armband?") optionBuilder2.option_playerl("Any hints on getting the thieves armband?")
.npcl("I'm sure you have the relevant contacts to find out about that.") .npcl("I'm sure you have the relevant contacts to find out about that.")
.end() .end()
optionBuilder2.option_playerl("Any hints on getting the feather?") optionBuilder2.option_playerl("Any hints on getting the feather?")
.npcl("Not really - other than Entranan firebirds tend to live on Entrana.") .npcl("Not really - other than Entranan Firebirds tend to live on Entrana.")
.end() .end()
optionBuilder2.option_playerl("Any hints on getting the eel?") optionBuilder2.option_playerl("Any hints on getting the eel?")
.npcl("Maybe go and find someone who knows a lot about fishing?") .npcl("Maybe go and find someone who knows a lot about fishing?")
@ -128,25 +176,49 @@ class AchiettiesDialogueFile : DialogueBuilderFile() {
optionBuilder2.option_playerl("I'll start looking for all those things then.") optionBuilder2.option_playerl("I'll start looking for all those things then.")
.npcl("Good luck with that.") .npcl("Good luck with that.")
.end() .end()
optionBuilder2.option_playerl("Or perhaps the guild needs a bit of financing?")
.npcl("Perhaps a small 'Loan' of 1 million coins?")
// Bribery branch
.options()
.let { optionBuilder3 ->
optionBuilder3.option_playerl("That sounds good")
.branch { player ->
if (inInventory(player!!, 995, AchiettiesDialogue.BRIBE_PRICE)) 1 else 0
}
.let { branch ->
branch.onValue(1)
.playerl(FacialExpression.FRIENDLY, "Here you go!")
.endWith { _, player ->
removeItem(player, Item(995, AchiettiesDialogue.BRIBE_PRICE), Container.INVENTORY)
finishQuest(player, Quests.HEROES_QUEST)
}
branch.onValue(0)
.playerl(FacialExpression.HALF_GUILTY, "Actually, I don't have that much.")
.end()
}
optionBuilder3.option_playerl("1 million coins for this dump? No way")
.end()
}
} }
b.onQuestStages(Quests.HEROES_QUEST, 6) b.onQuestStages(Quests.HEROES_QUEST, 6)
.npcl("Greetings. Welcome to the Heroes' Guild.") .npcl("Greetings. Welcome to the Heroes' Guild.")
.npcl("How goes thy quest adventurer?") .npcl("How goes thy quest adventurer?")
.branch { player -> .branch { player ->
return@branch if (HeroesQuest.allItemsInInventory(player)) { 1 } else { 0 } if (HeroesQuest.allItemsInInventory(player)) 1 else 0
}.let { branch -> }
.let { branch ->
branch.onValue(0) branch.onValue(0)
.playerl("It's tough. I've not done it yet.") .playerl("It's tough. I've not done it yet.")
.npcl("Remember, the items you need to enter are:") .npcl("Remember, the items you need to enter are:")
.npcl("An Entranan Firebirds' feather, A Master Thieves armband, and a cooked Lava Eel.") .npcl("An Entranan Firebird's feather, A Master Thieves' armband, and a cooked Lava Eel.")
.options() .options()
.let { optionBuilder2 -> .let { optionBuilder2 ->
optionBuilder2.option_playerl("Any hints on getting the thieves armband?") optionBuilder2.option_playerl("Any hints on getting the thieves armband?")
.npcl("I'm sure you have the relevant contacts to find out about that.") .npcl("I'm sure you have the relevant contacts to find out about that.")
.end() .end()
optionBuilder2.option_playerl("Any hints on getting the feather?") optionBuilder2.option_playerl("Any hints on getting the feather?")
.npcl("Not really - other than Entranan firebirds tend to live on Entrana.") .npcl("Not really - other than Entranan Firebirds tend to live on Entrana.")
.end() .end()
optionBuilder2.option_playerl("Any hints on getting the eel?") optionBuilder2.option_playerl("Any hints on getting the eel?")
.npcl("Maybe go and find someone who knows a lot about fishing?") .npcl("Maybe go and find someone who knows a lot about fishing?")
@ -154,8 +226,30 @@ class AchiettiesDialogueFile : DialogueBuilderFile() {
optionBuilder2.option_playerl("I'll start looking for all those things then.") optionBuilder2.option_playerl("I'll start looking for all those things then.")
.npcl("Good luck with that.") .npcl("Good luck with that.")
.end() .end()
optionBuilder2.option_playerl("Or perhaps the guild needs a bit of financing?")
.npcl("Perhaps a small 'Loan' of 1 million coins?")
// Bribery branch
.options()
.let { optionBuilder3 ->
optionBuilder3.option_playerl("That sounds good")
.branch { player ->
if (inInventory(player!!, 995, AchiettiesDialogue.BRIBE_PRICE)) 1 else 0
}
.let { branch ->
branch.onValue(1)
.playerl(FacialExpression.FRIENDLY, "Here you go!")
.endWith { _, player ->
removeItem(player, Item(995, AchiettiesDialogue.BRIBE_PRICE), Container.INVENTORY)
finishQuest(player, Quests.HEROES_QUEST)
}
branch.onValue(0)
.playerl(FacialExpression.HALF_GUILTY, "Actually, I don't have that much.")
.end()
}
optionBuilder3.option_playerl("1 million coins for this dump? No way")
.end()
}
} }
branch.onValue(1) branch.onValue(1)
.playerl("I have all the required items.") .playerl("I have all the required items.")
.npcl("I see that you have. Well done. Now, to complete the quest, and gain entry to the Heroes' Guild in your final task all that you have to do is...") .npcl("I see that you have. Well done. Now, to complete the quest, and gain entry to the Heroes' Guild in your final task all that you have to do is...")

View File

@ -170,7 +170,7 @@ class CatTrade : InteractionListener{
onUseWith(IntType.NPC, cats, NPCs.CIVILIAN_785, NPCs.CIVILIAN_786, NPCs.CIVILIAN_787){ player, used, with -> onUseWith(IntType.NPC, cats, NPCs.CIVILIAN_785, NPCs.CIVILIAN_786, NPCs.CIVILIAN_787){ player, used, with ->
if(removeItem(player, used)){ if(removeItem(player, used)){
val dialogue = CatTradeDialogue() val dialogue = CatTradeDialogue()
Remove the cat // Remove the cat
player.familiarManager.removeDetails(used.id) player.familiarManager.removeDetails(used.id)
addItem(player, Items.DEATH_RUNE_560, 100) addItem(player, Items.DEATH_RUNE_560, 100)
player.incrementAttribute("/save:stats_manager:cats_sold"); player.incrementAttribute("/save:stats_manager:cats_sold");

View File

@ -41,7 +41,7 @@ class KingRoaldDialogue(player: Player? = null) : DialoguePlugin(player) {
addOption("Priest in Peril", KingRoaldPIPDialogue(player.questRepository.getStage(Quests.PRIEST_IN_PERIL))) addOption("Priest in Peril", KingRoaldPIPDialogue(player.questRepository.getStage(Quests.PRIEST_IN_PERIL)))
} }
if (player.questRepository.getQuest(Quests.SHIELD_OF_ARRAV).isStarted(player) && !player.questRepository.getQuest(Quests.SHIELD_OF_ARRAV).isCompleted(player)) { if (!player.questRepository.getQuest(Quests.SHIELD_OF_ARRAV).isCompleted(player)) {
addOption("Shield of Arrav", KingRoaldArravDialogue()) addOption("Shield of Arrav", KingRoaldArravDialogue())
} }

View File

@ -6,12 +6,20 @@ import core.game.dialogue.DialogueFile
import core.tools.END_DIALOGUE import core.tools.END_DIALOGUE
import core.tools.START_DIALOGUE import core.tools.START_DIALOGUE
import content.data.Quests import content.data.Quests
import core.game.dialogue.FacialExpression
import core.api.Container
import core.api.inInventory
import core.api.removeItem
import core.game.dialogue.DialoguePlugin
private val CERTIFICATE = Item(769) private val CERTIFICATE = Item(769)
class KingRoaldArravDialogue() : DialogueFile() { class KingRoaldArravDialogue() : DialogueFile() {
companion object {
const val BRIBE_PRICE = 6000
}
override fun handle(componentID: Int, buttonID: Int) { override fun handle(componentID: Int, buttonID: Int) {
if (player!!.inventory.containsItem(ShieldofArrav.PHOENIX_SHIELD) || player!!.inventory.containsItem(ShieldofArrav.BLACKARM_SHIELD)) { if (player!!.inventory.containsItem(ShieldofArrav.PHOENIX_SHIELD) || player!!.inventory.containsItem(ShieldofArrav.BLACKARM_SHIELD)) {
@ -54,7 +62,29 @@ class KingRoaldArravDialogue() : DialogueFile() {
} }
else { else {
abandonFile() when (stage) {
START_DIALOGUE -> player("I would like to contribute to one of", "your Political Action Committees").also{ stage++ }
1 -> npcl("Which one?").also { stage++ }
2 -> playerl("The Citizens Who Can't Be Bothered To Do Shield of Arrav").also { stage++ }
3 -> npcl(FacialExpression.HALF_THINKING, "I see... that will be 6,000 coins").also { stage++ }
4 -> options("Here you go!", "Nevermind.").also { stage++ }
5 -> when (buttonID) {
1 -> {
if (inInventory(player!!, 995, BRIBE_PRICE))
playerl(FacialExpression.FRIENDLY, "Here you go!").also { stage = 20 }
else
playerl(FacialExpression.HALF_GUILTY, "Actually, I don't have that much.").also { stage = END_DIALOGUE }
}
2 -> playerl(FacialExpression.FRIENDLY, "On second thought, never mind.").also { stage = END_DIALOGUE }
}
20 -> {
npcl("Thank you so much, dear donor. The government of Varrock now has higher priorities than the Shield of Arrav.")
if (removeItem(player!!, Item(995, BRIBE_PRICE), Container.INVENTORY)) {
player!!.questRepository.getQuest(Quests.SHIELD_OF_ARRAV).finish(player)
}
stage = END_DIALOGUE
}
}
} }
} }
} }