/* * Copyright (c) 1998-2017 by Richard A. Wilkes. All rights reserved. * * This Source Code Form is subject to the terms of the Mozilla Public * License, version 2.0. If a copy of the MPL was not distributed with * this file, You can obtain one at http://mozilla.org/MPL/2.0/. * * This Source Code Form is "Incompatible With Secondary Licenses", as * defined by the Mozilla Public License, version 2.0. */ package com.trollworks.gcs.prereq; import com.trollworks.gcs.character.GURPSCharacter; import com.trollworks.gcs.criteria.IntegerCriteria; import com.trollworks.gcs.criteria.StringCompareType; import com.trollworks.gcs.criteria.StringCriteria; import com.trollworks.gcs.skill.Skill; import com.trollworks.gcs.widgets.outline.ListRow; import com.trollworks.toolkit.annotation.Localize; import com.trollworks.toolkit.io.xml.XMLReader; import com.trollworks.toolkit.io.xml.XMLWriter; import com.trollworks.toolkit.utility.Localization; import java.io.IOException; import java.text.MessageFormat; import java.util.HashMap; import java.util.HashSet; /** A Skill prerequisite. */ public class SkillPrereq extends NameLevelPrereq { @Localize("{0}{1} a skill whose name {2}") @Localize(locale = "de", value = "{0}{1} eine Fertigkeit, deren Name {2}") @Localize(locale = "ru", value = "{0}{1} умение с названием {2}") @Localize(locale = "es", value = "{0}{1} una habilidad cuyo nombre es {2}") private static String SKILL_NAME_PART; @Localize(", specialization {0},") @Localize(locale = "de", value = ", Spezialisierung {0},") @Localize(locale = "ru", value = ", специализация {0},") @Localize(locale = "es", value = ", especialización {0},") private static String SPECIALIZATION_PART; @Localize(" and level {0}") @Localize(locale = "de", value = " und Fertigkeitswert {0}") @Localize(locale = "ru", value = " и уровень {0}\n ") @Localize(locale = "es", value = " y nivel {0}") private static String LEVEL_PART; @Localize(" level {0} and tech level matches\n") @Localize(locale = "de", value = " Fertigkeitswert {0} und Techlevel stimmt überein") @Localize(locale = "ru", value = " уровень {0} и ТУ совпадают\n") @Localize(locale = "es", value = " nivel {0} y nivel tecnológico coincidente\n") private static String LEVEL_AND_TL_PART; static { Localization.initialize(); } /** The XML tag for this class. */ public static final String TAG_ROOT = "skill_prereq"; //$NON-NLS-1$ private static final String TAG_SPECIALIZATION = "specialization"; //$NON-NLS-1$ private StringCriteria mSpecializationCriteria; /** * Creates a new prerequisite. * * @param parent The owning prerequisite list, if any. */ public SkillPrereq(PrereqList parent) { super(TAG_ROOT, parent); mSpecializationCriteria = new StringCriteria(StringCompareType.IS_ANYTHING, ""); //$NON-NLS-1$ } /** * Loads a prerequisite. * * @param parent The owning prerequisite list, if any. * @param reader The XML reader to load from. */ public SkillPrereq(PrereqList parent, XMLReader reader) throws IOException { super(parent, reader); } private SkillPrereq(PrereqList parent, SkillPrereq prereq) { super(parent, prereq); mSpecializationCriteria = new StringCriteria(prereq.mSpecializationCriteria); } @Override protected void initializeForLoad() { mSpecializationCriteria = new StringCriteria(StringCompareType.IS_ANYTHING, ""); //$NON-NLS-1$ } @Override public boolean equals(Object obj) { if (obj == this) { return true; } if (obj instanceof SkillPrereq && super.equals(obj)) { return mSpecializationCriteria.equals(((SkillPrereq) obj).mSpecializationCriteria); } return false; } @Override protected void loadSelf(XMLReader reader) throws IOException { if (TAG_SPECIALIZATION.equals(reader.getName())) { mSpecializationCriteria.load(reader); } else { super.loadSelf(reader); } } @Override protected void saveSelf(XMLWriter out) { mSpecializationCriteria.save(out, TAG_SPECIALIZATION); } @Override public String getXMLTag() { return TAG_ROOT; } @Override public Prereq clone(PrereqList parent) { return new SkillPrereq(parent, this); } @Override public boolean satisfied(GURPSCharacter character, ListRow exclude, StringBuilder builder, String prefix) { boolean satisfied = false; String techLevel = null; StringCriteria nameCriteria = getNameCriteria(); IntegerCriteria levelCriteria = getLevelCriteria(); if (exclude instanceof Skill) { techLevel = ((Skill) exclude).getTechLevel(); } for (Skill skill : character.getSkillsIterator()) { if (exclude != skill && nameCriteria.matches(skill.getName()) && mSpecializationCriteria.matches(skill.getSpecialization())) { satisfied = levelCriteria.matches(skill.getLevel()); if (satisfied && techLevel != null) { String otherTL = skill.getTechLevel(); satisfied = otherTL == null || techLevel.equals(otherTL); } if (satisfied) { break; } } } if (!has()) { satisfied = !satisfied; } if (!satisfied && builder != null) { builder.append(MessageFormat.format(SKILL_NAME_PART, prefix, has() ? HAS : DOES_NOT_HAVE, nameCriteria.toString())); boolean notAnySpecialization = mSpecializationCriteria.getType() != StringCompareType.IS_ANYTHING; if (notAnySpecialization) { builder.append(MessageFormat.format(SPECIALIZATION_PART, mSpecializationCriteria.toString())); } if (techLevel == null) { builder.append(MessageFormat.format(LEVEL_PART, levelCriteria.toString())); } else { if (notAnySpecialization) { builder.append(","); //$NON-NLS-1$ } builder.append(MessageFormat.format(LEVEL_AND_TL_PART, levelCriteria.toString())); } } return satisfied; } @Override public void fillWithNameableKeys(HashSet<String> set) { super.fillWithNameableKeys(set); ListRow.extractNameables(set, mSpecializationCriteria.getQualifier()); } @Override public void applyNameableKeys(HashMap<String, String> map) { super.applyNameableKeys(map); mSpecializationCriteria.setQualifier(ListRow.nameNameables(map, mSpecializationCriteria.getQualifier())); } /** @return The specialization comparison object. */ public StringCriteria getSpecializationCriteria() { return mSpecializationCriteria; } }