Search code examples
javascriptcssreactjsreact-nativenative-base

How can you ensure flex shrink in react-native (and how can you debug react-native styles in general)?


I'm running a RN app using native-base for styling. I have four elements on my homepage: a header, a tab view from vreact-native-tab-view that contains a ScrollView that takes up about 70% of the viewport, and two smaller 100% width elements at the bottom.

However, the scrollview fills up more than 100% of the viewport and the two smaller elements get pushed to the bottom.

I looked in my element inspector and can apply a flexShrink to some of the many divs, but I'm not sure which one that is in my code because it's div hell when you use react-native. React devtools also has the same problem, except it's View hell.

So, two questions:

  1. How can I ensure the scroll container doesn't fill up more than it should on the page?
  2. How can I effectively debug react native when both chrome and react dev tools are a mess?

For reference, here's how I've styled so far:

Home.tsx:

<View flex={1}> // applied a flex for the entire homepage
  <TabView
    navigationState={{ index, routes }}
    renderScene={renderScene}
    renderTabBar={renderTabBar}
    onIndexChange={setIndex}
    initialLayout={{ width: layout.width, height: "100%" }}
  />

  <View width="100%">
    <Center width="100%">
      <StrengthSlider />
    </Center>
    <AdMobBanner
      ...props
    />
  </View>
</View>

Teas.tsx:

<View flex={1} bg="white">
  <ScrollCards teas={blackTeas} />
</View>

ScrollCards.tsx:

<ScrollView>
  <Center>
    {teas.length > 0 &&
      teas.map((teaObj) => (
        <TeaCard id={teaObj.id} teaData={teaObj.data} key={teaObj.id} />
      ))}
  </Center>
</ScrollView>

EDIT:

Code Sandbox link: https://codesandbox.io/s/gracious-sammet-l4tqz?file=/src/App.js&resolutionWidth=402&resolutionHeight=675

Note that the admob footer remains underneath the cards content. It should be sticky and remain always at the bottom of the screen. I also noticed that when I'm not using the header from the MainStackNavigator the footer works as intended - i.e. it remains sticky at the bottom - but I don't see why using the header (AppBar) component should interfere with my footer.


Solution

  • The proper solution to get the result you want is to add a flexBasis to the TabView like:

    <TabView 
      style={{ flexBasis: 0 }}
      // rest of the code
    /> ​
    

    Why? The TabView has a default style of flex: 1, overflow: 'hidden' (see source code) causing it to expanded to the size of its biggest child. The flexBasis prevents this and makes sure the tabview get the correct height.

    Resource: This is a nice article about flexBasis vs width/height: https://mastery.games/post/the-difference-between-width-and-flex-basis/


    Debugging styling in React-Native doesn't have the best developer experience. There are some things you can use to help you with debugging styling:

    • RN inspector: As Berci mentioned, React native has a dev menu where you can select "show inspector" that kinda acts like "inspect element" in a browser. It is a good tool to debug elements you can see, it also helps with debugging input/tab events.

    • Color: Most often I just use old fashioned colored borders & background to get a clear view of where elements are & their size/overlaps.

    • Comments & Simplify: Feel free to comment out components you're not interested in and replace complex components/views like ScrollCards with just a simple colored view. This can help prevent multiple behaviours from influencing the thing you're trying to debug

    • Browser inspect & React devtools: If you happen to run your RN app in the browser, then getting familiar with those tools will help you loads. Just keep in mind that React & React-Native isn't the same.

    When you debug visuals, the best way is start at the top layer and work you way down. Color the elements & feel free to comment out elements to get you a clearer view of the problem. Keep digging down until you find the problem, don't be afraid to look into the source code of the packages you use, it often helps clarify (unexpected) behaviours.