예제 #1
0
  public int baseAttackBonus(final PlayerCharacter aPC) {
    if (aPC.getLevel(this) == 0) {
      return 0;
    }

    return (int) getBonusTo("COMBAT", "BASEAB", aPC.getLevel(this), aPC);
  }
예제 #2
0
 @Override
 protected void reset() {
   for (final PlayerCharacter player : getPlayersInRoom()) {
     player.output("You got another chance!");
     Core.teleportCharacterTo(player, StartRoom.class);
   }
 }
예제 #3
0
  public void setLevel(final int newLevel, final PlayerCharacter aPC) {
    final int curLevel = aPC.getLevel(this);

    if (newLevel >= 0) {
      aPC.setLevelWithoutConsequence(this, newLevel);
    }

    if (newLevel == 1) {
      if (newLevel > curLevel || aPC.isImporting()) {
        addFeatPoolBonus(aPC);
      }
    }

    if (!aPC.isImporting()) {
      aPC.calcActiveBonuses();
      // Need to do this again if caching is re-integrated
      // aPC.getSpellTracker().buildSpellLevelMap(newLevel);
    }

    if ((newLevel == 1) && !aPC.isImporting() && (curLevel == 0)) {
      SubClassApplication.checkForSubClass(aPC, this);
      aPC.setSpellLists(this);
    }

    if (!aPC.isImporting() && (curLevel < newLevel)) {
      SubstitutionClassApplication.checkForSubstitutionClass(this, newLevel, aPC);
    }

    for (PCClass pcClass : aPC.getClassSet()) {
      aPC.calculateKnownSpellsForClassLevel(this);
    }
  }
예제 #4
0
 /**
  * Add the bonus to the character's feat pool that is granted by the class. NB: LEVELSPERFEAT is
  * now handled via PLayerCHaracter.getNumFeatsFromLevels() rather than bonuses. Only the standard
  * feat progression for the gamemode is handled here.
  *
  * @param aPC The character to bonus.
  */
 void addFeatPoolBonus(final PlayerCharacter aPC) {
   Integer mLevPerFeat = get(IntegerKey.LEVELS_PER_FEAT);
   int startLevel;
   int rangeLevel;
   int divisor;
   if (mLevPerFeat == null) {
     String aString = Globals.getBonusFeatString();
     StringTokenizer aTok = new StringTokenizer(aString, "|", false);
     startLevel = Integer.parseInt(aTok.nextToken());
     rangeLevel = Integer.parseInt(aTok.nextToken());
     divisor = rangeLevel;
     if (divisor > 0) {
       StringBuilder aBuf = new StringBuilder("FEAT|PCPOOL|").append("max(CL");
       // Make sure we only take off the startlevel value once
       if (this == aPC.getClassKeyed(aPC.getLevelInfoClassKeyName(0))) {
         aBuf.append("-").append(startLevel);
         aBuf.append("+").append(rangeLevel);
       }
       aBuf.append(",0)/").append(divisor);
       //						Logging.debugPrint("Feat bonus for " + this + " is "
       //							+ aBuf.toString());
       BonusObj bon = Bonus.newBonus(Globals.getContext(), aBuf.toString());
       aPC.addBonus(bon, this);
     }
   }
 }
예제 #5
0
  /**
   * Get the unarmed Damage for this class at the given level.
   *
   * @param aLevel the given level.
   * @param aPC the PC with the level.
   * @param adjustForPCSize whether to adjust the result for the PC's size.
   * @return the unarmed damage string
   */
  String getUDamForEffLevel(int aLevel, final PlayerCharacter aPC, boolean adjustForPCSize) {
    int pcSize = adjustForPCSize ? aPC.sizeInt() : aPC.getDisplay().racialSizeInt();

    //
    // Check "Unarmed Strike", then default to "1d3"
    //
    String aDamage;

    AbstractReferenceContext ref = Globals.getContext().getReferenceContext();
    final Equipment eq =
        ref.silentlyGetConstructedCDOMObject(Equipment.class, "KEY_Unarmed Strike");

    if (eq != null) {
      aDamage = eq.getDamage(aPC);
    } else {
      aDamage = "1d3";
    }

    // resize the damage as if it were a weapon
    if (adjustForPCSize) {
      int defSize = SizeUtilities.getDefaultSizeAdjustment().get(IntegerKey.SIZEORDER);
      aDamage = Globals.adjustDamage(aDamage, defSize, pcSize);
    }

    //
    // Check the UDAM list for monk-like damage
    //
    List<CDOMObject> classObjects = new ArrayList<>();
    // Negative increment to start at highest level until an UDAM is found
    for (int i = aLevel; i >= 1; i--) {
      classObjects.add(aPC.getActiveClassLevel(this, i));
    }
    classObjects.add(this);
    for (CDOMObject cdo : classObjects) {
      List<String> udam = cdo.getListFor(ListKey.UNARMED_DAMAGE);
      if (udam != null) {
        if (udam.size() == 1) {
          aDamage = udam.get(0);
        } else {
          aDamage = udam.get(pcSize);
        }
        break;
      }
    }
    return aDamage;
  }
