简体   繁体   中英

Rendering hundreds of Views/Touchs (how to be performatic) in React-Native

If you have any experience rendering lot of views I'm glad to hear:

Im trying to render about hundreds of views in a single page. More specifically i'm rendering a map of objects which has its own colors inside it. It will be a grid of about 144x256 (i dont remind the actual scale now)

the amount of views to render slows down the page to an unusable state

So far Iv tried:

  • Views
  • TouchableOpacities
  • reanimated components (for native like interaction)

Some steps i'm about to try yet are:

Bellow is an example using reanimated component and views. Even this simple grid is not fast enought, and its only 9x16

在此处输入图像描述

the code i'm using so far is a little bit complicated (because i'm structuring it for a big page) Haha, i dont think its worth pasting it here but i'll:

const DEFAULTS={
  city:{
    GENERALDATA:{
      prefixes:generalDatas.city.prefixes,
    },
    indexes:mapIndexes,
    rows:[...Array(mapIndexes.y).keys()].map(row=>row=[...Array(mapIndexes.x).keys()]),
    array:{...[...Array(mapIndexes.y*mapIndexes.x)].map(blk=>blk={color:'#000'})}
  }, // 256x144   // {coords:[],prev:[],owner,usersData:{'users sent data like [type,houseNumber,50km/h]'}}
}
 const stateDatas = {
    anm:{
      anmText:{

      },
      bitMapIndexes:DEFAULTS.city.indexes,
      bitMap:DEFAULTS.city.array,
      bitMapRows:DEFAULTS.city.rows,
      bitMapKeys:Object.keys(DEFAULTS.city.array),
    }
  }

const renderMap=()=>{
    const renderBlock=(rowI,i,rowLength)=>{
      return(
        <Animated.View style={[{
          width:anmBitMapProps.value.resProportion.x,
          height:anmBitMapProps.value.resProportion.y,
          backgroundColor:'#262626',
          borderColor:'#191919',
          borderWidth:1,
          justifyContent:'center',
          alignItems:'center',
          // borderStyle:'solid'
        },anm.bitMap[(rowI*rowLength)+i]]}>
          <Text style={styles.softText}>1km</Text>
          <Text style={styles.softText}>chunk</Text>
        </Animated.View>
      )
    }

    const renderRow=(row,rowI,rowLength)=>{
      return(
        <View style={{flexDirection:'row'}}>
          {row.map(i=>renderBlock(rowI,i,rowLength))}
        </View>
      )
    }

    const anmBitMapArray = stateDatas.anm.bitMapRows.map((row,rowI)=>renderRow(row,rowI,row.length))

    return(
      <View style={{position:'absolute',width:'100%',height:'100%',backgroundColor:'#121212'}}>
        {anmBitMapArray}
      </View>
    )

I truncated it a bit, might be missing some parts

It would require a lot more code snippet and analysis to reach to a snappy UI state. Anyway, I'll try to give some pointers based on the above snippet.

  1. Avoid using inline css. Use css classes are target the relevant elements.

  2. We don't have to initialize same objects again.

  3. { width:anmBitMapProps.value.resProportion.x, height:anmBitMapProps.value.resProportion.y, backgroundColor:'#262626', borderColor:'#191919', borderWidth:1, justifyContent:'center', alignItems:'center', // borderStyle:'solid' }

This object is same for all child elements. So we can initalize it next to stateDatas and reuse it.

  1. Another reusable piece of code is:
    <Text style={styles.softText}>1km</Text>
    <Text style={styles.softText}>chunk</Text>

This can be taken out in a separate component and wrapped inside a React.memo . Since this is same for all the components so no need to re-create it

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM