React canvas context.fillRect doesn't work - javascript

I'd like to draw rect with React,
is there anything wrong in the following?
I don't figure out why this code doesn't draw a rect.
class GameView{
constructor(props) {
this.canvas = React.createRef()
this.width = 0;
this.height = 0;
this.canvas_style = {
width: 600,
height: 400
}
}
componentDidMount() {
this.width = document.body.offsetWidth;
this.height = document.body.offsetHeight;
this.canvas_style = {
width: this.width,
height: this.height
}
this.context = this.canvas.current.getContext("2d");
}
render() {
return (
<canvas id="game-view" ref={this.canvas} width={this.width} height={this.height} />
)
}
}
class View extends GameView {
constructor(props) {
super(props);
}
componentDidMount() {
super.componentDidMount();
this.context.fillStyle = "black";
this.context.fillRect(0, 0, 200, 200)
}
render() {
return (
<canvas id="game-view" ref={this.canvas} width={this.width} height={this.height} style={this.canvas_style} />
)
}
}
I tried docment.getElementById("game-view") but I got the same result

The GameView needs to extend React.Component, so React can render it.
The height of the container (body in this case) needs to be greater than 0, so the canvas would have some height.
View doesn't need to render a different JSX:
class GameView extends React.Component {
canvas = React.createRef()
width = document.body.offsetWidth;
height = document.body.offsetHeight;
componentDidMount() {
this.context = this.canvas.current.getContext("2d");
}
render() {
return (
<canvas id="game-view" ref={this.canvas} width={this.width} height={this.height} />
)
}
}
class View extends GameView {
componentDidMount() {
super.componentDidMount();
this.context.fillStyle = "black";
this.context.fillRect(0, 0, 200, 200)
}
}
ReactDOM.render(
<View />,
root
);
html, body {
margin: 0;
height: 100%;
}
<script crossorigin src="https://unpkg.com/react#17/umd/react.development.js"></script>
<script crossorigin src="https://unpkg.com/react-dom#17/umd/react-dom.development.js"></script>
<div id="root"></div>

Related

How to find out what can be exported from npm package

I'm trying to replicate this https://codepen.io/swizec/pen/bgvEvp
I've installed the d3-timer package with npm https://www.npmjs.com/package/d3-timer
It is definitely there because I have read through the files.
What I am confused about is how to import the timer into my code. In the code on codepen it just uses d3.timer but doesn't show the import above. So I tried importing d3 but it can't find it in the d3-timer package. I tried timer, Timer, D3, d3.
So my question is - how do I go about investigating the package to work out what the names of the exports are?
Or if that is too complicated - in this particular case what should I be importing to get the functionality of d3.timer?
Many thanks!
Code from code pen:
const Component = React.Component;
const Ball = ({ x, y }) => (
<circle cx={x} cy={y} r={5} />
);
const MAX_H = 750;
class App extends Component {
constructor() {
super();
this.state = {
y: 5,
vy: 0
}
}
componentDidMount() {
this.timer = d3.timer(() => this.gameLoop());
this.gameLoop();
}
componentWillUnmount() {
this.timer.stop();
}
gameLoop() {
let { y, vy } = this.state;
if (y > MAX_H) {
vy = -vy*.87;
}
this.setState({
y: y+vy,
vy: vy+0.3
})
}
render() {
return (
<svg width="100%" height={MAX_H}>
<Ball x={50} y={this.state.y} />
</svg>
)
}
}
ReactDOM.render(<App />, document.getElementById('app'));
my code
import React from 'react';
import d3 from 'd3-timer'
const Component = React.Component;
const Ball = ({ x, y }) => (
<circle cx={x} cy={y} r={5} />
);
const MAX_H = 750;
export default class App extends Component {
constructor() {
super();
this.state = {
y: 5,
vy: 0
}
}
componentDidMount() {
this.timer = d3.timer(() => this.gameLoop());
this.gameLoop();
}
componentWillUnmount() {
this.timer.stop();
}
gameLoop() {
let { y, vy } = this.state;
if (y > MAX_H) {
vy = -vy*.87;
}
this.setState({
y: y+vy,
vy: vy+0.3
})
}
render() {
return (
<svg width="100%" height={MAX_H}>
<Ball x={50} y={this.state.y} />
</svg>
)
}
}
Error message:
Attempted import error: 'd3-timer' does not contain a default export (imported as 'd3').
Try
import { timer } from 'd3-timer' and then use timer()

