Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
99 changes: 99 additions & 0 deletions Mage.Sets/src/mage/cards/p/PetrifiedHamlet.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
package mage.cards.p;

import java.util.Optional;
import java.util.UUID;

import mage.MageObject;
import mage.abilities.Ability;
import mage.abilities.common.EntersBattlefieldTriggeredAbility;
import mage.abilities.common.SimpleStaticAbility;
import mage.abilities.effects.ContinuousRuleModifyingEffectImpl;
import mage.abilities.effects.common.ChooseACardNameEffect;
import mage.abilities.effects.common.continuous.GainAbilityAllEffect;
import mage.abilities.mana.ColorlessManaAbility;
import mage.cards.CardImpl;
import mage.cards.CardSetInfo;
import mage.constants.CardType;
import mage.constants.Duration;
import mage.constants.Outcome;
import mage.filter.FilterPermanent;
import mage.filter.common.FilterLandPermanent;
import mage.filter.predicate.mageobject.ChosenNamePredicate;
import mage.game.Game;
import mage.game.events.GameEvent;
import mage.util.CardUtil;

/**
*
* @author muz
*/
public final class PetrifiedHamlet extends CardImpl {

private static final FilterPermanent filter = new FilterLandPermanent("lands with the chosen name");

static {
filter.add(ChosenNamePredicate.instance);
}

public PetrifiedHamlet(UUID ownerId, CardSetInfo setInfo) {
super(ownerId, setInfo, new CardType[]{CardType.LAND}, "");

// When this land enters, choose a land card name.
this.addAbility(new EntersBattlefieldTriggeredAbility(new ChooseACardNameEffect(ChooseACardNameEffect.TypeOfName.LAND_NAME)));

// Activated abilities of sources with the chosen name can't be activated unless they're mana abilities.
this.addAbility(new SimpleStaticAbility(new PetrifiedHamletCostEffect()));

// Lands with the chosen name have "{T}: Add {C}."
this.addAbility(new SimpleStaticAbility(new GainAbilityAllEffect(
new ColorlessManaAbility(), Duration.WhileOnBattlefield, filter
)));

// {T}: Add {C}.
this.addAbility(new ColorlessManaAbility());
}

private PetrifiedHamlet(final PetrifiedHamlet card) {
super(card);
}

@Override
public PetrifiedHamlet copy() {
return new PetrifiedHamlet(this);
}
}