예제 #6
0
파일: Game.java 프로젝트: huayuxian/Game
  /** Perform the game update. */
  final void update() {
    boolean serverUpdateRequired = false;
    boolean movementChanged = player.updateMovement();
    if (movementChanged) {
      serverUpdateRequired = true;
    }
    // TODO: Other updates.

    if (serverUpdateRequired) {
      ClientMessage.GameData.Builder data = ClientMessage.GameData.newBuilder();
      if (moving) {
        data.setMovementInformation(
            ClientMessage.GameData.MovementInformation.newBuilder()
                .setDirection(player.getDirection())
                .build());
      }
      GameClientUtils.sendGameData(data.build());
    }
  }
예제 #7
0
 /**
  * returns all BonusObj's that are "active"
  *
  * @param pc TODO
  * @return active bonuses
  */
 @Override
 public List<BonusObj> getActiveBonuses(PlayerCharacter pc) {
   final List<BonusObj> aList = new ArrayList<>();
   for (BonusObj bonus : getBonuses()) {
     if (pc.isApplied(bonus)) {
       aList.add(bonus);
     }
   }
   return aList;
 }
예제 #8
0
 public int getSkillPointsForLevel(
     final PlayerCharacter aPC, PCClassLevel classLevel, int characterLevel) {
   // Update Skill Points. Modified 20 Nov 2002 by sage_sam
   // for bug #629643
   // final int spMod;
   int spMod = aPC.recalcSkillPointMod(this, characterLevel);
   if (classLevel.get(ObjectKey.DONTADD_SKILLPOINTS) != null) {
     spMod = 0;
   }
   return spMod;
 }
예제 #9
0
파일: BioSet.java 프로젝트: kidaa/pcgen
  private String generateBioValue(final String addKey, final PlayerCharacter pc) {
    final String line =
        getTokenNumberInMaps(
            addKey, 0, pc.getDisplay().getRegionString(), pc.getRace().getKeyName().trim());
    final String rv;

    if (line != null && line.length() > 0) {
      final StringTokenizer aTok = new StringTokenizer(line, "|");
      final List<String> aList = new ArrayList<String>();

      while (aTok.hasMoreTokens()) {
        aList.add(aTok.nextToken());
      }

      final int roll = RollingMethods.roll(1, aList.size()) - 1; // needs to be 0-offset
      rv = aList.get(roll);
    } else {
      rv = "";
    }

    return rv;
  }
예제 #10
0
파일: BioSet.java 프로젝트: kidaa/pcgen
  /**
   * Randomizes the values of the passed in attributes.
   *
   * @param randomizeStr .-delimited list of attributes to randomize. (AGE.HT.WT.EYES.HAIR.SKIN are
   *     the possible values.)
   * @param pc The Player Character
   */
  public void randomize(final String randomizeStr, final PlayerCharacter pc) {
    if ((pc == null) || (pc.getRace() == null)) {
      return;
    }

    final List<String> ranList = new ArrayList<String>();
    final StringTokenizer lineTok = new StringTokenizer(randomizeStr, ".", false);

    while (lineTok.hasMoreTokens()) {
      final String aString = lineTok.nextToken();

      if (aString.startsWith("AGECAT")) {
        generateAge(Integer.parseInt(aString.substring(6)), false, pc);
      } else {
        ranList.add(aString);
      }
    }

    if (ranList.contains("AGE")) {
      generateAge(0, true, pc);
    }

    if (ranList.contains("HT") || ranList.contains("WT")) {
      generateHeightWeight(pc);
    }

    if (ranList.contains("EYES")) {
      pc.setEyeColor(generateBioValue("EYES", pc));
    }

    if (ranList.contains("HAIR")) {
      pc.setHairColor(generateBioValue("HAIR", pc));
    }

    if (ranList.contains("SKIN")) {
      pc.setSkinColor(generateBioValue("SKINTONE", pc));
    }
  }
