Standalone Drupal add-on for `islandora_mirador` that adds persistent Mirador 4 annotations using Mirador Annotation Editor (MAE).
## Features
- Leaves the base `islandora_mirador` module untouched.
- Drupal-backed persistent Web Annotations.
- Existing MAE per-canvas annotation editor/sidebar.
- **All annotations** sidebar for multi-page manifests.
- All-annotations results are grouped by canvas/page label and searchable.
- Clicking an annotation in the all-annotations panel jumps Mirador to that canvas.
- A single Drupal query loads annotations for the complete manifest; it does not make one Drupal request per page.
## Architecture
The base `islandora_mirador` module is not patched. This module:
This module alters the base viewer library dependency so the viewer loads this module's annotated Mirador bundle. The bundle contains Mirador, the normal Islandora image-tools/text-overlay/download plugins, MAE, a Drupal persistence adapter, and the All Annotations companion-window plugin.
1. Alters the base viewer library dependency so the viewer loads this module's annotated Mirador bundle.
2. Builds that bundle from the same Mirador 4 plugins used by Islandora plus MAE.
3. Excludes MAE's currently incompatible `annotationSagaPlugin` and replaces only its annotation-loading behavior.
4. Adds a Drupal-backed MAE adapter.
5. Stores each Web Annotation as JSON in `islandora_mirador_annotation`.
6. Exposes an IIIF `AnnotationPage` at `/islandora-mirador/annotations?canvas=...`.
7. Protects POST/PATCH/DELETE with Drupal permissions and `X-CSRF-Token`.
MAE's incompatible `annotationSagaPlugin` is excluded and its canvas-loading behavior is replaced locally.
## Install
Place this directory next to `islandora_mirador`, then enable it:
```bash
drush en islandora_mirador_annotations -y
drush cr
```
Grant permissions as appropriate. For example, to let anonymous and authenticated users see annotations, grant `view mirador annotations` to those roles. Grant `manage mirador annotations` only to roles that may create/edit/delete annotations.
The module automatically sets MAE to read-only when the current user does not have `manage mirador annotations`.
Grant `view mirador annotations` to roles that may see annotations and `manage mirador annotations` to roles that may create/edit/delete them.
## Build `dist/main.js`
The build project is retained under `build/`.
## Build assets
```bash
cd build
@ -37,30 +35,38 @@ npm install
npm run build
```
Vite writes the bundle to `../dist/main.js`.
The bundle intentionally contains Mirador itself, the Islandora image-tools/text-overlay/download plugins, and MAE in one dependency graph. This avoids loading a second React/MUI runtime beside the base Mirador bundle.
Vite writes:
## Base module
```text
dist/main.js
dist/main.css
```
No changes to `islandora_mirador` are required. When this module is disabled, the base viewer returns to its normal `islandora_mirador/mirador` dependency after a cache rebuild.
Both compiled files should be committed to the module repository so Composer users do not need Node/npm/Vite.
## Endpoint
## Endpoints
GET:
Current-canvas AnnotationPage:
```text
/islandora-mirador/annotations?canvas=<canvasURI>
GET /islandora-mirador/annotations?canvas=<canvasURI>
```
returns:
Manifest-wide read endpoint used by the All Annotations panel:
MAE writes through the same endpoint using POST, PATCH, and DELETE.
Annotation writes use POST/PATCH/DELETE on `/islandora-mirador/annotations` and are protected by Drupal permissions and `X-CSRF-Token`.
## All annotations click-to-focus
Selecting an entry in the **All annotations** panel switches to its canvas, selects the Mirador annotation so its target is highlighted, and, when the annotation contains an `xywh` FragmentSelector, zooms OpenSeadragon to that region with a small amount of padding. Both pixel and percent `xywh` selectors are supported.
### 0.2.5 annotation targeting
The All Annotations panel uses the Web Annotation `target.source` as the authoritative canvas when it differs from the persistence row's canvas id. It also zooms to MAE `SvgSelector` geometry when an `xywh` FragmentSelector is not available.