Skip to content

fix: scale indexed images, tileset narrower than one tile - #163

Merged
dogo merged 2 commits into
masterfrom
fix/scale-and-tileset
Nov 5, 2026
Merged

dogo merged 2 commits into
masterfrom
fix/scale-and-tileset

Conversation

@dogo

@dogo dogo commented Nov 5, 2026

Copy link
Copy Markdown
Owner

Summary

Two drawing bugs found while doing #158.

oslScaleImage / oslScaleImageCreate
-   readRow: oslConvertColor(8888, indexed, index)   # no palette: r=g=b=a=0
+   readRow: oslConvertColorEx(palette, 8888, indexed, index)
+   indexed destination, source in the same format:
+       index of the source pixel under each output pixel's centre (indices can't be blended)
+       oslScaleImageCreate copies the source's palette into the new image
+   indexed destination, any other source: refused (NULL / destination untouched)

oslDrawMap
-   tilesPerLine = img->sizeX / tileX                # 0 for a tileset narrower than a tile
-   v % tilesPerLine                                  # division by zero: break 7
+   return early if the tileset is narrower than a tile, or a tile/map size isn't positive
Commit Fix
ccb2fc7 oslDrawMap draws nothing instead of trapping on a tileset narrower than one tile; it also guards the other divisors (OSL_MAP's fields can change after oslCreateMap)
627a703 oslScaleImage reads indexed sources through their palette; it scales indexed images to their own format by index, with a copy of the palette, and refuses other sources for an indexed destination

Evidence

PSP-2000 (5.00 M33) over PSPLink, drawfix:

Case Before After
scale 8-bit 2x2 to 8888 4x4 16/16 wrong (transparent black) 0/16
scale 4-bit 2x2 to 8888 4x4 16/16 wrong 0/16
scale 8-bit 2x2 to 8-bit 5x3 13/15 wrong, no palette 0/15, palette copied
scale 8888 to 8-bit returned an image NULL
map whose tileset is narrower than a tile Exception - Breakpoint (break 0x7 after divu, map.c:106) 0 pixels drawn

drawfix's other cases pass, as do imgpal, imgload, formats, blend, imgmem, imgmisc, palvram, bigdraw and rotate, all matching their expected.txt.

Merge Danger

Door: two-way.

Blast Radius: image

  • Scaling an indexed image to true colour now gives its colours; it used to give transparent black.
  • oslScaleImageCreate returns NULL for a true-colour image scaled to an indexed format. It used to return an image with meaningless indices. oslScaleImage into an indexed destination from another format is now a no-op.
  • Scaling indexed to indexed uses nearest neighbour: no smoothing, by design.
  • A map with a tileset narrower than one tile used to crash and now draws nothing.

dogo added 2 commits November 5, 2026 12:53
oslDrawMap computes the tile count per line as the tileset's width over
the tile width, then divides tile indices by it: with a tileset narrower
than a tile that count is 0, and the division traps (Exception -
Breakpoint, break 7 after divu, map.c:106 on the PSP). It now returns
before drawing in that case, and when a tile or map size isn't positive:
oslCreateMap checks those, but OSL_MAP's fields can change afterwards
and every one of them divides something below.
oslScaleImage read pixels with oslConvertColor, which has no palette:
an indexed source came out transparent black. Writing to an indexed
destination stored converted colours as if they were indices. A source
is now read through its palette. An indexed destination needs a source
in its own format and takes the index under each pixel (indices can't
be blended); oslScaleImageCreate then gives the new image a copy of the
source's palette. Any other source for an indexed destination is
refused: blended colours have no palette to map to (NULL from
oslScaleImageCreate, oslScaleImage leaves the destination untouched).

drawfix: 8 and 4-bit to 8888, 16/16 wrong before, 0 now; 8-bit to
8-bit, 13/15 wrong and no palette before, 0 and a copied palette now;
8888 to 8-bit returned an image, now NULL.
@chatgpt-codex-connector

chatgpt-codex-connector Bot commented Nov 5, 2026 •

Copy link
Copy Markdown

Codex Review Summary

This comment shows the latest Codex review activity on this pull request.

Review Status Commit Review trigger
📝 Code Review ✅ Completed 2026-11-05T15:55:05.030924Z 627a703 PR opened
ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review" or "@codex security review".

Codex reacts with 👀 while any review is running, comments if it has suggestions, and reacts with 👍 once all reviews finish with no findings.

@dogo
dogo merged commit f882dcd into master Nov 5, 2026
14 checks passed
@dogo
dogo deleted the fix/scale-and-tileset branch November 5, 2026 15:56
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant