Open svera opened 2 months ago
CFI is the recommended way of storing references to specific locations in a book. You should store the value of event.detail.cfi
from the relocate
event dispatched by the <foliate-view>
element. To restore the location, you should call view.init({ lastLocation: 'your CFI string here' })
, where view
is the <foliate-view>
element.
(The view.init()
method differs from view.goTo()
in that if lastLocation
is undefined or cannot be resolved, it will display the first page of the book, or the first page of the main body text, i.e. the first chapter, if showTextStart
is true
.)
Going through the documentation, there is
.goTo({ index, anchor })
method in the renderer, but I don't know the format of the attributes it requires, even after looking to theresolveHref()
mentioned.
index
is an integer representing the index of the target section in the section
array. anchor(doc)
is a function. It takes one argument, a Document
object, and returns either an Element
or a Range
that will be displayed. If the return value is null
, it will show the start of the section.
Hi @johnfactotum thank you for the comprehensive explanation. I've implemented your suggestion and it works great, but sometimes the reader crashes with the following error, showing the book cover although the paginator is in the right position. This is reproducible refreshing the page several times:
paginator.js:367 Uncaught (in promise)
TypeError: Failed to execute 'unobserve' on 'ResizeObserver': parameter 1 is not of type 'Element'.
at View.destroy (paginator.js:367:43)
at #createView (paginator.js:555:24)
at #display (paginator.js:868:42)
at async #goTo (paginator.js:904:13)
at async View.init (view.js:154:13)
```
Hard to say without reproducing the error. It might be that it's a sort of race condition where sometimes View.init() is called before the a previous call to display a page is resolved. This is just a guess, though.
Hi @johnfactotum thank you for the comprehensive explanation. I've implemented your suggestion and it works great, but sometimes the reader crashes with the following error, showing the book cover although the paginator is in the right position. This is reproducible refreshing the page several times:
paginator.js:367 Uncaught (in promise) TypeError: Failed to execute 'unobserve' on 'ResizeObserver': parameter 1 is not of type 'Element'. at View.destroy (paginator.js:367:43) at #createView (paginator.js:555:24) at #display (paginator.js:868:42) at async #goTo (paginator.js:904:13) at async View.init (view.js:154:13) ```
Could you share your implemention? I'm looking forward to achieve this function, let's find out the problem together.
@johnfactotum @laosuan Here you have my current code with the suggestions made by @johnfactotum . It is basically the reader example provided in the Foliate, with some changes removing some features and making it translatable. Unfortunately, I does not work now, it always opens the document from the beginning, not the last stored position.
https://github.com/svera/coreander/blob/v4/internal/webserver/embedded/js/foliate-js/reader.js
From what I gather, the onrelocate
observer is called several times. When reloading the document after moving to another position in the document, the location is retrieved correctly, but finally it goes back to the beginning.
This is the PR with the changes related to this exact feature: https://github.com/svera/coreander/pull/95/files
Any clue what might be wrong in the code?
Can't say what's wrong exactly, but you might need to await
the view.init()
call.
Can't say what's wrong exactly, but you might need to
await
theview.init()
call.
Thank you @johnfactotum , I'll try that and let everyone know if that works.
UPDATE: It works with the await
!
Hi @johnfactotum
First of all, thank you for this library, it's really awesome :)
I'm trying to store the current page of a document to the browser's local storage, so the user can resume reading where he or she left off. My idea was to update the values in the local storage every time the
onRelocate
event is triggered, as seen in thereader.js
example reader, and then retrieve this value when loading again the document.Going through the documentation, there is
.goTo({ index, anchor })
method in the renderer, but I don't know the format of the attributes it requires, even after looking to theresolveHref()
mentioned.How can I achieve this?