Toggling between chat list and chat tabs is noticeably laggy on many devices. Compare with Telegram e.g. Additionally, this might also impact other common transitions.
Bad performance for toggling between tabs is due to RN Bridge roundtrips being a bottleneck for rendering.
(This is a common performance bottleneck for React Native programs.)
1) Assuming this is still a critical problem for end user
2) Assuming it is reasonably easy to fixable
Use Spy or rn-snoopy to verify RN bridge roundtrips is the bottleneck.
Additionally, consider making use of re-frisk or manual timers to supplement above.
See
https://medium.com/@jondot/debugging-react-native-performance-snoopy-and-the-messagequeue-fe014cd047ac
https://github.com/status-im/status-react/pull/2765 (merged)
@rasom Do you want to own this issue? Do you agree with it?
@annadanchenko Concurrently with testing of this hypothesis, can you please confirm this is still a problem for end users on our supported devices?
@oskarth yes and yes
Use Spy or rn-snoopy to verify RN bridge roundtrips is the bottleneck.
One problem with this experiment setup is that a lot of calls, as @rasom pointed out, aren't bidirectional, e.g. some are async/unidirectional. This means it isn't always straightforward to see what the cost of each "bridge crossing".
@rasom You've posted a bunch of observations from this in Slack, would you mind posting a summary of things you found in this issue so we don't lose it?
To sum up communication through RN bridge, we have the next types of messages:
status-module
The main concern was related to the way how we use web3, but it seems that regardless of number of incoming messages we don’t have more than 6-8 in/out RN bridge messages related to this module.
Timing/JSTimers
This module is used by animation (not native), when we call setTimeout/setInterval explicitly and under the hood by core.async. Right now we have 20-24 messages per second related to this module. So we can define a threshold about 50 mps which means that if we have more than 50 mps for this module something suspicious is happening, and this will trigger some notification in app (in dev mode).
websocket
Is used only in develop mode for dev tools and probably figwheel/re-frisk
ui-manager
Most of calls related to this module happen on navigation. As far as I can say we have something similar to direct dependency between the number of these calls and duration of navigation between screens. We also can define a threshold for this type of messages, I suppose that it should be about 40 for Android and ~100 on iOS. That’s the numbers when delay before rendering a new screen starts being noticeable (anyway exact numbers TBD)
| ___________________ | ____________develop___________ | experiment/nav-groups
|- | ---- | ---- |
chats -> console chat | updateView 7 createView  205 setChildren 159 Total: 373 | updateView 12 Create view 80 setChildren 58 Total: 150
chats -> profile | updateView 10 createView 89 setChildren 62 Total: 161 | updateView 12 createView 9 setChildren 5 Total: 26
profile -> chats | updateView 10 Createview 58 setChildren. 41 Total: 109 | updateView 12 createView 10 setChildren 6 Total: 28
touches
These messages happen when we touch screen, so if we touch it a lot there can be a lot of them but I doubt that they have serious impact on perf.
native-animation
Messages related to animation with setNativeDriver=true.
keyboard-observer
We explicitly call this module once in root element, then it also is called by FlatList. Nothing important, but it looked for suspicious at first glance because I was under impression the we call it for no reason. But we don’t.
There are also different messages similar to
RCTEventEmitter.receiveEvent([23,”topLayout"
Many of them happens when animation with setNativeDriver=false is used, so in most cases we can notice same stuff by watching Timing/JSTimers
Most helpful comment
To sum up communication through RN bridge, we have the next types of messages:
status-module
The main concern was related to the way how we use web3, but it seems that regardless of number of incoming messages we don’t have more than 6-8 in/out RN bridge messages related to this module.
Timing/JSTimers
This module is used by animation (not native), when we call setTimeout/setInterval explicitly and under the hood by core.async. Right now we have 20-24 messages per second related to this module. So we can define a threshold about 50 mps which means that if we have more than 50 mps for this module something suspicious is happening, and this will trigger some notification in app (in dev mode).
websocket
Is used only in develop mode for dev tools and probably figwheel/re-frisk
ui-manager
Most of calls related to this module happen on navigation. As far as I can say we have something similar to direct dependency between the number of these calls and duration of navigation between screens. We also can define a threshold for this type of messages, I suppose that it should be about 40 for Android and ~100 on iOS. That’s the numbers when delay before rendering a new screen starts being noticeable (anyway exact numbers TBD)
| ___________________ | ____________develop___________ | experiment/nav-groups
|- | ---- | ---- |
chats -> console chat | updateView 7 createView  205 setChildren 159 Total: 373 | updateView 12 Create view 80 setChildren 58 Total: 150
chats -> profile | updateView 10 createView 89 setChildren 62 Total: 161 | updateView 12 createView 9 setChildren 5 Total: 26
profile -> chats | updateView 10 Createview 58 setChildren. 41 Total: 109 | updateView 12 createView 10 setChildren 6 Total: 28
touches
These messages happen when we touch screen, so if we touch it a lot there can be a lot of them but I doubt that they have serious impact on perf.
native-animation
Messages related to animation with setNativeDriver=true.
keyboard-observer
We explicitly call this module once in root element, then it also is called by FlatList. Nothing important, but it looked for suspicious at first glance because I was under impression the we call it for no reason. But we don’t.
There are also different messages similar to
RCTEventEmitter.receiveEvent([23,”topLayout"Many of them happens when animation with setNativeDriver=false is used, so in most cases we can notice same stuff by watching Timing/JSTimers