L2JMobius

Classic Interlude Buy XP from NPC

pipipopo · 2 · 1958

Offline pipipopo

  • Knight
  • ***
    • Posts: 80
Hi, everyone. Back again after a year.

So, now I am trying to implement buy experience for adena/anything functionality.



Player inputs amount, clicks buy and receive XP in exchange of item. In this case adena.

Everything works fine so far except when player puts in a number larger than long. Then this happens:

Code: [Select]
[27/03 15:47:58] Exception processing bypass from player crknt: npc_268447280_BuyXP
java.lang.ArrayIndexOutOfBoundsException: Index 1 out of bounds for length 1
at handlers.bypasshandlers.BuyExperience.useBypass(BuyExperience.java:43)
at org.l2jmobius.gameserver.model.actor.Npc.onBypassFeedback(Npc.java:604)
at org.l2jmobius.gameserver.model.actor.instance.VillageMasterInstance.onBypassFeedback(VillageMasterInstance.java:757)
at org.l2jmobius.gameserver.network.clientpackets.RequestBypassToServer.run(RequestBypassToServer.java:164)
at org.l2jmobius.gameserver.network.clientpackets.RequestBypassToServer.run(RequestBypassToServer.java:52)
at org.l2jmobius.gameserver.network.GameClient.channelRead0(GameClient.java:122)
at org.l2jmobius.gameserver.network.GameClient.channelRead0(GameClient.java:66)
at io.netty.channel.SimpleChannelInboundHandler.channelRead(SimpleChannelInboundHandler.java:99)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
at io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
at io.netty.handler.codec.ByteToMessageDecoder.fireChannelRead(ByteToMessageDecoder.java:324)
at io.netty.handler.codec.ByteToMessageDecoder.channelRead(ByteToMessageDecoder.java:296)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
at io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
at io.netty.handler.codec.ByteToMessageDecoder.fireChannelRead(ByteToMessageDecoder.java:324)
at io.netty.handler.codec.ByteToMessageDecoder.channelRead(ByteToMessageDecoder.java:296)
at io.netty.handler.codec.ByteToMessageCodec.channelRead(ByteToMessageCodec.java:103)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
at io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
at io.netty.handler.codec.ByteToMessageDecoder.fireChannelRead(ByteToMessageDecoder.java:324)
at io.netty.handler.codec.ByteToMessageDecoder.channelRead(ByteToMessageDecoder.java:296)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
at io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
at io.netty.channel.DefaultChannelPipeline$HeadContext.channelRead(DefaultChannelPipeline.java:1410)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
at io.netty.channel.DefaultChannelPipeline.fireChannelRead(DefaultChannelPipeline.java:919)
at io.netty.channel.nio.AbstractNioByteChannel$NioByteUnsafe.read(AbstractNioByteChannel.java:163)
at io.netty.channel.nio.NioEventLoop.processSelectedKey(NioEventLoop.java:714)
at io.netty.channel.nio.NioEventLoop.processSelectedKeysOptimized(NioEventLoop.java:650)
at io.netty.channel.nio.NioEventLoop.processSelectedKeys(NioEventLoop.java:576)
at io.netty.channel.nio.NioEventLoop.run(NioEventLoop.java:493)
at io.netty.util.concurrent.SingleThreadEventExecutor$4.run(SingleThreadEventExecutor.java:989)
at io.netty.util.internal.ThreadExecutorMap$2.run(ThreadExecutorMap.java:74)
at io.netty.util.concurrent.FastThreadLocalRunnable.run(FastThreadLocalRunnable.java:30)
at java.base/java.lang.Thread.run(Thread.java:832)

This is the code:

Code: [Select]
/*
 * This file is part of the L2J Mobius project.
 *
 * 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 handlers.bypasshandlers;

import org.l2jmobius.gameserver.handler.IBypassHandler;
import org.l2jmobius.gameserver.model.actor.Creature;
import org.l2jmobius.gameserver.model.actor.instance.PlayerInstance;
import org.l2jmobius.gameserver.model.itemcontainer.PlayerInventory;
import org.l2jmobius.gameserver.util.Util;

/**
 * @author n
 */
public class BuyExperience implements IBypassHandler
{
private static final int ADENA = 57;

private static final String[] COMMANDS =
{
"BuyXP"
};

@Override
public boolean useBypass(String command, PlayerInstance player, Creature target)
{
// Need to have at least one Name Change Ticket in order to proceed.
final PlayerInventory inventory = player.getInventory();

String input = command.split(" ")[1].trim();

if (!Util.isDigit(input))
{
player.sendMessage("You don't have enough adena.");
// player.sendMessage("Amount must only contain numeric characters.");
return false;
}

if (input.length() > 15)
{
player.sendMessage("You don't have enough adena.");
return false;
}

long amount = Long.parseLong(input);

if (inventory.getAdena() < amount)
{
player.sendMessage("You don't have enough adena.");
return false;
}

// Destroy item.
player.destroyItemByItemId(player.getName() + " purchased " + amount + " experience.", ADENA, amount, player, true);

// Set name and proceed.
player.addExpAndSp(amount, amount);
player.storeMe();

return true;
}

@Override
public String[] getBypassList()
{
return COMMANDS;
}
}

What do? Can anyone point me in the right direction?