Related
I would appreciate any help that I can get with this
I need to plot a pie chart with 4 standard pies: ABC, BCD, CDE and DEF
Each Pie has a data point coming in from my GraphiQL resolver which looks like this:
{
"data": {
"metrics": {
"A": 56147.85,
"B": 116480.51,
"C": 56147.85,
"D": 120329.45000000001,
}
}
}
This is my highchart code for piechart
function PieChart() {
const { loading, error, data } = useQuery(CONC, {
variables: {
Currency: 'USD',
Date: {
date: '2019-05-01',
date_range: ['2019-05-01', '2019-06-10'],
},
Options: {
a: {
prop: '44',
csprop: ['14', '14', '40', '60'],
},
d: {
prop: '104',
csprop: ['511', '289', '519', '62'],
},
},
C: 'G',
Incl: false,
DFilters: [
{
by: 'P',
values: [],
},
],
},
});
const Top = [];
const First = [];
const Second = [];
const Rest = [];
data &&
data.metrics.forEach((e) => {
Top.push(e['A']);
First.push(e['B']);
Second.push(e['C']);
Rest.push(e['D']);
});
return (
<HighchartWrapper
chartOptions={{
chart: {
type: 'pie',
height: 230,
// width: 565,
},
title: {
text: '',
},
tooltip: {
pointFormat: '{series.name}: <b>{point.percentage:.1f}%</b>',
},
accessibility: {
point: {
valueSuffix: '%',
},
},
exporting: {
enabled: false,
},
plotOptions: {
pie: {
allowPointSelect: true,
cursor: 'pointer',
dataLabels: {
enabled: true,
format: '<b>{point.name}</b>: {point.percentage:.1f} %',
},
},
},
series: [
{
name: 'R',
data: [
{ name: 'ABC', y: Top},
{ name: 'BCD', y: First},
{ name: 'CDE', y: Second},
{ name: 'DEF', y: Rest},
],
},
],
}}
/>
);
}
export default memo(PieChart);
PROBLEM:
The GraphiQL query is generating results.
But I believe it's the way I am trying to push data that's giving me an empty pie chart
Thank you all in advance
I have an API which gives me a JSON in the following format:
[{"timestamp":"1389442547000","PourcentRest":"50"},
{"timestamp":"1389442548000","PourcentRest":"55"},
{"timestamp":"1389868449000","PourcentRest":"45"}]
I need to turn the returned object into an array of values for integration with highchart like this:
[[1389442547000,50],[1389442548000,55],
[1389868449000,45],[1389868450000,73],
[1391177296000,37],[1391177297000,45]]
I've been trying for several days, but I can't do it.
Here is the dataservice which interrogates the API
export class TankDetailsService {
PHP_API_SERVER = "http://MY-API";
constructor(private httpClient: HttpClient) {}
readMeasures(idCit: string): Observable<Measure[]>{
return this.httpClient.get<Measure[]>(`${this.PHP_API_SERVER}/restFillingApi/?idcit=${idCit}`);
}
Here is the part of my component.ts
export class TankDetailsComponent implements OnInit {
Measure: Measure[];
idCit: string;
chartOptions: object;
constructor(private route: ActivatedRoute, private TankDetailsService: TankDetailsService, private http: HttpClient) {
this.route.queryParams
.subscribe(params => {
this.idCit = params['idCit'];
console.log(this.idCit);
}
);
this.TankDetailsService.readMeasures(this.idCit).subscribe((Measure: Measure[])=>{
this.Measure = Measure;
console.log(this.arr);
this.chartOptions = {
chart: {
type: "spline"
},
title: {
text: "Volumes"
},
yAxis: {
title:{
text:"Volumes"
}
},
tooltip: {
pointFormat: '<span style="color:{series.color}">{series.name}</span>: <b>{point.y} %</b><br/>',
valueDecimals: 0,
split: true
},
series: [
{
name: 'Tokyo',
data: this.Measure
},
{
name: 'New York',
data: [[1389442547000,50],[1389442548000,55],[1389868449000,45],[1389868450000,73],[1391177296000,37],[1391177297000,45],[1391528879000,38],[1391528880000,71],[1392217092000,54],[1392217093000,69],[1392641513000,61],[1392641514000,72],[1393844672000,40],[1393844673000,63]]
},
{
name: 'Berlin',
data: [-0.9, 0.6, 3.5, 8.4, 13.5, 17.0, 18.6, 17.9, 14.3, 9.0, 3.9, 1.0]
},
{
name: 'London',
data: [3.9, 4.2, 5.7, 8.5, 11.9, 15.2, 17.0, 16.6, 14.2, 10.3, 6.6, 4.8]
}
]
};
console.log(this.chartOptions);
})
}
Please can you help me see it more clearly?
Please use below code after your API response then you will get the output as you want
let a = [{"timestamp":"1389442547000","PourcentRest":"50"},
{"timestamp":"1389442548000","PourcentRest":"55"},
{"timestamp":"1389868449000","PourcentRest":"45"}];
const outputArr = [];
for (let i = 0; i < a.length; i++) {
let b = [];
b.push(parseInt(a[i].timestamp), parseInt(a[i].PourcentRest));
outputArr.push(b);
}
console.log(outputArr);
Parsing your data to int and setting xAxis.type to 'datetime' solves it.
let data = [{"timestamp":"1389442547000","PourcentRest":"50"},
{"timestamp":"1389442548000","PourcentRest":"55"},
{"timestamp":"1389868449000","PourcentRest":"45"}]
function parseData() {
return data.map(data => [parseInt(data.timestamp), parseInt(data.PourcentRest)])
}
Highcharts.chart('container', {
xAxis: {
type: 'datetime'
},
series: [{
data: parseData()
}],
});
<script src="https://code.highcharts.com/highcharts.js"></script>
<div id="container"></div>
I'm not use React Hook in TypeScript but I have a few lines of code like below:
const [columns] = React.useState<Column[]>([
{ name: 'product', title: 'Product' },
{ name: 'region', title: 'Region' },
{ name: 'amount', title: 'Sale Amount' },
{ name: 'saleDate', title: 'Sale Date' },
{ name: 'customer', title: 'Customer' },
]);
const [rows] = React.useState<ISale[]>(sales);
const [pageSizes] = React.useState<number[]>([5, 10, 15]);
const [currencyColumns] = React.useState<string[]>(['amount']);
I want to use these React Hook in Class but I don't know how to convert them!
Can someone help me? Thanks!
This is how you use class based components when you are working with TypeScript and React.
First, you need to define an interface or type alias for your class component's state/props.
interface YourComponentState {
columns: Column[];
rows: ISale[];
pageSizes: number[];
currencyColumns: string[];
}
Then, you will need to supply the generic type parameters for React.Component with the types for the props/state.
class YourComponentName extends React.Component<{}, YourComponentState> {
constructor(props) {
super(props);
this.state = {
columns: [
{ name: 'product', title: 'Product' },
{ name: 'region', title: 'Region' },
{ name: 'amount', title: 'Sale Amount' },
{ name: 'saleDate', title: 'Sale Date' },
{ name: 'customer', title: 'Customer' },
],
rows: sales,
pageSizes: [5, 10, 15],
currencyColumns: ['amount'],
}
}
}
In class based react components, you cannot use hooks.
so, if you want something to store in state of class based component. you are going to:
class YourComponentName extends React.Component {
constructor(props) {
super(props);
this.state = {
columns: [
{ name: 'product', title: 'Product' },
{ name: 'region', title: 'Region' },
{ name: 'amount', title: 'Sale Amount' },
{ name: 'saleDate', title: 'Sale Date' },
{ name: 'customer', title: 'Customer' },
],
rows: sales,
pageSizes: [5, 10, 15],
currencyColumns: ['amount']
}
}
}
you can access them in your component:
this.state.columns
I'm using the TreeView component from Kendo UI library and I would like to know how to update the data in the tree. Is it possible?
This is my code:
class TreeViewTest extends React.Component {
dataSource = [
{
id: 123,
text: "aaaa",
expanded: true,
spriteCssClass: "rootfolder",
items: [
{
id: 2,
text: "aaa1",
expanded: true,
spriteCssClass: "folder",
items: [
{
id: 3,
text: "aaa2",
spriteCssClass: "html"
},
{
id: 4,
text: "aaa3",
spriteCssClass: "html"
},
{
id: 5,
text: "aaa4",
spriteCssClass: "image"
}
]
}
]
}
];
async componentDidUpdate(prevProps) {
if (this.props.endpoint !== prevProps.endpoint) {
init(this.props, this);
}
}
render() {
return (
<div>
<TreeView dataSource={this.dataSource} />
</div>
);
}
}
const init = async (props, _this) => {
const { endpoint, selectContent, setModal } = props;
const actions = props;
const response = await fetch(`${endpoint}/my/api/here`);
const body = await response.json();
/* some work on body here....*/
const data = [
{
id: 345,
text: "bbbb",
expanded: true,
spriteCssClass: "rootfolder",
items: [
{
id: 2,
text: "bbb1",
expanded: true,
spriteCssClass: "folder",
items: [
{
id: 3,
text: "bbb2",
spriteCssClass: "html"
},
{
id: 4,
text: "bbb3",
spriteCssClass: "html"
},
{
id: 5,
text: "bbb4",
spriteCssClass: "image"
}
]
}
]
}
];
_this.dataSource.push(data);
};
How can I update the dataSource after a remote call with the new data?
Before to install the react package I add a working solution with the Kendo UI jquery version and it worked fine with all the updates.
With the jquery version I have to set the options and I have the function setDataSource(data) and it works perfectly, now what I have to do?
Edit
I improved the code with the componentDidUpdate and the network call.
You could take a reference to the wrapped kendo.ui.TreeView element. Then you could call the function you have mentioned - setDataSource(data). Here is an example:
class TreeViewContainer extends React.Component {
wrappedWidget;
constructor(props) {
super(props);
this.dataSource = [{
id: 1, text: "My Documents", expanded: true, spriteCssClass: "rootfolder", items: [
{
id: 2, text: "Kendo UI Project", expanded: true, spriteCssClass: "folder", items: [
{ id: 3, text: "about.html", spriteCssClass: "html" },
{ id: 4, text: "index.html", spriteCssClass: "html" },
{ id: 5, text: "logo.png", spriteCssClass: "image" }
]
}
]
}];
}
render() {
return (
<div>
<TreeView widgetRef={(el) => { this.wrappedWidget = el }} dataSource={this.dataSource} />
</div>
);
}
componentDidMount() {
// Simulate a response from a web request.
setTimeout(() => {
this.wrappedWidget.setDataSource(new kendo.data.HierarchicalDataSource({
data: [{
id: 1111, text: "My Documents1111", expanded: true, spriteCssClass: "rootfolder", items: [
{
id: 222, text: "Kendo UI Project222", expanded: true, spriteCssClass: "folder", items: [
{ id: 333, text: "about333.html", spriteCssClass: "html" },
{ id: 444, text: "index444.html", spriteCssClass: "html" },
{ id: 555, text: "logo555.png", spriteCssClass: "image" }
]
}
]
}]
}));
}, 1000)
}
}
ReactDOM.render(
<TreeViewContainer />,
document.querySelector('my-app')
);
I have a group of arrays on my Angular2 app that I use to build a grouped list with *ngFor in my view:
[
{
category: 1,
items: [{ id: 1, name: "helloworld1" }, { id: 2, name: "helloworld2" }]
},
{
category: 2,
items: [{ id: 3, name: "helloworld3" }, { id: 4 }]
},
{
category: 3,
items:[{ id: 5 }, { id: 6 }]
}
]
I also have a boolean that when it's true should filter only the items that have the name property. If a group does not have any item that matches this condition it should not pass. So the result would be the following if the boolean is true:
[
{
category: 1,
items: [{ id: 1, name: "helloworld1" }, { id: 2, name: "helloworld2" }]
},
{
category: 2,
items: [{ id: 3, name: "helloworld3" }]
}
]
How can I implement a pipe to achieve this kind of result?
http://plnkr.co/edit/je2RioK9pfKxiZg7ljVg?p=preview
#Pipe({name: 'filterName'})
export class FilterNamePipe implements PipeTransform {
transform(items: any[], checkName: boolean): number {
if(items === null) return [];
let ret = [];
items.forEach(function (item) {
let ret1 = item.items.filter(function (e) {
return !checkName || (checkName && (e.name !== undefined));
});
if(ret1.length > 0) {
item.items = ret1;
ret.push(item);
}
});
return ret;
}
}