max-kamps / jpd-breader

MIT License
100 stars 24 forks source link

JPDB Web Reader Extension

A browser extension that parses any text in your browser using JPDB, and allows you to mine new vocabulary from any page!

Is this ready to use yet?

Maybe? Some parts of the interface are temporary and quite ugly, but otherwise it should mostly work.

Installation

Chrome and other Chromium-based browsers

  1. Download the latest .zip file from the releases page
  2. Unpack the zip file in a location of your choosing
  3. Open up your browser and navigate to chrome://extensions/
  4. Check the Developer mode switch at the top right of your window
  5. Click the Load unpacked button at the top left
  6. In the file picker dialog, navigate to the folder you unpacked earlier. You should see a file called manifest.json inside the folder
  7. Click select/open/choose to exit the dialog and load the extension
  8. Continue with the Initial Setup section

That sounds like a hassle. Why don't you upload the extension to the Chrome store instead?

The Chrome store is not accepting new manifest v2 extensions, only manifest v3. But there are several problems with Manifest v3:

Firefox

  1. Download the latest .xpi file from the releases page
  2. Firefox should automatically ask you if you want to add the extension. Click Add
  3. Continue with the Initial Setup section

That's it, you are done. If this method does not work for you, you can try this alternate approach:

  1. Download the latest .xpi file from the releases page
  2. Open Firefox and navigate to about:addons
  3. Click on the little gear icon to the right of Manage Your Extensions
  4. Click Install Add-on from File...
  5. In the file picker dialog, select the .xpi file
  6. Continue with the Initial Setup section

Mobile browsers (Kiwi Browser)

Experimental Support: Although the UI is not yet optimized for mobile usage, you can still make use of it.

To Parse a Page:

  1. Click on the three dots located at the top right corner.
  2. From the menu that appears, select the extension to display the reader menu.
  3. Choose the option "Parse page" to initiate the parsing process.

To show the popup on tap activate the "Show the popup on hover" and "Touchscreen support" settings.

Initial Setup

Open the settings page. You can find it by clicking on the reader icon (読) in the browser menu bar. It might be hidden behind the extension overflow menu, which looks like a little puzzle piece (🧩) Here you will need to enter your jpdb API key. It can be found at the very bottom of the jpdb settings page. You can also change various hotkeys

Usage

You can use the reader on any website. Just select some text, right click, and choose the "Parse ... with jpdb" option. Words will be colored according to their state (known, new, etc.) Hover over words while holding to see their meaning, and to mine or review them.

The following pages require special support for technical reasons, and will therefore start parsing immediately:

Can I customize the colors? Can I customize which furigana get shown?

Customization is currently done with custom CSS, because that took the least amount of time to develop :) If you need some help, please ask in the jpdb Discord thread.

Here are some common customizations you might want. Feel free to use multiple of them, and modify them to your liking.

Don't color words:

.jpdb-word { color: inherit; /* inherit color from the website instead of using a custom color */ }

Only color new words:

.jpdb-word { color: inherit; }
.jpdb-word.new { color: rgb(75, 141, 255); }
.jpdb-word.not-in-deck { color: rgb(126, 173, 255); }

Show an underline rather than changing the text color:

.jpdb-word.new {
    color: inherit;
    text-decoration: underline 3px rgb(75, 141, 255);
}

Hide all jpdb furigana:

.jpdb-furi { display: none; }

Hide jpdb furigana only for some classes of words:

.jpdb-word:is(.never-forget, .known, .due, .failed) .jpdb-furi { display: none; }

Only show jpdb furigana while hovering:

.jpdb-word:not(:hover) .jpdb-furi { visibility: hidden; }

Notes if you aren't super familiar with CSS:

List of classes:

Building

You can run the following command to build the release zip file:

$ npm install
$ npm run build

The resulting file will be located in the dist/ folder

For development, you can also run the build in watch mode:

$ npm install
$ npm run watch

This will continuously rebuild the source code as it changes, and place the output in the build/ folder. It can be loaded as an unpacked extension from there. Please remember to wait until building is done, and reload the extension on the "manage extensions" page before testing your changes. Also, please look at the Contributing section if you plan on contributing your changes.

Contributing

Issues with feedback or ideas for new features are very welcome. You can also message me on the JPDB Discord server (@hmry#6502).

The following commands may be of interest to you:

Please note the following:

(Don't worry too much about this. If you forget, I will (probably) notice during code review and fix it after merging.)

If your change is large, or adds new dependencies, please consider opening an issue beforehand, so we may discuss. Otherwise, I may choose to reject your pull request. Sorry.

For contributing, you can of course use any editor you want. I use VSCode, and have included my .code-workspace file with recommended project-specific settings if you want it. You may need to open it using the File > Open Workspace from File menu option. To make full use of it, you will need to install the Prettier (esbenp.prettier-vscode) and ESlint (dbaeumer.vscode-eslint) extensions. No matter which editor you choose, having Prettier format on save is something you might find worth setting up.

This project uses ttypescript to automatically transform files. Any module with a leading @reader content-script comment, such as

// @reader content-script
import { nonNull } from '../util.js'
nonNull(12);

will get transformed into a file that can be used as a browser content script, like this:

(async () => {
    "use strict";
    const $browser = globalThis.browser ?? globalThis.chrome,
          $import = path => import($browser.runtime.getURL(path));

    const { nonNull } = await $import("/util.js");
    nonNull(12);
})();

License

MIT