use AutoHideScrollbar in ScrollPanel

This commit is contained in:
Bruno Windels 2019-03-12 16:30:06 +01:00
parent 99f82a3de9
commit 8cf2607415
3 changed files with 23 additions and 20 deletions
res/css/structures
src/components/structures

View file

@ -84,6 +84,7 @@ limitations under the License.
display: flex;
flex-direction: column;
flex: 1;
min-width: 0;
}
.mx_RoomView_body .mx_RoomView_timeline {
@ -111,6 +112,7 @@ limitations under the License.
.mx_RoomView_messagePanel {
width: 100%;
overflow-y: auto;
flex: 1 1 0;
}
.mx_RoomView_messagePanelSearchSpinner {

View file

@ -121,6 +121,7 @@ export default class AutoHideScrollbar extends React.Component {
render() {
return (<div
ref={this._collectContainerRef}
style={this.props.style}
className={["mx_AutoHideScrollbar", this.props.className].join(" ")}
onScroll={this.props.onScroll}
>

View file

@ -15,14 +15,13 @@ limitations under the License.
*/
const React = require("react");
const ReactDOM = require("react-dom");
import PropTypes from 'prop-types';
import Promise from 'bluebird';
import { KeyCode } from '../../Keyboard';
import sdk from '../../index.js';
import AutoHideScrollbar from "./AutoHideScrollbar";
const DEBUG_SCROLL = false;
// var DEBUG_SCROLL = true;
// const DEBUG_SCROLL = true;
// The amount of extra scroll distance to allow prior to unfilling.
// See _getExcessHeight.
@ -129,11 +128,6 @@ module.exports = React.createClass({
*/
onScroll: PropTypes.func,
/* onResize: a callback which is called whenever the Gemini scroll
* panel is resized
*/
onResize: PropTypes.func,
/* className: classnames to add to the top-level div
*/
className: PropTypes.string,
@ -150,7 +144,6 @@ module.exports = React.createClass({
onFillRequest: function(backwards) { return Promise.resolve(false); },
onUnfillRequest: function(backwards, scrollToken) {},
onScroll: function() {},
onResize: function() {},
};
},
@ -185,6 +178,16 @@ module.exports = React.createClass({
debuglog("Scroll event: offset now:", sn.scrollTop,
"_lastSetScroll:", this._lastSetScroll);
// ignore scroll events where scrollTop hasn't changed,
// appears to happen when the layout changes outside
// of the scroll container, like resizing the right panel.
if (sn.scrollTop === this._lastEventScroll) {
debuglog("ignore scroll event with same scrollTop as before");
return;
}
this._lastEventScroll = sn.scrollTop;
// Sometimes we see attempts to write to scrollTop essentially being
// ignored. (Or rather, it is successfully written, but on the next
// scroll event, it's been reset again).
@ -225,9 +228,7 @@ module.exports = React.createClass({
onResize: function() {
this.clearBlockShrinking();
this.props.onResize();
this.checkScroll();
if (this._gemScroll) this._gemScroll.forceUpdate();
},
// after an update to the contents of the panel, check that the scroll is
@ -672,17 +673,17 @@ module.exports = React.createClass({
throw new Error("ScrollPanel._getScrollNode called when unmounted");
}
if (!this._gemScroll) {
if (!this._divScroll) {
// Likewise, we should have the ref by this point, but if not
// turn the NPE into something meaningful.
throw new Error("ScrollPanel._getScrollNode called before gemini ref collected");
}
return this._gemScroll.scrollbar.getViewElement();
return this._divScroll;
},
_collectGeminiScroll: function(gemScroll) {
this._gemScroll = gemScroll;
_collectScroll: function(divScroll) {
this._divScroll = divScroll;
},
/**
@ -724,19 +725,18 @@ module.exports = React.createClass({
},
render: function() {
const GeminiScrollbarWrapper = sdk.getComponent("elements.GeminiScrollbarWrapper");
// TODO: the classnames on the div and ol could do with being updated to
// reflect the fact that we don't necessarily contain a list of messages.
// it's not obvious why we have a separate div and ol anyway.
return (<GeminiScrollbarWrapper autoshow={true} wrappedRef={this._collectGeminiScroll}
onScroll={this.onScroll} onResize={this.onResize}
return (<AutoHideScrollbar wrappedRef={this._collectScroll}
onScroll={this.onScroll}
className={this.props.className} style={this.props.style}>
<div className="mx_RoomView_messageListWrapper">
<ol ref="itemlist" className="mx_RoomView_MessageList" aria-live="polite">
{ this.props.children }
</ol>
</div>
</GeminiScrollbarWrapper>
);
</AutoHideScrollbar>
);
},
});