Skip to content

🐛 (expo): Fix various RTL reader issues#786

Merged
aaronleopold merged 10 commits intostumpapp:breaking/sea-ormfrom
Arklaum:expo
Oct 6, 2025
Merged

🐛 (expo): Fix various RTL reader issues#786
aaronleopold merged 10 commits intostumpapp:breaking/sea-ormfrom
Arklaum:expo

Conversation

@Arklaum
Copy link
Copy Markdown
Collaborator

@Arklaum Arklaum commented Oct 5, 2025

This contains various fixes for RTL mode, and of course make it work in the first place (it was a double inversion issue). I'm so happy to finally be able to read my books without the swipe direction confusing me.

It also contains a few visual improvements:

  1. fix uneven grid spacing when the number of columns is larger than 3, e.g. on an iPad. Here is Before and After (best viewed by flipping between the two browser tabs).
  2. Remove vertical centering of thumbnails in a library. Side note: the Before in (1.) was actually not technically the Before image, this is but it doesn't include removing the centering so it's hard to see the difference.
  3. Made landscape images use the same height as other thumbnails in the footer gallery. Note: need to do that for the browser too.

I saw some TODO's that said swap to FlashList for performance improvements, but they don't have any inverted prop (which the RTL logic currently relies on and I don't feel like changing it unless I have to). I also saw another comment somewhere else about LegendList and those do have an inverted prop, so I might give that a go.

I also updated my little list to be easy to tick completed stuff: #770 (comment)

I'm curious about if you look at each commit separately or the whole thing at once?

@Arklaum Arklaum changed the title 🐛 Fix various RTL reader issues 🐛 (expo): Fix various RTL reader issues Oct 5, 2025
Copy link
Copy Markdown
Collaborator

@aaronleopold aaronleopold left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As usual, this looks great! Thank you for consistently making this app better and better!

I saw some TODO's that said swap to FlashList for performance improvements, but they don't have any inverted prop (which the RTL logic currently relies on and I don't feel like changing it unless I have to)

They do have guidance for migrating usages of inverted from FlashList v1 to v2: https://shopify.github.io/flash-list/docs/v2-migration#step-4-replace-inverted-lists. It does mention manually reversing the data set which is an unfortunate burden on us (but understandable from their perspective I'm sure haha).

I also saw another comment somewhere else about LegendList and those do have an inverted prop, so I might give that a go.

I did try LegendList before really landing on FlashList and had lots of awkward recycler issues from what I remember, but especially on Android. I think they also released a v2 around the same time as FlashList, though, which I haven't tried yet

I also updated my little list to be easy to tick completed stuff: #770 (comment)

❤️

I'm curious about if you look at each commit separately or the whole thing at once?

I usually give the commits a glance before digging in, but I mostly just look at the whole thing all at once. I think having clean, smaller commits like this makes it really convenient if I encounter something that is easier to process in a reduced scope (i.e., just the commit) but the review tools GitHub provides makes the review overall easier all at once

Comment on lines +241 to +254
const getSliderValue = useCallback(
(idx: number) => {
if (readingDirection === ReadingDirection.Rtl) {
return pageSets.length - 1 - idx
} else return idx
},
[pageSets.length, readingDirection],
)

/**
* A function that takes the slider value and returns the corresponding pageSet index
* It uses the same logic as getSliderValue
*/
const getPageSetIndex = useCallback((value: number) => getSliderValue(value), [getSliderValue])
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Super unimportant, but I would say these should be "inverted" so that getSliderValue invokes getPageSetIndex (basically just swapping the names I guess)

Copy link
Copy Markdown
Collaborator Author

@Arklaum Arklaum Oct 5, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Note: I didn't use the same function just for clarity. I could've used

const getPageSetIndex = getSliderValue

but then the input name being idx on both annoyed me. I've done the swap, so if I did that (inverted obv) they both would say value , which is okay, even though I only intended to use that word for slider value. Would that be better?

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No yeah I totally agree with your choice against just doing const getPageSetIndex = getSliderValue, this was just a super minor nit. I don't have a super strong opinion either way, just something that stuck out in my brain

<Text className="text-center">{pageSet.map((i) => i + 1).join('-')}</Text>
<Text className="text-center">
{pageSet
.sort((a, b) => a - b) // we always use (from left to right) the smaller then larger number even if using RTL (e.g. pages 3-4 and never 4-3)
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

TIL, thank you

@Arklaum
Copy link
Copy Markdown
Collaborator Author

Arklaum commented Oct 6, 2025

As usual

❤️ Aww I like those words

They do have guidance for migrating usages of inverted from FlashList v1 to v2: https://shopify.github.io/flash-list/docs/v2-migration#step-4-replace-inverted-lists. It does mention manually reversing the data set which is an unfortunate burden on us (but understandable from their perspective I'm sure haha).
...
I did try LegendList before really landing on FlashList and had lots of awkward recycler issues from what I remember, but especially on Android. I think they also released a v2 around the same time as FlashList, though, which I haven't tried yet

Well it might be okay then. When I tried removing the inverted prop and using inverted page sets there was weirdness and flickering when changing page. I'll give it another look, I'm sure it's fine and I'm just being dramatic.

@aaronleopold
Copy link
Copy Markdown
Collaborator

aaronleopold commented Oct 6, 2025

Well it might be okay then. When I tried removing the inverted prop and using inverted page sets there was weirdness and flickering when changing page. I'll give it another look, I'm sure it's fine and I'm just being dramatic.

Haha I'm sure it's not the latter. Fwiw I do also remember some weirdness and flickering when using FlastList for the reader, in fact I recall writing a comment somewhere something to the effect of "this reader really doesn't like flashlist" which in hindsight is really vague. But also that was v1, I haven't tried again since upgrading.

Also I'd be curious how much benefit using it would even provide. I'd love to measure it, if possible, but I imagine most of the benefit will come to those using Android devices. For whatever reason, react native often just feels more optimized on iOS unfortunately. For instance, I just loaded up my TPB Invincible Universe (660 pages) almost instantaneously with no stutter or lag.


I'll aim to merge this shortly 🙂

@aaronleopold aaronleopold merged commit bdd7529 into stumpapp:breaking/sea-orm Oct 6, 2025
3 of 4 checks passed
@Arklaum Arklaum deleted the expo branch October 6, 2025 10:41
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.

2 participants