예제 #11
0
파일: BioSet.java 프로젝트: kidaa/pcgen
  private void generateHeightWeight(final PlayerCharacter pc) {
    int baseHeight = 0;
    int baseWeight = 0;
    int htAdd = 0;
    int wtAdd = 0;
    String totalWeight = null;
    final String htwt =
        getTokenNumberInMaps(
            "SEX", 0, pc.getDisplay().getRegionString(), pc.getRace().getKeyName().trim());

    if (htwt == null) {
      return;
    }

    final StringTokenizer genderTok = new StringTokenizer(htwt, "[]", false);

    while (genderTok.hasMoreTokens()) {
      if (genderTok.nextToken().equals(pc.getDisplay().getGenderObject().toString())) {
        final String htWtLine = genderTok.nextToken();
        final StringTokenizer htwtTok = new StringTokenizer(htWtLine, "|", false);

        while (htwtTok.hasMoreTokens()) {
          final String tag = htwtTok.nextToken();

          if (tag.startsWith("BASEHT:")) {
            baseHeight = Integer.parseInt(tag.substring(7));
          } else if (tag.startsWith("BASEWT:")) {
            baseWeight = Integer.parseInt(tag.substring(7));
          } else if (tag.startsWith("HTDIEROLL:")) {
            htAdd = RollingMethods.roll(tag.substring(10));
          } else if (tag.startsWith("WTDIEROLL:")) {
            wtAdd = RollingMethods.roll(tag.substring(10));
          } else if (tag.startsWith("TOTALWT:")) {
            totalWeight = tag.substring(8);
          }
        }

        if ((baseHeight != 0) && (htAdd != 0)) {
          pc.setHeight(baseHeight + htAdd);
        }

        if ((totalWeight != null) && (baseWeight != 0) && (wtAdd != 0)) {
          totalWeight = replaceString(totalWeight, "HTDIEROLL", htAdd);
          totalWeight = replaceString(totalWeight, "BASEWT", baseWeight);
          totalWeight = replaceString(totalWeight, "WTDIEROLL", wtAdd);
          pc.setWeight(pc.getVariableValue(totalWeight, "").intValue());
        }

        break;
      }
      genderTok.nextToken(); // burn next token
    }
  }
예제 #12
0
파일: Game.java 프로젝트: huayuxian/Game
 /** Render the game. */
 public final void render() {
   LOGGER.trace("Rendering game");
   // Camera
   camera.render(player);
   // Lighting
   ambientLight.render();
   //        terrain.render();
   for (Map.Entry<Integer, Structure> e : structures.entrySet()) {
     e.getValue().render();
   }
   for (Map.Entry<Integer, NPC> e : npcs.entrySet()) {
     e.getValue().render();
   }
   for (Map.Entry<Integer, OtherPlayerCharacter> e : otherPCs.entrySet()) {
     e.getValue().render();
   }
   player.render();
 }
예제 #13
0
  /*
   * REFACTOR This is BAD that this is referring to PCLevelInfo - that gets
   * VERY confusing as far as object interaction. Can we get rid of
   * PCLevelInfo altogether?
   */
  public final int getSkillPool(final PlayerCharacter aPC) {
    int returnValue = 0;
    // //////////////////////////////////
    // Using this method will return skills for level 0 even when there is
    // no information
    // Byngl - December 28, 2004
    // for (int i = 0; i <= level; i++)
    // {
    // final PCLevelInfo pcl = aPC.getLevelInfoFor(getKeyName(), i);
    //
    // if ((pcl != null) && pcl.getClassKeyName().equals(getKeyName()))
    // {
    // returnValue += pcl.getSkillPointsRemaining();
    // }
    // }
    for (PCLevelInfo pcl : aPC.getLevelInfo()) {
      if (pcl.getClassKeyName().equals(getKeyName())) {
        returnValue += pcl.getSkillPointsRemaining();
      }
    }
    // //////////////////////////////////

    return returnValue;
  }
