Index: D:/Source/trunk/L2_Gameserver/java/net/sf/l2j/gameserver/model/actor/pc/PcStat.java===================================================================--- D:/Source/trunk/L2_Gameserver/java/net/sf/l2j/gameserver/model/actor/pc/PcStat.java (revision 2201)+++ D:/Source/trunk/L2_Gameserver/java/net/sf/l2j/gameserver/model/actor/pc/PcStat.java (working copy)@@ -38,7 +38,8 @@ int karmaRemove = value; karmaRemove /= Config.KARMA_XP_DIVIDER;- if (karmaRemove < 0) karmaRemove = 0;+ // low level chars killing mobs with less XP than divider should still lose karma.+ if (karmaRemove < 0) karmaRemove = 1; if (karmaRemove > getActiveChar().getKarma()) karmaRemove = getActiveChar().getKarma(); getActiveChar().setKarma(getActiveChar().getKarma() - karmaRemove); }Index: D:/Source/trunk/L2_Gameserver/java/net/sf/l2j/gameserver/model/L2PcInstance.java===================================================================--- D:/Source/trunk/L2_Gameserver/java/net/sf/l2j/gameserver/model/L2PcInstance.java (revision 2201)+++ D:/Source/trunk/L2_Gameserver/java/net/sf/l2j/gameserver/model/L2PcInstance.java (working copy)@@ -2354,6 +2354,8 @@ */ public void doDie(L2Character killer) {+ int lostXP=0; //useful for new karma reduction...Team Olympus.+ // Kill the L2PcInstance super.doDie(killer);@@ -2364,15 +2366,15 @@ { if (!ZoneManager.getInstance().checkIfInZonePvP(this) && (getSkillLevel(L2Skill.SKILL_LUCKY) < 0 || getStat().getLevel() > 4)) if(killer instanceof L2PcInstance && ((L2PcInstance)killer).getClan() != null && this.getClan() != null && this.getClan().isAtWarWith(((L2PcInstance)killer).getClanId()))- deathPenalty(true);+ lostXP=deathPenalty(true); else- deathPenalty(false);+ lostXP=deathPenalty(false); } onDieDropItem(killer); // Check if any item should be dropped }- onDieUpdateKarma();+ onDieUpdateKarma(lostXP); setPvpFlag(0); // Clear the pvp flag // Unsummon the Pet@@ -2417,13 +2419,14 @@ Random rand = new Random(); boolean dropGM = Config.KARMA_DROP_GM; // do GMs drop gear or not? true = yes, false = no int dropPKLim = Config.KARMA_PK_LIMIT; // you do not drop items if you have less than dropPKLim PKs+ int droptype = 0; //initialize if ( thisKarma > 0 && !(this.getPkKills() < dropPKLim && killer instanceof L2NpcInstance) && !ZoneManager.getInstance().checkIfInZonePvP(this)) { // Get drop settings //boolean gmStat = false; // keeps track of if player is a gm or not and if they are able to drop items int dropConstant = Config.KARMA_DROP_CONSTANT; // a constant used for drop chance calculation- //int dropLim = Config.KARMA_DROP_ITEM_LIMIT; // dropLim items dropped at most, equipped or unequipped doesnt matter.+ int dropLim = Config.KARMA_DROP_ITEM_LIMIT; // dropLim items dropped at most, equipped or unequipped doesnt matter. //int randDropLim = Config.KARMA_RANDOM_DROP_LOCATION_LIMIT; // max amount of x/y units a dropped item may be placed double dropRate = Config.RATE_DROP_EQUIPMENT; // drop rate... double dropChanceINIT = Config.KARMA_DROPCHANCE_INITIAL_CHECK; // dropChanceINIT% drop chance, initial check@@ -2440,123 +2443,163 @@ dropequipweap = (int)dropChanceEQUIP_WEAP; count = 0; while (!(isGM() && !dropGM) &&- this.getPkKills() >= dropPKLim && rand.nextInt(100)<droppercent){- int droptype = rand.nextInt(dropitems+dropequip+dropequipweap);- _log.warning(getName()+" have karma and will be lose of items: droptype="+droptype);- //droptype- count = 0;- for (L2ItemInstance itemdrop : _inventory.getItems()){- if (itemdrop.getItemId()!=57 && L2Item.TYPE2_QUEST != itemdrop.getItem().getType2() &&- !noDropList.contains(itemdrop.getItemId()) && !petList.contains(itemdrop.getItemId()))- if ((!itemdrop.isEquipped() && droptype < dropitems) ||- (itemdrop.isEquipped() && itemdrop.getItem().getType2() != L2Item.TYPE2_WEAPON && droptype < (dropitems + dropequip)) ||- (itemdrop.isEquipped() && itemdrop.getItem().getType2() == L2Item.TYPE2_WEAPON && droptype >= (dropitems + dropequip)))- count++;- }- // _log.warning("count:"+count);- //if have items to drop- if (count>0){- int itemnrtodrop = rand.nextInt(count);- count = 0;- for (L2ItemInstance itemdrop : _inventory.getItems()){- if (itemdrop.getItemId()!=57 && L2Item.TYPE2_QUEST != itemdrop.getItem().getType2() &&- !noDropList.contains(itemdrop.getItemId()) && !petList.contains(itemdrop.getItemId()))- if ((!itemdrop.isEquipped() && droptype < dropitems) ||- (itemdrop.isEquipped() && itemdrop.getItem().getType2() != L2Item.TYPE2_WEAPON && droptype < (dropitems + dropequip)) ||- (itemdrop.isEquipped() && itemdrop.getItem().getType2() == L2Item.TYPE2_WEAPON && droptype >= (dropitems + dropequip)))- {- if (count == itemnrtodrop){- if (itemdrop.isEquipped())- this.getInventory().unEquipItemInSlotAndRecord(itemdrop.getEquipSlot());- itemdrop = this.getInventory().dropItem(itemdrop,itemdrop.getCount());- itemdrop.dropMe(this, this.getClientX(), this.getClientY(), this.getClientZ() + 20);- SystemMessage sm = new SystemMessage(298);- sm.addItemName(itemdrop.getItemId());- this.sendPacket(sm);- InventoryUpdate iu = new InventoryUpdate(); // for inventory updating- iu.addRemovedItem(itemdrop);- this.sendPacket(iu);- _log.warning(getName()+" have karma and dropped id="+itemdrop.getItemId()+", count="+itemdrop.getCount());-- break;- }- count++;- }- }- }- droppercent /= 1.5;+ this.getPkKills() >= dropPKLim && rand.nextInt(100)<droppercent && count <= dropLim)+ {+ //first check if the person is to drop a weapon+ int chance = rand.nextInt(dropitems+dropequip+dropequipweap); + if (chance<dropequipweap)+ //if yes, find and drop the equipped weapon.+ droptype = 1;+ // next, check if another equipped weapon is to be dropped.+ else if(chance<(dropequipweap+dropequip))+ //if yes, find and drop one equipped item+ droptype = 2;+ else //if(chance<(dropequiweap+dropequip+dropitems))+ //find and drop an item...(exclude quest items and adena)+ droptype = 3;+ _log.warning(getName()+" have karma and will be lose of items: droptype="+droptype);+ boolean itemFound = false;// initialize+ while ((!itemFound) && (droptype <= 3))+ {+ for (L2ItemInstance itemdrop : _inventory.getItems())+ {+ //if drop = 1 and no item drop 2+ //if drop = 2 and no item check 1 if not drop 3+ //id drop = 3 and no check 1 if not check 2 if not NO DROP+ if (itemdrop.getItemId()!=57 && L2Item.TYPE2_QUEST != itemdrop.getItem().getType2() &&+ !noDropList.contains(itemdrop.getItemId()) && !petList.contains(itemdrop.getItemId()))+ if ((!itemdrop.isEquipped() && droptype == 3) ||+ (itemdrop.isEquipped() && itemdrop.getItem().getType2() != L2Item.TYPE2_WEAPON && droptype == 2) ||+ (itemdrop.isEquipped() && itemdrop.getItem().getType2() == L2Item.TYPE2_WEAPON && droptype == 1))+ {+ if (itemdrop.isEquipped())+ this.getInventory().unEquipItemInSlotAndRecord(itemdrop.getEquipSlot());+ int quantity = rand.nextInt(itemdrop.getCount())+1;+ itemdrop = this.getInventory().dropItem(itemdrop,quantity);+ itemdrop.dropMe(this, this.getClientX(), this.getClientY(), this.getClientZ() + 20);+ SystemMessage sm = new SystemMessage(298);+ sm.addItemName(itemdrop.getItemId());+ this.sendPacket(sm);+ InventoryUpdate iu = new InventoryUpdate(); // for inventory updating+ iu.addRemovedItem(itemdrop);+ this.sendPacket(iu);+ _log.warning(getName()+" have karma and dropped id="+itemdrop.getItemId()+", count="+itemdrop.getCount());+ itemFound = true;+ count++;+ break;+ }+ }+ //if no item can be found for this droptype, try the next droptype + //(the next most rare type after the one originally selected - see comments above)+ if (!itemFound)+ droptype++;+ }+ droppercent /= 1.5; }- } else if (!ZoneManager.getInstance().checkIfInZonePvP(this) || !isFestivalParticipant() ){- //if player haven't karma and lvl>4 and chance of drop 50%- droppercent = Config.PLAYER_RATE_DROP;- dropequip = Config.PLAYER_RATE_DROP_EQUIP;- dropequipweap = Config.PLAYER_RATE_DROP_EQUIP_WEAPON;- dropitems = Config.PLAYER_RATE_DROP_ITEM;- count = 0;- while (!(isGM() && !dropGM) && killer instanceof L2NpcInstance- && getLevel()>4 && rand.nextInt(100)<droppercent){- int droptype = rand.nextInt(dropitems+dropequip+dropequipweap);- _log.warning(getName()+" killed by npcid="+((L2NpcInstance)killer).getNpcId()+" and will be lose of items: droptype="+droptype);- //droptype- count = 0;- for (L2ItemInstance itemdrop : _inventory.getItems()){- if (itemdrop.getItemId()!=57 && L2Item.TYPE2_QUEST != itemdrop.getItem().getType2() &&- !noDropList.contains(itemdrop.getItemId()) && !petList.contains(itemdrop.getItemId()))- if ((!itemdrop.isEquipped() && droptype < dropitems) ||- (itemdrop.isEquipped() && itemdrop.getItem().getType2() != L2Item.TYPE2_WEAPON && droptype < (dropitems + dropequip)) ||- (itemdrop.isEquipped() && itemdrop.getItem().getType2() == L2Item.TYPE2_WEAPON && droptype >= (dropitems + dropequip)))- count++;- }- //_log.warning("count:"+count);- //if have items to drop- if (count>0){- int itemnrtodrop = rand.nextInt(count);- count = 0;- for (L2ItemInstance itemdrop : _inventory.getItems()){- if (itemdrop.getItemId()!=57 && L2Item.TYPE2_QUEST != itemdrop.getItem().getType2() &&- !noDropList.contains(itemdrop.getItemId()) && !petList.contains(itemdrop.getItemId()))- if ((!itemdrop.isEquipped() && droptype < dropitems) ||- (itemdrop.isEquipped() && itemdrop.getItem().getType2() != L2Item.TYPE2_WEAPON && droptype < (dropitems + dropequip)) ||- (itemdrop.isEquipped() && itemdrop.getItem().getType2() == L2Item.TYPE2_WEAPON && droptype >= (dropitems + dropequip)))- {- if (count == itemnrtodrop){- if (itemdrop.isEquipped())- this.getInventory().unEquipItemInSlotAndRecord(itemdrop.getEquipSlot());- itemdrop = this.getInventory().dropItem(itemdrop,itemdrop.getCount());- itemdrop.dropMe(this, this.getClientX(), this.getClientY(), this.getClientZ() + 20);- SystemMessage sm = new SystemMessage(298);- sm.addItemName(itemdrop.getItemId());- this.sendPacket(sm);- InventoryUpdate iu = new InventoryUpdate(); // for inventory updating- iu.addRemovedItem(itemdrop);- this.sendPacket(iu);- _log.warning(getName()+" died and dropped id="+itemdrop.getItemId()+", count="+itemdrop.getCount());- break;- }- count++;- }- }- }- droppercent /= 5;- } }+ else if (!ZoneManager.getInstance().checkIfInZonePvP(this) || !isFestivalParticipant() )+ {+ //if player haven't karma and lvl>4 and chance of drop 50%+ droppercent = Config.PLAYER_RATE_DROP;+ dropequip = Config.PLAYER_RATE_DROP_EQUIP;+ dropequipweap = Config.PLAYER_RATE_DROP_EQUIP_WEAPON;+ dropitems = Config.PLAYER_RATE_DROP_ITEM;+ // whites should ONLY drop 1 item max.+ if(!(isGM() && !dropGM) && killer instanceof L2NpcInstance+ && getLevel()>4 && rand.nextInt(100)<droppercent)+ {+ //first check if the person is to drop a weapon+ int chance = rand.nextInt(dropitems+dropequip+dropequipweap); + if (chance<dropequipweap)+ //if yes, find and drop the equipped weapon.+ droptype = 1;+ // next, check if another equipped weapon is to be dropped.+ else if(chance<(dropequipweap+dropequip))+ //if yes, find and drop one equipped item+ droptype = 2;+ else //if(chance<(dropequiweap+dropequip+dropitems))+ //find and drop an item...(exclude quest items and adena)+ droptype = 3;++ _log.warning(getName()+" killed by npcid="+((L2NpcInstance)killer).getNpcId()+" and will be lose of items: droptype="+droptype);+ boolean itemFound = false;// initialize+ while ((!itemFound) && (droptype <= 3))+ {+ for (L2ItemInstance itemdrop : _inventory.getItems())+ {+ //make a list of all weapons dropable+ //make a list of all worn dropable+ //make a list of all inventory dropable++ //if drop = 1 and no item drop 2+ //if drop = 2 and no item check 1 if not drop 3+ //id drop = 3 and no check 1 if not check 2 if not NO DROP+ if (droptype == 3 && itemdrop.getItemId()!=57 && L2Item.TYPE2_QUEST != itemdrop.getItem().getType2() &&+ !noDropList.contains(itemdrop.getItemId()) && !petList.contains(itemdrop.getItemId()))+ if ((!itemdrop.isEquipped() && droptype == 3) ||+ (itemdrop.isEquipped() && itemdrop.getItem().getType2() != L2Item.TYPE2_WEAPON && droptype == 2) ||+ (itemdrop.isEquipped() && itemdrop.getItem().getType2() == L2Item.TYPE2_WEAPON && droptype == 1))+ {+ if (itemdrop.isEquipped())+ this.getInventory().unEquipItemInSlotAndRecord(itemdrop.getEquipSlot());+ int quantity = rand.nextInt(itemdrop.getCount())+1;+ itemdrop = this.getInventory().dropItem(itemdrop,quantity);+ itemdrop.dropMe(this, this.getClientX(), this.getClientY(), this.getClientZ() + 20);+ SystemMessage sm = new SystemMessage(298);+ sm.addItemName(itemdrop.getItemId());+ this.sendPacket(sm);+ InventoryUpdate iu = new InventoryUpdate(); // for inventory updating+ iu.addRemovedItem(itemdrop);+ this.sendPacket(iu);+ _log.warning(getName()+" died and dropped id="+itemdrop.getItemId()+", count="+quantity);+ itemFound = true;+ break;+ }+ }+ //if no item can be found for this droptype, try the next droptype + //(the next most rare type after the one originally selected - see comments above)+ if (!itemFound)+ droptype++;+ }+ }+ } }- private void onDieUpdateKarma()+ private void onDieUpdateKarma(int lostXP) { // KARMA LOSS FOR DEAD PLAYER- // when a PKer gets killed by another player or a L2MonsterInstance, it loseq a certain amount of Karma based on their level.+ //new karma loss code by team Olympus:+ //Lose karma as a fraction of the XP you lost upon dying (ignoring how much + //of that XP might be returned by ressurection).+ //NOTE: This also provides an elegant solution for no karma loss in PvP zones+ //and for limitted karma loss in sieges (as specified in discussions from retail).+ // old karma loss, used when options do not allow XP loss on death:+ // when a PKer gets killed by another player or a L2MonsterInstance, it loseq a certain amount of Karma based on their level. // this (with defaults) results in a level 1 losing about ~2 karma per death, and a lvl 70 loses about 11760 karma per death... // You lose karma as long as you were not in a pvp zone and you did not kill urself. if ( getKarma() > 0 ) {- // this formula seems to work relatively well:- // baseKarma * thisLVL * (thisLVL/100)- // Calculate the new Karma of the attacker : newKarma = baseKarma*pkCountMulti*lvlDiffMulti- int karmaLost = Config.KARMA_LOST_BASE;- karmaLost *= getLevel(); // multiply by char lvl- karmaLost *= (int)(getLevel() / 100); // divide by 0.charLVL- karmaLost = Math.round(karmaLost);+ int karmaLost = 0;+ if (Config.ALT_GAME_DELEVEL)+ {+ karmaLost = lostXP/260; //this 260 seems to work quite accurately.+ // leave karmalost to 0 only if 0 xp was lost + // This works greate with arena (0 xp loss, 0 karma loss),+ // sieges (reduced xp loss, reduced karma loss as described in official forums), + // and normal zones... + if (karmaLost ==0 && lostXP >0)+ karmaLost = 1;+ }+ else+ {+ // this formula seems to work relatively well:+ // baseKarma * thisLVL * (thisLVL/100)+ // Calculate the new Karma of the attacker : newKarma = baseKarma*pkCountMulti*lvlDiffMulti+ karmaLost = Config.KARMA_LOST_BASE;+ karmaLost *= getLevel(); // multiply by char lvl+ karmaLost *= (int)(getLevel() / 100); // divide by 0.charLVL+ karmaLost = Math.round(karmaLost);+ } if ( karmaLost < 0 ) karmaLost = 1; // Decrease Karma of the L2PcInstance and Send it a Server->Client StatusUpdate packet with Karma and PvP Flag if necessary@@ -2704,9 +2747,9 @@ * <li>Set the value of _expBeforeDeath </li> * <li>Set the new Experience value of the L2PcInstance and Decrease its level if necessary </li> * <li>Send a Server->Client StatusUpdate packet with its new Experience </li><BR><BR>- *+ * <li>return the amount of XP lost, to be used for karma loss. */- public void deathPenalty(boolean atwar)+ public int deathPenalty(boolean atwar) { // TODO Need Correct Penalty@@ -2728,6 +2771,7 @@ // Set the new Experience value of the L2PcInstance getStat().addExp(-lostExp);+ return lostExp; }