mirror of
https://github.com/Card-Forge/forge.git
synced 2025-11-19 12:18:00 +00:00
updated CHANGES.txt explaining about .draft and .sealed files
removed fields to store human's chioces from TriggerHandler, extracted method that confirms trigger.
This commit is contained in:
@@ -85,7 +85,7 @@ Combined declare attackers step for all Defending Players/Planeswalkers. On decl
|
|||||||
|
|
||||||
|
|
||||||
- Booster slots -
|
- Booster slots -
|
||||||
Booster slots are now way more customizable. This change allows us to implement DGM boosters correctly.
|
Booster slots are now way more customizable. This change allows us to implement DGM boosters correctly. Note that custom cube .draft and .sealed files have changed their format. They require a booster description instead of Num(Rarity) N lines. Find example records in files describing SkieraCube and Juzamjedi cude coming with Forge. Singleton parameter is obsolette, since all cards within a booster slot are unique. Ignore rarity is also deprecated, for Booster options allow you to pick cards regardless of rarity with 'any' word standing for ignored rarity. (ex: 15 Any)
|
||||||
|
|
||||||
|
|
||||||
---------
|
---------
|
||||||
|
|||||||
@@ -1,6 +1,5 @@
|
|||||||
Name:JuzamjediCube
|
Name:JuzamjediCube
|
||||||
DeckFile:JuzamjediCube
|
DeckFile:JuzamjediCube
|
||||||
IgnoreRarity:True
|
|
||||||
LandSetCode:M11
|
LandSetCode:M11
|
||||||
|
|
||||||
Booster: 5 Rare, 1 Mythic, 5 Common, 5 Uncommon
|
Booster: 5 Rare, 1 Mythic, 5 Common, 5 Uncommon
|
||||||
|
|||||||
@@ -437,45 +437,4 @@ public class TriggerHandler {
|
|||||||
regtrig.setTriggeredSA(wrapperAbility);
|
regtrig.setTriggeredSA(wrapperAbility);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
private final ArrayList<Integer> triggersAlwaysAccept = new ArrayList<Integer>();
|
|
||||||
private final ArrayList<Integer> triggersAlwaysDecline = new ArrayList<Integer>();
|
|
||||||
|
|
||||||
public final void setAlwaysAcceptTrigger(final int trigID) {
|
|
||||||
if (this.triggersAlwaysDecline.contains(trigID)) {
|
|
||||||
this.triggersAlwaysDecline.remove((Object) trigID);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!this.triggersAlwaysAccept.contains(trigID)) {
|
|
||||||
this.triggersAlwaysAccept.add(trigID);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public final void setAlwaysDeclineTrigger(final int trigID) {
|
|
||||||
if (this.triggersAlwaysAccept.contains(trigID)) {
|
|
||||||
this.triggersAlwaysAccept.remove((Object) trigID);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!this.triggersAlwaysDecline.contains(trigID)) {
|
|
||||||
this.triggersAlwaysDecline.add(trigID);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public final void setAlwaysAskTrigger(final int trigID) {
|
|
||||||
this.triggersAlwaysAccept.remove((Object) trigID);
|
|
||||||
this.triggersAlwaysDecline.remove((Object) trigID);
|
|
||||||
}
|
|
||||||
|
|
||||||
public final boolean isAlwaysAccepted(final int trigID) {
|
|
||||||
return this.triggersAlwaysAccept.contains(trigID);
|
|
||||||
}
|
|
||||||
|
|
||||||
public final boolean isAlwaysDeclined(final int trigID) {
|
|
||||||
return this.triggersAlwaysDecline.contains(trigID);
|
|
||||||
}
|
|
||||||
|
|
||||||
public final void clearTriggerSettings() {
|
|
||||||
this.triggersAlwaysAccept.clear();
|
|
||||||
this.triggersAlwaysDecline.clear();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -358,58 +358,11 @@ public class WrappedAbility extends Ability implements ISpellAbility {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
TriggerHandler th = game.getTriggerHandler();
|
TriggerHandler th = game.getTriggerHandler();
|
||||||
Map<String, String> triggerParams = regtrig.getMapParams();
|
Map<String, String> triggerParams = regtrig.getMapParams();
|
||||||
|
|
||||||
if (decider != null) {
|
if (decider != null && !confirmTrigger(decider, triggerParams))
|
||||||
if (decider.isHuman()) {
|
return;
|
||||||
if (th.isAlwaysAccepted(this.getSourceTrigger())) {
|
|
||||||
// No need to do anything.
|
|
||||||
} else if (th.isAlwaysDeclined(this.getSourceTrigger())) {
|
|
||||||
return;
|
|
||||||
} else {
|
|
||||||
final StringBuilder buildQuestion = new StringBuilder("Use triggered ability of ");
|
|
||||||
buildQuestion.append(regtrig.getHostCard().getName()).append("(")
|
|
||||||
.append(regtrig.getHostCard().getUniqueNumber()).append(")?");
|
|
||||||
buildQuestion.append("\r\n(");
|
|
||||||
buildQuestion.append(triggerParams.get("TriggerDescription").replace("CARDNAME",
|
|
||||||
regtrig.getHostCard().getName()));
|
|
||||||
buildQuestion.append(")\r\n");
|
|
||||||
if (sa.getTriggeringObjects().containsKey("Attacker")) {
|
|
||||||
buildQuestion
|
|
||||||
.append("[Attacker: " + sa.getTriggeringObjects().get("Attacker") + "]");
|
|
||||||
}
|
|
||||||
if (!GuiDialog.confirm(regtrig.getHostCard(), buildQuestion.toString())) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if (triggerParams.containsKey("DelayedTrigger")) {
|
|
||||||
//TODO: The only card with an optional delayed trigger is Shirei, Shizo's Caretaker,
|
|
||||||
// needs to be expanded when a more difficult cards comes up
|
|
||||||
} else {
|
|
||||||
// Store/replace target choices more properly to get this SA cleared.
|
|
||||||
Target tgt = sa.getTarget();
|
|
||||||
TargetChoices tc = null;
|
|
||||||
boolean storeChoices = tgt != null && tgt.getTargetChoices() != null;
|
|
||||||
|
|
||||||
if (storeChoices) {
|
|
||||||
tc = tgt.getTargetChoices();
|
|
||||||
tgt.resetTargets();
|
|
||||||
}
|
|
||||||
// There is no way this doTrigger here will have the same target as stored above
|
|
||||||
// So it's possible it's making a different decision here than will actually happen
|
|
||||||
if (!sa.doTrigger(this.isMandatory(), (AIPlayer) decider)) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
if (storeChoices) {
|
|
||||||
tgt.resetTargets();
|
|
||||||
tgt.setTargetChoices(tc);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (getActivatingPlayer().isHuman()) {
|
if (getActivatingPlayer().isHuman()) {
|
||||||
((HumanPlayer)getActivatingPlayer()).playSpellAbilityNoStack(sa, true);
|
((HumanPlayer)getActivatingPlayer()).playSpellAbilityNoStack(sa, true);
|
||||||
@@ -429,5 +382,45 @@ public class WrappedAbility extends Ability implements ISpellAbility {
|
|||||||
th.registerDelayedTrigger(deltrig);
|
th.registerDelayedTrigger(deltrig);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private boolean confirmTrigger(Player decider, Map<String, String> triggerParams) {
|
||||||
|
if (decider.isHuman()) {
|
||||||
|
String triggerDesc = triggerParams.get("TriggerDescription").replace("CARDNAME", regtrig.getHostCard().getName());
|
||||||
|
final StringBuilder buildQuestion = new StringBuilder("Use triggered ability of ");
|
||||||
|
buildQuestion.append(regtrig.getHostCard().toString()).append("?");
|
||||||
|
buildQuestion.append("\r\n(").append(triggerDesc).append(")\r\n");
|
||||||
|
if (sa.getTriggeringObjects().containsKey("Attacker")) {
|
||||||
|
buildQuestion.append("[Attacker: " + sa.getTriggeringObjects().get("Attacker") + "]");
|
||||||
|
}
|
||||||
|
if (!GuiDialog.confirm(regtrig.getHostCard(), buildQuestion.toString())) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (triggerParams.containsKey("DelayedTrigger")) {
|
||||||
|
//TODO: The only card with an optional delayed trigger is Shirei, Shizo's Caretaker,
|
||||||
|
// needs to be expanded when a more difficult cards comes up
|
||||||
|
} else {
|
||||||
|
// Store/replace target choices more properly to get this SA cleared.
|
||||||
|
Target tgt = sa.getTarget();
|
||||||
|
TargetChoices tc = null;
|
||||||
|
boolean storeChoices = tgt != null && tgt.getTargetChoices() != null;
|
||||||
|
|
||||||
|
if (storeChoices) {
|
||||||
|
tc = tgt.getTargetChoices();
|
||||||
|
tgt.resetTargets();
|
||||||
|
}
|
||||||
|
// There is no way this doTrigger here will have the same target as stored above
|
||||||
|
// So it's possible it's making a different decision here than will actually happen
|
||||||
|
if (!sa.doTrigger(this.isMandatory(), (AIPlayer) decider)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if (storeChoices) {
|
||||||
|
tgt.resetTargets();
|
||||||
|
tgt.setTargetChoices(tc);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -92,7 +92,6 @@ public class GameNew {
|
|||||||
// need this code here, otherwise observables fail
|
// need this code here, otherwise observables fail
|
||||||
forge.card.trigger.Trigger.resetIDs();
|
forge.card.trigger.Trigger.resetIDs();
|
||||||
TriggerHandler trigHandler = game.getTriggerHandler();
|
TriggerHandler trigHandler = game.getTriggerHandler();
|
||||||
trigHandler.clearTriggerSettings();
|
|
||||||
trigHandler.clearDelayedTrigger();
|
trigHandler.clearDelayedTrigger();
|
||||||
|
|
||||||
// friendliness
|
// friendliness
|
||||||
@@ -219,7 +218,6 @@ public class GameNew {
|
|||||||
// need this code here, otherwise observables fail
|
// need this code here, otherwise observables fail
|
||||||
forge.card.trigger.Trigger.resetIDs();
|
forge.card.trigger.Trigger.resetIDs();
|
||||||
TriggerHandler trigHandler = game.getTriggerHandler();
|
TriggerHandler trigHandler = game.getTriggerHandler();
|
||||||
trigHandler.clearTriggerSettings();
|
|
||||||
trigHandler.clearDelayedTrigger();
|
trigHandler.clearDelayedTrigger();
|
||||||
trigHandler.cleanUpTemporaryTriggers();
|
trigHandler.cleanUpTemporaryTriggers();
|
||||||
trigHandler.suppressMode(TriggerType.ChangesZone);
|
trigHandler.suppressMode(TriggerType.ChangesZone);
|
||||||
|
|||||||
Reference in New Issue
Block a user