diff --git a/__tests__/src/actions/window.test.js b/__tests__/src/actions/window.test.js index c144d7d2d94b9bdef18563b8e30ba7ccc04fd26c..a447ebc0a4a6e7cd4b60ef8bc53f890b7b9976ce 100644 --- a/__tests__/src/actions/window.test.js +++ b/__tests__/src/actions/window.test.js @@ -55,8 +55,24 @@ describe('window actions', () => { const expectedAction = { type: ActionTypes.REMOVE_WINDOW, windowId: id, + companionWindowIds: ['a', 'b', 'c'], }; - expect(actions.removeWindow(id)).toEqual(expectedAction); + + const mockState = { + windows: { + abc123: { companionWindowIds: ['a', 'b', 'c'] }, + }, + companionWindows: {}, + }; + + const mockDispatch = jest.fn(() => ({})); + const mockGetState = jest.fn(() => mockState); + const thunk = actions.removeWindow(id); + + thunk(mockDispatch, mockGetState); + + const action = mockDispatch.mock.calls[0][0]; + expect(action).toEqual(expectedAction); }); }); diff --git a/__tests__/src/components/WindowTopBar.test.js b/__tests__/src/components/WindowTopBar.test.js index 27aff2536a1ba090a803420df5a6d98f2b114490..f7bb55a46743d12c27c1d4e732163c37b49fa05b 100644 --- a/__tests__/src/components/WindowTopBar.test.js +++ b/__tests__/src/components/WindowTopBar.test.js @@ -22,7 +22,7 @@ function createWrapper(props) { maximizeWindow={() => {}} maximized={false} minimizeWindow={() => {}} - closeWindow={() => {}} + removeWindow={() => {}} toggleWindowSideBar={() => {}} {...props} />, @@ -63,9 +63,9 @@ describe('WindowTopBar', () => { }); it('passes correct props to <Button/>', () => { - const closeWindow = jest.fn(); - const wrapper = createWrapper({ closeWindow }); - expect(wrapper.find(IconButton).last().props().onClick).toBe(closeWindow); + const removeWindow = jest.fn(); + const wrapper = createWrapper({ removeWindow }); + expect(wrapper.find(IconButton).last().props().onClick).toBe(removeWindow); }); it('passes correct props to <Button/>', () => { diff --git a/__tests__/src/reducers/companionWindows.test.js b/__tests__/src/reducers/companionWindows.test.js index 9f33e9ecf64c6c1aa05470a9149c470e913678af..fc830f46e9343d4cb2ab47c2ad519818425d9f47 100644 --- a/__tests__/src/reducers/companionWindows.test.js +++ b/__tests__/src/reducers/companionWindows.test.js @@ -76,4 +76,21 @@ describe('companionWindowsReducer', () => { expect(companionWindowsReducer(beforeState, action)).toEqual(expectedState); }); }); + + describe('REMOVE_WINDOW', () => { + it('should remove a companion window', () => { + const action = { + type: ActionTypes.REMOVE_WINDOW, + id: 'abc123', + companionWindowIds: ['a', 'b'], + }; + const beforeState = { + a: {}, + b: {}, + c: {}, + }; + const expectedState = { c: {} }; + expect(companionWindowsReducer(beforeState, action)).toEqual(expectedState); + }); + }); }); diff --git a/src/components/WindowTopBar.js b/src/components/WindowTopBar.js index 2faea219b2fc8f8279f26d4c9ddc248e08681f48..7488297ee7371d3ef8a2418c2f1f0028f94bd8a0 100644 --- a/src/components/WindowTopBar.js +++ b/src/components/WindowTopBar.js @@ -24,7 +24,7 @@ export class WindowTopBar extends Component { */ render() { const { - closeWindow, windowId, classes, toggleWindowSideBar, t, manifestTitle, + removeWindow, windowId, classes, toggleWindowSideBar, t, manifestTitle, maximizeWindow, maximized, minimizeWindow, } = this.props; return ( @@ -56,7 +56,7 @@ export class WindowTopBar extends Component { color="inherit" className={ns('window-close')} aria-label={t('closeWindow')} - onClick={closeWindow} + onClick={removeWindow} > <CloseIcon /> </IconButton> @@ -71,7 +71,7 @@ WindowTopBar.propTypes = { maximizeWindow: PropTypes.func, maximized: PropTypes.bool, minimizeWindow: PropTypes.func, - closeWindow: PropTypes.func.isRequired, + removeWindow: PropTypes.func.isRequired, windowId: PropTypes.string.isRequired, classes: PropTypes.object.isRequired, // eslint-disable-line react/forbid-prop-types toggleWindowSideBar: PropTypes.func.isRequired, diff --git a/src/containers/WindowTopBar.js b/src/containers/WindowTopBar.js index 27e880e45e7b572e68e23d8d6998ae703f1f0b56..d63693b48eeb65dfb138509ecfc93b55f15c4090 100644 --- a/src/containers/WindowTopBar.js +++ b/src/containers/WindowTopBar.js @@ -19,7 +19,7 @@ const mapStateToProps = (state, { windowId }) => ({ * @private */ const mapDispatchToProps = (dispatch, { windowId }) => ({ - closeWindow: () => dispatch(actions.closeWindow(windowId)), + removeWindow: () => dispatch(actions.removeWindow(windowId)), maximizeWindow: () => dispatch(actions.maximizeWindow(windowId)), minimizeWindow: () => dispatch(actions.minimizeWindow(windowId)), toggleWindowSideBar: () => dispatch(actions.toggleWindowSideBar(windowId)), diff --git a/src/state/actions/window.js b/src/state/actions/window.js index b966c2dca801ab5818894cba3d3a57618c536a46..ff246162c9c018f2b20b2b2709060b6ab018e5e4 100644 --- a/src/state/actions/window.js +++ b/src/state/actions/window.js @@ -75,7 +75,12 @@ export function setCompanionAreaOpen(id, companionAreaOpen) { * @memberof ActionCreators */ export function removeWindow(windowId) { - return { type: ActionTypes.REMOVE_WINDOW, windowId }; + return (dispatch, getState) => { + const { windows } = getState(); + const { companionWindowIds } = windows[windowId]; + + dispatch({ type: ActionTypes.REMOVE_WINDOW, windowId, companionWindowIds }); + }; } /** @@ -99,17 +104,6 @@ export function setWindowSideBarPanel(windowId, panelType) { return { type: ActionTypes.SET_WINDOW_SIDE_BAR_PANEL, windowId, panelType }; } -/** -* Clean up state and remove window -*/ -export function closeWindow(windowId) { - return (dispatch, getState) => { - const { companionWindowIds } = getState().windows[windowId]; - companionWindowIds.map(id => dispatch(removeCompanionWindow(id))); - dispatch(removeWindow(windowId)); - }; -} - /** * setWindowThumbnailPosition - action creator * diff --git a/src/state/reducers/companionWindows.js b/src/state/reducers/companionWindows.js index e3d43b9809e8dbb417b9e4eef182e5ca464f21ca..6cd71b9595e82a1972742b110b2909a58c3e12e9 100644 --- a/src/state/reducers/companionWindows.js +++ b/src/state/reducers/companionWindows.js @@ -15,6 +15,9 @@ export function companionWindowsReducer(state = {}, action) { return newState; }, state); + case ActionTypes.REMOVE_WINDOW: + return action.companionWindowIds.reduce((newState, id) => removeIn(newState, [id]), state); + case ActionTypes.UPDATE_COMPANION_WINDOW: return updateIn(state, [action.id], orig => merge(orig, action.payload));