polats Claude Opus 4.8 (1M context) commited on
Commit
c2de8fb
·
1 Parent(s): 7411f15

Serve sprites at /sprites (not /assets — collided with Gradio's UI bundle)

Browse files
Files changed (2) hide show
  1. app.py +3 -1
  2. web/tiny.js +5 -2
app.py CHANGED
@@ -65,7 +65,9 @@ with gr.Blocks(title="Tiny Army") as demo:
65
  # Mount Gradio on FastAPI so we can also serve the JS module + the sprite assets.
66
  fastapi_app = FastAPI()
67
  fastapi_app.mount("/web", StaticFiles(directory=WEB), name="web")
68
- fastapi_app.mount("/assets", StaticFiles(directory=os.path.join(WEB, "assets")), name="assets")
 
 
69
  app = gr.mount_gradio_app(fastapi_app, demo, path="/", head=HEAD, theme=gr.themes.Soft())
70
 
71
 
 
65
  # Mount Gradio on FastAPI so we can also serve the JS module + the sprite assets.
66
  fastapi_app = FastAPI()
67
  fastapi_app.mount("/web", StaticFiles(directory=WEB), name="web")
68
+ # NOTE: serve sprite assets at /sprites, NOT /assets — Gradio serves its own UI
69
+ # bundle from /assets, and mounting there shadows it (breaks the whole UI).
70
+ fastapi_app.mount("/sprites", StaticFiles(directory=os.path.join(WEB, "assets")), name="sprites")
71
  app = gr.mount_gradio_app(fastapi_app, demo, path="/", head=HEAD, theme=gr.themes.Soft())
72
 
73
 
web/tiny.js CHANGED
@@ -31,9 +31,12 @@ window.tinyResize = () => {
31
 
32
  // ── Sprite Animations tab ────────────────────────────────────────────────────
33
  let charMap = null
 
 
 
34
  async function loadChars() {
35
  if (charMap) return charMap
36
- const d = await fetch('/assets/characters.json').then((r) => r.json())
37
  charMap = {}
38
  for (const p of d.packs || []) for (const c of p.characters || []) charMap[c.slug] = c
39
  return charMap
@@ -52,7 +55,7 @@ whenEl('sprite-stage', async (el) => {
52
  window.tinyShowSprite = async (slug, anim) => {
53
  const map = await loadChars()
54
  const c = map[slug]; if (!c) return
55
- const url = c[anim] || c.idle; if (!url) return
56
  const tex = await PIXI.Assets.load(url); tex.source.scaleMode = 'nearest'
57
  const cell = Math.round(tex.source.height / 4) // minifantasy: 4 facing rows
58
  const cols = Math.max(1, Math.round(tex.source.width / cell))
 
31
 
32
  // ── Sprite Animations tab ────────────────────────────────────────────────────
33
  let charMap = null
34
+ // Sprite assets are served at /sprites (not /assets — that's Gradio's bundle).
35
+ // The manifest paths are authored as /assets/… so rewrite the prefix.
36
+ const spriteUrl = (u) => (u || '').replace('/assets/', '/sprites/')
37
  async function loadChars() {
38
  if (charMap) return charMap
39
+ const d = await fetch('/sprites/characters.json').then((r) => r.json())
40
  charMap = {}
41
  for (const p of d.packs || []) for (const c of p.characters || []) charMap[c.slug] = c
42
  return charMap
 
55
  window.tinyShowSprite = async (slug, anim) => {
56
  const map = await loadChars()
57
  const c = map[slug]; if (!c) return
58
+ const url = spriteUrl(c[anim] || c.idle); if (!url) return
59
  const tex = await PIXI.Assets.load(url); tex.source.scaleMode = 'nearest'
60
  const cell = Math.round(tex.source.height / 4) // minifantasy: 4 facing rows
61
  const cols = Math.max(1, Math.round(tex.source.width / cell))