예제 #14
0
 public void act(ArrayList<Entity> cargs) {
   PlayerCharacter pc = (PlayerCharacter) cargs.get(0);
   pc.setQuit();
 }
예제 #15
0
파일: Game.java 프로젝트: huayuxian/Game
 @Override
 public final void handleGameData(final ServerMessage.GameData data) {
   if (data.hasMovementInformation()) {
     player.handleMovement(data.getMovementInformation());
   }
 }
예제 #16
0
  void subLevel(final PlayerCharacter aPC) {

    if (aPC != null) {
      int total = aPC.getTotalLevels();

      int oldLevel = aPC.getLevel(this);
      int spMod = 0;
      final PCLevelInfo pcl = aPC.getLevelInfoFor(getKeyName(), oldLevel);

      if (pcl != null) {
        spMod = pcl.getSkillPointsGained(aPC);
      } else {
        Logging.errorPrint(
            "ERROR: could not find class/level info for " + getDisplayName() + "/" + oldLevel);
      }

      final int newLevel = oldLevel - 1;

      if (oldLevel > 0) {
        PCClassLevel classLevel = aPC.getActiveClassLevel(this, oldLevel - 1);
        aPC.removeHP(classLevel);
      }

      //			aPC.adjustFeats(-aPC.getBonusFeatsForNewLevel(this));
      setLevel(newLevel, aPC);
      aPC.removeKnownSpellsForClassLevel(this);

      doMinusLevelMods(aPC, newLevel + 1);

      DomainApplication.removeDomainsForLevel(this, newLevel + 1, aPC);

      if (newLevel == 0) {
        SubClassApplication.setSubClassKey(aPC, this, Constants.NONE);

        //
        // Remove all skills associated with this class
        //
        for (Skill skill : aPC.getSkillSet()) {
          SkillRankControl.setZeroRanks(this, aPC, skill);
        }

        Integer currentPool = aPC.getSkillPool(this);
        spMod = currentPool == null ? 0 : currentPool;
      }

      if (!isMonster() && (total > aPC.getTotalLevels())) {
        total = aPC.getTotalLevels();

        // Roll back any stat changes that were made as part of the
        // level

        final List<PCLevelInfoStat> moddedStats = new ArrayList<>();
        if (pcl.getModifiedStats(true) != null) {
          moddedStats.addAll(pcl.getModifiedStats(true));
        }
        if (pcl.getModifiedStats(false) != null) {
          moddedStats.addAll(pcl.getModifiedStats(false));
        }
        if (!moddedStats.isEmpty()) {
          for (PCLevelInfoStat statToRollback : moddedStats) {
            for (PCStat aStat : aPC.getStatSet()) {
              if (aStat.equals(statToRollback.getStat())) {
                aPC.setStat(aStat, aPC.getStat(aStat) - statToRollback.getStatMod());
                break;
              }
            }
          }
        }
      }

      aPC.setLevelWithoutConsequence(this, newLevel);

      if (isMonster() || (total != 0)) {
        Integer currentPool = aPC.getSkillPool(this);
        int newSkillPool = (currentPool == null ? 0 : currentPool) - spMod;
        aPC.setSkillPool(this, newSkillPool);
        aPC.setDirty(true);
      }

      if (aPC.getLevel(this) == 0) {
        aPC.removeClass(this);
      }

      aPC.validateCharacterDomains();

      if (!aPC.isImporting()) {
        final int maxxp = aPC.minXPForNextECL();
        if (aPC.getXP() >= maxxp) {
          aPC.setXP(Math.max(maxxp - 1, 0));
        }
      }
    } else {
      Logging.errorPrint("No current pc in subLevel()? How did this happen?");

      return;
    }
  }
예제 #17
0
 /*
  * DELETEMETHOD I hope this can be deleted, since minus level support will not
  * work the same way in the new PCClass/PCClassLevel world. If nothing else, it
  * is massively a REFACTOR item to put this into the PlayerCharacter that is
  * doing the removal.
  */
 void doMinusLevelMods(final PlayerCharacter aPC, final int oldLevel) {
   PCClassLevel pcl = aPC.getActiveClassLevel(this, oldLevel);
   CDOMObjectUtilities.removeAdds(pcl, aPC);
   CDOMObjectUtilities.restoreRemovals(pcl, aPC);
 }
