I have always struggled to find a PDF or EPUB reader that I actually enjoy using.
My workflow is already deeply integrated with the browser. I use its history and bookmarks all the time, so I would like to read PDFs and ebooks directly in the browser.
A browser extension based on embedPDF. It intercepts file://*.pdf and https://*.pdf URLs and redirects them to the extension’s viewer.
More details and source code: jay-waves/pdf.ts
A Chrome extension based on foliate-js. It intercepts file://*.epub and https://*.epub URLs and redirects them to the extension’s reader.
More details and source code: jay-waves/epub.ts
Google’s design is consistent, but I do not find it attractive… The toolbar at the top is much too tall.
It is powerful, but most of its PDF editing features seem unnecessary for everyday reading.
It has a Windows 7 look. It is lightweight and certainly has a geeky feel.
I think it looks quite good, but recent updates keep adding features that do not make sense to me. Also, the web version cannot intercept file:// URLs directly, so you have to import files manually before reading them.
Web apps run in a controlled browser sandbox, where the browser governs and checks their behavior. When turning a web app into a local Windows or Linux app, the hardest part is extending its access to the local system. Web apps have limited access to the filesystem, process control, and system integration such as file associations and startup tasks.
Take the browser File System Access API as an example. To read a file, the app must open a file picker and ask the user to select it and grant permission. To write to a file, Chromium-based browsers show a dialog asking the user to select the original file and grant permission; subsequent writes overwrite that file. Safari/WebKit and Firefox still do not support writable handles to local files, so they can only download a copy to a fixed download directory.
In other words, access is restricted, and browser APIs and capabilities also differ. Maintaining the app across browsers is difficult.
There are three common approaches:
Here are the design choices I made for each platform:
When a user opens a *.pdf or *.epub file, the browser opens its file:// URI. The extension listens for this and redirects the file to its own viewer.
When the user edits a file and needs to save it, a dialog asks where to write it. Choosing the original file overwrites it in place.
When the user opens jay-waves.cn/epub.ts, a welcome screen appears. The user selects or drops a file to open it in the reader. Because this follows a direct user action, Chromium-based browsers allow the app to request both read and write access.
When the user edits a file and saves it, Safari or Firefox triggers a download, while Chrome writes the changes back to the original file.
I wrote a small Go launcher for the desktop app. It can run as a background service, though it does not do so automatically. For example, pdf.ts.exe embeds all the web app’s resources and registers itself as a PDF file handler.
When a PDF is opened, the web app’s resources are temporarily extracted and opened in the browser. When the user later saves changes, the web app communicates over the local network with the listening pdf.ts.exe, which performs the file write on its behalf.