[Mobile] Card Magnifier

- Add option to display larger version of the hovered card.
This commit is contained in:
Anthony Calosa
2022-02-15 15:31:44 +08:00
parent 1b5de6c2b3
commit ea6aaa1efb
12 changed files with 6012 additions and 5920 deletions

View File

@@ -61,6 +61,7 @@ public class DesktopAdapter implements IDeviceAdapter {
@Override
public void exit() {
Gdx.app.exit(); //can just use Gdx.app.exit for desktop
System.exit(0);
}
@Override

View File

@@ -47,8 +47,7 @@ public class StartScene extends UIScene {
}
public boolean Exit() {
Gdx.app.exit();
System.exit(0);
Forge.exit(true);
return true;
}

View File

@@ -604,9 +604,9 @@ public class CardRenderer {
}
}
public static void drawCard(Graphics g, CardView card, float x, float y, float w, float h, CardStackPosition pos, boolean rotate) {
drawCard(g, card, x, y, w, h, pos, rotate, false, false);
drawCard(g, card, x, y, w, h, pos, rotate, false, false, false);
}
public static void drawCard(Graphics g, CardView card, float x, float y, float w, float h, CardStackPosition pos, boolean rotate, boolean showAltState, boolean isChoiceList) {
public static void drawCard(Graphics g, CardView card, float x, float y, float w, float h, CardStackPosition pos, boolean rotate, boolean showAltState, boolean isChoiceList, boolean magnify) {
boolean canshow = MatchController.instance.mayView(card);
boolean showsleeves = card.isFaceDown() && card.isInZone(EnumSet.of(ZoneType.Exile)); //fix facedown card image ie gonti lord of luxury
Texture image = new RendererCachedCardImage(card, false).getImage( showAltState ? card.getAlternateState().getImageKey() : card.getCurrentState().getImageKey());
@@ -628,9 +628,9 @@ public class CardRenderer {
g.setAlphaComposite(oldAlpha);
} else if (showsleeves) {
if (!card.isForeTold())
g.drawCardImage(sleeves, crack_overlay, x, y, w, h, card.wasDestroyed(), card.getDamage() > 0);
g.drawCardImage(sleeves, crack_overlay, x, y, w, h, card.wasDestroyed(), magnify ? false : card.getDamage() > 0);
else
g.drawCardImage(image, crack_overlay, x, y, w, h, card.wasDestroyed(), card.getDamage() > 0);
g.drawCardImage(image, crack_overlay, x, y, w, h, card.wasDestroyed(), magnify ? false : card.getDamage() > 0);
} else {
if(FModel.getPreferences().getPrefBoolean(ForgePreferences.FPref.UI_ROTATE_PLANE_OR_PHENOMENON)
&& (card.getCurrentState().isPhenomenon() || card.getCurrentState().isPlane()) && rotate){
@@ -648,19 +648,19 @@ public class CardRenderer {
} else {
if (Forge.enableUIMask.equals("Full") && canshow) {
if (ImageCache.isBorderlessCardArt(image))
g.drawCardImage(image, crack_overlay, x, y, w, h, card.wasDestroyed(), card.getDamage() > 0);
g.drawCardImage(image, crack_overlay, x, y, w, h, card.wasDestroyed(), magnify ? false : card.getDamage() > 0);
else {
boolean t = (card.getCurrentState().getOriginalColors() != card.getCurrentState().getColors()) || card.getCurrentState().hasChangeColors();
g.drawBorderImage(ImageCache.getBorderImage(image.toString(), canshow), ImageCache.borderColor(image), ImageCache.getTint(card, image), x, y, w, h, t); //tint check for changed colors
g.drawCardImage(ImageCache.croppedBorderImage(image), crack_overlay, x + radius / 2.4f-minusxy, y + radius / 2-minusxy, w * croppedArea, h * croppedArea, card.wasDestroyed(), card.getDamage() > 0);
g.drawCardImage(ImageCache.croppedBorderImage(image), crack_overlay, x + radius / 2.4f-minusxy, y + radius / 2-minusxy, w * croppedArea, h * croppedArea, card.wasDestroyed(), magnify ? false : card.getDamage() > 0);
}
} else if (Forge.enableUIMask.equals("Crop") && canshow) {
g.drawCardImage(ImageCache.croppedBorderImage(image), crack_overlay, x, y, w, h, card.wasDestroyed(), card.getDamage() > 0);
g.drawCardImage(ImageCache.croppedBorderImage(image), crack_overlay, x, y, w, h, card.wasDestroyed(), magnify ? false : card.getDamage() > 0);
} else {
if (canshow)
g.drawCardImage(image, crack_overlay, x, y, w, h, card.wasDestroyed(), card.getDamage() > 0);
g.drawCardImage(image, crack_overlay, x, y, w, h, card.wasDestroyed(), magnify ? false : card.getDamage() > 0);
else // draw card back sleeves
g.drawCardImage(sleeves, crack_overlay, x, y, w, h, card.wasDestroyed(), card.getDamage() > 0);
g.drawCardImage(sleeves, crack_overlay, x, y, w, h, card.wasDestroyed(), magnify ? false : card.getDamage() > 0);
}
}
}
@@ -684,7 +684,7 @@ public class CardRenderer {
boolean unselectable = !MatchController.instance.isSelectable(card) && MatchController.instance.isSelecting();
float cx, cy, cw, ch;
cx = x; cy = y; cw = w; ch = h;
drawCard(g, card, x, y, w, h, pos, false, showAltState, isChoiceList);
drawCard(g, card, x, y, w, h, pos, false, showAltState, isChoiceList, false);
float padding = w * PADDING_MULTIPLIER; //adjust for card border
x += padding;

View File

@@ -6,8 +6,12 @@ import java.util.Map.Entry;
import com.badlogic.gdx.math.Vector2;
import forge.animation.ForgeAnimation;
import forge.assets.FImage;
import forge.card.CardRenderer;
import forge.card.CardZoom;
import forge.game.spellability.StackItemView;
import forge.gui.interfaces.IGuiGame;
import forge.toolbox.FDisplayObject;
import forge.util.Utils;
import forge.util.collect.FCollectionView;
import org.apache.commons.lang3.tuple.Pair;
@@ -66,7 +70,7 @@ import forge.util.Localizer;
public class MatchScreen extends FScreen {
public static FSkinColor BORDER_COLOR = FSkinColor.get(Colors.CLR_BORDERS);
private final Map<PlayerView, VPlayerPanel> playerPanels = Maps.newHashMap();
private static final Map<PlayerView, VPlayerPanel> playerPanels = Maps.newHashMap();
private List<VPlayerPanel> playerPanelsList;
private final VGameMenu gameMenu;
private final VPlayers players;
@@ -79,6 +83,7 @@ public class MatchScreen extends FScreen {
private AbilityEffect activeEffect;
private BGAnimation bgAnimation;
private ViewWinLose viewWinLose = null;
private List<FDisplayObject> potentialListener;
public MatchScreen(List<VPlayerPanel> playerPanels0) {
super(new FMenuBar());
@@ -87,6 +92,8 @@ public class MatchScreen extends FScreen {
int humanCount = 0;
playerPanels.clear();
for (VPlayerPanel playerPanel : playerPanels0) {
playerPanels.put(playerPanel.getPlayer(), scroller.add(playerPanel));
playerPanel.setFlipped(true);
@@ -306,7 +313,7 @@ public class MatchScreen extends FScreen {
return bottomPlayerPanel;
}
public Map<PlayerView, VPlayerPanel> getPlayerPanels() {
public static Map<PlayerView, VPlayerPanel> getPlayerPanels() {
return playerPanels;
}
@@ -452,6 +459,69 @@ public class MatchScreen extends FScreen {
}
}
}
if (FModel.getPreferences().getPrefBoolean(ForgePreferences.FPref.UI_ENABLE_MAGNIFIER)) {
if (Forge.isLandscapeMode() && !GuiBase.isAndroid() && !CardZoom.isOpen() && potentialListener != null) {
for (FDisplayObject object : potentialListener) {
if (object != null) {
if (object instanceof FCardPanel) {
FCardPanel cardPanel = (FCardPanel) object;
try {
if (cardPanel.isHovered()) {
VPlayerPanel vPlayerPanel = getPlayerPanel(cardPanel.getCard().getController());
if (vPlayerPanel == null)
vPlayerPanel = getPlayerPanel(cardPanel.getCard().getOwner());
if (vPlayerPanel != null) {
float cardW = getHeight() * 0.45f;
float cardH = FCardPanel.ASPECT_RATIO * cardW;
float cardX = !ZoneType.Battlefield.equals(cardPanel.getCard().getZone())
? cardPanel.screenPos.x-cardW : cardPanel.screenPos.x+(cardPanel.isTapped()
? cardPanel.getWidth() : cardPanel.getWidth()/1.4f);
if (vPlayerPanel.getSelectedTab() != null && vPlayerPanel.getSelectedTab().isVisible()
&& cardX > vPlayerPanel.getSelectedTab().getDisplayArea().getLeft()) {
cardX = cardPanel.screenPos.x-cardW;
}
if ((cardX+cardW) > scroller.getWidth()+scroller.getLeft())
cardX = cardPanel.screenPos.x-cardW;
if (vPlayerPanel.getCommandZone() != null
&& vPlayerPanel.getCommandZone().isVisible() && cardX > vPlayerPanel.getCommandZone().screenPos.x)
cardX = cardPanel.screenPos.x-cardW;
float cardY = (cardPanel.screenPos.y-cardH)+cardPanel.getHeight();
if (vPlayerPanel.getPlayer() == bottomPlayerPanel.getPlayer()) {
cardY = bottomPlayerPrompt.screenPos.y - cardH;
}
else if (cardY < vPlayerPanel.getField().screenPos.y && vPlayerPanel.getPlayer() != bottomPlayerPanel.getPlayer()) {
cardY = vPlayerPanel.getField().screenPos.y;
if ((cardY+cardH) > bottomPlayerPrompt.screenPos.y)
cardY = bottomPlayerPrompt.screenPos.y - cardH;
}
CardRenderer.drawCard(g, cardPanel.getCard(), cardX, cardY, cardW, cardH, CardRenderer.CardStackPosition.Top, false, false, false, true);
}
}
} catch (Exception e) {
e.printStackTrace();
}
} else if (object instanceof VStack.StackInstanceDisplay) {
try {
CardView cardView = ((VStack.StackInstanceDisplay) object).stackInstance.getSourceCard();
if (object.isHovered() && cardView != null) {
float cardW = getHeight() * 0.45f;
float cardH = FCardPanel.ASPECT_RATIO * cardW;
float cardX = object.screenPos.x-cardW-Utils.scale(4);
float cardY = object.screenPos.y-Utils.scale(2);
if (cardY < topPlayerPanel.getField().screenPos.y)
cardY = topPlayerPanel.getField().screenPos.y;
if ((cardY+cardH) > bottomPlayerPrompt.screenPos.y)
cardY = bottomPlayerPrompt.screenPos.y - cardH;
CardRenderer.drawCard(g, cardView, cardX, cardY, cardW, cardH, CardRenderer.CardStackPosition.Top, false, false, false, true);
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
}
}
}
}
@Override
@@ -585,7 +655,7 @@ public class MatchScreen extends FScreen {
}
}
public VPlayerPanel getPlayerPanel(final PlayerView playerView) {
public static VPlayerPanel getPlayerPanel(final PlayerView playerView) {
return getPlayerPanels().get(playerView);
}
@@ -779,16 +849,15 @@ public class MatchScreen extends FScreen {
for (VPlayerPanel playerPanel : playerPanelsList) {
if (playerPanel.getPlayer().getHasLost()) {
losers.add(playerPanel);
playerPanelsList.remove(playerPanel);
}
}
}
if (!losers.isEmpty()) {
float height = 0;
for (VPlayerPanel p : losers) {
p.clear();
p.noBG = true;
height = p.getAvatar().getHeight();
p.setVisible(false);
playerPanelsList.remove(p);
System.out.println("Removed panels: "+p.getPlayer().toString());
}
losers.clear();
@@ -928,4 +997,10 @@ public class MatchScreen extends FScreen {
return false;
}
}
@Override
public void buildTouchListeners(float screenX, float screenY, List<FDisplayObject> listeners) {
potentialListener = listeners;
super.buildTouchListeners(screenX, screenY, listeners);
}
}

View File

@@ -240,8 +240,8 @@ public class VStack extends FDropDown {
}
}
private class StackInstanceDisplay extends FDisplayObject {
private final StackItemView stackInstance;
public class StackInstanceDisplay extends FDisplayObject {
public final StackItemView stackInstance;
private final Color foreColor, backColor;
private String text;
private float preferredHeight;

View File

@@ -557,6 +557,12 @@ public class SettingsPage extends TabPage<SettingsScreen> {
localizer.getMessage("lblMatchScrollIndicator"),
localizer.getMessage("nlMatchScrollIndicator")),
4);
if (!GuiBase.isAndroid()) {
lstSettings.addItem(new BooleanSetting(FPref.UI_ENABLE_MAGNIFIER,
localizer.getMessage("lblEnableMagnifier"),
localizer.getMessage("nlEnableMagnifier")),
4);
}
lstSettings.addItem(new BooleanSetting(FPref.UI_SHOW_FPS,
localizer.getMessage("lblShowFPSDisplay"),
localizer.getMessage("nlShowFPSDisplay")){

View File

@@ -1055,6 +1055,8 @@ lblPreloadExtendedArtCards=Preload Extended Art Cards
nlPreloadExtendedArtCards=When enabled, Preloads Extended Art Cards to Cache on Startup (High RAM usage).
lblMatchScrollIndicator=Match Scroll Indicator
nlMatchScrollIndicator=When enabled, show the scroll indicator on the match screen.
lblEnableMagnifier=Card Magnifier
nlEnableMagnifier=When enabled, displays a larger version of the hovered card during a match.
lblShowFPSDisplay=Show FPS Display
nlShowFPSDisplay=When enabled, show the FPS Display (Experimental).
lblEnableUnknownCards=Enable Unknown Cards

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@@ -157,6 +157,7 @@ public class ForgePreferences extends PreferencesStore<ForgePreferences.FPref> {
UI_ENABLE_PRELOAD_EXTENDED_ART("false"),
UI_ENABLE_BORDER_MASKING("Crop"),
UI_ENABLE_MATCH_SCROLL_INDICATOR("false"),
UI_ENABLE_MAGNIFIER("true"),
UI_SHOW_FPS("false"),
UI_NETPLAY_COMPAT("false"),
UI_ENABLE_DISPOSE_TEXTURES("false"),