From c524dcd9d37fee1a943ee6d3ec0a8e3c29f877d6 Mon Sep 17 00:00:00 2001
From: Jack Reed <phillipjreed@gmail.com>
Date: Fri, 15 Mar 2019 16:52:41 -0600
Subject: [PATCH] Add getSelectedTargetsAnnotations that selects annotations by
 multiple targets

---
 __tests__/src/selectors/index.test.js         | 38 ++++++++++++++++---
 src/containers/OpenSeadragonViewer.js         |  4 +-
 .../WindowSideBarAnnotationsPanel.js          |  4 +-
 src/containers/WindowSideBarButtons.js        |  4 +-
 src/state/selectors/index.js                  | 25 +++++++++---
 5 files changed, 59 insertions(+), 16 deletions(-)

diff --git a/__tests__/src/selectors/index.test.js b/__tests__/src/selectors/index.test.js
index 22a5c8f14..d168e4894 100644
--- a/__tests__/src/selectors/index.test.js
+++ b/__tests__/src/selectors/index.test.js
@@ -19,7 +19,8 @@ import {
   getManifestProvider,
   getManifestTitle,
   getManifestThumbnail,
-  getSelectedCanvasAnnotations,
+  getSelectedTargetAnnotations,
+  getSelectedTargetsAnnotations,
   getWindowViewType,
   getIdAndLabelOfCanvases,
   getCompanionWindowsOfWindow,
@@ -325,7 +326,7 @@ describe('getDestructuredMetadata', () => {
   });
 });
 
