Search in sources :

Example 1 with PCLevelInfo

use of pcgen.core.pclevelinfo.PCLevelInfo in project pcgen by PCGen.

the class CharacterLevelsFacadeImpl method refreshClassList.

/**
	 * Update the list of class levels from scratch to match the current
	 * state of the character. 
	 */
private void refreshClassList() {
    List<PCClass> newClasses = charDisplay.getClassList();
    Collection<PCLevelInfo> levelInfo = charDisplay.getLevelInfo();
    Map<String, Integer> levelCount = new HashMap<>();
    Map<String, PCClass> classMap = new HashMap<>();
    for (PCClass pcClass : newClasses) {
        levelCount.put(pcClass.getKeyName(), 1);
        classMap.put(pcClass.getKeyName(), pcClass);
    }
    classLevels.clear();
    clearContents();
    for (PCLevelInfo lvlInfo : levelInfo) {
        final String classKeyName = lvlInfo.getClassKeyName();
        PCClass currClass = classMap.get(classKeyName);
        if (currClass == null) {
            Logging.errorPrint("No PCClass found for '" + classKeyName + "' in character's class list: " + newClasses);
            return;
        }
        int clsLvlNum = levelCount.get(classKeyName);
        levelCount.put(classKeyName, clsLvlNum + 1);
        classLevels.add(currClass);
        CharacterLevelFacadeImpl levelFI = new CharacterLevelFacadeImpl(currClass, classLevels.size());
        addElement(levelFI);
    //PCClassLevel classLevel = currClass.getClassLevel(clsLvlNum);
    }
    updateSkillsTodo();
}
Also used : HashMap(java.util.HashMap) PCLevelInfo(pcgen.core.pclevelinfo.PCLevelInfo) PCClass(pcgen.core.PCClass)

Example 2 with PCLevelInfo

use of pcgen.core.pclevelinfo.PCLevelInfo in project pcgen by PCGen.

the class ClassSkillChoiceActor method applyChoice.

/**
	 * Applies the given Skill choice to the given PlayerCharacter. The given
	 * Skill is added as a class skill for the PCClass provided during
	 * construction of this ClassSkillChoiceActor. If the number of ranks
	 * provided during construction of this ClassSkillChoiceActor was not null
	 * or zero, then ranks are also applied to the given skill.
	 * 
	 * @param owner
	 *            The owning object for this choice.
	 * @param choice
	 *            The Skill which should be added as a Class Skill for the
	 *            PCClass provided during construction of this
	 *            ClassSkillChoiceActor
	 * @param pc
	 *            The PlayerCharacter to which the changes driven by this
	 *            ClassSkillChoiceActor should be applied.
	 */
@Override
public void applyChoice(CDOMObject owner, Skill choice, PlayerCharacter pc) {
    PCClass pcc = getSourceClass(pc);
    if (pcc == null) {
        Logging.errorPrint("Unable to find the pc's class " + source + " to apply skill choices to.");
        return;
    }
    pc.addLocalCost(pcc, choice, SkillCost.CLASS, owner);
    if (applyRank != null) {
        if (owner instanceof PCClassLevel) {
            // Ensure that the skill points for this level are already calculated.
            PCClassLevel classLevel = (PCClassLevel) owner;
            PCClass pcClass = (PCClass) classLevel.getSafe(ObjectKey.PARENT);
            int levelIndex = 1;
            for (PCLevelInfo lvlInfo : pc.getLevelInfo()) {
                if (lvlInfo.getClassKeyName() == pcClass.getKeyName() && lvlInfo.getClassLevel() == classLevel.getSafe(IntegerKey.LEVEL)) {
                    pc.checkSkillModChangeForLevel(pcClass, lvlInfo, classLevel, levelIndex++);
                    break;
                }
            }
        }
        String result = SkillRankControl.modRanks(applyRank, pcc, false, pc, choice);
        if (StringUtils.isNotEmpty(result)) {
            Logging.errorPrint("Unable to apply {0} ranks of {1}. Error: {2}", applyRank, choice, result);
        }
    }
}
Also used : PCLevelInfo(pcgen.core.pclevelinfo.PCLevelInfo) PCClass(pcgen.core.PCClass) PCClassLevel(pcgen.cdom.inst.PCClassLevel)

Example 3 with PCLevelInfo

use of pcgen.core.pclevelinfo.PCLevelInfo in project pcgen by PCGen.

the class MonsterClassFacet method dataAdded.