class PetrifiedHamletCostEffect extends ContinuousRuleModifyingEffectImpl {

PetrifiedHamletCostEffect() {
super(Duration.WhileOnBattlefield, Outcome.Detriment);
staticText = "Activated abilities of sources with the chosen name can't be activated unless they're mana abilities";
}

private PetrifiedHamletCostEffect(final PetrifiedHamletCostEffect effect) {
super(effect);
}

@Override
public PetrifiedHamletCostEffect copy() {
return new PetrifiedHamletCostEffect(this);
}

@Override
public boolean checksEventType(GameEvent event, Game game) {
return event.getType() == GameEvent.EventType.ACTIVATE_ABILITY;
}

@Override
public boolean applies(GameEvent event, Ability source, Game game) {
MageObject object = game.getObject(event.getSourceId());
String cardName = (String) game.getState().getValue(source.getSourceId().toString() + ChooseACardNameEffect.INFO_KEY);
Optional<Ability> ability = game.getAbility(event.getTargetId(), event.getSourceId());
if (ability.isPresent() && object != null) {
return game.getState().getPlayersInRange(source.getControllerId(), game).contains(event.getPlayerId()) // controller in range
&& !ability.get().isManaAbility()
&& CardUtil.haveSameNames(object, cardName, game);
}
return false;
}
}
1 change: 1 addition & 0 deletions Mage.Sets/src/mage/sets/SecretsOfStrixhaven.java
Original file line number Diff line number Diff line change
Expand Up @@ -105,6 +105,7 @@ private SecretsOfStrixhaven() {
cards.add(new SetCardInfo("Pensive Professor", 321, Rarity.RARE, mage.cards.p.PensiveProfessor.class, NON_FULL_USE_VARIOUS));
cards.add(new SetCardInfo("Pensive Professor", 63, Rarity.RARE, mage.cards.p.PensiveProfessor.class, NON_FULL_USE_VARIOUS));
cards.add(new SetCardInfo("Pest Mascot", 209, Rarity.COMMON, mage.cards.p.PestMascot.class));
cards.add(new SetCardInfo("Petrified Hamlet", 259, Rarity.RARE, mage.cards.p.PetrifiedHamlet.class));
cards.add(new SetCardInfo("Plains", 267, Rarity.LAND, mage.cards.basiclands.Plains.class, FULL_ART_BFZ_VARIOUS));
cards.add(new SetCardInfo("Plains", 272, Rarity.LAND, mage.cards.basiclands.Plains.class, NON_FULL_USE_VARIOUS));
cards.add(new SetCardInfo("Plains", 273, Rarity.LAND, mage.cards.basiclands.Plains.class, NON_FULL_USE_VARIOUS));
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ public class ChooseACardNameEffect extends OneShotEffect {

public enum TypeOfName {
ALL("card name", CardRepository.instance::getNames),
LAND_NAME("land card name", CardRepository.instance::getLandNames),
NOT_BASIC_LAND_NAME("card name other than a basic land card name", CardRepository.instance::getNotBasicLandNames),
NONBASIC_LAND_NAME("nonbasic land card name", CardRepository.instance::getNonbasicLandNames),
NON_ARTIFACT_AND_NON_LAND_NAME("nonartifact, nonland card name", CardRepository.instance::getNonArtifactAndNonLandNames),
Expand Down
20 changes: 20 additions & 0 deletions Mage/src/main/java/mage/cards/repository/CardRepository.java
Original file line number Diff line number Diff line change
Expand Up @@ -178,6 +178,26 @@ public synchronized Set<String> getNames() {
return names;
}

public synchronized Set<String> getLandNames() {
Set<String> names = namesQueryCache.computeIfAbsent("getLandNames", x -> new TreeSet<>());
if (!names.isEmpty()) {
return names;
}
try {
QueryBuilder<CardInfo, Object> qb = cardsDao.queryBuilder();
qb.distinct().selectColumns("name", "doubleFacedSecondSideName", "secondSideName", "flipCardName", "spellOptionCardName");
qb.where().like("types", new SelectArg('%' + CardType.LAND.name() + '%'));
List<CardInfo> results = cardsDao.query(qb.prepare());
for (CardInfo card : results) {
addNewNames(card, names);
}
} catch (SQLException e) {
Logger.getLogger(CardRepository.class).error("Error getting land names from DB, possible low memory: " + e, e);
processMemoryErrors(e);
}
return names;
}

public synchronized Set<String> getNonLandNames() {
Set<String> names = namesQueryCache.computeIfAbsent("getNonLandNames", x -> new TreeSet<>());
if (!names.isEmpty()) {
Expand Down
1 change: 1 addition & 0 deletions Utils/mtg-cards-data.txt
Original file line number Diff line number Diff line change
Expand Up @@ -62086,6 +62086,7 @@ Fields of Strife|Secrets of Strixhaven|255|C||Land|||This land enters tapped.${T
Forum of Amity|Secrets of Strixhaven|256|C||Land|||This land enters tapped.${T}: Add {W} or {B}.${2}{W}{B}, {T}: Surveil 1.|
Great Hall of the Biblioplex|Secrets of Strixhaven|257|R||Land|||{T}: Add {C}.${T}, Pay 1 life: Add one mana of any color. Spend this mana only to cast an instant or sorcery spell.${5}: If this land isn't a creature, it becomes a 2/4 Wizard creature with "Whenever you cast an instant or sorcery spell, this creature gets +1/+0 until end of turn." It's still a land.|
Paradox Gardens|Secrets of Strixhaven|258|C||Land|||This land enters tapped.${T}: Add {G} or {U}.${2}{G}{U}, {T}: Surveil 1.|
Petrified Hamlet|Secrets of Strixhaven|259|R||Land|||When this land enters, choose a land card name.$Activated abilities of sources with the chosen name can't be activated unless they're mana abilities.$Lands with the chosen name have "{T}: Add {C}."${T}: Add {C}.|
Shattered Sanctum|Secrets of Strixhaven|260|R||Land|||This land enters tapped unless you control two or more other lands.${T}: Add {W} or {B}.|
Skycoach Waypoint|Secrets of Strixhaven|261|U||Land|||{T}: Add {C}.${3}, {T}: Target creature becomes prepared.|
Spectacle Summit|Secrets of Strixhaven|262|C||Land|||This land enters tapped.${T}: Add {U} or {R}.${2}{U}{R}, {T}: Surveil 1.|
Expand Down
Loading