setting state with onChange in React results in canvas being null

I have a simple application consisting of two - parent App and child Circle components. My aim is to draw circle on canvas (Circle component does that) and have input that takes number value and makes angle of that numerical value with the radius. like so :
example
The problem is, i've set up onChange event listener with handler on input, which is supposed to update my state, but whenever i type something into input field, it tells me that my canvas is null, and .getContext("2d") method can't be performed, which messes up entire application.
I've googled and found out that this is because of the fact that canvas renders after state is updated, or something like that. I can't think of any solution that would make that possible. here's my code :
App.js
import React, { Component } from "react";
import "./App.css";
import { degreesToRadiansFlipped } from "./helpers/helpers";
import Circle from "./components/Circle";
class App extends Component {
state = { degrees: 0 };
handleChange = (event) => {
this.setState({ degrees: event.target.value });
};
coordinates = {
x: Math.cos(degreesToRadiansFlipped(120)) * 100 + 150,
y: Math.sin(degreesToRadiansFlipped(120)) * 100 + 150
};
drawCircle = (context, x, y) => {
context.beginPath();
context.arc(150, 150, 100, 0, Math.PI * 2);
context.moveTo(150, 150);
context.lineTo(x, y);
context.stroke();
};
render() {
console.log(this.currentDegreeValue);
return (
<div className="main">
<Circle drawCircle={this.drawCircle} coordinates={this.coordinates} />
<form>
<input name="degrees" type="text" onChange={this.handleChange} />
</form>
</div>
);
}
}
export default App;
Circle.js
import React, { Component } from "react";
class Circle extends Component {
componentDidMount() {
this.props.drawCircle(
this.context,
this.props.coordinates.x,
this.props.coordinates.y
);
}
render() {
return (
<canvas
ref={(canvas) => (this.context = canvas.getContext("2d"))}
width={300}
height={300}
/>
);
}
}
export default Circle;
Actual Error is :
TypeError: Cannot read property 'getContext' of null
// index.js
import React, { Component } from "react";
import ReactDOM from "react-dom";
import Circle from "./Circle";
class App extends Component {
state = { degrees: 0, showCirle: false };
handleChange = event => {
this.setState({ degrees: event.target.value, showCirle: true });
};
degreesToRadiansFlipped(angle) {
return (angle + Math.PI) % (2 * Math.PI);
}
coordinates = {
x: Math.cos(this.degreesToRadiansFlipped(120)) * 100 + 150,
y: Math.sin(this.degreesToRadiansFlipped(120)) * 100 + 150
};
drawCircle = (context, x, y) => {
console.log("inside drawcircle");
context.beginPath();
context.arc(150, 150, 100, 0, Math.PI * 2);
context.moveTo(150, 150);
context.lineTo(x, y);
context.stroke();
};
render() {
console.log(this.currentDegreeValue);
return (
<div className="main">
{this.state.showCirle && (
<Circle drawCircle={this.drawCircle} coordinates={this.coordinates} />
)}
<form>
<input name="degrees" type="text" onChange={this.handleChange} />
</form>
</div>
);
}
}
const rootElement = document.getElementById("root");
ReactDOM.render(<App />, rootElement);
// Circel Component
import React, { Component } from "react";
class Circle extends Component {
constructor(props) {
super(props);
}
fillContext = () => {
const canvas = this.refs.canvas
const ctx = canvas.getContext("2d")
this.context = ctx
this.props.drawCircle(
this.context,
this.props.coordinates.x,
this.props.coordinates.y
);
}
componentDidMount() {
this.fillContext()
}
componentDidUpdate() {
this.fillContext()
}
render() {
return <canvas ref="canvas" width={300} height={300} />;
}
}
export default Circle;
In your example, x and y coordinates should change based on input value change, but coordinates is an object with fixed x and y values. I think that logic should also change.

