Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Converted all admonition boxes to new markup (#100) #101

Merged
merged 2 commits into from
Feb 4, 2024
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
12 changes: 6 additions & 6 deletions content/affbg.md
Original file line number Diff line number Diff line change
Expand Up @@ -159,11 +159,11 @@ const BG_AFFINE bg_aff_default= { 256, 0, 0, 256, 0, 0 };
REG_BG_AFFINE[2] = bg_aff_default;
```

<div class="note">
<div class="nhcare">Regular vs affine tilemap scrolling</div>
:::warning Regular vs affine tilemap scrolling

Affine tilemaps use **different** scrolling registers! Instead of REG_BG*x*HOFS and REG_BG*x*VOFS, they use REG_BG*x*X and REG_BG*x*Y. Also, these are 32bit fixed point numbers, not halfwords.
</div>

:::

## Positioning and transforming affine backgrounds {#sec-aff-ofs}

Expand Down Expand Up @@ -344,11 +344,11 @@ The screen entries themselves are also different from those of regular backgroun

And that's about it, really. No, wait there's one more issue: you have to be careful when filling or changing the map because *VRAM can only be accessed 16 or 32 bits at a time*. So if you have your map stored in an array of bytes, you'll have to cast it to `u16` or `u32` first. Or use [DMA](dma.html). OK, now I'm done.

<div class="note">
<div class="nhcare">Regular vs affine tilemap mapping differences</div>
:::warning Regular vs affine tilemap mapping differences

There are two important differences between regular and affine map formats. First, affine screen entries are merely one-byte tile indices. Secondly, the maps use a linear layout, rather than the division into 32x32t maps that bigger regular maps use.
</div>

:::

## *sbb_aff* demo {#sec-demo}

Expand Down
32 changes: 12 additions & 20 deletions content/affine.md
Original file line number Diff line number Diff line change
Expand Up @@ -71,13 +71,11 @@ In this chapter, I'll provide the **correct** interpretation of the **P**-matrix

This is going to be a purely theoretical page: you will find nothing that relates directly to sprites or backgrounds here; that's what the next two sections are for. Once again, we will be assisted by the lovely metroid (keep in cold storage for safe use). Please mind the direction of the y-axis and the angles, and do *not* leave without reading the [finishing up](#sec-finish) paragraph. This contains several key implementation details that will be ignored in the text preceding it, because they will only get in the way at that point.

<div class="note">
<div class="nhcare">
Be wary of documents covering affine parameters
</div>
:::warning Be wary of documents covering affine parameters

It's true. Pretty much every document I've seen that deals with this subject is problematic in some way. A lot of them give the wrong rotate-scale matrix (namely, the one in {@eq:incorrect_transform_matrix}), or misname and/or misrepresent the matrix and its elements.
</div>

:::

## Texture mapping and affine transformations.

Expand Down Expand Up @@ -399,23 +397,19 @@ We can now use these definitions to find the correct matrix for enlargements by

… ermm, wait a sec … I'm having this strange sense of déja-vu here …

<div class="note" markdown>
<div class="nh" markdown>
Clockwise vs counterclockwise
</div>
:::note Clockwise vs counterclockwise

It's a minor issue, but I have to mention it. If the definition of **R** uses a clockwise rotation, why am I suddenly using a counter-clockwise one? Well, traditionally **R** is given as that particular matrix, in which the angle runs from the x-axis towards the y-axis. Because *y* is downward, this comes down to clockwise. However, the affine routines in BIOS use a counter-clockwise rotation, and I thought it'd be a good idea to use that as a guideline for my functions.
</div>

<div class="note" markdown>
<div class="nh" markdown>
Nomenclature: Affine vs Rot/Scale
</div>
:::

:::note Nomenclature: Affine vs Rot/Scale

The matrix **P** is not a rotation matrix, not a scaling matrix, but a general affine transformation matrix. Rotation and scaling may be what the matrix is mostly used for, but that does not mean they're the only things possible, as the term ‘Rot/Scale’ would imply.

To set them apart from regular backgrounds and sprites, I suppose ‘Rotation’ or ‘Rot/Scale’ are suitable enough, just not entirely accurate. However, calling the **P**-matrix by those names is simply wrong.
</div>

:::

## “Many of the truths we cling to depend greatly upon our own point of view.”

Expand Down Expand Up @@ -607,15 +601,13 @@ Now, fixed point numbers are still just integers, but there are different types



<div class="note" markdown>
<div class="nhgood" markdown>
Use 32-bit signed ints for affine temporaries
</div>
:::tip Use 32-bit signed ints for affine temporaries

Of course you should use 32bit variables for everything anyway (unless you actually *want* your code to bloat and slow down). If you use 16bit variables (`short` or `s16`), not only will your code be slower because of all the extra instructions that are added to keep the variables 16bit, but overflow problems can occur much sooner.

Only in the final step to hardware should you go to 8.8 format. Before that, use the larger types for both speed and accuracy.
</div>

:::

### LUTs {#sec-luts}

Expand Down
16 changes: 6 additions & 10 deletions content/affobj.md
Original file line number Diff line number Diff line change
Expand Up @@ -184,15 +184,13 @@ p_{c} & p_{d}

Note that the origin of the transformation is *center* of the sprite, not the top-left corner. This is worth remembering if you want to align your sprite with other objects, which we'll do later.

<div class="note">
<div class="nhgood">
Essential affine sprite steps
</div>
:::tip Essential affine sprite steps

- Set-up an object as usual: load graphics and palette, set `REG_DISPCNT`, set-up an OAM entry.
- Set bit 8 of attribute 0 to enable affinity for that object, and choose an object affine matrix to use (attribute 1, bits 8-12).
- Set that obj affine matrix to something other than all zeroes, for example the identity matrix.
</div>

:::

## Graphical artifacts {#sec-artifact}

Expand Down Expand Up @@ -302,13 +300,11 @@ The center pixel is the reference point of the transformation algorithm, which h
</table>
</div>

<div class="note">
<div class="nhcare">
The offsets measure distance from the center pixel, not center position.
</div>
:::warning The offsets measure distance from the center pixel, not center position.

The offsets that are calculated from the affine matrix use the distances from the center pixel (*w*/2, *h*/2), not the center point. As such, there is a half a pixel deviation from the mathematical transformation, which may result in a ±pixel offset for the sprite as a whole and lost texture edges.
</div>

:::

### The wrapping artifact {#ssec-wrap}

Expand Down
Loading
Loading