/**
	 * Adds monster classes to the Player Character when a CDOMObject which
	 * grants monster classes is added to the Player Character.
	 * 
	 * Triggered when one of the Facets to which MonsterClassFacet listens fires
	 * a DataFacetChangeEvent to indicate a CDOMObject was added to a Player
	 * Character.
	 * 
	 * @param dfce
	 *            The DataFacetChangeEvent containing the information about the
	 *            change
	 * 
	 * @see pcgen.cdom.facet.event.DataFacetChangeListener#dataAdded(pcgen.cdom.facet.event.DataFacetChangeEvent)
	 */
@Override
public void dataAdded(DataFacetChangeEvent<CharID, CDOMObject> dfce) {
    CharID id = dfce.getCharID();
    CDOMObject cdo = dfce.getCDOMObject();
    // Get existing classes
    ClassInfo ci = classFacet.removeAllClasses(id);
    //
    for (int i = levelInfoFacet.getCount(id) - 1; i >= 0; --i) {
        PCLevelInfo pli = levelInfoFacet.get(id, i);
        final String classKeyName = pli.getClassKeyName();
        final PCClass aClass = Globals.getContext().getReferenceContext().silentlyGetConstructedCDOMObject(PCClass.class, classKeyName);
        if (aClass.isMonster()) {
            levelInfoFacet.remove(id, pli);
        }
    }
    PlayerCharacter pc = trackingFacet.getPC(id);
    final List<PCLevelInfo> existingLevelInfo = new ArrayList<>(levelInfoFacet.getSet(id));
    levelInfoFacet.removeAll(id);
    // Make sure monster classes are added first
    if (!pc.isImporting()) {
        LevelCommandFactory lcf = cdo.get(ObjectKey.MONSTER_CLASS);
        if (lcf != null) {
            int levelCount = formulaResolvingFacet.resolve(id, lcf.getLevelCount(), "").intValue();
            pc.incrementClassLevel(levelCount, lcf.getPCClass(), true);
        }
    }
    levelInfoFacet.addAll(id, existingLevelInfo);
    //
    if (!pc.isImporting() && ci != null && !ci.isEmpty()) {
        int totalLevels = levelFacet.getTotalLevels(id);
        for (PCClass pcClass : ci.getClassSet()) {
            //
            if (!pcClass.isMonster()) {
                classFacet.addClass(id, pcClass);
                int cLevels = ci.getLevel(pcClass);
                classFacet.setLevel(id, pcClass, cLevels);
                pc.setSkillPool(pcClass, 0);
                int cMod = 0;
                for (int j = 0; j < cLevels; ++j) {
                    cMod += pc.recalcSkillPointMod(pcClass, ++totalLevels);
                }
                pc.setSkillPool(pcClass, cMod);
            }
        }
    }
}
Also used : PlayerCharacter(pcgen.core.PlayerCharacter) LevelCommandFactory(pcgen.cdom.content.LevelCommandFactory) CDOMObject(pcgen.cdom.base.CDOMObject) ArrayList(java.util.ArrayList) PCLevelInfo(pcgen.core.pclevelinfo.PCLevelInfo) PCClass(pcgen.core.PCClass) CharID(pcgen.cdom.enumeration.CharID) ClassInfo(pcgen.cdom.facet.model.ClassFacet.ClassInfo)

Example 4 with PCLevelInfo

use of pcgen.core.pclevelinfo.PCLevelInfo in project pcgen by PCGen.

the class PCGVer2Parser method parseClassLine.

/*
	 * ###############################################################
	 * Character Class(es) methods
	 * ###############################################################
	 */
private void parseClassLine(final String line) throws PCGParseException {
    final PCGTokenizer tokens;
    try {
        tokens = new PCGTokenizer(line);
    } catch (PCGParseException pcgpex) {
        /*
			 * Classes are critical for characters,
			 * need to stop the load process
			 *
			 * Thomas Behr 14-08-02
			 */
        throw new PCGParseException("parseClassLine", line, //$NON-NLS-1$
        pcgpex.getMessage());
    }
    PCClass aPCClass = null;
    String tag;
    PCGElement element;
    final Iterator<PCGElement> it = tokens.getElements().iterator();
    // the first element defines the class key name!!!
    if (it.hasNext()) {
        element = it.next();
        String classKey = EntityEncoder.decode(element.getText());
        // First check for an existing class, say from a racial casting ability
        aPCClass = thePC.getClassKeyed(classKey);
        if (aPCClass == null) {
            aPCClass = Globals.getContext().getReferenceContext().silentlyGetConstructedCDOMObject(PCClass.class, classKey);
            if (aPCClass != null) {
                // Icky: Need to redesign the way classes work!
                // Icky: Having to clone the class here is UGLY!
                aPCClass = aPCClass.clone();
            } else {
                final String msg = LanguageBundle.getFormattedString(//$NON-NLS-1$
                "Warnings.PCGenParser.CouldntAddClass", element.getText());
                warnings.add(msg);
                return;
            }
        }
    }
    int level = -1;
    int skillPool = -1;
    String subClassKey = Constants.NONE;
    while (it.hasNext()) {
        element = it.next();
        tag = element.getName();
        if (IOConstants.TAG_SUBCLASS.equals(tag)) {
            subClassKey = EntityEncoder.decode(element.getText());
            if ((!subClassKey.isEmpty()) && !subClassKey.equals(Constants.NONE)) {
                SubClass sc = aPCClass.getSubClassKeyed(subClassKey);
                if (sc == null) {
                    if (subClassKey.equals(aPCClass.getKeyName())) {
                        subClassKey = Constants.NONE;
                    } else {
                        final String msg = LanguageBundle.getFormattedString(//$NON-NLS-1$
                        "Warnings.PCGenParser.InvalidSubclass", element.getText());
                        warnings.add(msg);
                    }
                }
            }
        }
        if (IOConstants.TAG_LEVEL.equals(tag)) {
            try {
                level = Integer.parseInt(element.getText());
            } catch (NumberFormatException nfe) {
                final String msg = LanguageBundle.getFormattedString(//$NON-NLS-1$
                "Warnings.PCGenParser.InvalidLevel", element.getText());
                warnings.add(msg);
            }
        } else if (IOConstants.TAG_SKILLPOOL.equals(tag)) {
            try {
                skillPool = Integer.parseInt(element.getText());
            } catch (NumberFormatException nfe) {
                final String msg = LanguageBundle.getFormattedString(//$NON-NLS-1$
                "Warnings.PCGenParser.InvalidSkillPool", element.getText());
                warnings.add(msg);
            }
        } else if (IOConstants.TAG_CANCASTPERDAY.equals(tag)) {
        // TODO
        } else if (IOConstants.TAG_SPELLBASE.equals(tag)) {
            final String spellBase = EntityEncoder.decode(element.getText());
            if (!Constants.NONE.equals(spellBase)) {
                Globals.getContext().unconditionallyProcess(aPCClass, "SPELLSTAT", spellBase);
            }
        } else if (IOConstants.TAG_PROHIBITED.equals(tag)) {
            String prohib = EntityEncoder.decode(element.getText());
            StringTokenizer st = new StringTokenizer(prohib, Constants.COMMA);
            while (st.hasMoreTokens()) {
                String choice = st.nextToken();
                if (!"None".equalsIgnoreCase(choice)) {
                    SpellProhibitor prohibSchool = new SpellProhibitor();
                    prohibSchool.setType(ProhibitedSpellType.SCHOOL);
                    prohibSchool.addValue(choice);
                    SpellProhibitor prohibSubSchool = new SpellProhibitor();
                    prohibSubSchool.setType(ProhibitedSpellType.SUBSCHOOL);
                    prohibSubSchool.addValue(choice);
                    thePC.addProhibitedSchool(prohibSchool, aPCClass);
                    thePC.addProhibitedSchool(prohibSubSchool, aPCClass);
                }
            }
        }
    }
    if (level > -1) {
        thePC.addClass(aPCClass);
        if (StringUtils.isNotBlank(subClassKey) && !subClassKey.equals(Constants.NONE)) {
            SubClassApplication.setSubClassKey(thePC, aPCClass, subClassKey);
        }
        for (int i = 0; i < level; ++i) {
            PCLevelInfo levelInfo = thePC.addLevelInfo(aPCClass.getKeyName());
            aPCClass.addLevel(false, false, thePC, true);
        }
    }
    //Must process ADD after CLASS is added to the PC
    for (PCGElement e : new PCGTokenizer(line).getElements()) {
        tag = e.getName();
        if (tag.equals(IOConstants.TAG_ADDTOKEN)) {
            parseAddTokenInfo(e, aPCClass);
        }
    }
    if (skillPool > -1) {
        thePC.setSkillPool(aPCClass, skillPool);
    }
}
Also used : SubClass(pcgen.core.SubClass) StringTokenizer(java.util.StringTokenizer) PCLevelInfo(pcgen.core.pclevelinfo.PCLevelInfo) PCClass(pcgen.core.PCClass) SpellProhibitor(pcgen.core.SpellProhibitor)

Example 5 with PCLevelInfo

use of pcgen.core.pclevelinfo.PCLevelInfo in project pcgen by PCGen.

the class PCGVer2Creator method appendClassLines.

