简体   繁体   中英

How to add legend to a react + d3 grouped and stacked bar chart?

I have a created a stacked and grouped bar chart with react + d3 and i want to add legend, i have added it like:

 {allKeys.map((key) => ( <div key={key} className="field" style={{ display: "flex" }}> <input id={key} type="checkbox" checked={keys.includes(key)} onChange={(e) => { if (e.target.checked) { setKeys(Array.from(new Set([...keys, key]))); } else { setKeys(keys.filter((_key) => _key !== key)); } }} /> <label htmlFor={key} style={{ color: colors[key] }}> {key} </label> </div> ))}
 <script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.6.3/umd/react.production.min.js"></script> <script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.6.3/umd/react-dom.production.min.js"></script>

but the problem is that when you toggle (for example clicking on facebook to toggle) it will change stack order (for example facebook color is green and it should be always at the bottom, but when you click on facebook legend to make it disappear and click again to appear first it is at the bottom and when you hide and show back it will go to the top)

you can check the full code and demo in demo

any help to make it work will be appreciated

Two possible solutions:

  1. Use an object instead of an array, the key being the label and the value being whether it's toggled or not:
const initialItems = {
  facebook: true,
  google: true,
  linkedin: true
}

{Object.keys(items).map((key) => (
  <div key={key} className="field" style={{ display: "flex" }}>
    <input
      id={key}
      type="checkbox"
      checked={items[key]}
      onChange={(e) => {
        if (e.target.checked) {
          items[key] = true;
        } else {
          items[key] = false;
        }
        setItems(items);
      }}
    />
    <label htmlFor={key} style={{ color: colors[key] }}>
      {key}
    </label>
  </div>
))}
  1. Change the set function to use allKeys as a base:
if (e.target.checked) {
  setKeys(allKeys.filter(k => keys.includes(k) || k === key));
}

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