-describe('getSelectedCanvasAnnotations', () => {
+describe('getSelectedTargetAnnotations', () => {
   it('returns annotations for the given canvasId that have resources', () => {
     const state = {
       annotations: {
@@ -337,15 +338,42 @@ describe('getSelectedCanvasAnnotations', () => {
       },
     };
 
-    expect(getSelectedCanvasAnnotations(state, 'abc123').length).toEqual(1);
+    expect(getSelectedTargetAnnotations(state, 'abc123').length).toEqual(1);
   });
 
   it('returns an empty array if there are no annotations', () => {
     const state = { annotations: { xyz321: {} } };
     const expected = [];
 
-    expect(getSelectedCanvasAnnotations({}, 'abc123')).toEqual(expected);
-    expect(getSelectedCanvasAnnotations(state, 'abc123')).toEqual(expected);
+    expect(getSelectedTargetAnnotations({}, 'abc123')).toEqual(expected);
+    expect(getSelectedTargetAnnotations(state, 'abc123')).toEqual(expected);
+  });
+});
+
+describe('getSelectedTargetsAnnotations', () => {
+  it('returns annotations for multiple canvasIds', () => {
+    const state = {
+      annotations: {
+        abc123: {
+          annoId1: { '@id': 'annoId1', json: { resources: ['aResource'] } },
+          annoId2: { '@id': 'annoId2' },
+          annoId3: { '@id': 'annoId3', json: { resources: [] } },
+        },
+        def456: {
+          annoId4: { '@id': 'annoId4', json: { resources: ['helloWorld'] } },
+        },
+      },
+    };
+
+    expect(getSelectedTargetsAnnotations(state, ['abc123', 'def456']).length).toEqual(2);
+  });
+
+  it('returns an empty array if there are no annotations', () => {
+    const state = { annotations: { xyz321: {} } };
+    const expected = [];
+
+    expect(getSelectedTargetsAnnotations({}, ['abc123'])).toEqual(expected);
+    expect(getSelectedTargetsAnnotations(state, ['abc123'])).toEqual(expected);
   });
 });
 
diff --git a/src/containers/OpenSeadragonViewer.js b/src/containers/OpenSeadragonViewer.js
index 176c92cc3..5d6570d46 100644
--- a/src/containers/OpenSeadragonViewer.js
+++ b/src/containers/OpenSeadragonViewer.js
@@ -8,7 +8,7 @@ import * as actions from '../state/actions';
 import {
   getCanvasLabel,
   getSelectedCanvas,
-  getSelectedCanvasAnnotations,
+  getSelectedTargetsAnnotations,
 } from '../state/selectors';
 
 /**
@@ -24,7 +24,7 @@ const mapStateToProps = ({
     getSelectedCanvas({ windows, manifests }, windowId),
     windows[windowId].canvasIndex,
   ),
-  annotations: getSelectedCanvasAnnotations(
+  annotations: getSelectedTargetsAnnotations(
     { annotations },
     currentCanvases.map(canvas => canvas.id),
   ),
diff --git a/src/containers/WindowSideBarAnnotationsPanel.js b/src/containers/WindowSideBarAnnotationsPanel.js
index 2480d1c64..0fe2ea737 100644
--- a/src/containers/WindowSideBarAnnotationsPanel.js
+++ b/src/containers/WindowSideBarAnnotationsPanel.js
@@ -4,7 +4,7 @@ import { withTranslation } from 'react-i18next';
 import {
   getIdAndContentOfResources,
   getSelectedCanvas,
-  getSelectedCanvasAnnotations,
+  getSelectedTargetAnnotations,
   getAnnotationResourcesByMotivation,
 } from '../state/selectors';
 import { WindowSideBarAnnotationsPanel } from '../components/WindowSideBarAnnotationsPanel';
@@ -17,7 +17,7 @@ import { WindowSideBarAnnotationsPanel } from '../components/WindowSideBarAnnota
 const mapStateToProps = (state, { windowId }) => ({
   annotations: getIdAndContentOfResources(
     getAnnotationResourcesByMotivation(
-      getSelectedCanvasAnnotations(state, getSelectedCanvas(state, windowId).id),
+      getSelectedTargetAnnotations(state, getSelectedCanvas(state, windowId).id),
       ['oa:commenting', 'sc:painting'],
     ),
   ),
diff --git a/src/containers/WindowSideBarButtons.js b/src/containers/WindowSideBarButtons.js
index 71738d39c..d534d4e2d 100644
--- a/src/containers/WindowSideBarButtons.js
+++ b/src/containers/WindowSideBarButtons.js
@@ -7,7 +7,7 @@ import * as actions from '../state/actions';
 import {
   getCompanionWindowForPosition,
   getSelectedCanvas,
-  getSelectedCanvasAnnotations,
+  getSelectedTargetAnnotations,
   getAnnotationResourcesByMotivation,
 } from '../state/selectors';
 import { WindowSideBarButtons } from '../components/WindowSideBarButtons';
@@ -32,7 +32,7 @@ const mapDispatchToProps = (dispatch, { windowId }) => ({
  */
 const mapStateToProps = (state, { windowId }) => ({
   hasAnnotations: getAnnotationResourcesByMotivation(
-    getSelectedCanvasAnnotations(state, (getSelectedCanvas(state, windowId) || {}).id),
+    getSelectedTargetAnnotations(state, (getSelectedCanvas(state, windowId) || {}).id),
     ['oa:commenting', 'sc:painting'],
   ).length > 0,
   sideBarPanel: (getCompanionWindowForPosition(state, windowId, 'left') || {}).content,
diff --git a/src/state/selectors/index.js b/src/state/selectors/index.js
index eb620776a..f244050a9 100644
--- a/src/state/selectors/index.js
+++ b/src/state/selectors/index.js
@@ -126,17 +126,32 @@ export function getSelectedCanvas(state, windowId) {
 }
 
 /**
-* Return the current canvas' (selected in a window) annotations
+* Return annotations for an array of targets
 * @param {object} state
-* @param {String} windowId
+* @param {Array} targets
+* @return {Array}
+*/
+export function getSelectedTargetsAnnotations(state, targets) {
+  const annotations = state.annotations
+    && targets.map(target => getSelectedTargetAnnotations(state, target));
+  if (!annotations) return [];
+
+  return flatten(annotations);
+}
+
+/**
+* Return a single target's annotations
+* @param {object} state
+* @param {String} target
 * @return {Array}
 */
-export function getSelectedCanvasAnnotations(state, canvasId) {
-  const annotations = state.annotations && state.annotations[canvasId];
+export function getSelectedTargetAnnotations(state, target) {
+  const annotations = state.annotations && state.annotations[target];
+
   if (!annotations) return [];
 
   return filter(
-    Object.keys(annotations).map(id => new Annotation(annotations[id].json)),
+    Object.keys(annotations).map(id => new Annotation(annotations[id].json, target)),
     annotation => annotation
                   && annotation.present(),
   );
-- 
GitLab