How to make this animation run smoothly using react and svg

I have the following component:
class Ball extends React.Component {
constructor(props) {
super(props);
this.state = { frame: 0, position: this.positionBall(0) };
this.nextFrame();
}
nextFrame() {
this.setState(prevState => ({
frame: prevState.frame + 1,
position: this.positionBall(prevState.frame + 1)
}));
requestAnimationFrame(() => this.nextFrame());
}
render() {
return (
<svg style={{ width: "100%", height: "100%" }}>
<circle
cx={this.state.position}
cy={this.height() / 2}
r={this.radius()}
/>
</svg>
);
}
height() {
return document.documentElement.clientHeight;
}
width() {
return document.documentElement.clientWidth;
}
radius() {
return this.height() / 10;
}
positionBall(frame) {
const maximumPosition = this.width() - 2 * this.radius();
const maximumFrame = 120;
const slope = maximumPosition / maximumFrame;
const position = Math.round(
maximumPosition +
this.radius() -
1 * Math.abs(frame % (maximumFrame * 2) - maximumFrame) * slope
);
return position;
}
}
It is a very simple animation, but it doesn't run entire smooth all the time, especially on wide screens. How can I improve this code?
See this codesandbox:
https://codesandbox.io/s/22kzjy21n

Reactjs, sending and reading variables

