如何在React Hooks中基于API数据配置React Apex Charts实现树形图(Treemap)
Got it, let's get that treemap up and running with your existing data! Here's a step-by-step breakdown of modifying your component to fit Apex Charts' treemap requirements:
1. Fix Data Access & Transform to Treemap Format
First off, your API returns the user array nested inside a data property—so we need to adjust how we save it to state. Plus, Apex Charts' treemap expects series to be an array of objects with x (label/name) and y (numeric value for block sizing). Your user count is perfect for the y value (it determines how big each treemap block is), while name will be our x label.
2. Update the Series Configuration
We'll use useMemo to avoid re-computing the series on every render (good performance practice) and map your raw data to the treemap-friendly format:
const series = useMemo(() => { return dataUser.map(item => ({ x: item.name, y: parseInt(item.user) // Convert string user count to a number })); }, [dataUser]);
3. Configure Treemap Options
Now set up the options to make your treemap readable and display all your data points in tooltips. We'll customize labels, tooltips, and basic styling:
const options = { title: { text: 'User Distribution by Zodiac Sign', align: 'left' }, tooltip: { formatter: function(val) { // Match the treemap item to your raw data to show the percent const matchedItem = dataUser.find(i => i.name === val.x); return `<div><strong>${val.x}</strong></div> <div>Total Users: ${matchedItem.user}</div> <div>Percentage: ${matchedItem.percent}</div>`; } }, plotOptions: { treemap: { distributed: true, // Spreads blocks evenly across the chart enableShades: false, // Removes gradient shading for a clean flat look dataLabels: { enabled: true, style: { fontSize: '12px', fontFamily: 'Arial' }, formatter: (val) => val.x // Show only the zodiac name on each block } } } };
4. Full Updated Component Code
Here's your complete component with all changes applied (don't forget to import useMemo!):
import React, { useState, useEffect, useMemo } from 'react'; import axios from 'axios'; import './App.css'; import Chart from 'react-apexcharts' import icUser from './image/profile-user.png' import icChart from './image/pie-chart.png' const App = () => { const [dataUser, setDataUser] = useState([]); useEffect(() => { axios.get("http://localhost:4000/data") .then(response => { setDataUser(response.data.data); // Access the nested data array from your API }).catch(e => { alert(e); }) }, []); // Transform raw data to treemap-compatible series const series = useMemo(() => { return dataUser.map(item => ({ x: item.name, y: parseInt(item.user) })); }, [dataUser]); // Treemap configuration options const options = { title: { text: 'User Distribution by Zodiac Sign', align: 'left' }, tooltip: { formatter: function(val) { const matchedItem = dataUser.find(i => i.name === val.x); return `<div><strong>${val.x}</strong></div> <div>Total Users: ${matchedItem.user}</div> <div>Percentage: ${matchedItem.percent}</div>`; } }, plotOptions: { treemap: { distributed: true, enableShades: false, dataLabels: { enabled: true, style: { fontSize: '12px', fontFamily: 'Arial' }, formatter: (val) => val.x } } } }; return ( <div> <Chart options={options} series={series} height={350} type="treemap"/> </div> ) }; export default App;
Quick Tips:
- You can tweak
plotOptions.treemapsettings (likedistributedorenableShades) to match your design preferences. - The
useMemohook ensures we only re-generate the series whendataUserchanges, keeping your component efficient.
内容的提问来源于stack exchange,提问作者ivanichi

