React Native Category Tabs - setiap tab menampilkan kategori yang berbeda

Nov 29 2020

Saat ini saya mencoba menerapkan layar penjelajahan, di mana pengguna dapat memilih kategori tertentu dari ScrollView yang menampilkan posting yang terkait dengan kategori itu.

Api saya mendapatkan semua data posting dari backend dan untuk setiap posting saya memiliki parameter call categoryId.

Yang saya coba lakukan adalah, misalnya jika salah satu kategori saya adalah olahraga. ketika pengguna memilih tab olahraga, daftar datar dengan semua posting tentang olahraga harus ditampilkan.

Dengan implementasi saat ini, saya memiliki tab kategori saya dan ketika saya memilih salah satu tab, semua posting tidak diberikan posting untuk kategori tertentu itu.

Ini kode saya:

function SearchScreen({ navigation }) {
const [posts, setPosts] = useState([]);
const [error, setError] = useState(false);
const [loading, setLoading] = useState(false);

const loadPosts = async () => {
setLoading(true);
const response = await postsApi.getPosts(page);
setLoading(false);

if (!response.ok) return setError(true);

setError(false);
setPosts(response.data);
};

const[page,setPage]=useState(0);

useEffect(() => {
loadPosts();
 }, []);

const categories = [
{
  label: "Sports",
  id: 1,
},
{
  label: "Fashion",
  id: 2,
},
{
  label: "News",
  id: 3,
   },
  ];

 const[label,setLabel]=useState('Sports')
 const[dataList,setDataList]=useState(posts)

const setLabelFilter=label=>{
setLabel(label)
}

return (
<>
  <ActivityIndicator visible={loading} />
  <Screen style={styles.screen}>
    {error && (
      <>
        <View style={styles.error}>
          <AppText>Could not retrieve posts from server.</AppText>
          <AppButton title="Retry" onPress={loadPosts} />
        </View>
      </>
    )}
    <ScrollView 
    horizontal 
    style={{flexDirection:"row",
    alignContent:"center",
    width:Dimensions.get('window').width/1.05,
    marginBottom:20,
    }} 
    showsHorizontalScrollIndicator={false}
    >
    {categories.map(e=>(
            <TouchableOpacity 
            style={[
                {paddingHorizontal:10,paddingBottom:10},
                label===e.label && 
                {borderBottomWidth:3,
                borderBottomColor:colors.primary,
                borderRadius:2,
            }
                ]} 
                onPress={()=>setLabelFilter(e.label)}
                >
            <AppText style={[{fontWeight:"500",color:colors.medium},label===e.label && 
{color:colors.primary,fontWeight:"700"}]}>{e.label}</AppText>
            </TouchableOpacity>
    ))}
    </ScrollView>

    <FlatList
      data={posts} // to have all the data
      keyExtractor={(post) => post.id.toString()}
      renderItem={({ item,index }) => (
        <Card
          title={item.title}
          subTitle={item.subTitle}
          onPress={() => navigation.navigate(routes.POST_DETAILS, {post:item,index})}            
  />
      )}
    />
  </Screen>
</> 
);
}

Ketika saya melakukan console.log (posts), berikut adalah tanggapan saya:

Object {
"Category": Object {
  "id": 1,
  "name": "Sports",
},
"categoryId": 3,
"createdAt": "2020-11-18T13:43:19.616Z",
"deletedAt": null,
"id": 506,
"subtTitle": "test",
"title": "test",
"updatedAt": "2020-11-23T06:57:44.150Z",
"userId": 1,
 },

Saya telah berpikir untuk mengubah panggilan API saya untuk mendapatkan kategori berdasarkan idnya kemudian memasukkan semua posting untuk setiap kategori tertentu tetapi itu tidak berhasil, jadi saya pergi dengan panggilan API untuk mendapatkan semua posting.

