|
- import { makeRemotelyCallable, remoteFunction } from 'webextension-rpc';
- import { parseMediaFragmentIdentifier } from '../util/media-fragment-identifier';
-
- const retrieveBookmarks = remoteFunction('retrieveBookmarks');
-
- function fragmentIdentifierToSelector(fragmentIdentifier) {
- if (fragmentIdentifier.startsWith('#')) {
- fragmentIdentifier = fragmentIdentifier.substring(1);
- }
- const selector = {
- type: 'FragmentSelector',
- value: fragmentIdentifier,
- };
- return selector;
- }
-
- function selectorToTime(selector) {
- if (selector.type !== 'FragmentSelector') {
- throw new Error(`Unsupported selector type: '${selector.type}'`);
- }
- const { start, end } = parseMediaFragmentIdentifier(selector.value);
- return { start, end };
- }
-
- export default async function init(playlist) {
- const eventEmitter = playlist.getEventEmitter();
-
- async function displayBookmarksInPage() {
- const bookmarks = await retrieveBookmarks({ url: document.URL });
- const bookmarksWithTime = bookmarks.map(bookmark => {
- const fragmentIdentifier = bookmark.url.split('#')[1];
- if (fragmentIdentifier === undefined) return null;
-
- const selector = fragmentIdentifierToSelector(fragmentIdentifier);
- try {
- const { start, end } = selectorToTime(selector);
- return { bookmark, start, end };
- } catch (err) {
- // Likely a fragment identifier we do not understand; skip it.
- return null;
- }
- }).filter(value => value !== null);
-
- bookmarksWithTime.sort(({ start: t1 }, { start: t2 }) => t1 - t2);
-
- const annotations = bookmarksWithTime.map(({ bookmark, start, end }) => ({
- start,
- end,
- id: bookmark.title,
- elementType: 'a',
- elementAttributes: {
- title: bookmark.title,
- href: bookmark.url,
- onclick: () => { eventEmitter.emit('select', start, end); },
- },
- }));
-
- playlist.setAnnotations({ annotations, annotationFormat: 'raw', editable: false });
- playlist.drawRequest();
- }
-
- makeRemotelyCallable({
- displayBookmarksInPage,
- });
-
- await displayBookmarksInPage();
- }
|