47

I am trying to use recharts to implement a BarChart. But the width={600} and height={300} causes the Barchart to be absolute, not responsive. How to make the Barchart a responsive one? I tried using percentage as width={'50%"} height={"40%"} but did not work.

import { BarChart, Bar, XAxis, YAxis, CartesianGrid, Tooltip, Legend } from 'recharts';


<BarChart className="barChart" width={600} height={300} data={data}
          margin={{top: 5, right: 30, left: 20, bottom: 5}} label="heaf">
      <CartesianGrid strokeDasharray="3 3"/>
      <XAxis dataKey="name"/>
      <YAxis/>
      <Tooltip/>
      <Legend />
      <Bar dataKey="occupied" barSize={10} fill="#05386b" />
      <Bar dataKey="available" barSize={10} fill="#fdaa00" />
      <Bar dataKey="cleaning" barSize={10} fill="#379583" />
      <Bar dataKey="reserved" barSize={10} fill="#c60505" />
</BarChart>
frogatto
  • 28,539
  • 11
  • 83
  • 129
Shrawan BK
  • 531
  • 1
  • 6
  • 13
  • All solutions here only work for width—did you get it working for height as well? All the provided answers all have a fixed height. – lony Aug 14 '22 at 20:01

5 Answers5

72

You need to use ResponsiveContainer for it to work. Also, use the percentage values without brackets.

<ResponsiveContainer width="95%" height={400}>
   // your chart
</ResponsiveContainer>

I used that and it worked just fine! :)

Source: Responsive Container Docs

Saulo Joab
  • 737
  • 5
  • 5
24

You can use ResponsiveContainer provided by recharts.

Docs of ResponsiveContainer says:

A container component to make charts adapt to the size of the parent container. One of the props width and height should be a percentage string.

Here is the working code https://codesandbox.io/s/react-recharts-responsive-stack-overflow-863bi. Try resizing the output window width:

import React from "react";
import ReactDOM from "react-dom";
import {
  BarChart,
  Bar,
  XAxis,
  YAxis,
  CartesianGrid,
  Tooltip,
  Legend,
  ResponsiveContainer
} from "recharts";

import "./styles.css";

const data = [
  { name: "Page A", uv: 4000, pv: 2400, amt: 2400 },
  { name: "Page B", uv: 3000, pv: 1398, amt: 2210 },
  { name: "Page C", uv: 2000, pv: 9800, amt: 2290 },
  { name: "Page D", uv: 2780, pv: 3908, amt: 2000 },
  { name: "Page E", uv: 1890, pv: 4800, amt: 2181 },
  { name: "Page F", uv: 2390, pv: 3800, amt: 2500 },
  { name: "Page G", uv: 3490, pv: 4300, amt: 2100 }
];

const SimpleAreaChart = () => {
  return (
    <ResponsiveContainer>
      <BarChart data={data} margin={{ top: 5, right: 30, left: 20, bottom: 5 }}>
        <CartesianGrid strokeDasharray="3 3" />
        <XAxis dataKey="name" />
        <YAxis />
        <Tooltip />
        <Legend />
        <Bar dataKey="pv" fill="#8884d8" />
        <Bar dataKey="uv" fill="#82ca9d" />
      </BarChart>
    </ResponsiveContainer>
  );
};

const rootElement = document.getElementById("container");
ReactDOM.render(<SimpleAreaChart />, rootElement);

Here is the css of container:

#container {
  -webkit-box-sizing: border-box;
  -moz-box-sizing: border-box;
  box-sizing: border-box;
  padding: 10px;
  width: 100%;
  height: 400px;
  background-color: #fff;
}
Murli Prajapati
  • 8,833
  • 5
  • 38
  • 55
3

If you want both of the dimension to scale, just use aspect property

<ResponsiveContainer aspect={1.2}>
   // chart with width = 1.2 height
</ResponsiveContainer>

<ResponsiveContainer aspect={0.8}>
   // chart with width = 0.8 height
</ResponsiveContainer>

The height / width will be 100% of the parent container in this case.

Mr Patience
  • 1,564
  • 16
  • 30
  • 1
    Thank you -- I had been looking for exactly this type of approach! Every example I've seen requires explicitly setting the height and/or width explicitly (if not for `` then for a parent div), but `aspect` lets me just have the chart adjust to its parent's size, regardless of whatever else is happening. – sernaferna Aug 19 '23 at 14:56
0

Wrap the bar chart with divs.

<div style={{ position: 'relative', width: '50%', paddingTop: '40%' }}>
  <div style={{ position: 'absolute', height: '100%' }}>
    <BarChart />
  </div>
</div>

for outer div: width of 50% is with respect to the container width. paddingTop is 40% of the container width.

for inner div: height of 100% will occupy its entire container whose height is only its paddingTop.

vijayst
  • 20,359
  • 18
  • 69
  • 113
0

this worked for me

<ResponsiveContainer width="95%" height={data.length*x}>

data.length -> number of components in y axis

x -> size of cell to increase (33 worked well in my case)

Kaushik SA
  • 43
  • 1
  • 7