예제 #18
0
  /*
   * REFACTOR Clearly this is part of the PCClass factory method that produces
   * PCClassLevels combined with some other work that will need to be done to
   * extract some of the complicated gunk out of here that goes out and puts
   * information into PCLevelInfo and PlayerCharacter.
   */
  public boolean addLevel(
      final boolean argLevelMax,
      final boolean bSilent,
      final PlayerCharacter aPC,
      final boolean ignorePrereqs) {

    // Check to see if we can add a level of this class to the
    // current character
    final int newLevel = aPC.getLevel(this) + 1;
    boolean levelMax = argLevelMax;

    aPC.setAllowInteraction(false);
    aPC.setLevelWithoutConsequence(this, newLevel);
    if (!ignorePrereqs) {
      // When loading a character, classes are added before feats, so
      // this test would always fail on loading if feats are required
      boolean doReturn = false;
      if (!qualifies(aPC, this)) {
        doReturn = true;
        if (!bSilent) {
          ShowMessageDelegate.showMessageDialog(
              "This character does not qualify for level " + newLevel,
              Constants.APPLICATION_NAME,
              MessageType.ERROR);
        }
      }
      aPC.setLevelWithoutConsequence(this, newLevel - 1);
      if (doReturn) {
        return false;
      }
    }
    aPC.setAllowInteraction(true);

    if (isMonster()) {
      levelMax = false;
    }

    if (hasMaxLevel() && (newLevel > getSafe(IntegerKey.LEVEL_LIMIT)) && levelMax) {
      if (!bSilent) {
        ShowMessageDelegate.showMessageDialog(
            "This class cannot be raised above level "
                + Integer.toString(getSafe(IntegerKey.LEVEL_LIMIT)),
            Constants.APPLICATION_NAME,
            MessageType.ERROR);
      }

      return false;
    }

    // Add the level to the current character
    int total = aPC.getTotalLevels();

    // No longer need this since the race now sets a bonus itself and Templates
    // are not able to reassign their feats.  There was nothing else returned in
    // this number
    //		if (total == 0) {
    //			aPC.setFeats(aPC.getInitialFeats());
    //		}
    setLevel(newLevel, aPC);

    // the level has now been added to the character,
    // so now assign the attributes of this class level to the
    // character...
    PCClassLevel classLevel = aPC.getActiveClassLevel(this, newLevel);

    // Make sure that if this Class adds a new domain that
    // we record where that domain came from
    final int dnum = aPC.getMaxCharacterDomains(this, aPC) - aPC.getDomainCount();

    if (dnum > 0 && !aPC.hasDefaultDomainSource()) {
      aPC.setDefaultDomainSource(new ClassSource(this, newLevel));
    }

    // Don't roll the hit points if the gui is not being used.
    // This is so GMGen can add classes to a person without pcgen flipping
    // out
    if (Globals.getUseGUI()) {
      final int levels =
          SettingsHandler.isHPMaxAtFirstClassLevel()
              ? aPC.totalNonMonsterLevels()
              : aPC.getTotalLevels();
      final boolean isFirst = levels == 1;

      aPC.rollHP(this, aPC.getLevel(this), isFirst);
    }

    if (!aPC.isImporting()) {
      DomainApplication.addDomainsUpToLevel(this, newLevel, aPC);
    }

    int levelUpStats = 0;

    // Add any bonus feats or stats that will be gained from this level
    // i.e. a bonus feat every 3 levels
    if (aPC.getTotalLevels() > total) {
      boolean processBonusStats = true;
      total = aPC.getTotalLevels();

      if (isMonster()) {
        // If we have less levels that the races monster levels
        // then we can not give a stat bonus (i.e. an Ogre has
        // 4 levels of Giant, so it does not get a stat increase at
        // 4th level because that is already taken into account in
        // its racial stat modifiers, but it will get one at 8th
        LevelCommandFactory lcf = aPC.getRace().get(ObjectKey.MONSTER_CLASS);
        int monLevels = 0;
        if (lcf != null) {
          monLevels = lcf.getLevelCount().resolve(aPC, "").intValue();
        }

        if (total <= monLevels) {
          processBonusStats = false;
        }
      }

      if (!aPC.isImporting()) {
        // We do not want to do these
        // calculations a second time when are
        // importing a character. The feat
        // number and the stat point pool are
        // already saved in the import file.

        // if (processBonusFeats) {
        //	final double bonusFeats = aPC.getBonusFeatsForNewLevel(this);
        //	if (bonusFeats > 0) {
        //		aPC.adjustFeats(bonusFeats);
        //	}
        // }

        if (processBonusStats) {
          final int bonusStats = Globals.getBonusStatsForLevel(total, aPC);
          if (bonusStats > 0) {
            aPC.setPoolAmount(aPC.getPoolAmount() + bonusStats);

            if (!bSilent && SettingsHandler.getShowStatDialogAtLevelUp()) {
              levelUpStats = StatApplication.askForStatIncrease(aPC, bonusStats, true);
            }
          }
        }
      }
    }

    int spMod = getSkillPointsForLevel(aPC, classLevel, total);

    PCLevelInfo pcl;

    if (aPC.getLevelInfoSize() > 0) {
      pcl = aPC.getLevelInfo(aPC.getLevelInfoSize() - 1);

      if (pcl != null) {
        pcl.setClassLevel(aPC.getLevel(this));
        pcl.setSkillPointsGained(aPC, spMod);
        pcl.setSkillPointsRemaining(pcl.getSkillPointsGained(aPC));
      }
    }

    Integer currentPool = aPC.getSkillPool(this);
    int newSkillPool = spMod + (currentPool == null ? 0 : currentPool);
    aPC.setSkillPool(this, newSkillPool);

    if (!aPC.isImporting()) {
      //
      // Ask for stat increase after skill points have been calculated
      //
      if (levelUpStats > 0) {
        StatApplication.askForStatIncrease(aPC, levelUpStats, false);
      }

      if (newLevel == 1) {
        AddObjectActions.doBaseChecks(this, aPC);
        CDOMObjectUtilities.addAdds(this, aPC);
        CDOMObjectUtilities.checkRemovals(this, aPC);
      }

      for (TransitionChoice<Kit> kit : classLevel.getSafeListFor(ListKey.KIT_CHOICE)) {
        kit.act(kit.driveChoice(aPC), classLevel, aPC);
      }
      TransitionChoice<Region> region = classLevel.get(ObjectKey.REGION_CHOICE);
      if (region != null) {
        region.act(region.driveChoice(aPC), classLevel, aPC);
      }
    }

    // this is a monster class, so don't worry about experience
    if (isMonster()) {
      return true;
    }

    if (!aPC.isImporting()) {
      CDOMObjectUtilities.checkRemovals(this, aPC);
      final int minxp = aPC.minXPForECL();
      if (aPC.getXP() < minxp) {
        aPC.setXP(minxp);
      } else if (aPC.getXP() >= aPC.minXPForNextECL()) {
        if (!bSilent) {
          ShowMessageDelegate.showMessageDialog(
              SettingsHandler.getGame().getLevelUpMessage(),
              Constants.APPLICATION_NAME,
              MessageType.INFORMATION);
        }
      }
    }

    //
    // Allow exchange of classes only when assign 1st level
    //
    if (containsKey(ObjectKey.EXCHANGE_LEVEL) && (aPC.getLevel(this) == 1) && !aPC.isImporting()) {
      ExchangeLevelApplication.exchangeLevels(aPC, this);
    }
    return true;
  }