Memperbarui

 const[label,setLabel]=useState('Sports')

 const setLabelFilter=label=>{
setLabel(label)
  }

 const [currentCategoryId, setCurrentCategoryId] = useState()

 const toggleBrands = (categoryId) => {
 setCurrentCategoryId(categoryId)
 setLabel(label)
   };

 return(
 <ScrollView 
    horizontal 
    showsHorizontalScrollIndicator={false}
    >
    {categories.map(e=>(
            <TouchableOpacity 
                key={e.id}
                onPress={()=>{toggleBrands(e.id),
                setLabelFilter(e.label)}}
                selected={e.id === currentCategoryId}
                >
            <AppText>{e.label}</AppText>
            </TouchableOpacity>
    ))}
    </ScrollView>

    <FlatList
      data={currentCategoryId ? 
posts.filter(post=>post.categoryId===currentCategoryId
        ):posts}

Saya mencoba kode berikut dapatkah seseorang memberi tahu saya apakah itu benar atau tidak?

Jawaban

KenLee Nov 29 2020 at 13:20

Sebagai contoh, katakanlah Anda pertama-tama akan mengklik sebuah item dalam Daftar Datar (menampilkan semua kategori) pada layar A, dan kemudian sistem akan dinavigasi ke layar B (dengan Daftar Datar yang menampilkan item dari kategori yang dipilih saja)

Metode normal adalah menampilkan secara dinamis hanya data dari kategori yang dipilih, misalnya dengan skrip php (untuk contoh ini, sjson.php)

Untuk layar A, akan seperti ini:

Layar Fungsi GetFlatListItem:

GetFlatListItem (fruit_name) {
   this.props.navigation.navigate('ScreenB', {unitserial: fruit_name}) 
   } 

Layar A Flatlist bisa seperti ini:


          data={ this.state.dataSource }
          
          ItemSeparatorComponent = {this.FlatListItemSeparator}
 
          renderItem={({item}) => 
          
 <View style={{flex: 1, flexDirection: 'row', justifyContent:'flex-start'}}>
<Text  onPress={this.GetFlatListItem.bind(this, item.serial)} > 
          {item.ok}</Text>
</View>
 

Untuk layar B akan seperti ini:

const enstring='https://www.test.com/sjson.php?serial=' + this.props.route.params.unitserial ;


       return fetch(enstring)
         .then((response) => response.json())
         .then((responseJson) => {
             

           this.setState({
             dataSource: responseJson
           }, function() {
             // In this block you can do something with new state.
           });
              
              
         })
         .catch((error) => {
           console.error(error);
         });
         }

dan Flatlist bisa seperti:

<FlatList
       data={ this.state.dataSource }

>

Harap dicatat bahwa Anda perlu mengubah kode Anda untuk menyesuaikan dengan kebutuhan Anda. Di atas hanyalah sebuah contoh.

RajshekharYadav Nov 29 2020 at 14:07

Status Definisi Pertama:

      const [apiRespPonse, setApiRespone] = useState("");
  const [selectedTabData, setSelectedPost] = useState("");
  const [category, setCategory] = useState("Sports");

Dalam panggilan api Anda, set The Response:

const fetchAllPost = () => {
    
    setApiRespone([]);
      const newArr = apiRespPonse.filter(obj => obj.label===category);
            setSelectedPost(newArr)
  };

Untuk opsi render Anda, gunakan filter untuk larik untuk mendapatkan data tab yang dipilih:

 return (
    <View style={styles.app}>
      <View style={styles.header}>
     
          <View style={{ flexDirection: "row" }}>
         {categories.map((item, index) => {
          return <Text onPress={()=>{
            setCategory(categories[index])
            const newArr = apiRespPonse.filter(obj => obj.label===category);
            setSelectedPost(newArr)
          }} style={styles.title}>{item.label}</Text>;
        })}
        </View>
     
      </View>


<FlatList
data={selectedTabData}/>
    </View>
  );
};

Mungkin bisa membantu.

SaachiTech Nov 30 2020 at 07:31

Jika saya mengerti benar, Anda hanya ingin menyegarkan konten daftar datar dengan kategori yang dipilih. Saya pikir kode yang Anda miliki sebelum pembaruan melakukan semua yang Anda butuhkan dengan sedikit pembaruan. Ini adalah bagian dari kode yang perlu Anda perbarui

{categories.map((e,index)=>(
  <TouchableOpacity 
    ...
    style={[
      ...
      index===page && {
        borderBottomWidth:3,
        borderBottomColor:colors.primary,
        borderRadius:2,
    }]
    onPress={()=>{setPage(index)}}
  >
  ...
  </TouchableOpacity>
)}

Pastikan postsApi.getPosts(page);mengembalikan data yang benar berdasarkan pageparameter yang diberikan .