about summary refs log tree commit diff
path: root/app
diff options
context:
space:
mode:
authorThibG <thib@sitedethib.com>2019-09-16 15:45:06 +0200
committerEugen Rochko <eugen@zeonfederated.com>2019-09-16 15:45:06 +0200
commitf1098675782944fe1dabec71cd58d3d091da06a0 (patch)
tree6cabc8ea376ee626c744e882401a31a4bd7a7a75 /app
parent5eff29b28c226e443ea5484ed50c8020a43fbc6b (diff)
Fix “slow mode” issues (#11859)
* Fix weird scroll-jumping behavior with pending items

* Treat pending items as unread items

* Fix scroll position being altered because of the “X new items” button
Diffstat (limited to 'app')
-rw-r--r--app/javascript/mastodon/components/scrollable_list.js10
-rw-r--r--app/javascript/mastodon/features/community_timeline/index.js2
-rw-r--r--app/javascript/mastodon/features/notifications/index.js2
-rw-r--r--app/javascript/mastodon/reducers/notifications.js4
-rw-r--r--app/javascript/mastodon/reducers/timelines.js4
5 files changed, 15 insertions, 7 deletions
diff --git a/app/javascript/mastodon/components/scrollable_list.js b/app/javascript/mastodon/components/scrollable_list.js
index 0bf817923..253646ed0 100644
--- a/app/javascript/mastodon/components/scrollable_list.js
+++ b/app/javascript/mastodon/components/scrollable_list.js
@@ -172,8 +172,9 @@ export default class ScrollableList extends PureComponent {
     const someItemInserted = React.Children.count(prevProps.children) > 0 &&
       React.Children.count(prevProps.children) < React.Children.count(this.props.children) &&
       this.getFirstChildKey(prevProps) !== this.getFirstChildKey(this.props);
+    const pendingChanged = (prevProps.numPending > 0) !== (this.props.numPending > 0);
 
-    if (someItemInserted && (this.getScrollTop() > 0 || this.mouseMovedRecently)) {
+    if (pendingChanged || someItemInserted && (this.getScrollTop() > 0 || this.mouseMovedRecently)) {
       return this.getScrollHeight() - this.getScrollTop();
     } else {
       return null;
@@ -261,6 +262,13 @@ export default class ScrollableList extends PureComponent {
   handleLoadPending = e => {
     e.preventDefault();
     this.props.onLoadPending();
+    // Prevent the weird scroll-jumping behavior, as we explicitly don't want to
+    // scroll to top, and we know the scroll height is going to change
+    this.scrollToTopOnMouseIdle = false;
+    this.lastScrollWasSynthetic = false;
+    this.clearMouseIdleTimer();
+    this.mouseIdleTimer = setTimeout(this.handleMouseIdle, MOUSE_IDLE_DELAY);
+    this.mouseMovedRecently = true;
   }
 
   render () {
diff --git a/app/javascript/mastodon/features/community_timeline/index.js b/app/javascript/mastodon/features/community_timeline/index.js
index f95fa4970..cb93f9c22 100644
--- a/app/javascript/mastodon/features/community_timeline/index.js
+++ b/app/javascript/mastodon/features/community_timeline/index.js
@@ -20,7 +20,7 @@ const mapStateToProps = (state, { onlyMedia, columnId }) => {
   const index = columns.findIndex(c => c.get('uuid') === uuid);
 
   return {
-    hasUnread: state.getIn(['timelines', `community${onlyMedia ? ':media' : ''}`, 'unread']) > 0,
+    hasUnread: state.getIn(['timelines', `community${onlyMedia ? ':media' : ''}`, 'unread']) > 0 || state.getIn(['timelines', `community${onlyMedia ? ':media' : ''}`, 'pendingItems']).size > 0,
     onlyMedia: (columnId && index >= 0) ? columns.get(index).getIn(['params', 'other', 'onlyMedia']) : state.getIn(['settings', 'community', 'other', 'onlyMedia']),
   };
 };
diff --git a/app/javascript/mastodon/features/notifications/index.js b/app/javascript/mastodon/features/notifications/index.js
index f2b239afe..7e5de0613 100644
--- a/app/javascript/mastodon/features/notifications/index.js
+++ b/app/javascript/mastodon/features/notifications/index.js
@@ -39,7 +39,7 @@ const mapStateToProps = state => ({
   showFilterBar: state.getIn(['settings', 'notifications', 'quickFilter', 'show']),
   notifications: getNotifications(state),
   isLoading: state.getIn(['notifications', 'isLoading'], true),
-  isUnread: state.getIn(['notifications', 'unread']) > 0,
+  isUnread: state.getIn(['notifications', 'unread']) > 0 || state.getIn(['notifications', 'pendingItems']).size > 0,
   hasMore: state.getIn(['notifications', 'hasMore']),
   numPending: state.getIn(['notifications', 'pendingItems'], ImmutableList()).size,
 });
diff --git a/app/javascript/mastodon/reducers/notifications.js b/app/javascript/mastodon/reducers/notifications.js
index 049c70cb4..69bd47940 100644
--- a/app/javascript/mastodon/reducers/notifications.js
+++ b/app/javascript/mastodon/reducers/notifications.js
@@ -36,7 +36,7 @@ const notificationToMap = notification => ImmutableMap({
 
 const normalizeNotification = (state, notification, usePendingItems) => {
   if (usePendingItems) {
-    return state.update('pendingItems', list => list.unshift(notificationToMap(notification)));
+    return state.update('pendingItems', list => list.unshift(notificationToMap(notification))).update('unread', unread => unread + 1);
   }
 
   const top = state.get('top');
@@ -91,7 +91,7 @@ const filterNotifications = (state, accountIds) => {
 
 const updateTop = (state, top) => {
   if (top) {
-    state = state.set('unread', 0);
+    state = state.set('unread', state.get('pendingItems').size);
   }
 
   return state.set('top', top);
diff --git a/app/javascript/mastodon/reducers/timelines.js b/app/javascript/mastodon/reducers/timelines.js
index 0b036f5fe..db45d4d40 100644
--- a/app/javascript/mastodon/reducers/timelines.js
+++ b/app/javascript/mastodon/reducers/timelines.js
@@ -65,7 +65,7 @@ const updateTimeline = (state, timeline, status, usePendingItems) => {
       return state;
     }
 
-    return state.update(timeline, initialTimeline, map => map.update('pendingItems', list => list.unshift(status.get('id'))));
+    return state.update(timeline, initialTimeline, map => map.update('pendingItems', list => list.unshift(status.get('id'))).update('unread', unread => unread + 1));
   }
 
   const top        = state.getIn([timeline, 'top']);
@@ -128,7 +128,7 @@ const filterTimeline = (timeline, state, relationship, statuses) => {
 
 const updateTop = (state, timeline, top) => {
   return state.update(timeline, initialTimeline, map => map.withMutations(mMap => {
-    if (top) mMap.set('unread', 0);
+    if (top) mMap.set('unread', mMap.get('pendingItems').size);
     mMap.set('top', top);
   }));
 };