예제 #19
0
파일: BioSet.java 프로젝트: kidaa/pcgen
  private void generateAge(
      final int ageCategory, final boolean useClassOnly, final PlayerCharacter pc) {
    // Can't find a base age for the category,
    // then there's nothing to do
    final String age =
        getTokenNumberInMaps(
            "BASEAGE",
            ageCategory,
            pc.getDisplay().getRegionString(),
            pc.getRace().getKeyName().trim());

    if (age == null) {
      return;
    }

    // First check for class age modification information
    final int baseAge = Integer.parseInt(age);
    int ageAdd = -1;

    String aClass =
        getTokenNumberInMaps(
            "CLASS",
            ageCategory,
            pc.getDisplay().getRegionString(),
            pc.getRace().getKeyName().trim());

    if (aClass != null && !aClass.equals("0")) {
      // aClass looks like:
      // Barbarian,Rogue,Sorcerer[BASEAGEADD:3d6]|Bard,Fighter,Paladin,Ranger[BASEAGEADD:1d6]
      // So first, get the BASEAGEADD
      final StringTokenizer aTok = new StringTokenizer(aClass, "|");

      while (aTok.hasMoreTokens()) {
        // String looks like:
        // Barbarian,Rogue,Sorcerer[BASEAGEADD:3d6]
        String aString = aTok.nextToken();

        final int start = aString.indexOf("[");
        final int end = aString.indexOf("]");

        // should be BASEAGEADD:xdy
        String dieString = aString.substring(start + 1, end);

        if (dieString.startsWith("BASEAGEADD:")) {
          dieString = dieString.substring(11);
        }

        // Remove the dieString
        aString = aString.substring(0, start);

        final StringTokenizer bTok = new StringTokenizer(aString, ",");

        while (bTok.hasMoreTokens() && (ageAdd < 0)) {
          final String tClass = bTok.nextToken();

          if (pc.getClassKeyed(tClass) != null) {
            ageAdd = RollingMethods.roll(dieString);
          }
        }
      }
    }

    // If there was no class age modification,
    // then generate a number based on the .LST
    if ((ageAdd < 0) && !useClassOnly) {
      aClass =
          getTokenNumberInMaps(
              "AGEDIEROLL",
              ageCategory,
              pc.getDisplay().getRegionString(),
              pc.getRace().getKeyName().trim());

      if (aClass != null) {
        ageAdd = RollingMethods.roll(aClass);
      }
    }

    if ((ageAdd >= 0) && (baseAge > 0)) {
      final String maxage =
          getTokenNumberInMaps(
              "MAXAGE",
              ageCategory,
              pc.getDisplay().getRegionString(),
              pc.getRace().getKeyName().trim());
      if (maxage != null) {
        final int maxAge = Integer.parseInt(maxage);
        if (baseAge + ageAdd > maxAge) {
          ageAdd = maxAge - baseAge;
        }
      }
      pc.setAge(baseAge + ageAdd);
    }
  }
