diff --git a/core/assets/warsmash131.ini b/core/assets/warsmash131.ini index 8b7bf66..2d0db59 100644 --- a/core/assets/warsmash131.ini +++ b/core/assets/warsmash131.ini @@ -18,7 +18,8 @@ Path04="." //FilePath="PrivateDontShare/Cult 8.w3x" //FilePath="TorchLight2.w3x" //FilePath="OrcAssault.w3x" -FilePath="PeonStartingBase.w3x" +//FilePath="PeonStartingBase.w3x" //FilePath="PhoenixAttack.w3x" //FilePath="OperationReforged.w3x" //FilePath="AzerothRoleplay1.909t03DecoratedV2.w3x" +FilePath="American Colo EX 1.0 unpro.w3x" diff --git a/core/src/com/etheller/warsmash/WarsmashGdxMapGame.java b/core/src/com/etheller/warsmash/WarsmashGdxMapGame.java index 17bfcbf..1d57f1c 100644 --- a/core/src/com/etheller/warsmash/WarsmashGdxMapGame.java +++ b/core/src/com/etheller/warsmash/WarsmashGdxMapGame.java @@ -218,7 +218,7 @@ public class WarsmashGdxMapGame extends ApplicationAdapter implements CanvasProv final String[] musics = musicField.split(";"); String musicPath = musics[(int) (Math.random() * musics.length)]; if (true) { - musicPath = "Sound\\Music\\mp3Music\\DarkAgents.mp3"; + musicPath = "Sound\\Music\\mp3Music\\PH1.mp3"; } final Music music = Gdx.audio.newMusic( new DataSourceFileHandle(WarsmashGdxMapGame.this.viewer.dataSource, musicPath)); diff --git a/core/src/com/etheller/warsmash/datasources/FolderDataSource.java b/core/src/com/etheller/warsmash/datasources/FolderDataSource.java index d429cdd..356eb7e 100644 --- a/core/src/com/etheller/warsmash/datasources/FolderDataSource.java +++ b/core/src/com/etheller/warsmash/datasources/FolderDataSource.java @@ -58,7 +58,7 @@ public class FolderDataSource implements DataSource { if (!has(path)) { return null; } - return ByteBuffer.wrap(Files.readAllBytes(Paths.get(path))); + return ByteBuffer.wrap(Files.readAllBytes(Paths.get(this.folderPath.toString(), path))); } @Override diff --git a/core/src/com/etheller/warsmash/parsers/fdf/frames/StringFrame.java b/core/src/com/etheller/warsmash/parsers/fdf/frames/StringFrame.java index 5375fbc..eef0852 100644 --- a/core/src/com/etheller/warsmash/parsers/fdf/frames/StringFrame.java +++ b/core/src/com/etheller/warsmash/parsers/fdf/frames/StringFrame.java @@ -97,6 +97,7 @@ public class StringFrame extends AbstractRenderableFrame { final char escapedCharacter = this.text.charAt(i + 1); switch (escapedCharacter) { case 'c': + case 'C': if ((i + 9) < this.text.length()) { int colorInt; try { @@ -161,6 +162,7 @@ public class StringFrame extends AbstractRenderableFrame { } break; case 'r': + case 'R': i++; { final String wordString = currentWord.toString(); currentWord.setLength(0); @@ -210,7 +212,8 @@ public class StringFrame extends AbstractRenderableFrame { } currentColor = this.color; break; - case 'n': { + case 'n': + case 'N': { final String wordString = currentWord.toString(); currentWord.setLength(0); @@ -344,6 +347,9 @@ public class StringFrame extends AbstractRenderableFrame { singleStringFrame.setHeight(this.frameFont.getLineHeight()); singleStringFrame.setWidth(glyphLayout.width); singleStringFrame.setAlpha(this.alpha); + singleStringFrame.setFontShadowColor(this.fontShadowColor); + singleStringFrame.setFontShadowOffsetX(this.fontShadowOffsetX); + singleStringFrame.setFontShadowOffsetY(this.fontShadowOffsetY); singleStringFrame.addAnchor(new AnchorDefinition(FramePoint.TOPLEFT, currentXCoordForFrames, -usedHeight)); this.internalFrames.add(singleStringFrame); currentXCoordForFrames = currentXCoordForWord; diff --git a/core/src/com/etheller/warsmash/util/ImageUtils.java b/core/src/com/etheller/warsmash/util/ImageUtils.java index c9c6844..6991a8a 100644 --- a/core/src/com/etheller/warsmash/util/ImageUtils.java +++ b/core/src/com/etheller/warsmash/util/ImageUtils.java @@ -98,7 +98,7 @@ public final class ImageUtils { } public boolean isNeedsSRGBFix() { - return this.needsSRGBFix; + return false; } } @@ -217,6 +217,9 @@ public final class ImageUtils { * @return Resulting sRGB image. */ public static BufferedImage forceBufferedImagesRGB(final BufferedImage in) { + if (true) { + return in; + } // Resolve input ColorSpace. final ColorSpace inCS = in.getColorModel().getColorSpace(); final ColorSpace sRGBCS = ColorSpace.getInstance(ColorSpace.CS_sRGB); diff --git a/core/src/com/etheller/warsmash/viewer5/RawOpenGLTextureResource.java b/core/src/com/etheller/warsmash/viewer5/RawOpenGLTextureResource.java index 0d09915..7c0fb8c 100644 --- a/core/src/com/etheller/warsmash/viewer5/RawOpenGLTextureResource.java +++ b/core/src/com/etheller/warsmash/viewer5/RawOpenGLTextureResource.java @@ -91,7 +91,8 @@ public abstract class RawOpenGLTextureResource extends Texture { final GL20 gl = this.viewer.gl; } - public void update(final BufferedImage image, final boolean sRGBFix) { + public void update(final BufferedImage image, boolean sRGBFix) { + sRGBFix = false; final GL20 gl = this.viewer.gl; final int imageWidth = image.getWidth(); diff --git a/core/src/com/etheller/warsmash/viewer5/WorldScene.java b/core/src/com/etheller/warsmash/viewer5/WorldScene.java index e00d9b0..f05a550 100644 --- a/core/src/com/etheller/warsmash/viewer5/WorldScene.java +++ b/core/src/com/etheller/warsmash/viewer5/WorldScene.java @@ -57,7 +57,7 @@ public class WorldScene extends Scene { // Update and collect all of the visible instances. for (final GridCell cell : this.grid.cells) { - if (cell.isVisible(this.camera)) { + if (cell.isVisible(this.camera) || true) { this.visibleCells += 1; for (final ModelInstance instance : new ArrayList<>(cell.instances)) { diff --git a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/rendersim/RenderUnit.java b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/rendersim/RenderUnit.java index 08bec1c..346ee7a 100644 --- a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/rendersim/RenderUnit.java +++ b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/rendersim/RenderUnit.java @@ -4,6 +4,7 @@ import java.util.EnumSet; import com.badlogic.gdx.Gdx; import com.badlogic.gdx.math.Quaternion; +import com.etheller.warsmash.parsers.fdf.GameUI; import com.etheller.warsmash.units.manager.MutableObjectData.MutableGameObject; import com.etheller.warsmash.util.RenderMathUtils; import com.etheller.warsmash.util.War3ID; @@ -142,10 +143,11 @@ public class RenderUnit implements RenderWidget { } - public void populateCommandCard(final CSimulation game, final CommandButtonListener commandButtonListener, - final AbilityDataUI abilityDataUI, final int subMenuOrderId) { + public void populateCommandCard(final CSimulation game, final GameUI gameUI, + final CommandButtonListener commandButtonListener, final AbilityDataUI abilityDataUI, + final int subMenuOrderId) { final CommandCardPopulatingAbilityVisitor commandCardPopulatingVisitor = CommandCardPopulatingAbilityVisitor.INSTANCE - .reset(game, this.simulationUnit, commandButtonListener, abilityDataUI, subMenuOrderId); + .reset(game, gameUI, this.simulationUnit, commandButtonListener, abilityDataUI, subMenuOrderId); for (final CAbility ability : this.simulationUnit.getAbilities()) { ability.visit(commandCardPopulatingVisitor); } diff --git a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/rendersim/RenderWidget.java b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/rendersim/RenderWidget.java index 4aa2e50..3eeabd0 100644 --- a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/rendersim/RenderWidget.java +++ b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/rendersim/RenderWidget.java @@ -44,7 +44,7 @@ public interface RenderWidget { private final EnumSet recycleSet = EnumSet .noneOf(AnimationTokens.SecondaryTag.class); private PrimaryTag currentAnimation; - private EnumSet currentAnimationSecondaryTags; + private EnumSet currentAnimationSecondaryTags = SequenceUtils.EMPTY; private float currentSpeedRatio; private boolean currentlyAllowingRarityVariations; private final Queue animationQueue = new LinkedList<>(); diff --git a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/rendersim/commandbuttons/CommandCardPopulatingAbilityVisitor.java b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/rendersim/commandbuttons/CommandCardPopulatingAbilityVisitor.java index 14f14ea..0293fc3 100644 --- a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/rendersim/commandbuttons/CommandCardPopulatingAbilityVisitor.java +++ b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/rendersim/commandbuttons/CommandCardPopulatingAbilityVisitor.java @@ -1,5 +1,6 @@ package com.etheller.warsmash.viewer5.handlers.w3x.rendersim.commandbuttons; +import com.etheller.warsmash.parsers.fdf.GameUI; import com.etheller.warsmash.util.War3ID; import com.etheller.warsmash.viewer5.handlers.w3x.rendersim.ability.AbilityDataUI; import com.etheller.warsmash.viewer5.handlers.w3x.rendersim.ability.AbilityIconUI; @@ -28,6 +29,8 @@ import com.etheller.warsmash.viewer5.handlers.w3x.simulation.abilities.queue.CAb import com.etheller.warsmash.viewer5.handlers.w3x.simulation.combat.attacks.CUnitAttack; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.orders.OrderIds; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.players.CPlayer; +import com.etheller.warsmash.viewer5.handlers.w3x.simulation.util.AbilityActivationReceiver; +import com.etheller.warsmash.viewer5.handlers.w3x.simulation.util.ResourceType; public class CommandCardPopulatingAbilityVisitor implements CAbilityVisitor { public static final CommandCardPopulatingAbilityVisitor INSTANCE = new CommandCardPopulatingAbilityVisitor(); @@ -38,11 +41,14 @@ public class CommandCardPopulatingAbilityVisitor implements CAbilityVisitor requiredPathingTypes; private final float propWindow; private final float turnRate; + private final List requirements; public CUnitType(final String name, final int life, final int manaInitial, final int manaMaximum, final int speed, final int defense, final String abilityList, final boolean isBldg, final MovementType movementType, @@ -68,7 +69,8 @@ public class CUnitType { final List unitsTrained, final List researchesAvailable, final CUnitRace unitRace, final int goldCost, final int lumberCost, final int foodUsed, final int foodMade, final int buildTime, final EnumSet preventedPathingTypes, - final EnumSet requiredPathingTypes, final float propWindow, final float turnRate) { + final EnumSet requiredPathingTypes, final float propWindow, final float turnRate, + final List requirements) { this.name = name; this.life = life; this.manaInitial = manaInitial; @@ -105,6 +107,7 @@ public class CUnitType { this.requiredPathingTypes = requiredPathingTypes; this.propWindow = propWindow; this.turnRate = turnRate; + this.requirements = requirements; } public String getName() { @@ -250,4 +253,8 @@ public class CUnitType { public float getTurnRate() { return this.turnRate; } + + public List getRequirements() { + return this.requirements; + } } diff --git a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/CUnitTypeRequirement.java b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/CUnitTypeRequirement.java new file mode 100644 index 0000000..63b810d --- /dev/null +++ b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/CUnitTypeRequirement.java @@ -0,0 +1,21 @@ +package com.etheller.warsmash.viewer5.handlers.w3x.simulation; + +import com.etheller.warsmash.util.War3ID; + +public class CUnitTypeRequirement { + private final War3ID requirement; + private final int requiredLevel; + + public CUnitTypeRequirement(final War3ID requirement, final int requiredLevel) { + this.requirement = requirement; + this.requiredLevel = requiredLevel; + } + + public War3ID getRequirement() { + return this.requirement; + } + + public int getRequiredLevel() { + return this.requiredLevel; + } +} diff --git a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/abilities/build/AbstractCAbilityBuild.java b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/abilities/build/AbstractCAbilityBuild.java index 21a284b..df29658 100644 --- a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/abilities/build/AbstractCAbilityBuild.java +++ b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/abilities/build/AbstractCAbilityBuild.java @@ -9,6 +9,7 @@ import com.etheller.warsmash.util.War3ID; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.CSimulation; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.CUnit; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.CUnitType; +import com.etheller.warsmash.viewer5.handlers.w3x.simulation.CUnitTypeRequirement; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.CWidget; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.abilities.AbstractCAbility; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.abilities.menu.CAbilityMenu; @@ -39,22 +40,37 @@ public abstract class AbstractCAbilityBuild extends AbstractCAbility implements final CUnitType unitType = game.getUnitData().getUnitType(orderIdAsRawtype); if (unitType != null) { final CPlayer player = game.getPlayer(unit.getPlayerIndex()); - if (player.getGold() >= unitType.getGoldCost()) { - if (player.getLumber() >= unitType.getLumberCost()) { - if ((unitType.getFoodUsed() == 0) - || ((player.getFoodUsed() + unitType.getFoodUsed()) <= player.getFoodCap())) { - receiver.useOk(); + final List requirements = unitType.getRequirements(); + boolean requirementsMet = true; + for (final CUnitTypeRequirement requirement : requirements) { + if (player.getTechtreeUnlocked(requirement.getRequirement()) < requirement.getRequiredLevel()) { + requirementsMet = false; + } + } + if (requirementsMet) { + if (player.getGold() >= unitType.getGoldCost()) { + if (player.getLumber() >= unitType.getLumberCost()) { + if ((unitType.getFoodUsed() == 0) + || ((player.getFoodUsed() + unitType.getFoodUsed()) <= player.getFoodCap())) { + + receiver.useOk(); + } + else { + receiver.notEnoughResources(ResourceType.FOOD); + } } else { - receiver.notEnoughResources(ResourceType.FOOD); + receiver.notEnoughResources(ResourceType.LUMBER); } } else { - receiver.notEnoughResources(ResourceType.LUMBER); + receiver.notEnoughResources(ResourceType.GOLD); } } else { - receiver.notEnoughResources(ResourceType.GOLD); + for (final CUnitTypeRequirement requirement : requirements) { + receiver.missingRequirement(requirement.getRequirement(), requirement.getRequiredLevel()); + } } } else { diff --git a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/abilities/queue/CAbilityQueue.java b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/abilities/queue/CAbilityQueue.java index daae13f..fbd44d8 100644 --- a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/abilities/queue/CAbilityQueue.java +++ b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/abilities/queue/CAbilityQueue.java @@ -8,6 +8,7 @@ import com.etheller.warsmash.util.War3ID; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.CSimulation; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.CUnit; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.CUnitType; +import com.etheller.warsmash.viewer5.handlers.w3x.simulation.CUnitTypeRequirement; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.CWidget; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.abilities.AbstractCAbility; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.abilities.CAbilityVisitor; @@ -45,22 +46,36 @@ public final class CAbilityQueue extends AbstractCAbility { final CUnitType unitType = game.getUnitData().getUnitType(orderIdAsRawtype); if (unitType != null) { final CPlayer player = game.getPlayer(unit.getPlayerIndex()); - if (player.getGold() >= unitType.getGoldCost()) { - if (player.getLumber() >= unitType.getLumberCost()) { - if ((unitType.getFoodUsed() == 0) - || ((player.getFoodUsed() + unitType.getFoodUsed()) <= player.getFoodCap())) { - receiver.useOk(); + final List requirements = unitType.getRequirements(); + boolean requirementsMet = true; + for (final CUnitTypeRequirement requirement : requirements) { + if (player.getTechtreeUnlocked(requirement.getRequirement()) < requirement.getRequiredLevel()) { + requirementsMet = false; + } + } + if (requirementsMet) { + if (player.getGold() >= unitType.getGoldCost()) { + if (player.getLumber() >= unitType.getLumberCost()) { + if ((unitType.getFoodUsed() == 0) + || ((player.getFoodUsed() + unitType.getFoodUsed()) <= player.getFoodCap())) { + receiver.useOk(); + } + else { + receiver.notEnoughResources(ResourceType.FOOD); + } } else { - receiver.notEnoughResources(ResourceType.FOOD); + receiver.notEnoughResources(ResourceType.LUMBER); } } else { - receiver.notEnoughResources(ResourceType.LUMBER); + receiver.notEnoughResources(ResourceType.GOLD); } } else { - receiver.notEnoughResources(ResourceType.GOLD); + for (final CUnitTypeRequirement requirement : requirements) { + receiver.missingRequirement(requirement.getRequirement(), requirement.getRequiredLevel()); + } } } else { diff --git a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/abilities/queue/CAbilityRally.java b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/abilities/queue/CAbilityRally.java index 2ea18ab..f1b7283 100644 --- a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/abilities/queue/CAbilityRally.java +++ b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/abilities/queue/CAbilityRally.java @@ -19,7 +19,7 @@ public class CAbilityRally extends AbstractCAbility { @Override public void onAdd(final CSimulation game, final CUnit unit) { - + unit.setRallyPoint(unit); } @Override diff --git a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/behaviors/harvest/CBehaviorHarvest.java b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/behaviors/harvest/CBehaviorHarvest.java index ab50413..3833f81 100644 --- a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/behaviors/harvest/CBehaviorHarvest.java +++ b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/behaviors/harvest/CBehaviorHarvest.java @@ -92,7 +92,12 @@ public class CBehaviorHarvest extends CAbstractRangedBehavior } } // weird invalid target and we have no resources, consider harvesting done - return this.unit.pollNextOrderBehavior(this.simulation); + if (this.abilityHarvest.getCarriedResourceAmount() == 0) { + return this.unit.pollNextOrderBehavior(this.simulation); + } + else { + return this.abilityHarvest.getBehaviorReturnResources().reset(this.simulation); + } } else { // we have some GOLD and we're not in a mine (?) lets do a return resources diff --git a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/data/CUnitData.java b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/data/CUnitData.java index 13e5bc7..f76ee68 100644 --- a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/data/CUnitData.java +++ b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/data/CUnitData.java @@ -16,6 +16,7 @@ import com.etheller.warsmash.viewer5.handlers.w3x.simulation.CSimulation; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.CUnit; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.CUnitClassification; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.CUnitType; +import com.etheller.warsmash.viewer5.handlers.w3x.simulation.CUnitTypeRequirement; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.HandleIdAllocator; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.abilities.CAbility; import com.etheller.warsmash.viewer5.handlers.w3x.simulation.abilities.CAbilityAttack; @@ -137,6 +138,9 @@ public class CUnitData { private static final War3ID RESEARCHES_AVAILABLE = War3ID.fromString("ures"); private static final War3ID UNIT_RACE = War3ID.fromString("urac"); + private static final War3ID REQUIRES = War3ID.fromString("ureq"); + private static final War3ID REQUIRES_AMOUNT = War3ID.fromString("urqc"); + private static final War3ID GOLD_COST = War3ID.fromString("ugol"); private static final War3ID LUMBER_COST = War3ID.fromString("ulum"); private static final War3ID BUILD_TIME = War3ID.fromString("ubld"); @@ -416,6 +420,40 @@ public class CUnitData { } } + final String requirementsString = unitType.getFieldAsString(REQUIRES, 0); + final String requirementsLevelsString = unitType.getFieldAsString(REQUIRES_AMOUNT, 0); + final String[] requirementsStringItems = requirementsString.split(","); + final String[] requirementsLevelsStringItems = requirementsLevelsString.split(","); + final List requirements = new ArrayList<>(); + for (int i = 0; i < requirementsStringItems.length; i++) { + final String item = requirementsStringItems[i]; + if (!item.isEmpty()) { + int level; + if (i < requirementsLevelsStringItems.length) { + if (requirementsLevelsStringItems[i].isEmpty()) { + level = 1; + } + else { + level = Integer.parseInt(requirementsLevelsStringItems[i]); + } + } + else if (requirementsLevelsStringItems.length > 0) { + final String requirementLevel = requirementsLevelsStringItems[requirementsLevelsStringItems.length + - 1]; + if (requirementLevel.isEmpty()) { + level = 1; + } + else { + level = Integer.parseInt(requirementLevel); + } + } + else { + level = 1; + } + requirements.add(new CUnitTypeRequirement(War3ID.fromString(item), level)); + } + } + final EnumSet preventedPathingTypes = CBuildingPathingType .parsePathingTypeListSet(unitType.getFieldAsString(PREVENT_PLACE, 0)); final EnumSet requiredPathingTypes = CBuildingPathingType @@ -429,7 +467,7 @@ public class CUnitData { defenseType, impactZ, buildingPathingPixelMap, deathTime, targetedAs, acquisitionRange, minimumAttackRange, structuresBuilt, unitsTrained, researchesAvailable, unitRace, goldCost, lumberCost, foodUsed, foodMade, buildTime, preventedPathingTypes, requiredPathingTypes, propWindow, - turnRate); + turnRate, requirements); this.unitIdToUnitType.put(typeId, unitTypeInstance); } return unitTypeInstance; diff --git a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/players/CPlayer.java b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/players/CPlayer.java index 078c8f2..e00070f 100644 --- a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/players/CPlayer.java +++ b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/players/CPlayer.java @@ -150,6 +150,26 @@ public class CPlayer { return techtreeUnlocked; } + public void addTechtreeUnlocked(final War3ID rawcode) { + final Integer techtreeUnlocked = this.rawcodeToTechtreeUnlocked.get(rawcode); + if (techtreeUnlocked == null) { + this.rawcodeToTechtreeUnlocked.put(rawcode, 1); + } + else { + this.rawcodeToTechtreeUnlocked.put(rawcode, techtreeUnlocked + 1); + } + } + + public void removeTechtreeUnlocked(final War3ID rawcode) { + final Integer techtreeUnlocked = this.rawcodeToTechtreeUnlocked.get(rawcode); + if (techtreeUnlocked == null) { + this.rawcodeToTechtreeUnlocked.put(rawcode, -1); + } + else { + this.rawcodeToTechtreeUnlocked.put(rawcode, techtreeUnlocked - 1); + } + } + public void addStateListener(final CPlayerStateListener listener) { this.stateNotifier.subscribe(listener); } diff --git a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/util/AbilityActivationReceiver.java b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/util/AbilityActivationReceiver.java index ff76f71..09d79a4 100644 --- a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/util/AbilityActivationReceiver.java +++ b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/util/AbilityActivationReceiver.java @@ -1,5 +1,7 @@ package com.etheller.warsmash.viewer5.handlers.w3x.simulation.util; +import com.etheller.warsmash.util.War3ID; + public interface AbilityActivationReceiver { void useOk(); @@ -7,7 +9,7 @@ public interface AbilityActivationReceiver { void notAnActiveAbility(); - void missingRequirement(String name); + void missingRequirement(War3ID type, int level); void casterMovementDisabled(); diff --git a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/util/BooleanAbilityActivationReceiver.java b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/util/BooleanAbilityActivationReceiver.java index aaec289..b6ae3b7 100644 --- a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/util/BooleanAbilityActivationReceiver.java +++ b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/util/BooleanAbilityActivationReceiver.java @@ -1,5 +1,7 @@ package com.etheller.warsmash.viewer5.handlers.w3x.simulation.util; +import com.etheller.warsmash.util.War3ID; + public class BooleanAbilityActivationReceiver implements AbilityActivationReceiver { public static final BooleanAbilityActivationReceiver INSTANCE = new BooleanAbilityActivationReceiver(); private boolean ok; @@ -20,7 +22,7 @@ public class BooleanAbilityActivationReceiver implements AbilityActivationReceiv } @Override - public void missingRequirement(final String name) { + public void missingRequirement(final War3ID type, final int level) { this.ok = false; } diff --git a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/util/MeleeUIAbilityActivationReceiver.java b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/util/MeleeUIAbilityActivationReceiver.java index 7012c8b..fe5420d 100644 --- a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/util/MeleeUIAbilityActivationReceiver.java +++ b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/util/MeleeUIAbilityActivationReceiver.java @@ -1,5 +1,6 @@ package com.etheller.warsmash.viewer5.handlers.w3x.simulation.util; +import com.etheller.warsmash.util.War3ID; import com.etheller.warsmash.viewer5.AudioContext; import com.etheller.warsmash.viewer5.handlers.w3x.rendersim.RenderUnit; import com.etheller.warsmash.viewer5.handlers.w3x.ui.command.CommandErrorListener; @@ -59,7 +60,7 @@ public class MeleeUIAbilityActivationReceiver implements AbilityActivationReceiv } @Override - public void missingRequirement(final String name) { + public void missingRequirement(final War3ID type, final int level) { this.genericError.onClick(this.commandErrorListener, this.worldSceneAudioContext, this.commandedUnit); } diff --git a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/util/StringMsgAbilityActivationReceiver.java b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/util/StringMsgAbilityActivationReceiver.java index 5ec8516..5f8697c 100644 --- a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/util/StringMsgAbilityActivationReceiver.java +++ b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/simulation/util/StringMsgAbilityActivationReceiver.java @@ -1,5 +1,7 @@ package com.etheller.warsmash.viewer5.handlers.w3x.simulation.util; +import com.etheller.warsmash.util.War3ID; + public class StringMsgAbilityActivationReceiver implements AbilityActivationReceiver { private String message; private boolean useOk = false; @@ -34,8 +36,8 @@ public class StringMsgAbilityActivationReceiver implements AbilityActivationRece } @Override - public void missingRequirement(final String name) { - this.message = "NOTEXTERN: Requires " + name; + public void missingRequirement(final War3ID type, final int level) { + this.message = "NOTEXTERN: Requires " + type; } @Override diff --git a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/ui/MeleeUI.java b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/ui/MeleeUI.java index 4eb17b5..11e6086 100644 --- a/core/src/com/etheller/warsmash/viewer5/handlers/w3x/ui/MeleeUI.java +++ b/core/src/com/etheller/warsmash/viewer5/handlers/w3x/ui/MeleeUI.java @@ -418,7 +418,7 @@ public class MeleeUI implements CUnitStateListener, CommandButtonListener, Comma this.unitManaText = (StringFrame) this.rootFrame.getFrameByName("UnitPortraitManaPointText", 0); final float infoPanelUnitDetailWidth = GameUI.convertY(this.uiViewport, 0.180f); - final float infoPanelUnitDetailHeight = GameUI.convertY(this.uiViewport, 0.105f); + final float infoPanelUnitDetailHeight = GameUI.convertY(this.uiViewport, 0.110f); this.smashSimpleInfoPanel = this.rootFrame.createSimpleFrame("SmashSimpleInfoPanel", this.rootFrame, 0); this.smashSimpleInfoPanel .addAnchor(new AnchorDefinition(FramePoint.BOTTOM, 0, GameUI.convertY(this.uiViewport, 0.0f))); @@ -556,7 +556,7 @@ public class MeleeUI implements CUnitStateListener, CommandButtonListener, Comma new Color(0xFFCC00FF), TextJustify.LEFT, TextJustify.MIDDLE, worldFrameMessageFontHeight); this.errorMessageFrame.addAnchor(new AnchorDefinition(FramePoint.BOTTOMLEFT, GameUI.convertX(this.uiViewport, 0.212f), GameUI.convertY(this.uiViewport, 0.182f))); - this.errorMessageFrame.setWidth(GameUI.convertX(this.uiViewport, 0.25f)); + this.errorMessageFrame.setWidth(GameUI.convertX(this.uiViewport, 0.35f)); this.errorMessageFrame.setHeight(GameUI.convertY(this.uiViewport, worldFrameMessageFontHeight)); this.errorMessageFrame.setFontShadowColor(new Color(0f, 0f, 0f, 0.9f)); @@ -1773,7 +1773,8 @@ public class MeleeUI implements CUnitStateListener, CommandButtonListener, Comma this.commandButton(cancelUI.getButtonPositionX(), cancelUI.getButtonPositionY(), cancelUI.getIcon(), 0, exitOrderId, 0, false, false, true, cancelUI.getToolTip(), cancelUI.getUberTip(), 0, 0, 0); } - this.selectedUnit.populateCommandCard(this.war3MapViewer.simulation, this, abilityDataUI, menuOrderId); + this.selectedUnit.populateCommandCard(this.war3MapViewer.simulation, this.rootFrame, this, abilityDataUI, + menuOrderId); } } @@ -1941,7 +1942,9 @@ public class MeleeUI implements CUnitStateListener, CommandButtonListener, Comma else { final List selectedUnits = this.war3MapViewer.selectUnit(screenX, worldScreenY, false); - selectWidgets(selectedUnits); + if (!selectedUnits.isEmpty()) { + selectWidgets(selectedUnits); + } } } } diff --git a/resources/UI/FrameDef/SmashUI/UnitPortrait.fdf b/resources/UI/FrameDef/SmashUI/UnitPortrait.fdf index ce7f91b..eb3aa55 100644 --- a/resources/UI/FrameDef/SmashUI/UnitPortrait.fdf +++ b/resources/UI/FrameDef/SmashUI/UnitPortrait.fdf @@ -31,13 +31,13 @@ Frame "SIMPLEFRAME" "UnitPortrait" { } String "UnitPortraitHitPointText" INHERITS "UnitPortraitTextTemplate" { - Anchor BOTTOM, 0, 0.0115, + Anchor BOTTOM, 0, 0.014, FontJustificationH JUSTIFYCENTER, FontColor 0.0 1.0 0.0 1.0, } String "UnitPortraitManaPointText" INHERITS "UnitPortraitTextTemplate" { - Anchor BOTTOM, 0, -0.0030, + Anchor BOTTOM, 0, -0.0005, FontJustificationH JUSTIFYCENTER, FontColor 1.0 1.0 1.0 1.0, }