/*
	 * ###############################################################
	 * Character Class(es) methods
	 * ###############################################################
	 */
private void appendClassLines(StringBuilder buffer) {
    Cache specials = new Cache();
    for (PCClass pcClass : charDisplay.getClassSet()) {
        int classLevel = charDisplay.getLevel(pcClass);
        buffer.append(IOConstants.TAG_CLASS).append(':');
        buffer.append(EntityEncoder.encode(pcClass.getKeyName()));
        final String subClassKey = charDisplay.getSubClassName(pcClass);
        if (subClassKey != null && !Constants.EMPTY_STRING.equals(subClassKey)) {
            buffer.append('|');
            buffer.append(IOConstants.TAG_SUBCLASS).append(':');
            buffer.append(EntityEncoder.encode(subClassKey));
        }
        buffer.append('|');
        buffer.append(IOConstants.TAG_LEVEL).append(':');
        buffer.append(classLevel);
        buffer.append('|');
        buffer.append(IOConstants.TAG_SKILLPOOL).append(':');
        Integer currentPool = thePC.getSkillPool(pcClass);
        buffer.append(currentPool == null ? 0 : currentPool);
        // determine if this class can cast spells
        boolean isCaster = false;
        if (!thePC.getSpellSupport(pcClass).canCastSpells(thePC)) {
            isCaster = true;
        }
        boolean isPsionic = thePC.getSpellSupport(pcClass).hasKnownList() && !isCaster;
        if (isCaster || isPsionic) {
            buffer.append('|');
            buffer.append(IOConstants.TAG_SPELLBASE).append(':');
            buffer.append(EntityEncoder.encode(pcClass.getSpellBaseStat()));
            buffer.append('|');
            buffer.append(IOConstants.TAG_CANCASTPERDAY).append(':');
            buffer.append(StringUtil.join(thePC.getSpellSupport(pcClass).getCastListForLevel(classLevel), ","));
        }
        Collection<? extends SpellProhibitor> prohib = charDisplay.getProhibitedSchools(pcClass);
        if (prohib != null) {
            Set<String> set = new TreeSet<>();
            for (SpellProhibitor sp : prohib) {
                set.addAll(sp.getValueList());
            }
            if (!set.isEmpty()) {
                buffer.append('|');
                buffer.append(IOConstants.TAG_PROHIBITED).append(':');
                buffer.append(EntityEncoder.encode(StringUtil.join(set, ",")));
            }
        }
        appendAddTokenInfo(buffer, pcClass);
        buffer.append(IOConstants.LINE_SEP);
        String spec = thePC.getAssoc(pcClass, AssociationKey.SPECIALTY);
        if (spec != null) {
            specials.put(pcClass.getKeyName() + IOConstants.TAG_SPECIALTY + '0', spec);
        }
        String key;
        key = pcClass.getKeyName() + IOConstants.TAG_SAVE + '0';
        List<? extends SpecialAbility> salist = charDisplay.getUserSpecialAbilityList(pcClass);
        if (salist != null && !salist.isEmpty()) {
            SpecialAbility sa = salist.get(0);
            specials.put(pcClass.getKeyName() + IOConstants.TAG_SA + 0, sa.getKeyName());
        }
        for (BonusObj save : thePC.getSaveableBonusList(pcClass)) {
            specials.put(key, "BONUS|" + save);
        }
        for (int i = 1; i <= charDisplay.getLevel(pcClass); i++) {
            key = pcClass.getKeyName() + IOConstants.TAG_SAVE + (i - 1);
            PCClassLevel pcl = charDisplay.getActiveClassLevel(pcClass, i);
            for (BonusObj save : thePC.getSaveableBonusList(pcl)) {
                specials.put(key, "BONUS|" + save);
            }
        }
    }
    //
    for (PCLevelInfo pcl : charDisplay.getLevelInfo()) {
        final String classKeyName = pcl.getClassKeyName();
        int lvl = pcl.getClassLevel() - 1;
        PCClass pcClass = thePC.getClassKeyed(classKeyName);
        buffer.append(IOConstants.TAG_CLASSABILITIESLEVEL).append(':');
        if (pcClass == null) {
            pcClass = Globals.getContext().getReferenceContext().silentlyGetConstructedCDOMObject(PCClass.class, classKeyName);
            if (pcClass != null) {
                pcClass = thePC.getClassKeyed(pcClass.get(ObjectKey.EX_CLASS).get().getKeyName());
            }
        }
        if (pcClass != null) {
            buffer.append(EntityEncoder.encode(pcClass.getKeyName()));
        } else {
            //$NON-NLS-1$
            buffer.append(EntityEncoder.encode("???"));
        }
        buffer.append('=').append(lvl + 1);
        if (pcClass != null) {
            String aKey = charDisplay.getSubstitutionClassName(charDisplay.getActiveClassLevel(pcClass, lvl + 1));
            if (aKey != null) {
                buffer.append('|');
                buffer.append(IOConstants.TAG_SUBSTITUTIONLEVEL).append(':');
                buffer.append(aKey);
            }
            buffer.append('|');
            buffer.append(IOConstants.TAG_HITPOINTS).append(':');
            PCClassLevel classLevel = charDisplay.getActiveClassLevel(pcClass, lvl);
            Integer hp = charDisplay.getHP(classLevel);
            buffer.append(hp == null ? 0 : hp);
            appendSpecials(buffer, specials.get(pcClass.getKeyName() + IOConstants.TAG_SAVE + lvl), IOConstants.TAG_SAVES, IOConstants.TAG_SAVE, lvl);
            appendSpecials(buffer, specials.get(pcClass.getKeyName() + IOConstants.TAG_SPECIALTY + lvl), IOConstants.TAG_SPECIALTIES, IOConstants.TAG_SPECIALTY, lvl);
            appendSpecials(buffer, specials.get(pcClass.getKeyName() + IOConstants.TAG_SA + lvl), IOConstants.TAG_SPECIALABILITIES, IOConstants.TAG_SA, lvl);
            if (lvl == 0) {
                appendSpecials(buffer, specials.get(pcClass.getKeyName() + IOConstants.TAG_SA + (lvl - 1)), IOConstants.TAG_SPECIALABILITIES, IOConstants.TAG_SA, -1);
            }
            //
            // Remember what choices were made for each of the ADD: tags
            //
            appendAddTokenInfo(buffer, charDisplay.getActiveClassLevel(pcClass, lvl + 1));
        }
        List<PCLevelInfoStat> statList = pcl.getModifiedStats(true);
        if (statList != null) {
            for (PCLevelInfoStat stat : statList) {
                buffer.append('|').append(IOConstants.TAG_PRESTAT).append(':').append(stat.toString());
            }
        }
        statList = pcl.getModifiedStats(false);
        if (statList != null) {
            for (PCLevelInfoStat stat : statList) {
                buffer.append('|').append(IOConstants.TAG_PRESTAT).append(':').append(stat.toString());
            }
        }
        int sp = pcl.getSkillPointsGained(thePC);
        //if (sp != 0)
        {
            buffer.append('|').append(IOConstants.TAG_SKILLPOINTSGAINED).append(':').append(sp);
        }
        sp = pcl.getSkillPointsRemaining();
        //if (sp != 0)
        {
            buffer.append('|').append(IOConstants.TAG_SKILLPOINTSREMAINING).append(':').append(sp);
        }
        buffer.append(IOConstants.LINE_SEP);
    }
}
Also used : PCLevelInfoStat(pcgen.core.pclevelinfo.PCLevelInfoStat) BonusObj(pcgen.core.bonus.BonusObj) SpecialAbility(pcgen.core.SpecialAbility) PCClass(pcgen.core.PCClass) SpellProhibitor(pcgen.core.SpellProhibitor) PCClassLevel(pcgen.cdom.inst.PCClassLevel) TreeSet(java.util.TreeSet) PCLevelInfo(pcgen.core.pclevelinfo.PCLevelInfo)

Aggregations

PCLevelInfo (pcgen.core.pclevelinfo.PCLevelInfo)33 PCClass (pcgen.core.PCClass)11 PCClassLevel (pcgen.cdom.inst.PCClassLevel)9 ArrayList (java.util.ArrayList)5 HashMap (java.util.HashMap)3 Skill (pcgen.core.Skill)3 StringTokenizer (java.util.StringTokenizer)2 CDOMObject (pcgen.cdom.base.CDOMObject)2 LevelCommandFactory (pcgen.cdom.content.LevelCommandFactory)2 ClassSource (pcgen.cdom.helper.ClassSource)2 Language (pcgen.core.Language)2 PlayerCharacter (pcgen.core.PlayerCharacter)2 SpecialAbility (pcgen.core.SpecialAbility)2 SpellProhibitor (pcgen.core.SpellProhibitor)2 BonusObj (pcgen.core.bonus.BonusObj)2 PCLevelInfoStat (pcgen.core.pclevelinfo.PCLevelInfoStat)2 BigDecimal (java.math.BigDecimal)1 TreeSet (java.util.TreeSet)1 Test (org.junit.Test)1 HitDie (pcgen.cdom.content.HitDie)1