예제 #20
0
  /*
   * REFACTOR There is potentially redundant information here - level and PC...
   * is this ever out of sync or can this method be removed/made private??
   */
  public double getBonusTo(
      final String argType, final String argMname, final int asLevel, final PlayerCharacter aPC) {
    double i = 0;

    List<BonusObj> rawBonusList = getRawBonusList(aPC);

    for (int lvl = 1; lvl < asLevel; lvl++) {
      rawBonusList.addAll(aPC.getActiveClassLevel(this, lvl).getRawBonusList(aPC));
    }
    if ((asLevel == 0) || rawBonusList.isEmpty()) {
      return 0;
    }

    final String type = argType.toUpperCase();
    final String mname = argMname.toUpperCase();

    for (final BonusObj bonus : rawBonusList) {
      final StringTokenizer breakOnPipes =
          new StringTokenizer(bonus.toString().toUpperCase(), Constants.PIPE, false);
      final String theType = breakOnPipes.nextToken();

      if (!theType.equals(type)) {
        continue;
      }

      final String str = breakOnPipes.nextToken();
      final StringTokenizer breakOnCommas = new StringTokenizer(str, Constants.COMMA, false);

      while (breakOnCommas.hasMoreTokens()) {
        final String theName = breakOnCommas.nextToken();

        if (theName.equals(mname)) {
          final String aString = breakOnPipes.nextToken();
          final List<Prerequisite> localPreReqList = new ArrayList<>();
          if (bonus.hasPrerequisites()) {
            localPreReqList.addAll(bonus.getPrerequisiteList());
          }

          // TODO: This code should be removed after the 5.8 release
          // as the prereqs are processed by the bonus loading code.
          while (breakOnPipes.hasMoreTokens()) {
            final String bString = breakOnPipes.nextToken();

            if (PreParserFactory.isPreReqString(bString)) {
              Logging.debugPrint(
                  "Why is this prerequisite '"
                      + bString
                      + "' parsed in '"
                      + getClass().getName()
                      + ".getBonusTo(String,String,int)' rather than in the persistence layer?"); //$NON-NLS-1$ //$NON-NLS-2$//$NON-NLS-3$
              try {
                final PreParserFactory factory = PreParserFactory.getInstance();
                localPreReqList.add(factory.parse(bString));
              } catch (PersistenceLayerException ple) {
                Logging.errorPrint(ple.getMessage(), ple);
              }
            }
          }

          // must meet criteria for bonuses before adding them in
          // TODO: This is a hack to avoid VARs etc in class defs
          // being qualified for when Bypass class prereqs is
          // selected.
          // Should we be passing in the BonusObj here to allow it to
          // be referenced in Qualifies statements?
          if (PrereqHandler.passesAll(localPreReqList, aPC, null)) {
            final double j = aPC.getVariableValue(aString, getQualifiedKey()).doubleValue();
            i += j;
          }
        }
      }
    }

    return i;
  }