so basically I'm using ref to get component dimensions in componentDidMount() and I can read and console.log that and it gives me the width I want(look into code), but when I want to read and console.log that in the render() method and to use that informations, it gives me undefined. And I don't know what is wrong
var Tooltip = React.createClass({
componentDidMount() {
this.tooltipSize = this.refs.tooltip.getBoundingClientRect();
this.tooltipWidth = this.tooltipSize.width;
// console.log(this.tooltipWidth); here it gives me the width
},
render(){
var tooltipSize,
tooltipWidth,
tooltipStyle = {
top: 0,
left: 0,
};
// console.log(tooltipWidth); here it gives me undefined
return(
<div ref="tooltip" className="tooltip" style={tooltipStyle}>{this.props.tooltip}</div>
);
}
});
var Button = React.createClass({
getInitialState() {
return {
iconStyle: this.props.iconStyle,
style: this.props.style,
cursorPos: {},
};
},
componentDidMount() {
this.size = this.refs.button.getBoundingClientRect();
this.width = this.size.width;
this.height = this.size.height;
this.top = this.size.top;
this.left = this.size.left;
},
...
render() {
var _props = this.props,
top,
left,
width,
height,
size,
//other variables
...
return(
<Style>
{`
.IconButton{
position: relative;
}
.IconButton:disabled{
color: ${_props.disabledColor};
}
.btnhref{
text-decoration: none;
background-color: blue;
}
`}
<a {...opts} className="btnhref" id="tak">
<button ref="button" className={"IconButton" + _props.className} disabled={disabled} style={buttonStyle}
onMouseEnter={this.showTooltip} onMouseLeave={this.removeTooltip} >
<Ink background={true} style={rippleStyle} opacity={rippleOpacity} />
<FontIcon className={_props.iconClassName}/>
</button>
</a>
</Style>
);
}
});
class IconButton extends React.Component {
render(){
return(
<div>
<Tooltip tooltip={this.props.tooltip} />
<Button href={this.props.href} className={this.props.className} iconStyle={this.props.iconStyle} style={this.props.style} iconClassName={this.props.iconClassName} disabled={this.props.disabled} disableTouchRipple={this.props.disableTouchRipple} />
</div>
);
}
}
And one thing else. How can I send variables with informations about dimensions of another component(Button component) to the Tooltip component? Because I need to use them inside of this component to place it. Thanks
Updated code:
var Tooltip = React.createClass({
getInitialState() {
return {
tooltipWidth: null,
tooltipHeight: null
};
},
componentDidMount() {
this.tooltipSize = this.refs.tooltip.getBoundingClientRect();
this.setState({
tooltipWidth: this.tooltipSize.width,
tooltipHeight: this.tooltipSize.height
});
},
...
render(){
var _props = this.props,
fontSize,
fontStyle,
tooltipSize,
tooltipWidth = this.state.tooltipWidth,
tooltipHeight = this.state.tooltipHeight,
w = this.props.buttonWidth,
h = this.props.buttonHeight,
y = this.props.buttonTop,
x = this.props.buttonLeft,
tooltipStyle = {
top: y - tooltipHeight - 20 + "px",
left: x - tooltipWidth/2 + w/2 + "px",
};;
...
return(
<div ref="tooltip" className="tooltip" style={fontStyle}>{this.props.tooltip}</div>
);
}
});
var Button = React.createClass({
getInitialState() {
return {
iconStyle: this.props.iconStyle,
style: this.props.style,
cursorPos: {},
width: null,
height: null,
top: null,
left: null,
};
},
componentDidMount() {
this.size = this.refs.button.getBoundingClientRect();
this.width = this.size.width;
this.height = this.size.height;
this.top = this.size.top;
this.left = this.size.left;
},
transferring1(){
var width = this.width;
return width;
},
transferring2(){
var height = this.height;
return height;
},
transferring3(){
var top = this.top;
return top;
},
transferring4(){
var left = this.left;
return left;
},
...
render() {
var _props = this.props,
opts,
top,
left,
width,
height,
size;
...
return(
<Style>
{`
.IconButton{
position: relative;
}
.IconButton:disabled{
color: ${_props.disabledColor};
}
.btnhref{
text-decoration: none;
background-color: blue;
}
`}
<a {...opts} className="btnhref" id="tak">
<button ref="button" className={"IconButton" + _props.className} disabled={disabled} style={buttonStyle}
onMouseEnter={this.showTooltip} onMouseLeave={this.removeTooltip} >
<Ink background={true} style={rippleStyle} opacity={rippleOpacity} />
<FontIcon className={_props.iconClassName}/>
</button>
</a>
</Style>
);
}
});
class IconButton extends React.Component {
constructor(props) {
super(props);
this.state = {
buttonWidth: null,
buttonHeight: null,
buttonTop: null,
buttonLeft: null,
};
}
componentDidMount() {
this.setState({
buttonWidth: this.refs.btn.transferring1(),
buttonHeight: this.refs.btn.transferring2(),
buttonTop: this.refs.btn.transferring3(),
buttonLeft: this.refs.btn.transferring4(),
});
}
render(){
return(
<div>
<Tooltip tooltipPosition={this.props.tooltipPosition} tooltip={this.props.tooltip} touch={this.props.touch} buttonWidth={this.state.buttonWidth} buttonHeight={this.state.buttonHeight} buttonTop={this.state.buttonTop} buttonLeft={this.state.buttonLeft}/>
<Button ref="btn" href={this.props.href} className={this.props.className} iconStyle={this.props.iconStyle} style={this.props.style} iconClassName={this.props.iconClassName}
disabled={this.props.disabled} disableTouchRipple={this.props.disableTouchRipple} />
</div>
);
}
}
ReactDOM.render(
<IconButton href="" className="" iconStyle="" style="" iconClassName="face" disabled="" disableTouchRipple="" tooltip="! ! ! Guzik ! to ! kozak ! ! !" tooltipPosition="" touch="true" />,
document.getElementById('app')
);
I think you should use state for setting variables in react
example
var Tooltip = React.createClass({
constructor(){
super();
this.state = {tooltipWidth: 0}
}
componentDidMount() {
this.tooltipSize = this.refs.tooltip.getBoundingClientRect();
this.setState({tooltipWidth: this.tooltipSize.width}); //Update the state of this component
},
render(){
console.log(this.state.tooltipWidth) //your tooltip width
return(
<div ref="tooltip" className="tooltip" style={tooltipStyle}>{this.props.tooltip}</div>
);
}
});
and for passing another's component dimension, you should calculate the size of Button component on the parent component (IconButton).
Then pass it to Tooltip like this (just example)
<Tooltip buttonHeight={this.state.buttonHeight} tooltip={this.props.tooltip} />

Reactjs dashboard - multiple instances with an array of parameters

