legend, chart, table
add Drumheller
add Banff
add Grande Prairie
delete RedDeer
bubbleChart.js
import React, { Component } from 'react';
import '../App.css';
import '../../node_modules/react-vis/dist/style.css';
import { Table } from 'reactstrap';
import TextField from '@material-ui/core/TextField';
import { withStyles } from '@material-ui/core/styles';
import MenuItem from '@material-ui/core/MenuItem';
import DeleteIcon from '@material-ui/icons/Delete';
import Button from '@material-ui/core/Button';
import {
XYPlot,
XAxis,
YAxis,
VerticalGridLines,
HorizontalGridLines,
MarkSeries,
LineSeries,
DiscreteColorLegend,
} from 'react-vis';
const styles = theme => ({
textField: {
margin: 0,
width: 100,
},
textFieldShort: {
margin: 0,
width: 50,
},
button: {
margin: theme.spacing.unit,
},
});
class BubbleChart extends Component {
constructor(props) {
super(props);
this.state = {
data: [
{ x: 48, y: 20, size: 20, title: 'Calgary'},
{ x: 50, y: 50, size: 10, title: 'RedDeer'},
{ x: 60, y: 80, size: 20, title: 'Edmonton'},
],
newCity:'',
};
}
handleTitleChange(value, index) {
const dataLength = this.state.data.length;
const oldProperty = this.state.data[index];
//check if it is an update or add request
const newProperty = {
title: value,
x: index < dataLength ? oldProperty.x : null,
y: index < dataLength ? oldProperty.y : null,
size: index < dataLength ? oldProperty.size : null,
}
const newData = [...this.state.data];
newData.splice(index, 1, newProperty);
this.setState({ data: newData });
}
handleXChange(value, index) {
const oldProperty = this.state.data[index];
const newProperty = {
x: parseFloat(value),
y: oldProperty.y,
size: oldProperty.size,
title: oldProperty.title,
}
const newData = [...this.state.data];
newData.splice(index, 1, newProperty);
this.setState({ data: newData });
}
handleYChange(value, index) {
const oldProperty = this.state.data[index];
const newProperty = {
x: oldProperty.x,
y: parseFloat(value),
size: oldProperty.size,
title: oldProperty.title,
}
const newData = [...this.state.data];
newData.splice(index, 1, newProperty);
this.setState({ data: newData });
}
handleSizeChange(value, index) {
const oldProperty = this.state.data[index];
const newProperty = {
x: oldProperty.x,
y: oldProperty.y,
size: parseFloat(value),
title: oldProperty.title,
}
const newData = [...this.state.data];
newData.splice(index, 1, newProperty);
this.setState({ data: newData });
}
handleDelete(index) {
const newData = [...this.state.data];
newData.splice(index, 1);
this.setState({ data: newData });
colorArray.splice(index, 1);
colorArray.splice(index, 1);
}
render() {
const { classes } = this.props;
const linePlots = [];
const stateData = this.state.data;
for (let i = 0; i < stateData.length - 1; i++) {
for (let j = i+1; j < stateData.length ; j++) {
linePlots.push(
<LineSeries key={i * 100 + j}
data={[
{ x: stateData[i].x, y: stateData[i].y },
{ x: stateData[j].x, y: stateData[j].y },
]}
stroke={"#12939A"}
strokeWidth={1}
/>
)
}
}
const markPlots = stateData.map((item, index) =>
<MarkSeries
key={index}
strokeWidth={item.size / 2}
size={item.size}
data={[item]}
color={colorArray[index]}
/>
)
return (
<div>
<h4 className="my-subTitle">4G Data Coverage</h4>
<DiscreteColorLegend
orientation="horizontal"
width={300}
items={
stateData.map((item, index) => {
return { title: item.title, color: colorArray[index] }
})}
/>
<XYPlot
yDomain={[0, 100]}
xDomain={[0, 100]}
width={300}
height={300}>
<VerticalGridLines tickValues={[0, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100]} />
<HorizontalGridLines tickValues={[0, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100]} />
<XAxis tickValues={[0, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100]} />
<YAxis tickValues={[0, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100]} />
{markPlots}
{linePlots.map((item, index) => { return item; })}
</XYPlot>
<Table bordered hover size="sm">
<thead className="my-table-header">
<tr>
<th>City</th>
<th>X</th>
<th>Y</th>
<th>Diameter</th>
<th>Delete</th>
</tr>
</thead>
<tbody>
{
stateData.map((item, index) =>
<tr key={index}>
<td>
<TextField
required
onChange={(e) => this.handleTitleChange(e.target.value, index)}
value={item.title}
className={classes.textField}
/>
</td>
<td>
<TextField
required
onChange={(e) => this.handleXChange(e.target.value, index)}
value={item.x}
type="number"
className={classes.textFieldShort}
/>
</td>
<td>
<TextField
required
onChange={(e) => this.handleYChange(e.target.value, index)}
value={item.y}
type="number"
className={classes.textFieldShort}
/>
</td>
<td>
<TextField
required
onChange={(e) => this.handleSizeChange(e.target.value, index)}
value={item.size}
type="number"
className={classes.textFieldShort}
/>
</td>
<td>
<DeleteIcon className="deleteIcon"
onClick={() => this.handleDelete(index)} />
</td>
</tr>
)
}
{/*-----------add new city----------*/}
<tr>
<td>
<TextField
required
label="New city"
onChange={(e) => this.setState({ newCity: e.target.value })}
className={classes.textField}
/>
</td>
<td>
<Button variant="contained" size="small"
className={classes.button}
onClick={() => this.handleTitleChange(this.state.newCity, stateData.length)}>
Add new
</Button>
</td>
<td></td>
<td></td>
</tr>
</tbody>
</Table>
</div>
);
}
}
const colorArray = [
"#ef0707",
"#dbef07",
"#07c8ef",
"#8e07ef",
"#ef0799",
"#2b5b36",
"#ef6707",
"#35ef07",
"#072def",
"#ef0707",
"#392b5b",
"#dee5e5",
"#12939A",
"#ef2907",
"#ef5007",
"#ef8a07",
"#efd307",
"#92ef07",
"#07ef7e",
"#07efeb",
"#0786ef",
"#6307ef",
"#b807ef",
"#df07ef",
"#ef0763",
"#5b542c",
"#2b465b",
"#5b2b52",
"#000000",
];
export default withStyles(styles)( BubbleChart);
No comments:
Post a Comment