예제 #21
0
  @Override
  public void makeRaceChoices(PlayerCharacter pc, DndClass dndClass) {
    Utils.print(
        "What is your character's name? From the book it suggests the following male and female names:");
    Utils.print(
        "Male Names: Alston, Alvyn, Brocc, Eldon, Frug, Kellen, Ku, Nim, Orryn, Pock, Sindri, Warryn, Wrenn");
    Utils.print(
        "Female Names: Breena, Carlin, Donella, Ella, Lilli, Lorilla, Nissa, Nyx, Oda, Orla, Roswyn, Tana, Zanna");
    Utils.print("Your name?");
    pc.setName(Utils.getInput());

    Utils.print("What Height is your character?  The book suggests 3' 4\" - 3' 8\" (40\" - 48\")");
    Utils.print("Your choice (in inches):");
    pc.setHeight(Utils.getValidIntInputInRange(0, 200));

    Utils.print("What Weight is your character?  The book suggests 50 - 75 lb");
    Utils.print("Your choice (in pounds):");
    pc.setWeight(Utils.getValidIntInputInRange(0, 1000));

    Utils.print("Setting size to Small.");
    pc.setSize(Size.SMALL);

    Utils.print("Setting speed to 5.");
    pc.setBaseSpeed(5);

    Utils.print("Adding low-light vision to senses.");
    pc.addSense(new Sense(SenseType.LOWLIGHT_VISION));

    pc.addLanguage("Common");
    pc.addLanguage("Elven");

    Utils.print("As a Gnome, you get +2 Arcana and Stealth");
    Skill arcana = pc.getSkill(SkillType.ARCANA);
    arcana.setMisc(arcana.getMisc() + 2);

    Skill stealth = pc.getSkill(SkillType.STEALTH);
    stealth.setMisc(stealth.getMisc() + 2);

    pc.addPower(new FadeAway());

    pc.setOrigin(Origin.FEY);

    // TODO: Master Trickster, Reactive Stealth, Trickster's Cunning.
    Utils.print(
        "NOTE: I have not yet coded Master Trickster, Reactive Stealth, Trickster's Cunning.");
  }
예제 #22
0
 /**
  * Sets all the BonusObj's to "active"
  *
  * @param aPC
  */
 @Override
 public void activateBonuses(final PlayerCharacter aPC) {
   for (BonusObj bonus : getBonuses()) {
     aPC.setApplied(bonus, bonus.qualifies(aPC, null));
   }
 }
예제 #23
0
 /**
  * Get the unarmed Damage for this class at the given level.
  *
  * @param aLevel the given level.
  * @param aPC the PC with the level.
  * @param adjustForPCSize whether to adjust the result for the PC's size.
  * @return the unarmed damage string
  */
 public String getUdamForLevel(int aLevel, final PlayerCharacter aPC, boolean adjustForPCSize) {
   aLevel += (int) aPC.getTotalBonusTo("UDAM", "CLASS." + getKeyName());
   return getUDamForEffLevel(aLevel, aPC, adjustForPCSize);
 }
예제 #24
0
 /**
  * Sends the statistics of the given character to the client.
  *
  * @param task the task for this action
  * @param character the character who's statistics will be sent
  */
 public void sendCharacter(PlayerCharacter character) {
   Messages.sendCharacter(
       character.getID(), character.getStatistics(),
       channel(), getCurrentSession());
 }
 public void draw(PositionData p) {
   glPushMatrix();
   glTranslatef(p.getTranslate_x(), p.getTranslate_y(), 0);
   drawQuadTex(character.getTexture(), x, y, width, height);
   glPopMatrix();
 }