** LATEST Fiddle -- http://jsfiddle.net/cfrapLma/28/
adding chart types -- is there a better way to move this forward -- would the config json be handled via redux -- what is the next step forward. Has anyone tried making a dashboard application using reactjs and d3 before?
I am working on a reactjs project and I am keen to output a set of div holders that will contain future chart parameters, like width, height, url service.
++ How do I push and pull about multiple parameters to create different instances of a chart, placeholder..?
++ Is this a good start for creating a dashboard set of components do I need to create a configuration json for what charts, sizes, services I want to absorb.
//config json?
[{
"width": 200,
"height": 200,
"type": "piechart",
"serviceApi": "api.php?mode=GetCars"
}, {
"width": 100,
"height": 100,
"type": "barchart",
"serviceApi": "api.php?mode=GetBoats"
}]
do I need to create a config json that will control the parameters - an array of charts that are needing to be rendered?
var MultipleCharts = React.createClass({
render: function() {
return (
<div>
<div className="holder1"><PieChart width={this.props.width} height={this.props.height} service={this.props.service}/></div>
<div className="holder2"><PieChart width={this.props.width} height={this.props.height} service={this.props.service}/></div>
</div>
);
}
});
^ this is a hard coded approach and I would need to loop and push through a configuration json so each chart has different properties.
<div data-role="piechart" data-width=240 data-height=240 data-service="api.php?mode=GetCars">
//Latest Fiddle
http://jsfiddle.net/cfrapLma/24/
here is the first prototype build - whether I would have reactjs handle a stack of charts -- as if this information is coming from a configuration json -- like a dashboard setup.
Or the dashboard configuration is hardcoded on the template -- and reactjs invokes the charting tool.
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<title>React Charts</title>
<script src="https://npmcdn.com/react#15.3.0/dist/react.js"></script>
<script src="https://npmcdn.com/react-dom#15.3.0/dist/react-dom.js"></script>
<script src="https://npmcdn.com/babel-core#5.8.38/browser.min.js"></script>
<script src="https://npmcdn.com/jquery#3.1.0/dist/jquery.min.js"></script>
<script src="https://npmcdn.com/remarkable#1.6.2/dist/remarkable.min.js"></script>
<script src="http://d3js.org/d3.v3.min.js"></script>
</head>
<body>
<div id="example"></div>
<script type="text/babel">
var config = [{
"width": 200,
"height": 200,
"type": "piechart",
"serviceApi": "api.php?mode=GetCars"
}, {
"width": 100,
"height": 100,
"type": "barchart",
"serviceApi": "api.php?mode=GetBoats"
}];
var MultipleCharts = React.createClass({
render: function() {
return (
<div>
<div className="holder1"><PieChart width={this.props.width} height={this.props.height} service={this.props.service}/></div>
<div className="holder2"><BarChart width={this.props.width} height={this.props.height} service={this.props.service}/></div>
</div>
);
}
});
var PieChart = React.createClass({
componentDidMount: function() {
var $this = $(ReactDOM.findDOMNode(this));
console.log("rendered div now engage d3");
// set el height and width etc.
},
render: function() {
return (
<div className="piechart" data-role="piechart" data-width={this.props.width} data-height={this.props.height} data-service={this.props.service}>pie.
</div>
);
}
});
var BarChart = React.createClass({
componentDidMount: function() {
var $this = $(ReactDOM.findDOMNode(this));
console.log("rendered div now engage d3");
// set el height and width etc.
},
render: function() {
return (
<div className="barchart" data-role="barchart" data-width={this.props.width} data-height={this.props.height} data-service={this.props.service}>pie.
</div>
);
}
});
ReactDOM.render(
<MultipleCharts width="200" height="200" service="api.php?mode=GetCars"/>,
document.getElementById('example')
);
</script>
</body>
</html>
So, what you can do is to create fabric method that will return corresponding component based on config.type.
Then, you can iterate through all your configs in render method.
And also pass config as props to your component MultipleCharts.
var config = [{
"width": 200,
"height": 200,
"type": "piechart",
"serviceApi": "api.php?mode=GetCars"
}, {
"width": 100,
"height": 100,
"type": "barchart",
"serviceApi": "api.php?mode=GetBoats"
}];
var MultipleCharts = React.createClass({
getChart: function(config) {
switch (config.type) {
case 'piechart':
return <PieChart width={config.width} height={config.height} service={config.service} />
case 'barchart':
return <BarChart width={config.width} height={config.height} service={config.service} />
}
},
render: function () {
var config = this.props.config;
return (
<div>
{config.map((chartConfig, index) => {
return (
<div key={index} className={'holder' + index}>
{this.getChart(chartConfig)}
</div>
)
})}
</div>
);
}
});
var PieChart = React.createClass({
componentDidMount: function () {
var $this = $(ReactDOM.findDOMNode(this));
console.log("rendered div now engage d3");
// set el height and width etc.
},
render: function () {
return (
<div className="piechart" data-role="piechart" data-width={this.props.width} data-height={this.props.height}
data-service={this.props.service}>pie.
</div>
);
}
});
var BarChart = React.createClass({
componentDidMount: function () {
var $this = $(ReactDOM.findDOMNode(this));
console.log("rendered div now engage d3");
// set el height and width etc.
},
render: function () {
return (
<div className="barchart" data-role="barchart" data-width={this.props.width} data-height={this.props.height}
data-service={this.props.service}>pie.
</div>
);
}
});
ReactDOM.render(
<MultipleCharts config={config} />,
document.getElementById('example')
);
And please, try to avoid using data-* attributes in React components.
Based in #Sergey's answer I have added a couple of modifications to make it really dynamic. Now there is a typeMapping object that maps from strings to components. If you want to add a new component, you just need to add it there. For convenience I am using ES6, I hope that you can translate it to ES5 if you need to.
var config = [{
"type": "PieChart",
"width": 200,
"height": 200,
"serviceApi": "api.php?mode=GetCars"
}, {
"type": "BarChart",
"width": 100,
"height": 100,
"serviceApi": "api.php?mode=GetBoats"
}];
var MultipleCharts = React.createClass({
getChart: function(config) {
const { type, ...props } = config;
return React.createElement(typeMapping[type], props);
},
render: function () {
var config = this.props.config;
return (
<div>
{config.map((chartConfig, index) => {
return (
<div key={index} className={'holder' + index}>
{this.getChart(chartConfig)}
</div>
)
})}
</div>
);
}
});
var PieChart = React.createClass({
componentDidMount: function () {
var $this = $(ReactDOM.findDOMNode(this));
console.log("rendered div now engage d3");
// set el height and width etc.
},
render: function () {
return (
<div className="piechart" data-role="piechart" data-width={this.props.width} data-height={this.props.height}
data-service={this.props.serviceApi}>pie.
</div>
);
}
});
var BarChart = React.createClass({
componentDidMount: function () {
var $this = $(ReactDOM.findDOMNode(this));
console.log("rendered div now engage d3");
// set el height and width etc.
},
render: function () {
return (
<div className="barchart" data-role="barchart" data-width={this.props.width} data-height={this.props.height}
data-service={this.props.serviceApi}>bar.
</div>
);
}
});
// Allowed types
const typeMapping = {
PieChart, // In ES6, it is the same as "PieChart": PieChart,
BarChart,
};
ReactDOM.render(
<MultipleCharts config={config} />,
document.getElementById('example')
);
.piechart{
background: pink;
width: 100px;
height: 50px;
border: 1px solid black;
}
.barchart{
background: green;
width: 100px;
height: 50px;
border: 1px solid black;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="https://npmcdn.com/react#15.3.1/dist/react.js"></script>
<script src="https://npmcdn.com/react-dom#15.3.1/dist/react-dom.js"></script>
<div id="example"></div>
Alright so using the create-react-app as a base..
I've tried to start cutting up the files. I get an error when I try and put the PieChart/BarChart parts into their respective files -- do I need to modify them as a class?
/src/App.css
.App {
text-align: center;
}
.App-logo {
animation: App-logo-spin infinite 20s linear;
height: 80px;
}
.App-header {
background-color: #222;
height: 150px;
padding: 20px;
color: white;
}
.App-intro {
font-size: large;
}
#keyframes App-logo-spin {
from { transform: rotate(0deg); }
to { transform: rotate(360deg); }
}
/src/App.js
import React, { Component } from 'react';
import './App.css';
import BarChart from './BarChart';
import PieChart from './PieChart';
import LineChart from './LineChart';
// Allowed types
const typeMapping = {
PieChart, // In ES6, it is the same as "PieChart": PieChart,
BarChart,
LineChart
};
class App extends Component {
getChart(config) {
const { type, ...props } = config;
return React.createElement(typeMapping[type], props);
}
render() {
var config = this.props.config;
return (
<div>
{config.map((chartConfig, index) => {
return (
<div key={index} className={'holder' + index}>
{this.getChart(chartConfig)}
</div>
)
})}
</div>
);
}
}
export default App;
/src/BarChart.js
//barchart
import React, { Component } from 'react';
import ReactDOM from 'react-dom';
var $ = require("jquery");
class BarChart extends Component {
componentDidMount() {
var $this = $(ReactDOM.findDOMNode(this));
console.log("rendered div now engage d3", $this);
// set el height and width etc.
}
render() {
return (
<div className="barchart" data-role="barchart" data-width={this.props.width} data-height={this.props.height}
data-service={this.props.serviceApi}>bar.
</div>
);
}
};
export default BarChart;
/src/Index.css
body {
margin: 0;
padding: 0;
font-family: sans-serif;
}
.piechart{
background: pink;
width: 100px;
height: 50px;
border: 1px solid black;
}
.barchart{
background: green;
width: 100px;
height: 50px;
border: 1px solid black;
}
.linechart{
background: purple;
width: 100px;
height: 50px;
border: 1px solid black;
}
/src/Index.js
import React from 'react';
import ReactDOM from 'react-dom';
import App from './App';
import './index.css';
var config = [{
"type": "PieChart",
"width": 200,
"height": 200,
"serviceApi": "api.php?mode=GetCars"
}, {
"type": "BarChart",
"width": 100,
"height": 100,
"serviceApi": "api.php?mode=GetBoats"
}, {
"type": "LineChart",
"width": 100,
"height": 100,
"serviceApi": "api.php?mode=GetBoats"
}];
ReactDOM.render(
<App config={config} />,
document.getElementById('root')
);
/src/LineChart.js
//linechart
import React, { Component } from 'react';
import ReactDOM from 'react-dom';
var $ = require("jquery");
class LineChart extends Component {
componentDidMount() {
var $this = $(ReactDOM.findDOMNode(this));
console.log("rendered div now engage d3", $this);
// set el height and width etc.
}
render() {
return (
<div className="linechart" data-role="linechart" data-width={this.props.width} data-height={this.props.height}
data-service={this.props.serviceApi}>line.
</div>
);
}
};
export default LineChart;
/src/PieChart.js
//piechart
import React, { Component } from 'react';
import ReactDOM from 'react-dom';
var $ = require("jquery");
class PieChart extends Component {
componentDidMount() {
var $this = $(ReactDOM.findDOMNode(this));
console.log("rendered div now engage d3", $this);
// set el height and width etc.
var dataset = {
apples: [53245, 28479, 19697, 24037, 40245],
};
var width = 460,
height = 300,
radius = Math.min(width, height) / 2;
var color = d3.scale.category20();
var pie = d3.layout.pie()
.sort(null);
var arc = d3.svg.arc()
.innerRadius(radius - 100)
.outerRadius(radius - 50);
var svg = d3.select($this[0]).append("svg")
.attr("width", width)
.attr("height", height)
.append("g")
.attr("transform", "translate(" + width / 2 + "," + height / 2 + ")");
var path = svg.selectAll("path")
.data(pie(dataset.apples))
.enter().append("path")
.attr("fill", function(d, i) { return color(i); })
.attr("d", arc);
}
render() {
return (
<div className="piechart" data-role="piechart" data-width={this.props.width} data-height={this.props.height}
data-service={this.props.serviceApi}>pie.
</div>
);
}
};
export default PieChart;

Categories

Resources