Merge pull request #8197 from kevlahnota/master2

refactor planechase BG fetcher
This commit is contained in:
kevlahnota
2025-07-25 09:18:02 +08:00
committed by GitHub
3 changed files with 78 additions and 72 deletions

View File

@@ -37,50 +37,50 @@ public enum FSkinTexture implements FImage {
ADV_BG_DUNGEON(ForgeConstants.ADV_BG_DUNGEON_FILE, false, false), ADV_BG_DUNGEON(ForgeConstants.ADV_BG_DUNGEON_FILE, false, false),
ADV_BG_CASTLE(ForgeConstants.ADV_BG_CASTLE_FILE, false, false), ADV_BG_CASTLE(ForgeConstants.ADV_BG_CASTLE_FILE, false, false),
//CARD BG //CARD BG
CARDBG_A (ForgeConstants.IMG_CARDBG_A, false, false), CARDBG_A(ForgeConstants.IMG_CARDBG_A, false, false),
CARDBG_B (ForgeConstants.IMG_CARDBG_B, false, false), CARDBG_B(ForgeConstants.IMG_CARDBG_B, false, false),
CARDBG_BG (ForgeConstants.IMG_CARDBG_BG, false, false), CARDBG_BG(ForgeConstants.IMG_CARDBG_BG, false, false),
CARDBG_BR (ForgeConstants.IMG_CARDBG_BR, false, false), CARDBG_BR(ForgeConstants.IMG_CARDBG_BR, false, false),
CARDBG_C (ForgeConstants.IMG_CARDBG_C, false, false), CARDBG_C(ForgeConstants.IMG_CARDBG_C, false, false),
CARDBG_G (ForgeConstants.IMG_CARDBG_G, false, false), CARDBG_G(ForgeConstants.IMG_CARDBG_G, false, false),
CARDBG_L (ForgeConstants.IMG_CARDBG_L, false, false), CARDBG_L(ForgeConstants.IMG_CARDBG_L, false, false),
CARDBG_M (ForgeConstants.IMG_CARDBG_M, false, false), CARDBG_M(ForgeConstants.IMG_CARDBG_M, false, false),
CARDBG_R (ForgeConstants.IMG_CARDBG_R, false, false), CARDBG_R(ForgeConstants.IMG_CARDBG_R, false, false),
CARDBG_RG (ForgeConstants.IMG_CARDBG_RG, false, false), CARDBG_RG(ForgeConstants.IMG_CARDBG_RG, false, false),
CARDBG_U (ForgeConstants.IMG_CARDBG_U, false, false), CARDBG_U(ForgeConstants.IMG_CARDBG_U, false, false),
CARDBG_UB (ForgeConstants.IMG_CARDBG_UB, false, false), CARDBG_UB(ForgeConstants.IMG_CARDBG_UB, false, false),
CARDBG_UG (ForgeConstants.IMG_CARDBG_UG, false, false), CARDBG_UG(ForgeConstants.IMG_CARDBG_UG, false, false),
CARDBG_UR (ForgeConstants.IMG_CARDBG_UR, false, false), CARDBG_UR(ForgeConstants.IMG_CARDBG_UR, false, false),
CARDBG_V (ForgeConstants.IMG_CARDBG_V, false, false), CARDBG_V(ForgeConstants.IMG_CARDBG_V, false, false),
CARDBG_W (ForgeConstants.IMG_CARDBG_W, false, false), CARDBG_W(ForgeConstants.IMG_CARDBG_W, false, false),
CARDBG_WB (ForgeConstants.IMG_CARDBG_WB, false, false), CARDBG_WB(ForgeConstants.IMG_CARDBG_WB, false, false),
CARDBG_WG (ForgeConstants.IMG_CARDBG_WG, false, false), CARDBG_WG(ForgeConstants.IMG_CARDBG_WG, false, false),
CARDBG_WR (ForgeConstants.IMG_CARDBG_WR, false, false), CARDBG_WR(ForgeConstants.IMG_CARDBG_WR, false, false),
CARDBG_WU (ForgeConstants.IMG_CARDBG_WU, false, false), CARDBG_WU(ForgeConstants.IMG_CARDBG_WU, false, false),
PWBG_B (ForgeConstants.IMG_PWBG_B, false, false), PWBG_B(ForgeConstants.IMG_PWBG_B, false, false),
PWBG_BG (ForgeConstants.IMG_PWBG_BG, false, false), PWBG_BG(ForgeConstants.IMG_PWBG_BG, false, false),
PWBG_BR (ForgeConstants.IMG_PWBG_BR, false, false), PWBG_BR(ForgeConstants.IMG_PWBG_BR, false, false),
PWBG_C (ForgeConstants.IMG_PWBG_C, false, false), PWBG_C(ForgeConstants.IMG_PWBG_C, false, false),
PWBG_G (ForgeConstants.IMG_PWBG_G, false, false), PWBG_G(ForgeConstants.IMG_PWBG_G, false, false),
PWBG_M (ForgeConstants.IMG_PWBG_M, false, false), PWBG_M(ForgeConstants.IMG_PWBG_M, false, false),
PWBG_R (ForgeConstants.IMG_PWBG_R, false, false), PWBG_R(ForgeConstants.IMG_PWBG_R, false, false),
PWBG_RG (ForgeConstants.IMG_PWBG_RG, false, false), PWBG_RG(ForgeConstants.IMG_PWBG_RG, false, false),
PWBG_U (ForgeConstants.IMG_PWBG_U, false, false), PWBG_U(ForgeConstants.IMG_PWBG_U, false, false),
PWBG_UB (ForgeConstants.IMG_PWBG_UB, false, false), PWBG_UB(ForgeConstants.IMG_PWBG_UB, false, false),
PWBG_UG (ForgeConstants.IMG_PWBG_UG, false, false), PWBG_UG(ForgeConstants.IMG_PWBG_UG, false, false),
PWBG_UR (ForgeConstants.IMG_PWBG_UR, false, false), PWBG_UR(ForgeConstants.IMG_PWBG_UR, false, false),
PWBG_W (ForgeConstants.IMG_PWBG_W, false, false), PWBG_W(ForgeConstants.IMG_PWBG_W, false, false),
PWBG_WB (ForgeConstants.IMG_PWBG_WB, false, false), PWBG_WB(ForgeConstants.IMG_PWBG_WB, false, false),
PWBG_WG (ForgeConstants.IMG_PWBG_WG, false, false), PWBG_WG(ForgeConstants.IMG_PWBG_WG, false, false),
PWBG_WR (ForgeConstants.IMG_PWBG_WR, false, false), PWBG_WR(ForgeConstants.IMG_PWBG_WR, false, false),
PWBG_WU (ForgeConstants.IMG_PWBG_WU, false, false), PWBG_WU(ForgeConstants.IMG_PWBG_WU, false, false),
NYX_B (ForgeConstants.IMG_NYX_B, false, false), NYX_B(ForgeConstants.IMG_NYX_B, false, false),
NYX_G (ForgeConstants.IMG_NYX_G, false, false), NYX_G(ForgeConstants.IMG_NYX_G, false, false),
NYX_M (ForgeConstants.IMG_NYX_M, false, false), NYX_M(ForgeConstants.IMG_NYX_M, false, false),
NYX_R (ForgeConstants.IMG_NYX_R, false, false), NYX_R(ForgeConstants.IMG_NYX_R, false, false),
NYX_U (ForgeConstants.IMG_NYX_U, false, false), NYX_U(ForgeConstants.IMG_NYX_U, false, false),
NYX_W (ForgeConstants.IMG_NYX_W, false, false), NYX_W(ForgeConstants.IMG_NYX_W, false, false),
NYX_C (ForgeConstants.IMG_NYX_C, false, false), NYX_C(ForgeConstants.IMG_NYX_C, false, false),
GENERIC_PLANE("", false, true); GENERIC_PLANE("", false, true);
@@ -97,6 +97,7 @@ public enum FSkinTexture implements FImage {
repeat = repeat0; repeat = repeat0;
isPlanechaseBG = isPlanechaseBG0; isPlanechaseBG = isPlanechaseBG0;
} }
public static List<String> getValues() { public static List<String> getValues() {
if (planechaseString == null) { if (planechaseString == null) {
planechaseString = new ArrayList<>(); planechaseString = new ArrayList<>();
@@ -114,12 +115,13 @@ public enum FSkinTexture implements FImage {
public void load() { public void load() {
load(""); load("");
} }
public boolean load(String planeName) { public boolean load(String planeName) {
if (hasError) if (hasError)
return false; return false;
if (!planeName.isEmpty()) { if (!planeName.isEmpty()) {
texture = null; //reset texture = null; //reset
this.filename = planeName + ".jpg"; this.filename = ImageFetcher.getPlanechaseFilename(planeName);
} }
FileHandle preferredFile = isPlanechaseBG ? FSkin.getCachePlanechaseFile(filename) : FSkin.getSkinFile(filename); FileHandle preferredFile = isPlanechaseBG ? FSkin.getCachePlanechaseFile(filename) : FSkin.getSkinFile(filename);
if (preferredFile.exists()) { if (preferredFile.exists()) {
@@ -127,8 +129,7 @@ public enum FSkinTexture implements FImage {
texture = Forge.getAssets().getTexture(preferredFile, false); texture = Forge.getAssets().getTexture(preferredFile, false);
if (texture != null) if (texture != null)
isloaded = true; isloaded = true;
} } catch (final Exception e) {
catch (final Exception e) {
System.err.println("Failed to load skin file: " + preferredFile); System.err.println("Failed to load skin file: " + preferredFile);
e.printStackTrace(); e.printStackTrace();
isloaded = false; isloaded = false;
@@ -138,14 +139,14 @@ public enum FSkinTexture implements FImage {
if (texture == null) { if (texture == null) {
//use default file if can't use preferred file //use default file if can't use preferred file
FileHandle defaultFile = FSkin.getDefaultSkinFile(filename); FileHandle defaultFile = FSkin.getDefaultSkinFile(filename);
if(isPlanechaseBG) { if (isPlanechaseBG) {
ImageFetcher fetcher = GuiBase.getInterface().getImageFetcher(); ImageFetcher fetcher = GuiBase.getInterface().getImageFetcher();
fetcher.fetchImage("PLANECHASEBG:" + filename, () -> { fetcher.fetchImage("PLANECHASEBG:" + planeName, () -> {
hasError = false; hasError = false;
load(); load();
}); });
defaultFile = FSkin.getSkinFile(ForgeConstants.MATCH_BG_FILE); defaultFile = FSkin.getSkinFile(ForgeConstants.MATCH_BG_FILE);
if(!defaultFile.exists()) if (!defaultFile.exists())
defaultFile = FSkin.getDefaultSkinFile(ForgeConstants.MATCH_BG_FILE); defaultFile = FSkin.getDefaultSkinFile(ForgeConstants.MATCH_BG_FILE);
} }
@@ -153,16 +154,14 @@ public enum FSkinTexture implements FImage {
try { try {
texture = Forge.getAssets().getTexture(defaultFile); texture = Forge.getAssets().getTexture(defaultFile);
isloaded = true; isloaded = true;
} } catch (final Exception e) {
catch (final Exception e) {
System.err.println("Failed to load skin file: " + defaultFile); System.err.println("Failed to load skin file: " + defaultFile);
e.printStackTrace(); e.printStackTrace();
isloaded = false; isloaded = false;
hasError = true; hasError = true;
return false; return false;
} }
} } else {
else {
System.err.println("Failed to load skin file: " + defaultFile); System.err.println("Failed to load skin file: " + defaultFile);
isloaded = false; isloaded = false;
hasError = true; hasError = true;

View File

@@ -969,8 +969,7 @@ public class MatchScreen extends FScreen {
//overrideBG //overrideBG
if (!Forge.isMobileAdventureMode) { if (!Forge.isMobileAdventureMode) {
if (hasActivePlane()) { if (hasActivePlane()) {
imageName = getPlaneName().replace(" ", "_").replace("'", "") imageName = getPlaneName();
.replace("-", "").replace("!", "");
if (!plane.equals(imageName)) { if (!plane.equals(imageName)) {
plane = imageName; plane = imageName;
bgAnimation.progress = 0; bgAnimation.progress = 0;

View File

@@ -33,7 +33,8 @@ public abstract class ImageFetcher {
langCodeMap.put("ru-RU", "ru"); langCodeMap.put("ru-RU", "ru");
langCodeMap.put("zh-CN", "zhs"); langCodeMap.put("zh-CN", "zhs");
langCodeMap.put("zh-HK", "zht"); langCodeMap.put("zh-HK", "zht");
}; }
private HashMap<String, HashSet<Callback>> currentFetches = new HashMap<>(); private HashMap<String, HashSet<Callback>> currentFetches = new HashMap<>();
private HashMap<String, String> tokenImages; private HashMap<String, String> tokenImages;
@@ -49,7 +50,7 @@ public abstract class ImageFetcher {
if (!c.getEdition().equalsIgnoreCase(pc.getEdition())) { if (!c.getEdition().equalsIgnoreCase(pc.getEdition())) {
CardEdition ed = data.getEditions().get(pc.getEdition()); CardEdition ed = data.getEditions().get(pc.getEdition());
if (ed != null) { if (ed != null) {
String setCode =ed.getScryfallCode(); String setCode = ed.getScryfallCode();
String langCode = ed.getCardsLangCode(); String langCode = ed.getCardsLangCode();
downloadUrls.add(ForgeConstants.URL_PIC_SCRYFALL_DOWNLOAD + ImageUtil.getScryfallDownloadUrl(pc, face, setCode, langCode, useArtCrop)); downloadUrls.add(ForgeConstants.URL_PIC_SCRYFALL_DOWNLOAD + ImageUtil.getScryfallDownloadUrl(pc, face, setCode, langCode, useArtCrop));
} }
@@ -57,7 +58,7 @@ public abstract class ImageFetcher {
} else {// original from set } else {// original from set
CardEdition ed = data.getEditions().get(pc.getEdition()); CardEdition ed = data.getEditions().get(pc.getEdition());
if (ed != null) { if (ed != null) {
String setCode =ed.getScryfallCode(); String setCode = ed.getScryfallCode();
String langCode = ed.getCardsLangCode(); String langCode = ed.getCardsLangCode();
downloadUrls.add(ForgeConstants.URL_PIC_SCRYFALL_DOWNLOAD + ImageUtil.getScryfallDownloadUrl(pc, face, setCode, langCode, useArtCrop)); downloadUrls.add(ForgeConstants.URL_PIC_SCRYFALL_DOWNLOAD + ImageUtil.getScryfallDownloadUrl(pc, face, setCode, langCode, useArtCrop));
} }
@@ -81,6 +82,11 @@ public abstract class ImageFetcher {
return null; return null;
} }
public static String getPlanechaseFilename(final String cardName) {
return cardName.replace(" ", "_").replace("'", "")
.replace("-", "").replace("!", "").replace(":", "") + ".jpg";
}
public void fetchImage(final String imageKey, final Callback callback) { public void fetchImage(final String imageKey, final Callback callback) {
FThreads.assertExecutedByEdt(true); FThreads.assertExecutedByEdt(true);
@@ -93,20 +99,20 @@ public abstract class ImageFetcher {
// Fake card (like the ante prompt) trying to be "fetched" // Fake card (like the ante prompt) trying to be "fetched"
if (imageKey.length() < 2) if (imageKey.length() < 2)
return; return;
if (imageKey.startsWith(ImageKeys.BOOSTER_PREFIX)) if (imageKey.startsWith(ImageKeys.BOOSTER_PREFIX)) {
{
final ArrayList<String> downloadUrls = new ArrayList<>(); final ArrayList<String> downloadUrls = new ArrayList<>();
final String filename = imageKey.substring(ImageKeys.BOOSTER_PREFIX.length()); final String filename = imageKey.substring(ImageKeys.BOOSTER_PREFIX.length());
downloadUrls.add("https://downloads.cardforge.org/images/products/boosters/"+ filename); // TODO Update image server or alternative hosting
System.out.println("Fetching from "+downloadUrls); downloadUrls.add("https://downloads.cardforge.org/images/products/boosters/" + filename);
System.out.println("Fetching from " + downloadUrls);
FileUtil.ensureDirectoryExists(ForgeConstants.CACHE_BOOSTER_PICS_DIR); FileUtil.ensureDirectoryExists(ForgeConstants.CACHE_BOOSTER_PICS_DIR);
File destFile = new File(ForgeConstants.CACHE_BOOSTER_PICS_DIR, filename); File destFile = new File(ForgeConstants.CACHE_BOOSTER_PICS_DIR, filename);
System.out.println("Destination File "+ destFile.getAbsolutePath()+" exists: " + destFile.exists()); System.out.println("Destination File " + destFile.getAbsolutePath() + " exists: " + destFile.exists());
if(destFile.exists()) if (destFile.exists())
return; return;
setupObserver(destFile.getAbsolutePath(),callback,downloadUrls); setupObserver(destFile.getAbsolutePath(), callback, downloadUrls);
return; return;
} }
if (imageKey.equalsIgnoreCase("t:null")) if (imageKey.equalsIgnoreCase("t:null"))
@@ -115,8 +121,8 @@ public abstract class ImageFetcher {
//planechaseBG file... //planechaseBG file...
final ArrayList<String> downloadUrls = new ArrayList<>(); final ArrayList<String> downloadUrls = new ArrayList<>();
if (imageKey.startsWith("PLANECHASEBG:")) { if (imageKey.startsWith("PLANECHASEBG:")) {
final String filename = imageKey.substring("PLANECHASEBG:".length()); final String cardName = imageKey.substring("PLANECHASEBG:".length());
PaperCard pc = StaticData.instance().getVariantCards().getCard(filename.replace("_", " ").replace(".jpg", "")); PaperCard pc = StaticData.instance().getVariantCards().getCard(cardName);
if (pc != null) { if (pc != null) {
CardEdition ed = StaticData.instance().getEditions().get(pc.getEdition()); CardEdition ed = StaticData.instance().getEditions().get(pc.getEdition());
if (ed != null) { if (ed != null) {
@@ -124,7 +130,7 @@ public abstract class ImageFetcher {
String langCode = ed.getCardsLangCode(); String langCode = ed.getCardsLangCode();
downloadUrls.add("PLANECHASEBG:" + ForgeConstants.URL_PIC_SCRYFALL_DOWNLOAD + ImageUtil.getScryfallDownloadUrl(pc, "", setCode, langCode, true)); downloadUrls.add("PLANECHASEBG:" + ForgeConstants.URL_PIC_SCRYFALL_DOWNLOAD + ImageUtil.getScryfallDownloadUrl(pc, "", setCode, langCode, true));
FileUtil.ensureDirectoryExists(ForgeConstants.CACHE_PLANECHASE_PICS_DIR); FileUtil.ensureDirectoryExists(ForgeConstants.CACHE_PLANECHASE_PICS_DIR);
File destFile = new File(ForgeConstants.CACHE_PLANECHASE_PICS_DIR, filename); File destFile = new File(ForgeConstants.CACHE_PLANECHASE_PICS_DIR, getPlanechaseFilename(cardName));
if (destFile.exists()) if (destFile.exists())
return; return;
@@ -282,7 +288,8 @@ public abstract class ImageFetcher {
// Load the paper token from filename + edition // Load the paper token from filename + edition
CardEdition edition = StaticData.instance().getEditions().get(setCode); CardEdition edition = StaticData.instance().getEditions().get(setCode);
if (edition == null || edition.getType() == CardEdition.Type.CUSTOM_SET) return; //Custom set token, skip fetching. if (edition == null || edition.getType() == CardEdition.Type.CUSTOM_SET)
return; //Custom set token, skip fetching.
//PaperToken pt = StaticData.instance().getAllTokens().getToken(tokenName, setCode); //PaperToken pt = StaticData.instance().getAllTokens().getToken(tokenName, setCode);
Collection<CardEdition.EditionEntry> allTokens = edition.getTokens().get(tokenName); Collection<CardEdition.EditionEntry> allTokens = edition.getTokens().get(tokenName);
@@ -299,9 +306,9 @@ public abstract class ImageFetcher {
// Ideally we would have some mapping for generating card to determine which art indexed/collector number to try to fetch // Ideally we would have some mapping for generating card to determine which art indexed/collector number to try to fetch
// Token art we're downloading and which location we're storing it in. // Token art we're downloading and which location we're storing it in.
// Once we're pulling from PaperTokens this section will change a bit // Once we're pulling from PaperTokens this section will change a bit
Iterator <CardEdition.EditionEntry> it = allTokens.iterator(); Iterator<CardEdition.EditionEntry> it = allTokens.iterator();
CardEdition.EditionEntry tis; CardEdition.EditionEntry tis;
while(it.hasNext()) { while (it.hasNext()) {
tis = it.next(); tis = it.next();
String tokenCode = edition.getTokensCode(); String tokenCode = edition.getTokensCode();
String langCode = edition.getCardsLangCode(); String langCode = edition.getCardsLangCode();
@@ -335,6 +342,7 @@ public abstract class ImageFetcher {
setupObserver(destFile.getAbsolutePath(), callback, downloadUrls); setupObserver(destFile.getAbsolutePath(), callback, downloadUrls);
} }
private void setupObserver(final String destPath, final Callback callback, final ArrayList<String> downloadUrls) { private void setupObserver(final String destPath, final Callback callback, final ArrayList<String> downloadUrls) {
// Note: No synchronization is needed here because this is executed on // Note: No synchronization is needed here because this is executed on
// EDT thread (see assert on top) and so is the notification of observers. // EDT thread (see assert on top) and so is the notification of observers.