Skip to content
Snippets Groups Projects
Commit 890057ad authored by Christopher Johnson's avatar Christopher Johnson
Browse files

adds configurations for OSD click-zoom behavior

provides option to disable click-zoom on focus only
parent 1d562f8d
Branches
No related tags found
No related merge requests found
......@@ -163,21 +163,17 @@ describe('OpenSeadragonViewer', () => {
});
});
describe('componentDidMount', () => {
let panTo;
let zoomTo;
let addHandler;
beforeEach(() => {
panTo = jest.fn();
zoomTo = jest.fn();
addHandler = jest.fn();
wrapper = shallow(
/**
*
* @param props
* @returns {*}
*/
const createWrapper = props => shallow(
<OpenSeadragonViewer
tileSources={[{ '@id': 'http://foo' }]}
windowId="base"
viewer={{ x: 1, y: 0, zoom: 0.5 }}
config={{}}
config={props}
updateViewport={updateViewport}
canvasWorld={new CanvasWorld([])}
t={k => k}
......@@ -186,6 +182,16 @@ describe('OpenSeadragonViewer', () => {
</OpenSeadragonViewer>,
);
describe('componentDidMount', () => {
let panTo;
let zoomTo;
let addHandler;
beforeEach(() => {
panTo = jest.fn();
zoomTo = jest.fn();
addHandler = jest.fn();
wrapper = createWrapper();
wrapper.instance().ref = { current: true };
OpenSeadragon.mockImplementation(() => ({
......@@ -223,20 +229,45 @@ describe('OpenSeadragonViewer', () => {
wrapper.instance().componentDidMount();
expect(addHandler).toHaveBeenCalledWith('update-viewport', expect.anything());
});
});
it('sets up a listener on canvas-click', () => {
describe('canvas-click handlers', () => {
const addHandler = jest.fn();
const panTo = jest.fn();
const zoomTo = jest.fn();
it('conditionally sets up "disable zoom action" handler on canvas-click', () => {
wrapper = createWrapper({ isCanvasClickZoomActionDisabled: true });
wrapper.instance().ref = { current: true };
OpenSeadragon.mockImplementation(() => ({
addHandler,
viewport: { panTo, zoomTo },
}));
wrapper.instance().componentDidMount();
expect(addHandler).toHaveBeenNthCalledWith(5, 'canvas-click', OpenSeadragonViewer.onCanvasClick);
});
expect(addHandler).toHaveBeenCalledWith('canvas-click', OpenSeadragonViewer.onCanvasClick);
});
describe('onCanvasClick', () => {
it('sets preventDefaultAction', () => {
it('sets preventDefaultAction on CanvasClick', () => {
const event = { preventDefaultAction: () => {} };
jest.spyOn(event, 'preventDefaultAction');
OpenSeadragonViewer.onCanvasClick(event);
expect(event.preventDefaultAction).toBe(true);
});
it('conditionally sets up "after focus, enable click zoom action" handler on canvas-click', () => {
wrapper = createWrapper({ isCanvasClickZoomActionAfterFocusEnabled: true });
wrapper.instance().ref = { current: true };
OpenSeadragon.mockImplementation(() => ({
addHandler,
viewport: { panTo, zoomTo },
}));
wrapper.instance().componentDidMount();
expect(addHandler).toHaveBeenCalledWith('canvas-click', wrapper.instance().onCanvasFocus);
});
it('sets preventDefaultAction on CanvasFocus', () => {
const event = { preventDefaultAction: () => {} };
jest.spyOn(event, 'preventDefaultAction');
wrapper.instance().justReceivedFocus = true;
wrapper.instance().onCanvasFocus(event);
expect(event.preventDefaultAction).toBe(true);
});
});
describe('componentDidUpdate', () => {
......
......@@ -53,17 +53,22 @@ export class OpenSeadragonViewer extends Component {
// An initial value for the updateCanvas method
this.updateCanvas = () => {};
this.ref = React.createRef();
this.onCanvasFocus = this.onCanvasFocus.bind(this);
this.onUpdateViewport = this.onUpdateViewport.bind(this);
this.onViewportChange = this.onViewportChange.bind(this);
this.zoomToWorld = this.zoomToWorld.bind(this);
this.osdUpdating = false;
this.justReceivedFocus = false;
}
/**
* React lifecycle event
*/
componentDidMount() {
const { viewer } = this.props;
const {
config,
viewer,
} = this.props;
if (!this.ref.current) {
return;
}
......@@ -75,7 +80,6 @@ export class OpenSeadragonViewer extends Component {
preserveImageSizeOnResize: true,
preserveViewport: true,
showNavigationControl: false,
});
this.osdCanvasOverlay = new OpenSeadragonCanvasOverlay(this.viewer);
......@@ -88,7 +92,11 @@ export class OpenSeadragonViewer extends Component {
this.viewer.addHandler('animation-finish', () => {
this.osdUpdating = false;
});
if (config && config.isCanvasClickZoomActionDisabled) {
this.viewer.addHandler('canvas-click', OpenSeadragonViewer.onCanvasClick);
} else if (config && config.isCanvasClickZoomActionAfterFocusEnabled) {
this.viewer.addHandler('canvas-click', this.onCanvasFocus);
}
if (viewer) {
this.viewer.viewport.panTo(viewer, true);
this.viewer.viewport.zoomTo(viewer.zoom, viewer, true);
......@@ -104,7 +112,7 @@ export class OpenSeadragonViewer extends Component {
*/
componentDidUpdate(prevProps) {
const {
viewer, highlightedAnnotations, selectedAnnotations,
focused, highlightedAnnotations, selectedAnnotations, viewer,
} = this.props;
const highlightsUpdated = !OpenSeadragonViewer.annotationsMatch(
highlightedAnnotations, prevProps.highlightedAnnotations,
......@@ -125,6 +133,11 @@ export class OpenSeadragonViewer extends Component {
this.viewer.forceRedraw();
}
if (focused && prevProps.focused !== focused) {
this.justReceivedFocus = true;
setTimeout(() => { this.justReceivedFocus = false; }, 50);
}
if (!this.tileSourcesMatch(prevProps.tileSources)) {
this.viewer.close();
this.addAllTileSources();
......@@ -148,6 +161,15 @@ export class OpenSeadragonViewer extends Component {
this.viewer.removeAllHandlers();
}
/**
*
* @param e
*/
onCanvasFocus(e) {
e.preventDefaultAction = this.justReceivedFocus;
this.justReceivedFocus = false;
}
/**
* onUpdateViewport - fires during OpenSeadragon render method.
*/
......@@ -293,17 +315,20 @@ export class OpenSeadragonViewer extends Component {
OpenSeadragonViewer.defaultProps = {
children: null,
config: null,
focused: false,
highlightedAnnotations: [],
label: null,
selectedAnnotations: [],
tileSources: [],
viewer: null,
};
OpenSeadragonViewer.propTypes = {
canvasWorld: PropTypes.instanceOf(CanvasWorld).isRequired,
children: PropTypes.node,
config: PropTypes.object, // eslint-disable-line react/forbid-prop-types
focused: PropTypes.bool,
highlightedAnnotations: PropTypes.arrayOf(PropTypes.object),
label: PropTypes.string,
selectedAnnotations: PropTypes.arrayOf(PropTypes.object),
......
......@@ -198,6 +198,10 @@ export default {
displayAllAnnotations: false, // Configure if annotations to be displayed on the canvas by default when fetched
translations: { // Translations can be added to inject new languages or override existing labels
},
viewer: {
isCanvasClickZoomActionDisabled: false,
isCanvasClickZoomActionAfterFocusEnabled: true,
},
window: {
allowClose: true, // Configure if windows can be closed or not
allowMaximize: true, // Configure if windows can be maximized or not
......
......@@ -20,6 +20,8 @@ import {
*/
const mapStateToProps = (state, { windowId }) => ({
canvasWorld: new CanvasWorld(getSelectedCanvases(state, { windowId })),
config: state.config.viewer,
focused: state.workspace.focusedWindowId === windowId,
highlightedAnnotations: getHighlightedAnnotationsOnCanvases(state, { windowId }),
label: getCanvasLabel(state, { windowId }),
selectedAnnotations: getSelectedAnnotationsOnCanvases(state, { windowId }),
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment