Improve modal flow and back button handling (#16499)
* Refactor shouldUpdateScroll passing So far, shouldUpdateScroll has been manually passed down from the very top of the React component hierarchy even though it is a static function common to all ScrollContainer instances, so replaced that with a custom class extending ScrollContainer. * Generalize “press back to close modal” to any modal and to public pages * Fix boost confirmation modal closing media modal
This commit is contained in:
parent
a2ce7508c9
commit
d3791cca0c
35 changed files with 120 additions and 197 deletions
|
@ -1,6 +1,7 @@
|
|||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
import 'wicg-inert';
|
||||
import { createBrowserHistory } from 'history';
|
||||
import { multiply } from 'color-blend';
|
||||
|
||||
export default class ModalRoot extends React.PureComponent {
|
||||
|
@ -48,6 +49,7 @@ export default class ModalRoot extends React.PureComponent {
|
|||
componentDidMount () {
|
||||
window.addEventListener('keyup', this.handleKeyUp, false);
|
||||
window.addEventListener('keydown', this.handleKeyDown, false);
|
||||
this.history = this.context.router ? this.context.router.history : createBrowserHistory();
|
||||
}
|
||||
|
||||
componentWillReceiveProps (nextProps) {
|
||||
|
@ -69,6 +71,14 @@ export default class ModalRoot extends React.PureComponent {
|
|||
this.activeElement.focus({ preventScroll: true });
|
||||
this.activeElement = null;
|
||||
}).catch(console.error);
|
||||
|
||||
this._handleModalClose();
|
||||
}
|
||||
if (this.props.children && !prevProps.children) {
|
||||
this._handleModalOpen();
|
||||
}
|
||||
if (this.props.children) {
|
||||
this._ensureHistoryBuffer();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -77,6 +87,32 @@ export default class ModalRoot extends React.PureComponent {
|
|||
window.removeEventListener('keydown', this.handleKeyDown);
|
||||
}
|
||||
|
||||
_handleModalOpen () {
|
||||
this._modalHistoryKey = Date.now();
|
||||
this.unlistenHistory = this.history.listen((_, action) => {
|
||||
if (action === 'POP') {
|
||||
this.props.onClose();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
_handleModalClose () {
|
||||
if (this.unlistenHistory) {
|
||||
this.unlistenHistory();
|
||||
}
|
||||
const { state } = this.history.location;
|
||||
if (state && state.mastodonModalKey === this._modalHistoryKey) {
|
||||
this.history.goBack();
|
||||
}
|
||||
}
|
||||
|
||||
_ensureHistoryBuffer () {
|
||||
const { pathname, state } = this.history.location;
|
||||
if (!state || state.mastodonModalKey !== this._modalHistoryKey) {
|
||||
this.history.push(pathname, { ...state, mastodonModalKey: this._modalHistoryKey });
|
||||
}
|
||||
}
|
||||
|
||||
getSiblings = () => {
|
||||
return Array(...this.node.parentElement.childNodes).filter(node => node !== this.node);
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue